@prestack/thread-ui 0.0.2 → 0.1.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.
@@ -1,17 +1,9 @@
1
- var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExtension) || function (path, preserveJsx) {
2
- if (typeof path === "string" && /^\.\.?\//.test(path)) {
3
- return path.replace(/\.(tsx)$|((?:\.d)?)((?:\.[^./]+?)?)\.([cm]?)ts$/i, function (m, tsx, d, ext, cm) {
4
- return tsx ? preserveJsx ? ".jsx" : ".js" : d && (!ext || !cm) ? m : (d + ext + "." + cm.toLowerCase() + "js");
5
- });
6
- }
7
- return path;
8
- };
9
- import { existsSync, mkdirSync, readFileSync, readdirSync, rmSync, writeFileSync } from 'node:fs';
1
+ import { existsSync, readFileSync, readdirSync, rmSync, writeFileSync } from "@prestack/thread/core/files";
10
2
  import { basename, dirname, join, relative } from 'node:path';
11
3
  import { argv, stdout } from 'node:process';
12
- import { pathToFileURL } from 'node:url';
13
- import { wrapped } from "@prestack/thread/core/asking";
4
+ import { TYPED, wrapped } from "@prestack/thread/core/answers";
14
5
  import { exit, invoked } from "@prestack/thread/core/invoked";
6
+ import { valuesIn } from "@prestack/thread/core/rows";
15
7
  import { named as packageOf } from "@prestack/thread/core/scope";
16
8
  import { findTree, inTree } from "@prestack/thread/core/tree";
17
9
  import { compiled } from "./generators/react.js";
@@ -134,29 +126,25 @@ export function nameOf(at) {
134
126
  const file = at.split('\\').join('/').split('/').at(-1) ?? at;
135
127
  return PASCAL(file.replace(/^cmp_/, '').replace(/\.[^.]+$/, ''));
136
128
  }
137
- async function sheetOf(tree, file, ...named) {
138
- try {
139
- const held = (await import(__rewriteRelativeImportExtension(pathToFileURL(inTree(tree, file)).href)));
140
- for (const one of named) {
141
- const found = held[one]?.declares;
142
- if (found !== undefined)
143
- return found;
144
- }
145
- return [];
146
- }
147
- catch {
129
+ function sheetOf(tree, file, ...named) {
130
+ const at = inTree(tree, file);
131
+ if (!existsSync(at))
148
132
  return [];
133
+ const held = valuesIn(readFileSync(at));
134
+ for (const one of named) {
135
+ const found = held[one]?.declares;
136
+ if (found !== undefined)
137
+ return found;
149
138
  }
139
+ return [];
150
140
  }
151
141
  const camelOf = (id) => id.replace(/-([a-z0-9])/g, (_, one) => one.toUpperCase());
152
142
  const sentence = (one, pad) => String(one.describes ?? '').trim() === '' ? [] : wrapped(String(one.describes), pad);
153
- async function listed(tree, making) {
154
- const [elements, variants, compositions, screens] = await Promise.all([
155
- sheetOf(tree, `elements.${'ts'}`, 'ELEMENT', 'ELEMENTS'),
156
- sheetOf(tree, `variants.${'ts'}`, 'VARIANT', 'VARIANTS'),
157
- sheetOf(tree, `compositions.${'ts'}`, 'COMPOSITION', 'COMPOSITIONS'),
158
- making === 'screen' ? sheetOf(tree, `screens.${'ts'}`, 'SCREEN', 'SCREENS') : Promise.resolve([]),
159
- ]);
143
+ function listed(tree, making) {
144
+ const elements = sheetOf(tree, `elements.${'ts'}`, 'ELEMENT', 'ELEMENTS');
145
+ const variants = sheetOf(tree, `variants.${'ts'}`, 'VARIANT', 'VARIANTS');
146
+ const compositions = sheetOf(tree, `compositions.${'ts'}`, 'COMPOSITION', 'COMPOSITIONS');
147
+ const screens = making === 'screen' ? sheetOf(tree, `screens.${'ts'}`, 'SCREEN', 'SCREENS') : [];
160
148
  const worn = new Map();
161
149
  for (const one of variants) {
162
150
  for (const each of one.wears ?? []) {
@@ -201,11 +189,11 @@ async function listed(tree, making) {
201
189
  '',
202
190
  ]),
203
191
  ' Materials, style guide values, fonts and animations are chosen inside a VARIANT, never inside',
204
- ' a body — `npx thread create variant` prints every one of them at the moment one is needed.',
192
+ ` a body — \`${TYPED} create variant\` prints every one of them at the moment one is needed.`,
205
193
  '',
206
- ' Every element and the tags it is written as: `npx thread create element`. Every variant and',
207
- ' the tag it is worn as: `npx thread create variant`. Then open the one nearest to what you are',
208
- ' about to build with `npx thread read <id>` — it already answers how a body is arranged, how a',
194
+ ` Every element and the tags it is written as: \`${TYPED} create element\`. Every variant and`,
195
+ ` the tag it is worn as: \`${TYPED} create variant\`. Then open the one nearest to what you are`,
196
+ ` about to build with \`${TYPED} read <id>\` — it already answers how a body is arranged, how a`,
209
197
  ' variant is worn and how a control reaches an operation, and a file cannot be wrong in the way',
210
198
  ' a remembered example can.',
211
199
  '',
@@ -305,7 +293,6 @@ export function settled(root, rows, checking, by, kept) {
305
293
  });
306
294
  const at = join(root, where);
307
295
  if (!checking) {
308
- mkdirSync(dirname(at), { recursive: true });
309
296
  writeFileSync(at, text, 'utf8');
310
297
  continue;
311
298
  }
@@ -364,7 +351,6 @@ export function emitting(root, entries, checking, kept) {
364
351
  }
365
352
  }
366
353
  else {
367
- mkdirSync(dirname(to), { recursive: true });
368
354
  writeFileSync(to, text, 'utf8');
369
355
  }
370
356
  for (const one of text.matchAll(REACHED)) {
@@ -441,7 +427,7 @@ export function handing(at, text) {
441
427
  }
442
428
  return found;
443
429
  }
444
- export async function undeclared(tree, rows) {
430
+ export function undeclared(tree, rows) {
445
431
  const elements = new Set();
446
432
  const declared = new Set();
447
433
  for (const [file, exported] of [
@@ -452,7 +438,7 @@ export async function undeclared(tree, rows) {
452
438
  const where = inTree(tree, file);
453
439
  if (!existsSync(where))
454
440
  continue;
455
- const sheet = (await import(__rewriteRelativeImportExtension(pathToFileURL(where).href)));
441
+ const sheet = valuesIn(readFileSync(where));
456
442
  for (const row of sheet[exported]?.declares ?? []) {
457
443
  if (exported === 'ELEMENT')
458
444
  elements.add(row.id);
@@ -488,14 +474,14 @@ export const ${name} = composition('${name}', () => <Box.card />)
488
474
  export function seeds(rows, held) {
489
475
  return rows.filter((row) => !held(row.at)).map((row) => ({ path: row.at, content: starter(row) }));
490
476
  }
491
- async function run() {
477
+ function run() {
492
478
  const tree = findTree();
493
479
  const at = inTree(tree, 'compositions.ts');
494
480
  if (!existsSync(at)) {
495
481
  stdout.write(`thread: this tree has no ${tree.name}/${basename(at)}, so it declares no composition and there is nothing to seed or check.\n`);
496
482
  return 0;
497
483
  }
498
- const held = (await import(__rewriteRelativeImportExtension(pathToFileURL(at).href)));
484
+ const held = valuesIn(readFileSync(at));
499
485
  if (held.COMPOSITION === undefined) {
500
486
  stdout.write(`thread: ${tree.name}/compositions.ts exports no \`COMPOSITION\`, so nothing declares a composition here.\n`);
501
487
  return 1;
@@ -511,24 +497,23 @@ async function run() {
511
497
  }
512
498
  if (!checking) {
513
499
  for (const one of made) {
514
- mkdirSync(dirname(join(tree.at, one.path)), { recursive: true });
515
500
  writeFileSync(join(tree.at, one.path), one.content, 'utf8');
516
501
  stdout.write(`thread: seeded ${one.path}\n`);
517
502
  }
518
503
  }
519
- const parts = await sheetOf(tree, 'elements.ts', 'ELEMENT', 'ELEMENTS');
504
+ const parts = sheetOf(tree, 'elements.ts', 'ELEMENT', 'ELEMENTS');
520
505
  const shipped = `node_modules/${packageOf('ui')}/dist/ui/`;
521
506
  const entries = [
522
507
  ...RUNTIME,
523
508
  ...parts.flatMap((one) => (one.at ?? '').startsWith(shipped) ? [(one.at ?? '').slice(shipped.length).replace(/\.js$/, '.tsx')] : []),
524
509
  ];
525
510
  const kept = new Set();
526
- for (const one of await sheetOf(tree, 'screens.ts', 'SCREEN', 'SCREENS')) {
511
+ for (const one of sheetOf(tree, 'screens.ts', 'SCREEN', 'SCREENS')) {
527
512
  if (one.at !== undefined && one.at !== '')
528
513
  kept.add(compiledAt(one.at));
529
514
  }
530
515
  const found = [
531
- ...(await undeclared(tree, rows)),
516
+ ...undeclared(tree, rows),
532
517
  ...emitting(tree.at, entries, checking, kept),
533
518
  ...settled(tree.at, rows, checking, 'thread compositions', kept),
534
519
  ];
@@ -541,4 +526,4 @@ async function run() {
541
526
  return loose.length === 0 ? 0 : 1;
542
527
  }
543
528
  if (invoked(import.meta.url))
544
- exit(await run());
529
+ exit(run());
@@ -1,10 +1,10 @@
1
- import { existsSync, mkdirSync, readFileSync, readdirSync, rmSync, writeFileSync } from 'node:fs'
1
+ import { existsSync, readFileSync, readdirSync, rmSync, writeFileSync } from '@prestack/thread/core/files'
2
2
  import { basename, dirname, join, relative } from 'node:path'
3
3
  import { argv, stdout } from 'node:process'
4
- import { pathToFileURL } from 'node:url'
5
4
 
6
- import { wrapped } from '@prestack/thread/core/asking'
5
+ import { TYPED, wrapped } from '@prestack/thread/core/answers'
7
6
  import { exit, invoked } from '@prestack/thread/core/invoked'
7
+ import { valuesIn } from '@prestack/thread/core/rows'
8
8
  import type { Threaded } from '@prestack/thread/core/thread'
9
9
  import { named as packageOf } from '@prestack/thread/core/scope'
10
10
  import type { Tree } from '@prestack/thread/core/tree'
@@ -149,19 +149,17 @@ type Listed = {
149
149
  readonly arranges?: boolean
150
150
  }
151
151
 
152
- async function sheetOf(tree: Tree, file: string, ...named: readonly string[]): Promise<readonly Listed[]> {
153
- try {
154
- const held = (await import(pathToFileURL(inTree(tree, file)).href)) as Readonly<
155
- Record<string, { readonly declares?: readonly Listed[] } | undefined>
156
- >
157
- for (const one of named) {
158
- const found = held[one]?.declares
159
- if (found !== undefined) return found
160
- }
161
- return []
162
- } catch {
163
- return []
152
+ function sheetOf(tree: Tree, file: string, ...named: readonly string[]): readonly Listed[] {
153
+ const at = inTree(tree, file)
154
+ if (!existsSync(at)) return []
155
+ const held = valuesIn(readFileSync(at)) as Readonly<
156
+ Record<string, { readonly declares?: readonly Listed[] } | undefined>
157
+ >
158
+ for (const one of named) {
159
+ const found = held[one]?.declares
160
+ if (found !== undefined) return found
164
161
  }
162
+ return []
165
163
  }
166
164
 
167
165
  const camelOf = (id: string): string => id.replace(/-([a-z0-9])/g, (_, one: string) => one.toUpperCase())
@@ -169,13 +167,11 @@ const camelOf = (id: string): string => id.replace(/-([a-z0-9])/g, (_, one: stri
169
167
  const sentence = (one: Listed, pad: string): readonly string[] =>
170
168
  String(one.describes ?? '').trim() === '' ? [] : wrapped(String(one.describes), pad)
171
169
 
172
- async function listed(tree: Tree, making: 'composition' | 'screen'): Promise<readonly string[]> {
173
- const [elements, variants, compositions, screens] = await Promise.all([
174
- sheetOf(tree, `elements.${'ts'}`, 'ELEMENT', 'ELEMENTS'),
175
- sheetOf(tree, `variants.${'ts'}`, 'VARIANT', 'VARIANTS'),
176
- sheetOf(tree, `compositions.${'ts'}`, 'COMPOSITION', 'COMPOSITIONS'),
177
- making === 'screen' ? sheetOf(tree, `screens.${'ts'}`, 'SCREEN', 'SCREENS') : Promise.resolve([]),
178
- ])
170
+ function listed(tree: Tree, making: 'composition' | 'screen'): readonly string[] {
171
+ const elements = sheetOf(tree, `elements.${'ts'}`, 'ELEMENT', 'ELEMENTS')
172
+ const variants = sheetOf(tree, `variants.${'ts'}`, 'VARIANT', 'VARIANTS')
173
+ const compositions = sheetOf(tree, `compositions.${'ts'}`, 'COMPOSITION', 'COMPOSITIONS')
174
+ const screens = making === 'screen' ? sheetOf(tree, `screens.${'ts'}`, 'SCREEN', 'SCREENS') : []
179
175
 
180
176
  const worn = new Map<string, string[]>()
181
177
  for (const one of variants) {
@@ -227,12 +223,12 @@ async function listed(tree: Tree, making: 'composition' | 'screen'): Promise<rea
227
223
  '',
228
224
  ]),
229
225
  ' Materials, style guide values, fonts and animations are chosen inside a VARIANT, never inside',
230
- ' a body — `npx thread create variant` prints every one of them at the moment one is needed.',
226
+ ` a body — \`${TYPED} create variant\` prints every one of them at the moment one is needed.`,
231
227
  '',
232
228
 
233
- ' Every element and the tags it is written as: `npx thread create element`. Every variant and',
234
- ' the tag it is worn as: `npx thread create variant`. Then open the one nearest to what you are',
235
- ' about to build with `npx thread read <id>` — it already answers how a body is arranged, how a',
229
+ ` Every element and the tags it is written as: \`${TYPED} create element\`. Every variant and`,
230
+ ` the tag it is worn as: \`${TYPED} create variant\`. Then open the one nearest to what you are`,
231
+ ` about to build with \`${TYPED} read <id>\` — it already answers how a body is arranged, how a`,
236
232
  ' variant is worn and how a control reaches an operation, and a file cannot be wrong in the way',
237
233
  ' a remembered example can.',
238
234
  '',
@@ -362,7 +358,6 @@ export function settled(
362
358
  })
363
359
  const at = join(root, where)
364
360
  if (!checking) {
365
- mkdirSync(dirname(at), { recursive: true })
366
361
  writeFileSync(at, text, 'utf8')
367
362
  continue
368
363
  }
@@ -438,7 +433,6 @@ export function emitting(
438
433
  )
439
434
  }
440
435
  } else {
441
- mkdirSync(dirname(to), { recursive: true })
442
436
  writeFileSync(to, text, 'utf8')
443
437
  }
444
438
  for (const one of text.matchAll(REACHED)) {
@@ -519,10 +513,10 @@ export function handing(at: string, text: string): readonly string[] {
519
513
  return found
520
514
  }
521
515
 
522
- export async function undeclared(
516
+ export function undeclared(
523
517
  tree: Tree,
524
518
  rows: readonly Threaded[],
525
- ): Promise<readonly string[]> {
519
+ ): readonly string[] {
526
520
  const elements = new Set<string>()
527
521
  const declared = new Set<string>()
528
522
 
@@ -533,7 +527,7 @@ export async function undeclared(
533
527
  ] as const) {
534
528
  const where = inTree(tree, file)
535
529
  if (!existsSync(where)) continue
536
- const sheet = (await import(pathToFileURL(where).href)) as Readonly<
530
+ const sheet = valuesIn(readFileSync(where)) as Readonly<
537
531
  Record<string, { readonly declares?: readonly Threaded[] } | undefined>
538
532
  >
539
533
  for (const row of sheet[exported]?.declares ?? []) {
@@ -574,14 +568,14 @@ export function seeds(rows: readonly Threaded[], held: (at: string) => boolean):
574
568
  return rows.filter((row) => !held(row.at)).map((row) => ({ path: row.at, content: starter(row) }))
575
569
  }
576
570
 
577
- async function run(): Promise<number> {
571
+ function run(): number {
578
572
  const tree = findTree()
579
573
  const at = inTree(tree, 'compositions.ts')
580
574
  if (!existsSync(at)) {
581
575
  stdout.write(`thread: this tree has no ${tree.name}/${basename(at)}, so it declares no composition and there is nothing to seed or check.\n`)
582
576
  return 0
583
577
  }
584
- const held = (await import(pathToFileURL(at).href)) as { COMPOSITION?: { readonly declares?: readonly Threaded[] } }
578
+ const held = valuesIn(readFileSync(at)) as { COMPOSITION?: { readonly declares?: readonly Threaded[] } }
585
579
 
586
580
  if (held.COMPOSITION === undefined) {
587
581
  stdout.write(`thread: ${tree.name}/compositions.ts exports no \`COMPOSITION\`, so nothing declares a composition here.\n`)
@@ -603,13 +597,12 @@ async function run(): Promise<number> {
603
597
 
604
598
  if (!checking) {
605
599
  for (const one of made) {
606
- mkdirSync(dirname(join(tree.at, one.path)), { recursive: true })
607
600
  writeFileSync(join(tree.at, one.path), one.content, 'utf8')
608
601
  stdout.write(`thread: seeded ${one.path}\n`)
609
602
  }
610
603
  }
611
604
 
612
- const parts = await sheetOf(tree, 'elements.ts', 'ELEMENT', 'ELEMENTS')
605
+ const parts = sheetOf(tree, 'elements.ts', 'ELEMENT', 'ELEMENTS')
613
606
  const shipped = `node_modules/${packageOf('ui')}/dist/ui/`
614
607
  const entries = [
615
608
  ...RUNTIME,
@@ -618,11 +611,11 @@ async function run(): Promise<number> {
618
611
  ),
619
612
  ]
620
613
  const kept = new Set<string>()
621
- for (const one of await sheetOf(tree, 'screens.ts', 'SCREEN', 'SCREENS')) {
614
+ for (const one of sheetOf(tree, 'screens.ts', 'SCREEN', 'SCREENS')) {
622
615
  if (one.at !== undefined && one.at !== '') kept.add(compiledAt(one.at))
623
616
  }
624
617
  const found = [
625
- ...(await undeclared(tree, rows)),
618
+ ...undeclared(tree, rows),
626
619
  ...emitting(tree.at, entries, checking, kept),
627
620
  ...settled(tree.at, rows, checking, 'thread compositions', kept),
628
621
  ]
@@ -637,4 +630,4 @@ async function run(): Promise<number> {
637
630
  return loose.length === 0 ? 0 : 1
638
631
  }
639
632
 
640
- if (invoked(import.meta.url)) exit(await run())
633
+ if (invoked(import.meta.url)) exit(run())
@@ -1,8 +1,9 @@
1
1
  import { spawnSync } from 'node:child_process';
2
- import { existsSync, readFileSync, writeSync } from 'node:fs';
2
+ import { writeSync } from 'node:fs';
3
3
  import { basename, join } from 'node:path';
4
4
  import { argv } from 'node:process';
5
5
  import { generators, settling } from "@prestack/thread/core/chain";
6
+ import { existsSync, readFileSync } from "@prestack/thread/core/files";
6
7
  import { exit, invoked } from "@prestack/thread/core/invoked";
7
8
  import { named } from "@prestack/thread/core/scope";
8
9
  import { findTree } from "@prestack/thread/core/tree";
@@ -1,9 +1,10 @@
1
1
  import { spawnSync } from 'node:child_process'
2
- import { existsSync, readFileSync, writeSync } from 'node:fs'
2
+ import { writeSync } from 'node:fs'
3
3
  import { basename, join } from 'node:path'
4
4
  import { argv } from 'node:process'
5
5
 
6
6
  import { generators, settling } from '@prestack/thread/core/chain'
7
+ import { existsSync, readFileSync } from '@prestack/thread/core/files'
7
8
  import { exit, invoked } from '@prestack/thread/core/invoked'
8
9
  import { named } from '@prestack/thread/core/scope'
9
10
  import { findTree } from '@prestack/thread/core/tree'
@@ -6,7 +6,7 @@ var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExte
6
6
  }
7
7
  return path;
8
8
  };
9
- import { existsSync, readFileSync, writeFileSync } from 'node:fs';
9
+ import { existsSync, readFileSync, writeFileSync } from "@prestack/thread/core/files";
10
10
  import { join, resolve } from 'node:path';
11
11
  import { argv, stdout } from 'node:process';
12
12
  import { fileURLToPath, pathToFileURL } from 'node:url';
@@ -1,4 +1,4 @@
1
- import { existsSync, readFileSync, writeFileSync } from 'node:fs'
1
+ import { existsSync, readFileSync, writeFileSync } from '@prestack/thread/core/files'
2
2
  import { join, resolve } from 'node:path'
3
3
  import { argv, stdout } from 'node:process'
4
4
  import { fileURLToPath, pathToFileURL } from 'node:url'
@@ -6,8 +6,8 @@ var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExte
6
6
  }
7
7
  return path;
8
8
  };
9
- import { existsSync, mkdirSync, readFileSync, readdirSync, writeFileSync } from 'node:fs';
10
- import { dirname, join, relative } from 'node:path';
9
+ import { existsSync, readFileSync, readdirSync, writeFileSync } from "@prestack/thread/core/files";
10
+ import { join, relative } from 'node:path';
11
11
  import { argv, stderr, stdout } from 'node:process';
12
12
  import { pathToFileURL } from 'node:url';
13
13
  import { exit, invoked } from "@prestack/thread/core/invoked";
@@ -248,7 +248,6 @@ async function run() {
248
248
  return 0;
249
249
  }
250
250
  for (const one of files) {
251
- mkdirSync(dirname(join(at, one.path)), { recursive: true });
252
251
  writeFileSync(join(at, one.path), one.made, 'utf8');
253
252
  }
254
253
  stdout.write(`i18n: ${String(everything.length)} key(s) across ${String(languages.length)} language(s) — ` +
@@ -1,4 +1,4 @@
1
- import { existsSync, mkdirSync, readFileSync, readdirSync, writeFileSync } from 'node:fs'
1
+ import { existsSync, readFileSync, readdirSync, writeFileSync } from '@prestack/thread/core/files'
2
2
  import { dirname, join, relative } from 'node:path'
3
3
  import { argv, stderr, stdout } from 'node:process'
4
4
  import { pathToFileURL } from 'node:url'
@@ -280,7 +280,6 @@ async function run(): Promise<number> {
280
280
  }
281
281
 
282
282
  for (const one of files) {
283
- mkdirSync(dirname(join(at, one.path)), { recursive: true })
284
283
  writeFileSync(join(at, one.path), one.made, 'utf8')
285
284
  }
286
285
 
@@ -1,16 +1,8 @@
1
- var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExtension) || function (path, preserveJsx) {
2
- if (typeof path === "string" && /^\.\.?\//.test(path)) {
3
- return path.replace(/\.(tsx)$|((?:\.d)?)((?:\.[^./]+?)?)\.([cm]?)ts$/i, function (m, tsx, d, ext, cm) {
4
- return tsx ? preserveJsx ? ".jsx" : ".js" : d && (!ext || !cm) ? m : (d + ext + "." + cm.toLowerCase() + "js");
5
- });
6
- }
7
- return path;
8
- };
9
1
  import { createRequire } from 'node:module';
10
- import { existsSync, mkdirSync, readdirSync, readFileSync, writeFileSync } from 'node:fs';
2
+ import { existsSync, readdirSync, readFileSync, writeFileSync } from "@prestack/thread/core/files";
3
+ import { valuesIn } from "@prestack/thread/core/rows";
11
4
  import { dirname, join } from 'node:path';
12
5
  import { argv, stderr, stdout } from 'node:process';
13
- import { pathToFileURL } from 'node:url';
14
6
  import { exit } from "@prestack/thread/core/invoked";
15
7
  import { findTree, inTree } from "@prestack/thread/core/tree";
16
8
  import { brandExport, drawnAs, setNamed, sizeRows, SET_ROW } from "../icons.js";
@@ -104,7 +96,7 @@ async function node(file, name) {
104
96
  stdout.write(`icons: this tree has no ${findTree().name}/${file}, so it declares no icon and there is no module to write or check.\n`);
105
97
  exit(0);
106
98
  }
107
- const held = (await import(__rewriteRelativeImportExtension(pathToFileURL(at).href)));
99
+ const held = valuesIn(readFileSync(at));
108
100
  const one = held[name];
109
101
  if (one === undefined)
110
102
  throw new Error(`_threads/${file} exports no \`${name}\`.`);
@@ -178,7 +170,6 @@ async function run() {
178
170
  'its generator is a hand edit wearing a generated name. Run `thread icons` and commit what it writes.\n');
179
171
  return 1;
180
172
  }
181
- mkdirSync(dirname(at), { recursive: true });
182
173
  writeFileSync(at, made, 'utf8');
183
174
  stdout.write(`thread: wrote app/_generated/icons.ts — ${String(drawn.length)} icons drawn from \`${set.name}\`\n`);
184
175
  return 0;
@@ -1,6 +1,7 @@
1
1
  import { createRequire } from 'node:module'
2
2
 
3
- import { existsSync, mkdirSync, readdirSync, readFileSync, writeFileSync } from 'node:fs'
3
+ import { existsSync, readdirSync, readFileSync, writeFileSync } from '@prestack/thread/core/files'
4
+ import { valuesIn } from '@prestack/thread/core/rows'
4
5
  import { dirname, join } from 'node:path'
5
6
  import { argv, stderr, stdout } from 'node:process'
6
7
  import { pathToFileURL } from 'node:url'
@@ -112,7 +113,7 @@ async function node(file: string, name: string): Promise<Node> {
112
113
  stdout.write(`icons: this tree has no ${findTree().name}/${file}, so it declares no icon and there is no module to write or check.\n`)
113
114
  exit(0)
114
115
  }
115
- const held = (await import(pathToFileURL(at).href)) as Record<string, unknown>
116
+ const held = valuesIn(readFileSync(at)) as Record<string, unknown>
116
117
  const one = held[name]
117
118
  if (one === undefined) throw new Error(`_threads/${file} exports no \`${name}\`.`)
118
119
  return one as Node
@@ -203,7 +204,6 @@ async function run(): Promise<number> {
203
204
  return 1
204
205
  }
205
206
 
206
- mkdirSync(dirname(at), { recursive: true })
207
207
  writeFileSync(at, made, 'utf8')
208
208
  stdout.write(
209
209
  `thread: wrote app/_generated/icons.ts — ${String(drawn.length)} icons drawn from \`${set.name}\`\n`,
@@ -1,5 +1,6 @@
1
1
  import { createHash } from 'node:crypto';
2
- import { existsSync, readFileSync, statSync } from 'node:fs';
2
+ import { readFileSync as bytesAt } from 'node:fs';
3
+ import { existsSync, readFileSync, statSync } from "@prestack/thread/core/files";
3
4
  import { cwd } from 'node:process';
4
5
  import { dirname, join, resolve } from 'node:path';
5
6
  import ts from 'typescript';
@@ -192,7 +193,7 @@ export function ungated(from) {
192
193
  const held = JSON.parse(readFileSync(at, 'utf8'));
193
194
  for (const [named, was] of Object.entries(held.of ?? {})) {
194
195
  const now = existsSync(join(dirname(dirname(at)), named))
195
- ? createHash('sha256').update(readFileSync(join(dirname(dirname(at)), named))).digest('hex').slice(0, 16)
196
+ ? createHash('sha256').update(bytesAt(join(dirname(dirname(at)), named))).digest('hex').slice(0, 16)
196
197
  : 'gone';
197
198
  if (now === was)
198
199
  continue;
@@ -1,5 +1,6 @@
1
1
  import { createHash } from 'node:crypto'
2
- import { existsSync, readFileSync, statSync } from 'node:fs'
2
+ import { readFileSync as bytesAt } from 'node:fs'
3
+ import { existsSync, readFileSync, statSync } from '@prestack/thread/core/files'
3
4
  import { cwd } from 'node:process'
4
5
  import { dirname, join, resolve } from 'node:path'
5
6
 
@@ -236,7 +237,7 @@ export function ungated(from: string): string | null {
236
237
  const held = JSON.parse(readFileSync(at, 'utf8')) as { of?: Record<string, string> }
237
238
  for (const [named, was] of Object.entries(held.of ?? {})) {
238
239
  const now = existsSync(join(dirname(dirname(at)), named))
239
- ? createHash('sha256').update(readFileSync(join(dirname(dirname(at)), named))).digest('hex').slice(0, 16)
240
+ ? createHash('sha256').update(bytesAt(join(dirname(dirname(at)), named))).digest('hex').slice(0, 16)
240
241
  : 'gone'
241
242
  if (now === was) continue
242
243
  checked = `${named} has changed since the gate last passed, so what this tree declares and what it was measured as no longer agree. Run \`thread gate\``
@@ -1,17 +1,9 @@
1
- var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExtension) || function (path, preserveJsx) {
2
- if (typeof path === "string" && /^\.\.?\//.test(path)) {
3
- return path.replace(/\.(tsx)$|((?:\.d)?)((?:\.[^./]+?)?)\.([cm]?)ts$/i, function (m, tsx, d, ext, cm) {
4
- return tsx ? preserveJsx ? ".jsx" : ".js" : d && (!ext || !cm) ? m : (d + ext + "." + cm.toLowerCase() + "js");
5
- });
6
- }
7
- return path;
8
- };
9
- import { existsSync, mkdirSync, readFileSync, realpathSync, writeFileSync } from 'node:fs';
10
1
  import { dirname, join, relative } from 'node:path';
11
2
  import { argv, stderr, stdout } from 'node:process';
12
- import { pathToFileURL } from 'node:url';
13
3
  import ts from 'typescript';
4
+ import { existsSync, readFileSync, realpathSync, writeFileSync } from "@prestack/thread/core/files";
14
5
  import { exit, invoked } from "@prestack/thread/core/invoked";
6
+ import { valuesIn } from "@prestack/thread/core/rows";
15
7
  import { named as packageOf } from "@prestack/thread/core/scope";
16
8
  import { findTree, inTree } from "@prestack/thread/core/tree";
17
9
  import { PERMITS_AT } from "@prestack/thread/operations/access";
@@ -28,6 +20,11 @@ const MAP = `app/_generated/map.${'ts'}`;
28
20
  const PROVIDER = `${COMPILED}/ui/provider.tsx`;
29
21
  const GRAMMAR = `${COMPILED}/ui/islands/map.ts`;
30
22
  const MOVES = 'navigateTo';
23
+ const sheetAt = (at) => {
24
+ if (!existsSync(at))
25
+ return {};
26
+ return valuesIn(readFileSync(at));
27
+ };
31
28
  function door(knowing, wording, dispatching, moving, presenting) {
32
29
  const opening = presenting.length > 0;
33
30
  const props = `asking={ASKING}${knowing ? ' actor={actor} permits={gate}' : ''}${dispatching ? ' dispatch={dispatchTo}' : ''}` +
@@ -475,14 +472,14 @@ async function run() {
475
472
  stdout.write(`routes: this tree has no ${relative(at, screensAt)}, so it declares no screen and there is no map, page or layout to write or check.\n`);
476
473
  return 0;
477
474
  }
478
- const sheet = (await import(__rewriteRelativeImportExtension(pathToFileURL(screensAt).href)));
475
+ const sheet = valuesIn(readFileSync(screensAt));
479
476
  if (sheet.SCREEN === undefined) {
480
477
  stderr.write('routes: _threads/screens.ts exports no `SCREEN`, so nothing declares a screen here.\n');
481
478
  return 1;
482
479
  }
483
- const held = (await import(__rewriteRelativeImportExtension(pathToFileURL(inTree(tree, `localizations.${'ts'}`)).href)).catch(() => ({})));
480
+ const held = sheetAt(inTree(tree, `localizations.${'ts'}`));
484
481
  const source = held.LOCALIZATION?.holds?.find((one) => one.id === 'source')?.is ?? 'en';
485
- const placed = (await import(__rewriteRelativeImportExtension(pathToFileURL(inTree(tree, `compositions.${'ts'}`)).href)).catch(() => ({})));
482
+ const placed = sheetAt(inTree(tree, `compositions.${'ts'}`));
486
483
  const compositions = placed.COMPOSITION?.declares ?? [];
487
484
  const rows = sheet.SCREEN.declares ?? [];
488
485
  const texts = new Map();
@@ -604,7 +601,6 @@ async function run() {
604
601
  return 0;
605
602
  }
606
603
  for (const one of made) {
607
- mkdirSync(dirname(join(at, one.path)), { recursive: true });
608
604
  writeFileSync(join(at, one.path), one.text, 'utf8');
609
605
  }
610
606
  stdout.write(`routes: the map — ${counted}\n`);
@@ -1,11 +1,11 @@
1
- import { existsSync, mkdirSync, readFileSync, realpathSync, writeFileSync } from 'node:fs'
2
1
  import { dirname, join, relative } from 'node:path'
3
2
  import { argv, stderr, stdout } from 'node:process'
4
- import { pathToFileURL } from 'node:url'
5
3
 
6
4
  import ts from 'typescript'
7
5
 
6
+ import { existsSync, readFileSync, realpathSync, writeFileSync } from '@prestack/thread/core/files'
8
7
  import { exit, invoked } from '@prestack/thread/core/invoked'
8
+ import { valuesIn } from '@prestack/thread/core/rows'
9
9
  import { named as packageOf } from '@prestack/thread/core/scope'
10
10
  import { findTree, inTree } from '@prestack/thread/core/tree'
11
11
  import { PERMITS_AT } from '@prestack/thread/operations/access'
@@ -35,6 +35,11 @@ const GRAMMAR = `${COMPILED}/ui/islands/map.ts`
35
35
 
36
36
  const MOVES = 'navigateTo'
37
37
 
38
+ const sheetAt = (at: string): Record<string, unknown> => {
39
+ if (!existsSync(at)) return {}
40
+ return valuesIn(readFileSync(at)) as Record<string, unknown>
41
+ }
42
+
38
43
  function door(
39
44
  knowing: boolean,
40
45
  wording: boolean,
@@ -564,18 +569,18 @@ async function run(): Promise<number> {
564
569
  stdout.write(`routes: this tree has no ${relative(at, screensAt)}, so it declares no screen and there is no map, page or layout to write or check.\n`)
565
570
  return 0
566
571
  }
567
- const sheet = (await import(pathToFileURL(screensAt).href)) as { SCREEN?: Node }
572
+ const sheet = valuesIn(readFileSync(screensAt)) as { SCREEN?: Node }
568
573
  if (sheet.SCREEN === undefined) {
569
574
  stderr.write('routes: _threads/screens.ts exports no `SCREEN`, so nothing declares a screen here.\n')
570
575
  return 1
571
576
  }
572
577
 
573
- const held = (await import(pathToFileURL(inTree(tree, `localizations.${'ts'}`)).href).catch(() => ({}))) as {
578
+ const held = sheetAt(inTree(tree, `localizations.${'ts'}`)) as {
574
579
  LOCALIZATION?: { readonly holds?: readonly { readonly id: string; readonly is?: string }[] }
575
580
  }
576
581
  const source = held.LOCALIZATION?.holds?.find((one) => one.id === 'source')?.is ?? 'en'
577
582
 
578
- const placed = (await import(pathToFileURL(inTree(tree, `compositions.${'ts'}`)).href).catch(() => ({}))) as {
583
+ const placed = sheetAt(inTree(tree, `compositions.${'ts'}`)) as {
579
584
  COMPOSITION?: Node
580
585
  }
581
586
  const compositions = placed.COMPOSITION?.declares ?? []
@@ -727,7 +732,6 @@ async function run(): Promise<number> {
727
732
  }
728
733
 
729
734
  for (const one of made) {
730
- mkdirSync(dirname(join(at, one.path)), { recursive: true })
731
735
  writeFileSync(join(at, one.path), one.text, 'utf8')
732
736
  }
733
737
  stdout.write(`routes: the map — ${counted}\n`)