rooklang 0.0.0-stage → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (314) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +177 -2
  3. package/README.ru.md +178 -0
  4. package/dist/ast/declarations.d.ts +185 -0
  5. package/dist/ast/declarations.js +1 -0
  6. package/dist/ast/expressions.d.ts +201 -0
  7. package/dist/ast/expressions.js +1 -0
  8. package/dist/ast/markup.d.ts +141 -0
  9. package/dist/ast/markup.js +1 -0
  10. package/dist/ast/statements.d.ts +173 -0
  11. package/dist/ast/statements.js +1 -0
  12. package/dist/ast.d.ts +18 -0
  13. package/dist/ast.js +18 -0
  14. package/dist/attrs.d.ts +8 -0
  15. package/dist/attrs.js +23 -0
  16. package/dist/browser.d.ts +30 -0
  17. package/dist/browser.js +36 -0
  18. package/dist/build.d.ts +48 -0
  19. package/dist/build.js +112 -0
  20. package/dist/checker/assignments.d.ts +14 -0
  21. package/dist/checker/assignments.js +197 -0
  22. package/dist/checker/base.d.ts +124 -0
  23. package/dist/checker/base.js +180 -0
  24. package/dist/checker/bigint.d.ts +15 -0
  25. package/dist/checker/bigint.js +85 -0
  26. package/dist/checker/builtins.d.ts +9 -0
  27. package/dist/checker/builtins.js +307 -0
  28. package/dist/checker/bytes.d.ts +11 -0
  29. package/dist/checker/bytes.js +72 -0
  30. package/dist/checker/calls.d.ts +23 -0
  31. package/dist/checker/calls.js +210 -0
  32. package/dist/checker/channel.d.ts +14 -0
  33. package/dist/checker/channel.js +44 -0
  34. package/dist/checker/channels.d.ts +9 -0
  35. package/dist/checker/channels.js +95 -0
  36. package/dist/checker/checker.d.ts +4 -0
  37. package/dist/checker/checker.js +22 -0
  38. package/dist/checker/classes.d.ts +24 -0
  39. package/dist/checker/classes.js +223 -0
  40. package/dist/checker/completion-names.d.ts +11 -0
  41. package/dist/checker/completion-names.js +100 -0
  42. package/dist/checker/completion.d.ts +25 -0
  43. package/dist/checker/completion.js +222 -0
  44. package/dist/checker/component-values.d.ts +11 -0
  45. package/dist/checker/component-values.js +88 -0
  46. package/dist/checker/components.d.ts +37 -0
  47. package/dist/checker/components.js +287 -0
  48. package/dist/checker/context.d.ts +196 -0
  49. package/dist/checker/context.js +35 -0
  50. package/dist/checker/control-flow.d.ts +24 -0
  51. package/dist/checker/control-flow.js +237 -0
  52. package/dist/checker/declarations.d.ts +26 -0
  53. package/dist/checker/declarations.js +259 -0
  54. package/dist/checker/decorator-exports.d.ts +5 -0
  55. package/dist/checker/decorator-exports.js +40 -0
  56. package/dist/checker/decorator-members.d.ts +28 -0
  57. package/dist/checker/decorator-members.js +140 -0
  58. package/dist/checker/decorator-wrappers.d.ts +20 -0
  59. package/dist/checker/decorator-wrappers.js +132 -0
  60. package/dist/checker/decorators.d.ts +28 -0
  61. package/dist/checker/decorators.js +265 -0
  62. package/dist/checker/dom-svg.d.ts +7 -0
  63. package/dist/checker/dom-svg.js +19 -0
  64. package/dist/checker/dom.d.ts +22 -0
  65. package/dist/checker/dom.js +361 -0
  66. package/dist/checker/expressions.d.ts +32 -0
  67. package/dist/checker/expressions.js +244 -0
  68. package/dist/checker/flow.d.ts +18 -0
  69. package/dist/checker/flow.js +134 -0
  70. package/dist/checker/forwarding.d.ts +15 -0
  71. package/dist/checker/forwarding.js +78 -0
  72. package/dist/checker/functions.d.ts +24 -0
  73. package/dist/checker/functions.js +154 -0
  74. package/dist/checker/go-for.d.ts +12 -0
  75. package/dist/checker/go-for.js +93 -0
  76. package/dist/checker/goroutines.d.ts +19 -0
  77. package/dist/checker/goroutines.js +110 -0
  78. package/dist/checker/helpers.d.ts +35 -0
  79. package/dist/checker/helpers.js +162 -0
  80. package/dist/checker/imports.d.ts +7 -0
  81. package/dist/checker/imports.js +83 -0
  82. package/dist/checker/initializers.d.ts +22 -0
  83. package/dist/checker/initializers.js +104 -0
  84. package/dist/checker/iterables.d.ts +5 -0
  85. package/dist/checker/iterables.js +17 -0
  86. package/dist/checker/iterators.d.ts +13 -0
  87. package/dist/checker/iterators.js +95 -0
  88. package/dist/checker/loops.d.ts +10 -0
  89. package/dist/checker/loops.js +82 -0
  90. package/dist/checker/markup.d.ts +28 -0
  91. package/dist/checker/markup.js +220 -0
  92. package/dist/checker/members.d.ts +29 -0
  93. package/dist/checker/members.js +233 -0
  94. package/dist/checker/operators.d.ts +13 -0
  95. package/dist/checker/operators.js +177 -0
  96. package/dist/checker/promise.d.ts +17 -0
  97. package/dist/checker/promise.js +49 -0
  98. package/dist/checker/refs.d.ts +26 -0
  99. package/dist/checker/refs.js +136 -0
  100. package/dist/checker/resolution.d.ts +23 -0
  101. package/dist/checker/resolution.js +173 -0
  102. package/dist/checker/statements.d.ts +28 -0
  103. package/dist/checker/statements.js +212 -0
  104. package/dist/checker/styles.d.ts +14 -0
  105. package/dist/checker/styles.js +49 -0
  106. package/dist/checker/transfer.d.ts +5 -0
  107. package/dist/checker/transfer.js +83 -0
  108. package/dist/checker/types/bytes.d.ts +4 -0
  109. package/dist/checker/types/bytes.js +51 -0
  110. package/dist/checker/types/classes.d.ts +22 -0
  111. package/dist/checker/types/classes.js +93 -0
  112. package/dist/checker/types/constructors.d.ts +27 -0
  113. package/dist/checker/types/constructors.js +129 -0
  114. package/dist/checker/types/generics.d.ts +20 -0
  115. package/dist/checker/types/generics.js +75 -0
  116. package/dist/checker/types/lazy.d.ts +30 -0
  117. package/dist/checker/types/lazy.js +92 -0
  118. package/dist/checker/types/model.d.ts +149 -0
  119. package/dist/checker/types/model.js +15 -0
  120. package/dist/checker/types/params.d.ts +7 -0
  121. package/dist/checker/types/params.js +220 -0
  122. package/dist/checker/types/printing.d.ts +6 -0
  123. package/dist/checker/types/printing.js +109 -0
  124. package/dist/checker/types/relations.d.ts +16 -0
  125. package/dist/checker/types/relations.js +294 -0
  126. package/dist/checker/types.d.ts +9 -0
  127. package/dist/checker/types.js +10 -0
  128. package/dist/cli.d.ts +2 -0
  129. package/dist/cli.js +195 -0
  130. package/dist/codegen/analysis.d.ts +18 -0
  131. package/dist/codegen/analysis.js +144 -0
  132. package/dist/codegen/attributes.d.ts +40 -0
  133. package/dist/codegen/attributes.js +227 -0
  134. package/dist/codegen/calls.d.ts +22 -0
  135. package/dist/codegen/calls.js +106 -0
  136. package/dist/codegen/chan-helpers.d.ts +2 -0
  137. package/dist/codegen/chan-helpers.js +253 -0
  138. package/dist/codegen/component-helpers.d.ts +33 -0
  139. package/dist/codegen/component-helpers.js +18 -0
  140. package/dist/codegen/component-props.d.ts +42 -0
  141. package/dist/codegen/component-props.js +173 -0
  142. package/dist/codegen/component-values.d.ts +27 -0
  143. package/dist/codegen/component-values.js +146 -0
  144. package/dist/codegen/components.d.ts +53 -0
  145. package/dist/codegen/components.js +268 -0
  146. package/dist/codegen/control-flow.d.ts +25 -0
  147. package/dist/codegen/control-flow.js +152 -0
  148. package/dist/codegen/control-statements.d.ts +28 -0
  149. package/dist/codegen/control-statements.js +226 -0
  150. package/dist/codegen/creation.d.ts +31 -0
  151. package/dist/codegen/creation.js +113 -0
  152. package/dist/codegen/early-returns.d.ts +59 -0
  153. package/dist/codegen/early-returns.js +244 -0
  154. package/dist/codegen/element-helpers.d.ts +12 -0
  155. package/dist/codegen/element-helpers.js +54 -0
  156. package/dist/codegen/elements.d.ts +71 -0
  157. package/dist/codegen/elements.js +293 -0
  158. package/dist/codegen/emitter.d.ts +135 -0
  159. package/dist/codegen/emitter.js +296 -0
  160. package/dist/codegen/expressions.d.ts +49 -0
  161. package/dist/codegen/expressions.js +262 -0
  162. package/dist/codegen/functions.d.ts +28 -0
  163. package/dist/codegen/functions.js +170 -0
  164. package/dist/codegen/go-helpers.d.ts +9 -0
  165. package/dist/codegen/go-helpers.js +307 -0
  166. package/dist/codegen/helpers.d.ts +10 -0
  167. package/dist/codegen/helpers.js +356 -0
  168. package/dist/codegen/imported.d.ts +38 -0
  169. package/dist/codegen/imported.js +71 -0
  170. package/dist/codegen/js.d.ts +20 -0
  171. package/dist/codegen/js.js +113 -0
  172. package/dist/codegen/mutations.d.ts +10 -0
  173. package/dist/codegen/mutations.js +102 -0
  174. package/dist/codegen/parallel.d.ts +7 -0
  175. package/dist/codegen/parallel.js +63 -0
  176. package/dist/codegen/reactive.d.ts +95 -0
  177. package/dist/codegen/reactive.js +280 -0
  178. package/dist/codegen/refs.d.ts +62 -0
  179. package/dist/codegen/refs.js +160 -0
  180. package/dist/codegen/select-helpers.d.ts +2 -0
  181. package/dist/codegen/select-helpers.js +135 -0
  182. package/dist/codegen/simple-statements.d.ts +42 -0
  183. package/dist/codegen/simple-statements.js +253 -0
  184. package/dist/codegen/statements.d.ts +22 -0
  185. package/dist/codegen/statements.js +142 -0
  186. package/dist/codegen/styles.d.ts +54 -0
  187. package/dist/codegen/styles.js +157 -0
  188. package/dist/codegen/syntax.d.ts +18 -0
  189. package/dist/codegen/syntax.js +70 -0
  190. package/dist/codegen/thread-helpers.d.ts +2 -0
  191. package/dist/codegen/thread-helpers.js +198 -0
  192. package/dist/codegen/updates.d.ts +51 -0
  193. package/dist/codegen/updates.js +201 -0
  194. package/dist/codegen/web-components.d.ts +20 -0
  195. package/dist/codegen/web-components.js +149 -0
  196. package/dist/compile-file.d.ts +11 -0
  197. package/dist/compile-file.js +24 -0
  198. package/dist/compile.d.ts +53 -0
  199. package/dist/compile.js +187 -0
  200. package/dist/completion.d.ts +10 -0
  201. package/dist/completion.js +134 -0
  202. package/dist/config.d.ts +2 -0
  203. package/dist/config.js +44 -0
  204. package/dist/css/hash.d.ts +1 -0
  205. package/dist/css/hash.js +10 -0
  206. package/dist/css/parse.d.ts +42 -0
  207. package/dist/css/parse.js +138 -0
  208. package/dist/css/print.d.ts +9 -0
  209. package/dist/css/print.js +35 -0
  210. package/dist/css/selectors.d.ts +29 -0
  211. package/dist/css/selectors.js +168 -0
  212. package/dist/declarations.d.ts +3 -0
  213. package/dist/declarations.js +207 -0
  214. package/dist/decorator-copy.d.ts +18 -0
  215. package/dist/decorator-copy.js +158 -0
  216. package/dist/decorators.d.ts +61 -0
  217. package/dist/decorators.js +241 -0
  218. package/dist/diagnostics.d.ts +17 -0
  219. package/dist/diagnostics.js +22 -0
  220. package/dist/go-for.d.ts +26 -0
  221. package/dist/go-for.js +155 -0
  222. package/dist/goroutines.d.ts +37 -0
  223. package/dist/goroutines.js +253 -0
  224. package/dist/html-tag.d.ts +21 -0
  225. package/dist/html-tag.js +103 -0
  226. package/dist/index.d.ts +33 -0
  227. package/dist/index.js +55 -0
  228. package/dist/inline-packages.d.ts +32 -0
  229. package/dist/inline-packages.js +129 -0
  230. package/dist/iterators.d.ts +10 -0
  231. package/dist/iterators.js +33 -0
  232. package/dist/lexer/base.d.ts +24 -0
  233. package/dist/lexer/base.js +87 -0
  234. package/dist/lexer/lexer.d.ts +8 -0
  235. package/dist/lexer/lexer.js +134 -0
  236. package/dist/lexer/literals.d.ts +18 -0
  237. package/dist/lexer/literals.js +203 -0
  238. package/dist/lexer/markup.d.ts +10 -0
  239. package/dist/lexer/markup.js +93 -0
  240. package/dist/lexer/style.d.ts +17 -0
  241. package/dist/lexer/style.js +97 -0
  242. package/dist/lexer/tables.d.ts +53 -0
  243. package/dist/lexer/tables.js +101 -0
  244. package/dist/lexer/token.d.ts +42 -0
  245. package/dist/lexer/token.js +108 -0
  246. package/dist/loader.d.ts +1 -0
  247. package/dist/loader.js +50 -0
  248. package/dist/methods.d.ts +5 -0
  249. package/dist/methods.js +81 -0
  250. package/dist/modules.d.ts +3 -0
  251. package/dist/modules.js +49 -0
  252. package/dist/names.d.ts +23 -0
  253. package/dist/names.js +267 -0
  254. package/dist/parser/base.d.ts +96 -0
  255. package/dist/parser/base.js +202 -0
  256. package/dist/parser/classes.d.ts +8 -0
  257. package/dist/parser/classes.js +164 -0
  258. package/dist/parser/control-flow.d.ts +29 -0
  259. package/dist/parser/control-flow.js +232 -0
  260. package/dist/parser/declarations.d.ts +27 -0
  261. package/dist/parser/declarations.js +238 -0
  262. package/dist/parser/decorators.d.ts +30 -0
  263. package/dist/parser/decorators.js +176 -0
  264. package/dist/parser/expressions.d.ts +15 -0
  265. package/dist/parser/expressions.js +255 -0
  266. package/dist/parser/literals.d.ts +27 -0
  267. package/dist/parser/literals.js +206 -0
  268. package/dist/parser/markup.d.ts +22 -0
  269. package/dist/parser/markup.js +193 -0
  270. package/dist/parser/parser.d.ts +14 -0
  271. package/dist/parser/parser.js +22 -0
  272. package/dist/parser/simple-statements.d.ts +22 -0
  273. package/dist/parser/simple-statements.js +156 -0
  274. package/dist/parser/statements.d.ts +37 -0
  275. package/dist/parser/statements.js +267 -0
  276. package/dist/parser/syntax.d.ts +51 -0
  277. package/dist/parser/syntax.js +173 -0
  278. package/dist/parser/types.d.ts +23 -0
  279. package/dist/parser/types.js +218 -0
  280. package/dist/recursion.d.ts +25 -0
  281. package/dist/recursion.js +170 -0
  282. package/dist/refs.d.ts +49 -0
  283. package/dist/refs.js +210 -0
  284. package/dist/run.d.ts +1 -0
  285. package/dist/run.js +21 -0
  286. package/dist/source.d.ts +15 -0
  287. package/dist/source.js +34 -0
  288. package/dist/style-modules.d.ts +17 -0
  289. package/dist/style-modules.js +49 -0
  290. package/dist/styles.d.ts +36 -0
  291. package/dist/styles.js +160 -0
  292. package/dist/svg.d.ts +8 -0
  293. package/dist/svg.js +77 -0
  294. package/dist/ts-types.d.ts +11 -0
  295. package/dist/ts-types.js +133 -0
  296. package/dist/typed-arrays.d.ts +8 -0
  297. package/dist/typed-arrays.js +43 -0
  298. package/dist/typescript/convert-base.d.ts +42 -0
  299. package/dist/typescript/convert-base.js +135 -0
  300. package/dist/typescript/convert-objects.d.ts +28 -0
  301. package/dist/typescript/convert-objects.js +245 -0
  302. package/dist/typescript/convert.d.ts +14 -0
  303. package/dist/typescript/convert.js +67 -0
  304. package/dist/typescript/importer.d.ts +37 -0
  305. package/dist/typescript/importer.js +152 -0
  306. package/dist/typescript/library.d.ts +23 -0
  307. package/dist/typescript/library.js +81 -0
  308. package/dist/vite.d.ts +11 -0
  309. package/dist/vite.js +86 -0
  310. package/dist/walk-types.d.ts +4 -0
  311. package/dist/walk-types.js +56 -0
  312. package/dist/walk.d.ts +5 -0
  313. package/dist/walk.js +315 -0
  314. package/package.json +105 -4
@@ -0,0 +1,129 @@
1
+ import { BOOL, NEVER, NULL, NUMBER, STRING, } from "./model.js";
2
+ import { typesEqual } from "./relations.js";
3
+ // Making types: arrays, nullable types, literals, unions, functions, members, classes.
4
+ export function arrayOf(element) {
5
+ return { kind: 'array', element };
6
+ }
7
+ export function nullable(type) {
8
+ switch (type.kind) {
9
+ case 'nullable':
10
+ case 'null':
11
+ case 'any':
12
+ case 'unknown':
13
+ return type;
14
+ default:
15
+ return { kind: 'nullable', type };
16
+ }
17
+ }
18
+ export function literal(value) {
19
+ return { kind: 'literal', value };
20
+ }
21
+ /** The type that a literal belongs to: `"all"` → `string`. */
22
+ export function literalBase(type) {
23
+ return typeof type.value === 'string' ? STRING : typeof type.value === 'number' ? NUMBER : BOOL;
24
+ }
25
+ /**
26
+ * A union of types, simplified: nested unions are flattened, repeats and `never` are dropped, a
27
+ * literal goes into its base type when that is a member (`"a" | string` → `string`), `true | false`
28
+ * is `bool`, `any` absorbs everything, and `null` makes the union nullable.
29
+ */
30
+ export function union(types) {
31
+ let hasNull = false;
32
+ const members = [];
33
+ const add = (type) => {
34
+ switch (type.kind) {
35
+ case 'union':
36
+ type.types.forEach(add);
37
+ return;
38
+ case 'nullable':
39
+ hasNull = true;
40
+ add(type.type);
41
+ return;
42
+ case 'null':
43
+ hasNull = true;
44
+ return;
45
+ case 'never':
46
+ return;
47
+ default:
48
+ if (!members.some((member) => typesEqual(member, type)))
49
+ members.push(type);
50
+ }
51
+ };
52
+ types.forEach(add);
53
+ const special = members.find((member) => member.kind === 'any' || member.kind === 'unknown');
54
+ if (special)
55
+ return special;
56
+ if (members.some((m) => m.kind === 'literal' && m.value === true) &&
57
+ members.some((m) => m.kind === 'literal' && m.value === false)) {
58
+ members.push(BOOL);
59
+ }
60
+ const kept = members.filter((member) => member.kind !== 'literal' ||
61
+ !members.some((other) => other.kind === literalBase(member).kind));
62
+ const result = kept.length === 0
63
+ ? hasNull
64
+ ? NULL
65
+ : NEVER
66
+ : kept.length === 1
67
+ ? kept[0]
68
+ : { kind: 'union', types: kept };
69
+ return hasNull ? nullable(result) : result;
70
+ }
71
+ /** The type a variable gets from a value: literals become their base types, `"a" | "b"` → `string`. */
72
+ export function widenLiterals(type) {
73
+ switch (type.kind) {
74
+ case 'literal':
75
+ return literalBase(type);
76
+ case 'union':
77
+ return union(type.types.map(widenLiterals));
78
+ case 'nullable':
79
+ return nullable(widenLiterals(type.type));
80
+ default:
81
+ return type;
82
+ }
83
+ }
84
+ /** The members of a union, or the type itself. */
85
+ export function unionMembers(type) {
86
+ return type.kind === 'union' ? type.types : [type];
87
+ }
88
+ export function nonNull(type) {
89
+ if (type.kind === 'nullable')
90
+ return type.type;
91
+ return type.kind === 'null' ? NEVER : type;
92
+ }
93
+ export function isNullable(type) {
94
+ return type.kind === 'nullable' || type.kind === 'null';
95
+ }
96
+ export function func(params, results, options = {}) {
97
+ return {
98
+ kind: 'function',
99
+ params,
100
+ required: options.required ?? params.length,
101
+ rest: options.rest ?? null,
102
+ results,
103
+ typeParams: options.typeParams ?? [],
104
+ ...(options.iterator ? { iterator: true } : {}),
105
+ };
106
+ }
107
+ export function property(type, owner = null) {
108
+ return { type, method: false, visibility: 'public', owner };
109
+ }
110
+ export function method(type, owner = null) {
111
+ return { type, method: true, visibility: 'public', owner };
112
+ }
113
+ export function createClass(name) {
114
+ const info = {
115
+ name,
116
+ superClass: null,
117
+ untypedBase: false,
118
+ members: new Map(),
119
+ statics: new Map(),
120
+ ctor: null,
121
+ typeParams: [],
122
+ ctorVisibility: 'public',
123
+ instance: undefined,
124
+ value: undefined,
125
+ };
126
+ info.instance = { kind: 'class', info };
127
+ info.value = { kind: 'classValue', info };
128
+ return info;
129
+ }
@@ -0,0 +1,20 @@
1
+ import { type ClassInfo, type ClassType, type Member, type ObjectType, type Type, type TypeParam } from './model.ts';
2
+ /** Bindings of type parameters to type arguments. */
3
+ export declare function bindParams(params: readonly TypeParam[], args: readonly Type[]): Map<TypeParam, Type>;
4
+ export declare const instances: WeakMap<ObjectType, {
5
+ args: Type[];
6
+ instance: ObjectType;
7
+ }[]>;
8
+ /**
9
+ * `Box<number>` from `interface Box<T>`. Instances are cached, so that a type that refers to itself
10
+ * (`interface Node<T> { next ?Node<T> }`) gets the same instance back; arguments that are the
11
+ * parameters themselves give the generic interface.
12
+ */
13
+ export declare function instantiate(template: ObjectType, args: readonly Type[]): ObjectType;
14
+ /** An instance of a class with type arguments; a class without parameters has one instance. */
15
+ export declare function classInstance(info: ClassInfo, args: readonly Type[]): ClassType;
16
+ /**
17
+ * The type of a member as seen on an instance: `Stack<number>.items` is `[]number`. A member of a
18
+ * generic base class gets the arguments that the subclass gives it.
19
+ */
20
+ export declare function memberTypeOf(object: Type, member: Member): Type;
@@ -0,0 +1,75 @@
1
+ import { LazyMap, memberNames } from "./lazy.js";
2
+ import { UNKNOWN, } from "./model.js";
3
+ import { substitute } from "./params.js";
4
+ import { typesEqual } from "./relations.js";
5
+ // Generic interfaces and classes with type arguments.
6
+ /** Bindings of type parameters to type arguments. */
7
+ export function bindParams(params, args) {
8
+ return new Map(params.map((param, i) => [param, args[i] ?? UNKNOWN]));
9
+ }
10
+ export const instances = new WeakMap();
11
+ /**
12
+ * `Box<number>` from `interface Box<T>`. Instances are cached, so that a type that refers to itself
13
+ * (`interface Node<T> { next ?Node<T> }`) gets the same instance back; arguments that are the
14
+ * parameters themselves give the generic interface.
15
+ */
16
+ export function instantiate(template, args) {
17
+ const params = template.typeParams ?? [];
18
+ if (params.every((param, i) => args[i] === param))
19
+ return template;
20
+ let cached = instances.get(template);
21
+ if (!cached) {
22
+ cached = [];
23
+ instances.set(template, cached);
24
+ }
25
+ const found = cached.find((entry) => entry.args.every((arg, i) => typesEqual(arg, args[i])));
26
+ if (found)
27
+ return found.instance;
28
+ const bindings = bindParams(params, args);
29
+ // Members are substituted when they are used: a template from a `.d.ts` may still be filling
30
+ // its own members, and large interfaces are mostly not used whole.
31
+ const instance = {
32
+ kind: 'object',
33
+ name: template.name,
34
+ members: new LazyMap(() => memberNames(template.members), (name) => {
35
+ const member = template.members.get(name);
36
+ return member && { ...member, type: substitute(member.type, bindings) };
37
+ }),
38
+ call: template.call && substitute(template.call, bindings),
39
+ instanceOf: { template, args: [...args] },
40
+ };
41
+ if (template.construct) {
42
+ instance.construct = substitute(template.construct, bindings);
43
+ }
44
+ // The indexes and the values of a loop, substituted when first used: the template of a
45
+ // `.d.ts` may get them after its instances.
46
+ for (const key of ['index', 'numberIndex', 'iterates']) {
47
+ let substituted;
48
+ Object.defineProperty(instance, key, {
49
+ enumerable: true,
50
+ get: () => (substituted ??= template[key] && substitute(template[key], bindings)),
51
+ });
52
+ }
53
+ cached.push({ args: [...args], instance });
54
+ return instance;
55
+ }
56
+ /** An instance of a class with type arguments; a class without parameters has one instance. */
57
+ export function classInstance(info, args) {
58
+ return info.typeParams.length === 0 ? info.instance : { kind: 'class', info, args: [...args] };
59
+ }
60
+ /**
61
+ * The type of a member as seen on an instance: `Stack<number>.items` is `[]number`. A member of a
62
+ * generic base class gets the arguments that the subclass gives it.
63
+ */
64
+ export function memberTypeOf(object, member) {
65
+ if (object.kind !== 'class' || !member.owner)
66
+ return member.type;
67
+ let info = object.info;
68
+ let bindings = bindParams(info.typeParams, object.args ?? info.typeParams);
69
+ while (info !== member.owner && info.superClass) {
70
+ const args = (info.superArgs ?? []).map((arg) => substitute(arg, bindings));
71
+ info = info.superClass;
72
+ bindings = bindParams(info.typeParams, args.length > 0 ? args : info.typeParams);
73
+ }
74
+ return substitute(member.type, bindings);
75
+ }
@@ -0,0 +1,30 @@
1
+ /**
2
+ * A map whose keys are known up front and whose values are computed when first read. Members of
3
+ * types from `.d.ts` files use it: `@types/node` has thousands of them, and few are ever used.
4
+ */
5
+ export declare class LazyMap<V> extends Map<string, V> {
6
+ private names;
7
+ private complete;
8
+ private filling;
9
+ private readonly listNames;
10
+ private readonly compute;
11
+ constructor(listNames: () => Iterable<string>, compute: (name: string) => V | undefined);
12
+ private known;
13
+ /** The names, without computing the values. */
14
+ knownNames(): Iterable<string>;
15
+ /** Computes every value, keeping the order of the names. */
16
+ private fill;
17
+ get(name: string): V | undefined;
18
+ has(name: string): boolean;
19
+ set(name: string, value: V): this;
20
+ delete(name: string): boolean;
21
+ clear(): void;
22
+ get size(): number;
23
+ keys(): MapIterator<string>;
24
+ values(): MapIterator<V>;
25
+ entries(): MapIterator<[string, V]>;
26
+ forEach(callback: (value: V, key: string, map: Map<string, V>) => void): void;
27
+ [Symbol.iterator](): MapIterator<[string, V]>;
28
+ }
29
+ /** The names of a map of members, without computing a lazy one. */
30
+ export declare function memberNames<V>(map: Map<string, V>): Iterable<string>;
@@ -0,0 +1,92 @@
1
+ /**
2
+ * A map whose keys are known up front and whose values are computed when first read. Members of
3
+ * types from `.d.ts` files use it: `@types/node` has thousands of them, and few are ever used.
4
+ */
5
+ export class LazyMap extends Map {
6
+ names = null;
7
+ complete = false;
8
+ filling = false;
9
+ listNames;
10
+ compute;
11
+ constructor(listNames, compute) {
12
+ super();
13
+ this.listNames = listNames;
14
+ this.compute = compute;
15
+ }
16
+ known() {
17
+ this.names ??= new Set(this.listNames());
18
+ return this.names;
19
+ }
20
+ /** The names, without computing the values. */
21
+ knownNames() {
22
+ return this.known();
23
+ }
24
+ /** Computes every value, keeping the order of the names. */
25
+ fill() {
26
+ if (this.complete || this.filling)
27
+ return;
28
+ this.filling = true;
29
+ const values = [...this.known()].map((name) => [name, this.get(name)]);
30
+ this.complete = true;
31
+ this.filling = false;
32
+ super.clear();
33
+ for (const [name, value] of values)
34
+ if (value !== undefined)
35
+ super.set(name, value);
36
+ }
37
+ get(name) {
38
+ if (super.has(name))
39
+ return super.get(name);
40
+ if (this.complete || !this.known().has(name))
41
+ return undefined;
42
+ const value = this.compute(name);
43
+ if (value === undefined)
44
+ this.names.delete(name);
45
+ else
46
+ super.set(name, value);
47
+ return value;
48
+ }
49
+ has(name) {
50
+ return this.get(name) !== undefined;
51
+ }
52
+ set(name, value) {
53
+ this.known().add(name);
54
+ return super.set(name, value);
55
+ }
56
+ delete(name) {
57
+ const known = this.known().delete(name);
58
+ return super.delete(name) || known;
59
+ }
60
+ clear() {
61
+ this.names = new Set();
62
+ this.complete = true;
63
+ super.clear();
64
+ }
65
+ get size() {
66
+ this.fill();
67
+ return super.size;
68
+ }
69
+ keys() {
70
+ this.fill();
71
+ return super.keys();
72
+ }
73
+ values() {
74
+ this.fill();
75
+ return super.values();
76
+ }
77
+ entries() {
78
+ this.fill();
79
+ return super.entries();
80
+ }
81
+ forEach(callback) {
82
+ this.fill();
83
+ super.forEach(callback);
84
+ }
85
+ [Symbol.iterator]() {
86
+ return this.entries();
87
+ }
88
+ }
89
+ /** The names of a map of members, without computing a lazy one. */
90
+ export function memberNames(map) {
91
+ return map instanceof LazyMap ? map.knownNames() : map.keys();
92
+ }
@@ -0,0 +1,149 @@
1
+ import type { Visibility } from '../../ast.ts';
2
+ /** Types as the checker sees them, after names and aliases have been resolved. */
3
+ export type Type = SimpleType | ArrayType | NullableType | FunctionType | ComponentType | ObjectType | ClassType | ClassValueType | TupleType | TypeParam | UnionType | LiteralType;
4
+ export interface SimpleType {
5
+ kind: 'number' | 'bigint' | 'string' | 'bool' | 'any' | 'void' | 'null' | 'never' | 'unknown';
6
+ }
7
+ export declare const NUMBER: SimpleType;
8
+ /** Whole numbers of any size, `10n`; they do not mix with numbers. */
9
+ export declare const BIGINT: SimpleType;
10
+ export declare const STRING: SimpleType;
11
+ export declare const BOOL: SimpleType;
12
+ /** Values from JS: anything goes, nothing is checked. */
13
+ export declare const ANY: SimpleType;
14
+ /** What a call to a function without results gives. */
15
+ export declare const VOID: SimpleType;
16
+ /** The type of the `null` literal. */
17
+ export declare const NULL: SimpleType;
18
+ /** Element type of an empty array literal: assignable to every type. */
19
+ export declare const NEVER: SimpleType;
20
+ /** The type of an expression that already has an error: accepted everywhere to avoid follow-up errors. */
21
+ export declare const UNKNOWN: SimpleType;
22
+ export interface ArrayType {
23
+ kind: 'array';
24
+ element: Type;
25
+ }
26
+ /** `?T`; the inner type itself is never nullable. */
27
+ export interface NullableType {
28
+ kind: 'nullable';
29
+ type: Type;
30
+ }
31
+ export interface FunctionType {
32
+ kind: 'function';
33
+ params: Type[];
34
+ /** How many parameters must be passed; the others may be left out (builtins only). */
35
+ required: number;
36
+ /** Element type of a trailing `...rest` parameter (builtins only). */
37
+ rest: Type | null;
38
+ results: Type[];
39
+ /** Type parameters inferred from the arguments of each call, e.g. `map` or `func first<T any>`. */
40
+ typeParams: TypeParam[];
41
+ /** The other signatures of an overloaded function from a `.d.ts`; a call uses the first that fits. */
42
+ overloads?: FunctionType[];
43
+ /**
44
+ * `func(yield func(T) bool)`, a function with a `yield` parameter: an iterator, as in Go 1.23. It
45
+ * compiles to a JS generator, and `for v in f` goes over what it yields.
46
+ */
47
+ iterator?: boolean;
48
+ }
49
+ /**
50
+ * `comp(title string, kind ?Kind)`: a component as a value, which a tag uses,
51
+ * `<section.content />`. A tag passes the properties in this order.
52
+ */
53
+ export interface ComponentType {
54
+ kind: 'component';
55
+ params: ComponentParam[];
56
+ }
57
+ export interface ComponentParam {
58
+ name: string;
59
+ type: Type;
60
+ /** May be left out: the type is nullable, the property has a default value, or is `children`. */
61
+ optional: boolean;
62
+ }
63
+ export interface Member {
64
+ type: Type;
65
+ method: boolean;
66
+ visibility: Visibility;
67
+ /** The class that declares the member, for visibility checks. */
68
+ owner: ClassInfo | null;
69
+ }
70
+ /** Interfaces, object type literals and the types of object literals. */
71
+ export interface ObjectType {
72
+ kind: 'object';
73
+ name: string | null;
74
+ members: Map<string, Member>;
75
+ /** For callable builtins like `Number(x)`. */
76
+ call: FunctionType | null;
77
+ /** `new` on a value of this type, as with `declare var Foo: { new(): Foo }` in a `.d.ts`. */
78
+ construct?: FunctionType;
79
+ /** `[key: string]: T` in a `.d.ts`: the type of members that are not listed. */
80
+ index?: Type;
81
+ /** `[index: number]: T` in a `.d.ts`: what `x[i]` gives, as with typed arrays. */
82
+ numberIndex?: Type;
83
+ /** What `for v in x` gives: the values of `[Symbol.iterator]()` in a `.d.ts`. */
84
+ iterates?: Type;
85
+ /** A generic interface, `interface Box<T>`: its members use these parameters. */
86
+ typeParams?: TypeParam[];
87
+ /** `Box<number>`: the generic interface and the type arguments it was made from. */
88
+ instanceOf?: {
89
+ template: ObjectType;
90
+ args: Type[];
91
+ };
92
+ }
93
+ export interface ClassInfo {
94
+ name: string;
95
+ superClass: ClassInfo | null;
96
+ /** Extends a JS class whose members are unknown. */
97
+ untypedBase: boolean;
98
+ /** Own instance members; inherited ones are found through `superClass`. */
99
+ members: Map<string, Member>;
100
+ statics: Map<string, Member>;
101
+ /** Own constructor; `null` means it is inherited (or empty). */
102
+ ctor: FunctionType | null;
103
+ /** `class Stack<T>`: members use these parameters, instances give them arguments. */
104
+ typeParams: TypeParam[];
105
+ /** Type arguments for a generic base class: the defaults of a class from a `.d.ts`. */
106
+ superArgs?: Type[];
107
+ ctorVisibility: Visibility;
108
+ instance: ClassType;
109
+ value: ClassValueType;
110
+ }
111
+ /** An instance of a class; `args` are the type arguments of a generic class: `Stack<number>`. */
112
+ export interface ClassType {
113
+ kind: 'class';
114
+ info: ClassInfo;
115
+ args?: Type[];
116
+ }
117
+ /** The class itself: its constructor and static members. */
118
+ export interface ClassValueType {
119
+ kind: 'classValue';
120
+ info: ClassInfo;
121
+ }
122
+ /** Several results of a call; only allowed where they are unpacked into variables. */
123
+ export interface TupleType {
124
+ kind: 'tuple';
125
+ types: Type[];
126
+ }
127
+ export interface TypeParam {
128
+ kind: 'param';
129
+ name: string;
130
+ /** `T Shape`: what the argument must be, and what a value of type `T` can do. */
131
+ constraint?: Type | null;
132
+ /** Used when no argument is given: `T = string` in a `.d.ts`. */
133
+ default?: Type;
134
+ }
135
+ /**
136
+ * `string | number`: at least two members, none of them nullable, a union or `any` (see `union`).
137
+ * A union that may also be null is wrapped in `NullableType`: `?(string | number)`.
138
+ */
139
+ export interface UnionType {
140
+ kind: 'union';
141
+ types: Type[];
142
+ /** The `type` alias it was declared with, for messages: `Filter`. */
143
+ name?: string;
144
+ }
145
+ /** `"all"`, `42`, `true`: a type with a single value. */
146
+ export interface LiteralType {
147
+ kind: 'literal';
148
+ value: string | number | boolean;
149
+ }
@@ -0,0 +1,15 @@
1
+ export const NUMBER = { kind: 'number' };
2
+ /** Whole numbers of any size, `10n`; they do not mix with numbers. */
3
+ export const BIGINT = { kind: 'bigint' };
4
+ export const STRING = { kind: 'string' };
5
+ export const BOOL = { kind: 'bool' };
6
+ /** Values from JS: anything goes, nothing is checked. */
7
+ export const ANY = { kind: 'any' };
8
+ /** What a call to a function without results gives. */
9
+ export const VOID = { kind: 'void' };
10
+ /** The type of the `null` literal. */
11
+ export const NULL = { kind: 'null' };
12
+ /** Element type of an empty array literal: assignable to every type. */
13
+ export const NEVER = { kind: 'never' };
14
+ /** The type of an expression that already has an error: accepted everywhere to avoid follow-up errors. */
15
+ export const UNKNOWN = { kind: 'unknown' };
@@ -0,0 +1,7 @@
1
+ import { type Type, type TypeParam } from './model.ts';
2
+ /** Whether a type mentions type parameters: any of them, or only those in `only`. */
3
+ export declare function containsTypeParam(type: Type, only?: ReadonlySet<TypeParam> | null, seen?: Set<Type>): boolean;
4
+ /** Replaces inferred type parameters; with `fallback`, also those that were not inferred. */
5
+ export declare function substitute(type: Type, bindings: Map<TypeParam, Type>, fallback?: Type): Type;
6
+ /** Infers type parameters in `param` from the argument type `arg`. */
7
+ export declare function inferTypeParams(param: Type, arg: Type, bindings: Map<TypeParam, Type>, depth?: number): void;