TypeScript to ArkTS Syntax Differences
This file highlights TypeScript patterns that often need rewriting in ArkTS.
Dynamic JavaScript patterns are narrower
- ArkTS is not a drop-in TypeScript superset in practice.
- Patterns that depend on dynamic object mutation, loose shape matching, or reflective syntax are often rejected.
- Patterns based on
Record<string, T>, arbitrary indexes, or namespace objects often need explicit ArkTS models.
Reference:
- Guide:
docs/ArkTS-Language-Guide/09-Migration-Guide/01-TypeScript-to-ArkTS/typescript-to-arkts-migration-guide.md - Linter summary: overview section
Prefer named types over inline shapes
TypeScript style:
function printPoint(point: { x: number; y: number }): void {}
ArkTS style:
interface PointLike {
x: number
y: number
}
function printPoint(point: PointLike): void {}
Reference:
- Guide:
docs/ArkTS-Language-Guide/02-Basic-Syntax/interfaces.md
Prefer declarations over expressions
- Rewrite function expressions to arrow functions when the function is used as a value.
- Rewrite class expressions to named class declarations.
- Move nested function declarations to top-level declarations, class methods, or arrow-function values.
Reference:
- Guide:
docs/ArkTS-Language-Guide/02-Basic-Syntax/classes.md - Linter summary: function and class sections
Prefer explicit class and interface modeling
- TypeScript often treats classes as object shapes; ArkTS prefers constructor-based initialization and declared members.
- TypeScript often relies on structural typing; ArkTS narrows that style and expects explicit named contracts.
- TypeScript often uses
Recordor indexed access for flexible maps; ArkTS authoring should prefer named interfaces/classes and direct property access when property names are known.
Reference:
- Guide:
docs/ArkTS-Language-Guide/02-Basic-Syntax/classes.md - Guide:
docs/ArkTS-Language-Guide/02-Basic-Syntax/interfaces.md - Linter summary: structural typing restriction
Rewrite template strings
TypeScript style:
const label: string = `Count: ${count}`
ArkTS style:
const label: string = "Count: " + count.toString()
Reference:
- Linter summary: syntax restriction section
Rewrite namespace-as-value patterns
TypeScript style:
const api = common
api.doWork()
ArkTS style:
common.doWork()
If the code needs a runtime object, define that object explicitly instead of using a namespace as the value.
Reference:
- Linter summary: namespace section
Remove unsupported or narrowed syntax
Common rewrites:
var->letorconst- destructuring declaration -> explicit local bindings
value as T-> typed variable, typed function return, constructor, or explicit conversion`${value}`-> string concatenation with explicit conversiondelete obj.x-> construct the desired value without runtime property deletioncatch (err: Error)->catch (err)type T = typeof Foo-> use the explicit type you need instead of a type query
Reference:
- Linter summary: declaration, operator, and statement sections