tangled
alpha
login
or
join now
maxine.puppykitty.racing
/
typelex
forked from
danabra.mov/typelex
0
fork
atom
An experimental TypeSpec syntax for Lexicon
0
fork
atom
overview
issues
pulls
pipelines
fixes
danabra.mov
5 months ago
936dfa97
846457ba
+61
-15
2 changed files
expand all
collapse all
unified
split
packages
cli
package.json
src
commands
init.ts
+1
-1
packages/cli/package.json
···
1
1
{
2
2
"name": "@typelex/cli",
3
3
-
"version": "0.2.10",
3
3
+
"version": "0.2.12",
4
4
"main": "dist/index.js",
5
5
"type": "module",
6
6
"bin": {
+60
-14
packages/cli/src/commands/init.ts
···
4
4
import { createInterface } from "readline";
5
5
import pc from "picocolors";
6
6
7
7
+
// Gradient colors matching website (approximated with ANSI 256 colors)
8
8
+
// Darker variant for better readability on white terminals
9
9
+
function gradientText(text: string): string {
10
10
+
// Approximating: #4a9eff -> #7a8ef7 -> #ff85c1 -> #9b7ef7
11
11
+
// Using darker ANSI 256 color codes for a blue->purple->pink gradient
12
12
+
const colors = [
13
13
+
'\x1b[38;5;33m', // darker blue
14
14
+
'\x1b[38;5;69m', // blue-purple
15
15
+
'\x1b[38;5;99m', // purple
16
16
+
'\x1b[38;5;133m', // purple-pink
17
17
+
'\x1b[38;5;170m', // pink
18
18
+
'\x1b[38;5;170m', // pink
19
19
+
'\x1b[38;5;133m', // purple-pink
20
20
+
];
21
21
+
const reset = '\x1b[0m';
22
22
+
23
23
+
return text.split('').map((char, i) => {
24
24
+
const colorIndex = Math.floor((i / text.length) * colors.length);
25
25
+
return colors[colorIndex] + char;
26
26
+
}).join('') + reset;
27
27
+
}
28
28
+
7
29
function createMainTemplate(namespace: string): string {
8
30
return `import "@typelex/emitter";
9
31
import "./externals.tsp";
···
50
72
return initSetup();
51
73
}
52
74
53
53
-
console.log(pc.bold("Initializing typelex project...\n"));
54
54
-
console.log("Installing dependencies...");
75
75
+
console.log(`Adding ${gradientText("typelex")}...\n`);
55
76
56
77
// Detect package manager: walk up from cwd
57
78
let packageManager = "npm";
···
87
108
88
109
install.on("close", (code) => {
89
110
if (code === 0) {
90
90
-
console.log("\n✓ Installed @typelex/cli and @typelex/emitter\n");
111
111
+
console.log(`\n${pc.green("✓")} Installed ${pc.dim("@typelex/cli")} and ${pc.dim("@typelex/emitter")}\n`);
91
112
resolvePromise();
92
113
} else {
93
114
console.error(pc.red("✗ Failed to install dependencies"));
···
102
123
});
103
124
104
125
// Hand off to locally installed version
105
105
-
console.log("Continuing with local installation...\n");
126
126
+
// Find where node_modules actually is (could be at workspace root with pnpm)
127
127
+
let nodeModulesDir = resolve(cwd, "node_modules");
128
128
+
let searchDir = cwd;
129
129
+
130
130
+
// Search upward for node_modules with typelex installed
131
131
+
while (searchDir !== resolve(searchDir, "..")) {
132
132
+
try {
133
133
+
const candidatePath = resolve(searchDir, "node_modules/.bin/typelex");
134
134
+
await access(candidatePath);
135
135
+
nodeModulesDir = resolve(searchDir, "node_modules");
136
136
+
break;
137
137
+
} catch {
138
138
+
// Not found, try parent
139
139
+
}
140
140
+
searchDir = resolve(searchDir, "..");
141
141
+
}
106
142
107
143
return new Promise((resolvePromise, reject) => {
108
108
-
const localCli = resolve(cwd, "node_modules/.bin/typelex");
144
144
+
const localCli = resolve(nodeModulesDir, ".bin/typelex");
109
145
const setup = spawn(localCli, ["init", "--setup"], {
110
146
cwd,
111
147
stdio: "inherit",
···
176
212
}
177
213
}
178
214
215
215
+
// Determine the actual lexicons path for display
216
216
+
const displayLexiconsPath = hasLocalLexicons
217
217
+
? "./lexicons"
218
218
+
: lexiconsDir || "./lexicons";
219
219
+
220
220
+
// Inform about external lexicons
221
221
+
console.log(`\nLexicons other than ${pc.cyan(namespace)} will be considered external.`);
222
222
+
console.log(`Put them into the ${pc.cyan(displayLexiconsPath)} folder as JSON.\n`);
223
223
+
179
224
// Create typelex directory
180
225
await mkdir(typelexDir, { recursive: true });
181
226
···
185
230
await access(mainTspPath);
186
231
const content = await readFile(mainTspPath, "utf-8");
187
232
if (content.trim().length > 0) {
188
188
-
console.log(`✓ ${pc.cyan("typelex/main.tsp")} already exists, skipping`);
233
233
+
console.log(`${pc.green("✓")} ${pc.cyan("typelex/main.tsp")} already exists, skipping`);
189
234
shouldCreateMain = false;
190
235
}
191
236
} catch {
···
194
239
195
240
if (shouldCreateMain) {
196
241
await writeFile(mainTspPath, createMainTemplate(namespacePrefix), "utf-8");
197
197
-
console.log(`✓ Created ${pc.cyan("typelex/main.tsp")}`);
242
242
+
console.log(`${pc.green("✓")} Created ${pc.cyan("typelex/main.tsp")}`);
198
243
}
199
244
200
245
// Always create/overwrite externals.tsp
201
246
await writeFile(externalsTspPath, EXTERNALS_TSP_TEMPLATE, "utf-8");
202
202
-
console.log(`✓ Created ${pc.cyan("typelex/externals.tsp")}`);
247
247
+
console.log(`${pc.green("✓")} Created ${pc.cyan("typelex/externals.tsp")}`);
203
248
204
249
// Add build script to package.json
205
250
const packageJsonPath = resolve(cwd, "package.json");
···
212
257
const outFlag = lexiconsDir ? ` --out ${lexiconsDir}` : "";
213
258
packageJson.scripts["build:typelex"] = `typelex compile ${namespace}${outFlag}`;
214
259
await writeFile(packageJsonPath, JSON.stringify(packageJson, null, 2) + "\n", "utf-8");
215
215
-
console.log(`✓ Added ${pc.cyan("build:typelex")} script to ${pc.cyan("package.json")}`);
260
260
+
console.log(`${pc.green("✓")} Added ${pc.cyan("build:typelex")} script to ${pc.cyan("package.json")}`);
216
261
if (hasLocalLexicons) {
217
262
console.log(pc.dim(` Using existing lexicons directory: ${pc.cyan("./lexicons")}`));
218
263
} else if (lexiconsDir) {
219
264
console.log(pc.dim(` Using existing lexicons directory: ${pc.cyan(lexiconsDir)}`));
220
265
}
221
266
} else {
222
222
-
console.log(`✓ ${pc.cyan("build:typelex")} script already exists in ${pc.cyan("package.json")}`);
267
267
+
console.log(`${pc.green("✓")} ${pc.cyan("build:typelex")} script already exists in ${pc.cyan("package.json")}`);
223
268
}
224
269
} catch (err) {
225
270
console.warn(pc.yellow(`⚠ Could not update ${pc.cyan("package.json")}:`), (err as Error).message);
226
271
}
227
272
228
228
-
console.log(pc.bold("\n✓ Typelex initialized successfully!"));
229
229
-
console.log(pc.bold("\nNext steps:"));
230
230
-
console.log(` 1. Edit ${pc.cyan("typelex/main.tsp")} to define your lexicons`);
231
231
-
console.log(` 2. Run: ${pc.cyan("npm run build:typelex")}`);
273
273
+
console.log(`\n${pc.green("✓")} ${pc.bold("All set!")}`);
274
274
+
console.log(`\n${pc.bold("Next steps:")}`);
275
275
+
console.log(` ${pc.dim("1.")} Edit ${pc.cyan("typelex/main.tsp")} to define your lexicons`);
276
276
+
console.log(` ${pc.dim("2.")} Keep putting external lexicons into ${pc.cyan(displayLexiconsPath)}`);
277
277
+
console.log(` ${pc.dim("3.")} Run ${pc.cyan("npm run build:typelex")} to compile to JSON`);
232
278
}