@mbsi/mkcmd 0.2.0 → 0.2.2
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.
- package/CHANGELOG.md +58 -0
- package/README.md +3 -1
- package/dist/index.js +336 -23
- package/package.json +23 -22
- package/src/commands/index.ts +0 -13
- package/src/config.ts +0 -6
- package/src/core/cli.ts +0 -93
- package/src/core/helpers/file-builder.ts +0 -19
- package/src/core/helpers/file-utils.ts +0 -19
- package/src/core/log.ts +0 -82
- package/src/data/init.ts +0 -102
- package/src/functions/orchestrate-scaffold.ts +0 -21
- package/src/functions/prompt-project.ts +0 -31
- package/src/functions/scaffold-core.ts +0 -18
- package/src/functions/scaffold-project.ts +0 -19
- package/src/index.ts +0 -10
package/CHANGELOG.md
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
## [Unreleased]
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
## [0.2.2] - 2025-12-30
|
|
12
|
+
|
|
13
|
+
### Added
|
|
14
|
+
- `src/core/helpers/stringifier.ts` to codegen before building
|
|
15
|
+
- `prebuild` script to dynamically update the code located in data/core at build time.
|
|
16
|
+
- `src/data/core.ts` is generated / regenerated at before building for use in dist
|
|
17
|
+
|
|
18
|
+
### Fixed
|
|
19
|
+
- `src/functions/scaffold-core.ts` doesn't try to pull data that doesn't exist anymore :^)
|
|
20
|
+
|
|
21
|
+
## [0.2.1] - 2025-12-30
|
|
22
|
+
### Added
|
|
23
|
+
- `CHANGELOG.md` for tracking changes
|
|
24
|
+
|
|
25
|
+
### Changed
|
|
26
|
+
- Simplified `file-utils.ts` by removing path caching (was causing issues with non-existent directories)
|
|
27
|
+
|
|
28
|
+
### Fixed
|
|
29
|
+
- Directory creation bug: `realpath()` now replaced with `resolve()` to handle new target directories
|
|
30
|
+
- Path resolution in bundled code for version command
|
|
31
|
+
|
|
32
|
+
### Removed
|
|
33
|
+
- Path caching in `file-utils.ts` (unnecessary optimization causing failures)
|
|
34
|
+
- Removed unused imports in `src/functions/orchestrate-scaffold.ts` to lint warnings
|
|
35
|
+
|
|
36
|
+
## [0.2.0] - 2025-12-30
|
|
37
|
+
|
|
38
|
+
### Added
|
|
39
|
+
- Build system with `bun build --target=bun`
|
|
40
|
+
- Build scripts: `build`, `build:exe`, `prepack`
|
|
41
|
+
- npm package preparation (removed `private: true`)
|
|
42
|
+
|
|
43
|
+
### Changed
|
|
44
|
+
- Moved `typescript` from peerDependencies to devDependencies
|
|
45
|
+
- Updated package.json entry points to `./dist/index.js`
|
|
46
|
+
- Fixed `--version` command to use `process.cwd()` for package.json resolution
|
|
47
|
+
|
|
48
|
+
## [0.1.0] - 2025-12-30
|
|
49
|
+
|
|
50
|
+
### Added
|
|
51
|
+
- Initial CLI scaffolding tool
|
|
52
|
+
- Interactive project setup with `@clack/prompts`
|
|
53
|
+
- Full CLI scaffold generation (package.json, tsconfig.json, README.md, core files)
|
|
54
|
+
- `FileBuilder` utility for indentation-aware code generation
|
|
55
|
+
- `file-utils` for path resolution and file writing
|
|
56
|
+
- Dynamic core file copying (all `.ts` files in `src/core/`)
|
|
57
|
+
- `init` command for scaffolding new CLI projects
|
|
58
|
+
- `--help` and `--version` flags
|
package/README.md
CHANGED
|
@@ -2,6 +2,8 @@
|
|
|
2
2
|
|
|
3
3
|
A remote node executable for scaffolding other remote node executables with sensible defaults.
|
|
4
4
|
|
|
5
|
+
**Version:** 0.2.0 | See [CHANGELOG.md](./CHANGELOG.md) for version history.
|
|
6
|
+
|
|
5
7
|
## Features
|
|
6
8
|
|
|
7
9
|
- **Interactive Project Setup** - Prompts for project name, target directory, and description using `@clack/prompts`
|
|
@@ -106,4 +108,4 @@ npm publish
|
|
|
106
108
|
|
|
107
109
|
This project was created using `bun init` in bun v1.2.13. [Bun](https://bun.sh) is a fast all-in-one JavaScript runtime.
|
|
108
110
|
|
|
109
|
-
See [AGENTS.md](./AGENTS.md) for development guidelines
|
|
111
|
+
See [AGENTS.md](./AGENTS.md) for development guidelines, [CHANGELOG.md](./CHANGELOG.md) for version history.
|
package/dist/index.js
CHANGED
|
@@ -2123,19 +2123,10 @@ async function promptProjectDetails() {
|
|
|
2123
2123
|
}
|
|
2124
2124
|
|
|
2125
2125
|
// src/core/helpers/file-utils.ts
|
|
2126
|
-
import { mkdir
|
|
2127
|
-
import { join as join3 } from "path";
|
|
2128
|
-
var pathCache = new Map;
|
|
2129
|
-
async function getRealPath(dir) {
|
|
2130
|
-
if (!pathCache.has(dir)) {
|
|
2131
|
-
const real = await realpath(dir);
|
|
2132
|
-
pathCache.set(dir, real);
|
|
2133
|
-
}
|
|
2134
|
-
return pathCache.get(dir);
|
|
2135
|
-
}
|
|
2126
|
+
import { mkdir } from "fs/promises";
|
|
2127
|
+
import { resolve, join as join3 } from "path";
|
|
2136
2128
|
async function writeFileTuple([targetDir, relativePath, content]) {
|
|
2137
|
-
const
|
|
2138
|
-
const fullPath = join3(realDir, relativePath);
|
|
2129
|
+
const fullPath = resolve(targetDir, relativePath);
|
|
2139
2130
|
await mkdir(join3(fullPath, ".."), { recursive: true });
|
|
2140
2131
|
await Bun.write(fullPath, content);
|
|
2141
2132
|
}
|
|
@@ -2259,18 +2250,340 @@ async function scaffoldProject(prompts) {
|
|
|
2259
2250
|
}
|
|
2260
2251
|
|
|
2261
2252
|
// src/functions/scaffold-core.ts
|
|
2262
|
-
import { join as join4 } from "path";
|
|
2263
|
-
import {
|
|
2264
|
-
import {
|
|
2265
|
-
|
|
2266
|
-
|
|
2253
|
+
import { join as join4, dirname as dirname2 } from "path";
|
|
2254
|
+
import { existsSync } from "fs";
|
|
2255
|
+
import { mkdir as mkdir2, writeFile } from "fs/promises";
|
|
2256
|
+
import { cwd } from "process";
|
|
2257
|
+
|
|
2258
|
+
// src/data/core.ts
|
|
2259
|
+
var src_core_cli_init = () => {
|
|
2260
|
+
const fb = new FileBuilder;
|
|
2261
|
+
fb.addLine('import log from "./log";');
|
|
2262
|
+
fb.addLine('import { join } from "node:path";');
|
|
2263
|
+
fb.addLine('import { config } from "../config";');
|
|
2264
|
+
fb.addLine("");
|
|
2265
|
+
fb.addLine("export type Command = {");
|
|
2266
|
+
fb.addLine(" name: string;");
|
|
2267
|
+
fb.addLine(" description: string;");
|
|
2268
|
+
fb.addLine(" instructions: string;");
|
|
2269
|
+
fb.addLine(" run: (args: string[]) => Promise<void> | void;");
|
|
2270
|
+
fb.addLine("};");
|
|
2271
|
+
fb.addLine("");
|
|
2272
|
+
fb.addLine("const commands = new Map<string, Command>();");
|
|
2273
|
+
fb.addLine("");
|
|
2274
|
+
fb.addLine("export function registerCommand(cmd: Command) {");
|
|
2275
|
+
fb.addLine(" commands.set(cmd.name, cmd);");
|
|
2276
|
+
fb.addLine("}");
|
|
2277
|
+
fb.addLine("");
|
|
2278
|
+
fb.addLine("export async function runCLI(argv = Bun.argv.slice(2)) {");
|
|
2279
|
+
fb.addLine(" const [name, ...args] = argv;");
|
|
2280
|
+
fb.addLine(" // -- TS Defense --");
|
|
2281
|
+
fb.addLine(" if (!name) {");
|
|
2282
|
+
fb.addLine(' log.single.err("ARGS", "No Argument Supplied");');
|
|
2283
|
+
fb.addLine(" return;");
|
|
2284
|
+
fb.addLine(" }");
|
|
2285
|
+
fb.addLine(' if (["-h", "--help"].includes(name)) {');
|
|
2286
|
+
fb.addLine(" const multiLog: any[] = [];");
|
|
2287
|
+
fb.addLine(" multiLog.push({");
|
|
2288
|
+
fb.addLine(' t: "About",');
|
|
2289
|
+
fb.addLine(" m: config.about_text,");
|
|
2290
|
+
fb.addLine(" });");
|
|
2291
|
+
fb.addLine(" multiLog.push({");
|
|
2292
|
+
fb.addLine(' t: "Commands",');
|
|
2293
|
+
fb.addLine(' m: "Available Commands",');
|
|
2294
|
+
fb.addLine(" });");
|
|
2295
|
+
fb.addLine(" for (const cmd of commands.values()) {");
|
|
2296
|
+
fb.addLine(" multiLog.push({");
|
|
2297
|
+
fb.addLine(" t: cmd.name,");
|
|
2298
|
+
fb.addLine(" m: `${cmd.description}\\n |-> [Instructions]: ${cmd.instructions}\\n`,");
|
|
2299
|
+
fb.addLine(" });");
|
|
2300
|
+
fb.addLine(" }");
|
|
2301
|
+
fb.addLine(" multiLog.push({");
|
|
2302
|
+
fb.addLine(' t: "More Info",');
|
|
2303
|
+
fb.addLine(" m: config.more_info_text,");
|
|
2304
|
+
fb.addLine(" });");
|
|
2305
|
+
fb.addLine(" log.multi.info(multiLog);");
|
|
2306
|
+
fb.addLine(" return;");
|
|
2307
|
+
fb.addLine(" }");
|
|
2308
|
+
fb.addLine("");
|
|
2309
|
+
fb.addLine(' if (["-v", "--version"].includes(name)) {');
|
|
2310
|
+
fb.addLine(' const pkgText = await Bun.file(join(process.cwd(), "package.json")).text();');
|
|
2311
|
+
fb.addLine(" const pkg = JSON.parse(pkgText);");
|
|
2312
|
+
fb.addLine(" log.multi.info([");
|
|
2313
|
+
fb.addLine(" {");
|
|
2314
|
+
fb.addLine(' t: "Package Name",');
|
|
2315
|
+
fb.addLine(" m: pkg.name,");
|
|
2316
|
+
fb.addLine(" },");
|
|
2317
|
+
fb.addLine(" {");
|
|
2318
|
+
fb.addLine(' t: "Package Version",');
|
|
2319
|
+
fb.addLine(" m: pkg.version,");
|
|
2320
|
+
fb.addLine(" },");
|
|
2321
|
+
fb.addLine(" ]);");
|
|
2322
|
+
fb.addLine(" return;");
|
|
2323
|
+
fb.addLine(" }");
|
|
2324
|
+
fb.addLine("");
|
|
2325
|
+
fb.addLine(" const command = commands.get(name);");
|
|
2326
|
+
fb.addLine(" if (!command) {");
|
|
2327
|
+
fb.addLine(' log.single.err("Command", "No Command Supplied");');
|
|
2328
|
+
fb.addLine(" process.exit(1);");
|
|
2329
|
+
fb.addLine(" }");
|
|
2330
|
+
fb.addLine("");
|
|
2331
|
+
fb.addLine(" try {");
|
|
2332
|
+
fb.addLine(" await command.run(args);");
|
|
2333
|
+
fb.addLine(" } catch (err) {");
|
|
2334
|
+
fb.addLine(" const multilog: any[] = [];");
|
|
2335
|
+
fb.addLine(" multilog.push({");
|
|
2336
|
+
fb.addLine(' t: "Panic",');
|
|
2337
|
+
fb.addLine(" m: `Failed to run ${name}`,");
|
|
2338
|
+
fb.addLine(" });");
|
|
2339
|
+
fb.addLine(" if (err instanceof Error) {");
|
|
2340
|
+
fb.addLine(" multilog.push({");
|
|
2341
|
+
fb.addLine(' t: "Error",');
|
|
2342
|
+
fb.addLine(" m: err.message,");
|
|
2343
|
+
fb.addLine(" });");
|
|
2344
|
+
fb.addLine(" } else {");
|
|
2345
|
+
fb.addLine(" multilog.push({");
|
|
2346
|
+
fb.addLine(' t: "Unknown Error",');
|
|
2347
|
+
fb.addLine(" m: JSON.stringify(err),");
|
|
2348
|
+
fb.addLine(" });");
|
|
2349
|
+
fb.addLine(" }");
|
|
2350
|
+
fb.addLine(" log.multi.err(multilog);");
|
|
2351
|
+
fb.addLine(" process.exit(1);");
|
|
2352
|
+
fb.addLine(" }");
|
|
2353
|
+
fb.addLine("}");
|
|
2354
|
+
fb.addLine("");
|
|
2355
|
+
return fb.build();
|
|
2356
|
+
};
|
|
2357
|
+
var src_core_cli = {
|
|
2358
|
+
location: "src/core/cli.ts",
|
|
2359
|
+
content: src_core_cli_init
|
|
2360
|
+
};
|
|
2361
|
+
var src_core_log_init = () => {
|
|
2362
|
+
const fb = new FileBuilder;
|
|
2363
|
+
fb.addLine('import figlet from "figlet";');
|
|
2364
|
+
fb.addLine("");
|
|
2365
|
+
fb.addLine("const infoLogSingle = (title: string, message: string) => {");
|
|
2366
|
+
fb.addLine(' console.log("");');
|
|
2367
|
+
fb.addLine(' console.info(" [INFO]");');
|
|
2368
|
+
fb.addLine(" console.info(` [${title}]: ${message}`);");
|
|
2369
|
+
fb.addLine(' console.log("");');
|
|
2370
|
+
fb.addLine("};");
|
|
2371
|
+
fb.addLine("");
|
|
2372
|
+
fb.addLine("type MultiLogArgs = {");
|
|
2373
|
+
fb.addLine(" t: string;");
|
|
2374
|
+
fb.addLine(" m: string;");
|
|
2375
|
+
fb.addLine("}[];");
|
|
2376
|
+
fb.addLine("");
|
|
2377
|
+
fb.addLine("const infoLogMulti = (args: MultiLogArgs) => {");
|
|
2378
|
+
fb.addLine(' console.log("");');
|
|
2379
|
+
fb.addLine(' console.info(" [INFO]");');
|
|
2380
|
+
fb.addLine(" for (const arg of args) {");
|
|
2381
|
+
fb.addLine(" console.info(` [${arg.t}]: ${arg.m}`);");
|
|
2382
|
+
fb.addLine(" }");
|
|
2383
|
+
fb.addLine(' console.log("");');
|
|
2384
|
+
fb.addLine("};");
|
|
2385
|
+
fb.addLine("");
|
|
2386
|
+
fb.addLine("const warnLogSingle = (title: string, message: string) => {");
|
|
2387
|
+
fb.addLine(' console.log("");');
|
|
2388
|
+
fb.addLine(' console.warn(" [WARNING]");');
|
|
2389
|
+
fb.addLine(" console.warn(` [${title}]: ${message}`);");
|
|
2390
|
+
fb.addLine(' console.log("");');
|
|
2391
|
+
fb.addLine("};");
|
|
2392
|
+
fb.addLine("");
|
|
2393
|
+
fb.addLine("const warnLogMulti = (args: MultiLogArgs) => {");
|
|
2394
|
+
fb.addLine(' console.log("");');
|
|
2395
|
+
fb.addLine(' console.warn(" [WARNING]");');
|
|
2396
|
+
fb.addLine(" for (const arg of args) {");
|
|
2397
|
+
fb.addLine(" console.warn(` [${arg.t}]: ${arg.m}`);");
|
|
2398
|
+
fb.addLine(" }");
|
|
2399
|
+
fb.addLine(' console.log("");');
|
|
2400
|
+
fb.addLine("};");
|
|
2401
|
+
fb.addLine("");
|
|
2402
|
+
fb.addLine("const errLogSingle = (title: string, message: string) => {");
|
|
2403
|
+
fb.addLine(' console.log("");');
|
|
2404
|
+
fb.addLine(' console.error(" [ERROR]");');
|
|
2405
|
+
fb.addLine(" console.error(` [${title}]: ${message}`);");
|
|
2406
|
+
fb.addLine(' console.log("");');
|
|
2407
|
+
fb.addLine("};");
|
|
2408
|
+
fb.addLine("");
|
|
2409
|
+
fb.addLine("const errLogMulti = (args: MultiLogArgs) => {");
|
|
2410
|
+
fb.addLine(' console.log("");');
|
|
2411
|
+
fb.addLine(' console.error(" [ERROR]");');
|
|
2412
|
+
fb.addLine(" for (const arg of args) {");
|
|
2413
|
+
fb.addLine(" console.error(` [${arg.t}]: ${arg.m}`);");
|
|
2414
|
+
fb.addLine(" }");
|
|
2415
|
+
fb.addLine(' console.log("");');
|
|
2416
|
+
fb.addLine("};");
|
|
2417
|
+
fb.addLine("");
|
|
2418
|
+
fb.addLine("const title = (title: string, subtitle?: string) => {");
|
|
2419
|
+
fb.addLine(" console.clear();");
|
|
2420
|
+
fb.addLine(" console.log();");
|
|
2421
|
+
fb.addLine(" console.log(");
|
|
2422
|
+
fb.addLine(" figlet.textSync(title, {");
|
|
2423
|
+
fb.addLine(' font: "ANSI Regular",');
|
|
2424
|
+
fb.addLine(" }),");
|
|
2425
|
+
fb.addLine(" );");
|
|
2426
|
+
fb.addLine(" console.log(` [${subtitle}]`);");
|
|
2427
|
+
fb.addLine(" console.log();");
|
|
2428
|
+
fb.addLine("};");
|
|
2429
|
+
fb.addLine("");
|
|
2430
|
+
fb.addLine("const log = {");
|
|
2431
|
+
fb.addLine(" single: {");
|
|
2432
|
+
fb.addLine(" info: infoLogSingle,");
|
|
2433
|
+
fb.addLine(" warn: warnLogSingle,");
|
|
2434
|
+
fb.addLine(" err: errLogSingle,");
|
|
2435
|
+
fb.addLine(" },");
|
|
2436
|
+
fb.addLine(" multi: {");
|
|
2437
|
+
fb.addLine(" info: infoLogMulti,");
|
|
2438
|
+
fb.addLine(" warn: warnLogMulti,");
|
|
2439
|
+
fb.addLine(" err: errLogMulti,");
|
|
2440
|
+
fb.addLine(" },");
|
|
2441
|
+
fb.addLine(" title,");
|
|
2442
|
+
fb.addLine("};");
|
|
2443
|
+
fb.addLine("");
|
|
2444
|
+
fb.addLine("export default log;");
|
|
2445
|
+
fb.addLine("");
|
|
2446
|
+
return fb.build();
|
|
2447
|
+
};
|
|
2448
|
+
var src_core_log = {
|
|
2449
|
+
location: "src/core/log.ts",
|
|
2450
|
+
content: src_core_log_init
|
|
2451
|
+
};
|
|
2452
|
+
var src_core_helpers_file_builder_init = () => {
|
|
2453
|
+
const fb = new FileBuilder;
|
|
2454
|
+
fb.addLine("export function line(content: string, depth: number): string {");
|
|
2455
|
+
fb.addLine(' return `\\n${"\\t".repeat(depth)}${content}`;');
|
|
2456
|
+
fb.addLine("}");
|
|
2457
|
+
fb.addLine("");
|
|
2458
|
+
fb.addLine("export class FileBuilder {");
|
|
2459
|
+
fb.addLine(" private lines: string[] = [];");
|
|
2460
|
+
fb.addLine("");
|
|
2461
|
+
fb.addLine(" addLine(content: string, depth: number = 0): void {");
|
|
2462
|
+
fb.addLine(' this.lines.push(`${"\\t".repeat(depth)}${content}`);');
|
|
2463
|
+
fb.addLine(" }");
|
|
2464
|
+
fb.addLine("");
|
|
2465
|
+
fb.addLine(" addEmptyLine(): void {");
|
|
2466
|
+
fb.addLine(' this.lines.push("");');
|
|
2467
|
+
fb.addLine(" }");
|
|
2468
|
+
fb.addLine("");
|
|
2469
|
+
fb.addLine(" build(): string {");
|
|
2470
|
+
fb.addLine(' return this.lines.join("\\n");');
|
|
2471
|
+
fb.addLine(" }");
|
|
2472
|
+
fb.addLine("}");
|
|
2473
|
+
fb.addLine("");
|
|
2474
|
+
return fb.build();
|
|
2475
|
+
};
|
|
2476
|
+
var src_core_helpers_file_builder = {
|
|
2477
|
+
location: "src/core/helpers/file-builder.ts",
|
|
2478
|
+
content: src_core_helpers_file_builder_init
|
|
2479
|
+
};
|
|
2480
|
+
var src_core_helpers_stringifier_init = () => {
|
|
2481
|
+
const fb = new FileBuilder;
|
|
2482
|
+
fb.addLine('import { join } from "node:path";');
|
|
2483
|
+
fb.addLine('import { readdir, writeFile } from "node:fs/promises";');
|
|
2484
|
+
fb.addLine('import { FileBuilder } from "./file-builder";');
|
|
2485
|
+
fb.addLine('import { statSync } from "node:fs";');
|
|
2486
|
+
fb.addLine("");
|
|
2487
|
+
fb.addLine("const outExport: string[] = [];");
|
|
2488
|
+
fb.addLine("");
|
|
2489
|
+
fb.addLine("async function generateTemplate(path: string) {");
|
|
2490
|
+
fb.addLine(' if (path.endsWith(".ts")) {');
|
|
2491
|
+
fb.addLine(" const content = await Bun.file(path).text();");
|
|
2492
|
+
fb.addLine(" const fb = new FileBuilder();");
|
|
2493
|
+
fb.addLine(" const snaked_title = path");
|
|
2494
|
+
fb.addLine(' .split("/")');
|
|
2495
|
+
fb.addLine(' .join("_")');
|
|
2496
|
+
fb.addLine(' .split("-")');
|
|
2497
|
+
fb.addLine(' .join("_")');
|
|
2498
|
+
fb.addLine(' .split(".")[0];');
|
|
2499
|
+
fb.addLine(' fb.addLine(`const ${snaked_title + "_init"} = () => {`);');
|
|
2500
|
+
fb.addLine(" fb.addLine(`const fb = new FileBuilder();`, 1);");
|
|
2501
|
+
fb.addLine(' const lines = content.split("\\n");');
|
|
2502
|
+
fb.addLine(" for (const line of lines) {");
|
|
2503
|
+
fb.addLine(` const cleanLine = line.replaceAll("\\\\", "\\\\\\\\").replaceAll('"', '\\\\"');`);
|
|
2504
|
+
fb.addLine(' fb.addLine(`fb.addLine("${cleanLine}")`, 1);');
|
|
2505
|
+
fb.addLine(" }");
|
|
2506
|
+
fb.addLine(' fb.addLine("return fb.build();", 1);');
|
|
2507
|
+
fb.addLine(' fb.addLine("};");');
|
|
2508
|
+
fb.addLine(" fb.addEmptyLine();");
|
|
2509
|
+
fb.addLine(" fb.addLine(`export const ${snaked_title} = {`);");
|
|
2510
|
+
fb.addLine(' fb.addLine(`location: "${path}",`, 1);');
|
|
2511
|
+
fb.addLine(' fb.addLine(`content: ${snaked_title + "_init"}`, 1);');
|
|
2512
|
+
fb.addLine(" fb.addLine(`};`);");
|
|
2513
|
+
fb.addLine(" const out = fb.build();");
|
|
2514
|
+
fb.addLine(" outExport.push(`${snaked_title}`);");
|
|
2515
|
+
fb.addLine(" return out;");
|
|
2516
|
+
fb.addLine(" }");
|
|
2517
|
+
fb.addLine(' return "";');
|
|
2518
|
+
fb.addLine("}");
|
|
2519
|
+
fb.addLine("");
|
|
2520
|
+
fb.addLine("async function parseFolder(path: string, fb: FileBuilder) {");
|
|
2521
|
+
fb.addLine(" const items = await readdir(path);");
|
|
2522
|
+
fb.addLine(" for (const item of items) {");
|
|
2523
|
+
fb.addLine(" const relPath = join(path, item);");
|
|
2524
|
+
fb.addLine(" const itemStat = statSync(relPath);");
|
|
2525
|
+
fb.addLine(" if (itemStat.isDirectory()) {");
|
|
2526
|
+
fb.addLine(" await parseFolder(relPath, fb);");
|
|
2527
|
+
fb.addLine(" }");
|
|
2528
|
+
fb.addLine(' if (item.endsWith(".ts")) {');
|
|
2529
|
+
fb.addLine(" fb.addLine(await generateTemplate(relPath));");
|
|
2530
|
+
fb.addLine(" fb.addEmptyLine();");
|
|
2531
|
+
fb.addLine(" }");
|
|
2532
|
+
fb.addLine(" }");
|
|
2533
|
+
fb.addLine("}");
|
|
2534
|
+
fb.addLine("");
|
|
2535
|
+
fb.addLine("async function generateTemplates() {");
|
|
2536
|
+
fb.addLine(' const sourceCoreDir = join(".", "src", "core");');
|
|
2537
|
+
fb.addLine(" const fb = new FileBuilder();");
|
|
2538
|
+
fb.addLine(' fb.addLine(`import { FileBuilder } from "../core/helpers/file-builder";`);');
|
|
2539
|
+
fb.addLine(" fb.addEmptyLine();");
|
|
2540
|
+
fb.addLine(" await parseFolder(sourceCoreDir, fb);");
|
|
2541
|
+
fb.addLine(' fb.addLine(`const core = [${outExport.join(", ")}]`);');
|
|
2542
|
+
fb.addLine(" fb.addLine(`export { core }`);");
|
|
2543
|
+
fb.addLine(" const out = fb.build();");
|
|
2544
|
+
fb.addLine(' await writeFile(join(".", "src", "data", "core.ts"), out, "utf8");');
|
|
2545
|
+
fb.addLine("}");
|
|
2546
|
+
fb.addLine("");
|
|
2547
|
+
fb.addLine("generateTemplates();");
|
|
2548
|
+
fb.addLine("");
|
|
2549
|
+
return fb.build();
|
|
2550
|
+
};
|
|
2551
|
+
var src_core_helpers_stringifier = {
|
|
2552
|
+
location: "src/core/helpers/stringifier.ts",
|
|
2553
|
+
content: src_core_helpers_stringifier_init
|
|
2554
|
+
};
|
|
2555
|
+
var src_core_helpers_file_utils_init = () => {
|
|
2556
|
+
const fb = new FileBuilder;
|
|
2557
|
+
fb.addLine('import { mkdir } from "node:fs/promises";');
|
|
2558
|
+
fb.addLine('import { resolve, join } from "node:path";');
|
|
2559
|
+
fb.addLine("");
|
|
2560
|
+
fb.addLine("export async function writeFileTuple([targetDir, relativePath, content]: [string, string, string]): Promise<void> {");
|
|
2561
|
+
fb.addLine(" const fullPath = resolve(targetDir, relativePath);");
|
|
2562
|
+
fb.addLine(' await mkdir(join(fullPath, ".."), { recursive: true });');
|
|
2563
|
+
fb.addLine(" await Bun.write(fullPath, content);");
|
|
2564
|
+
fb.addLine("}");
|
|
2565
|
+
fb.addLine("");
|
|
2566
|
+
return fb.build();
|
|
2567
|
+
};
|
|
2568
|
+
var src_core_helpers_file_utils = {
|
|
2569
|
+
location: "src/core/helpers/file-utils.ts",
|
|
2570
|
+
content: src_core_helpers_file_utils_init
|
|
2571
|
+
};
|
|
2572
|
+
var core = [src_core_cli, src_core_log, src_core_helpers_file_builder, src_core_helpers_stringifier, src_core_helpers_file_utils];
|
|
2573
|
+
|
|
2574
|
+
// src/functions/scaffold-core.ts
|
|
2575
|
+
var currentDir = join4(cwd());
|
|
2267
2576
|
async function scaffoldCore(targetDir) {
|
|
2268
|
-
const
|
|
2269
|
-
|
|
2270
|
-
|
|
2271
|
-
|
|
2272
|
-
|
|
2273
|
-
}
|
|
2577
|
+
const combinedPath = join4(currentDir, targetDir);
|
|
2578
|
+
console.dir(combinedPath);
|
|
2579
|
+
for (const file of core) {
|
|
2580
|
+
const relativePath = file.location.replace(/^\.\//, "");
|
|
2581
|
+
const parentDir = join4(combinedPath, dirname2(relativePath));
|
|
2582
|
+
console.dir({ parentDir });
|
|
2583
|
+
if (!existsSync(parentDir)) {
|
|
2584
|
+
mkdir2(parentDir, { recursive: true });
|
|
2585
|
+
}
|
|
2586
|
+
writeFile(join4(combinedPath, relativePath), file.content(), "utf8");
|
|
2274
2587
|
}
|
|
2275
2588
|
}
|
|
2276
2589
|
|
package/package.json
CHANGED
|
@@ -1,24 +1,25 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
2
|
+
"name": "@mbsi/mkcmd",
|
|
3
|
+
"version": "0.2.2",
|
|
4
|
+
"main": "./dist/index.js",
|
|
5
|
+
"module": "./dist/index.js",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"bin": {
|
|
8
|
+
"mkcmd": "./dist/index.js"
|
|
9
|
+
},
|
|
10
|
+
"scripts": {
|
|
11
|
+
"prebuild": "bun run src/core/helpers/stringifier.ts",
|
|
12
|
+
"build": "bun build --target=bun --outfile=dist/index.js src/index.ts",
|
|
13
|
+
"build:exe": "bun build --compile --outfile=dist/mkcmd src/index.ts",
|
|
14
|
+
"prepack": "bun run build"
|
|
15
|
+
},
|
|
16
|
+
"devDependencies": {
|
|
17
|
+
"@types/bun": "latest",
|
|
18
|
+
"typescript": "^5"
|
|
19
|
+
},
|
|
20
|
+
"dependencies": {
|
|
21
|
+
"@clack/prompts": "^0.11.0",
|
|
22
|
+
"@types/figlet": "^1.7.0",
|
|
23
|
+
"figlet": "^1.9.4"
|
|
24
|
+
}
|
|
24
25
|
}
|
package/src/commands/index.ts
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import { registerCommand } from "../core/cli";
|
|
2
|
-
import { orchestrateScaffold } from "../functions/orchestrate-scaffold";
|
|
3
|
-
|
|
4
|
-
export function registerCommands() {
|
|
5
|
-
registerCommand({
|
|
6
|
-
name: "init",
|
|
7
|
-
description: "Initialize a new CLI project",
|
|
8
|
-
instructions: "You will be prompted for project details",
|
|
9
|
-
run: async () => {
|
|
10
|
-
await orchestrateScaffold();
|
|
11
|
-
},
|
|
12
|
-
});
|
|
13
|
-
}
|
package/src/config.ts
DELETED
package/src/core/cli.ts
DELETED
|
@@ -1,93 +0,0 @@
|
|
|
1
|
-
import log from "./log";
|
|
2
|
-
import { join } from "node:path";
|
|
3
|
-
import { config } from "../config";
|
|
4
|
-
|
|
5
|
-
export type Command = {
|
|
6
|
-
name: string;
|
|
7
|
-
description: string;
|
|
8
|
-
instructions: string;
|
|
9
|
-
run: (args: string[]) => Promise<void> | void;
|
|
10
|
-
};
|
|
11
|
-
|
|
12
|
-
const commands = new Map<string, Command>();
|
|
13
|
-
|
|
14
|
-
export function registerCommand(cmd: Command) {
|
|
15
|
-
commands.set(cmd.name, cmd);
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
export async function runCLI(argv = Bun.argv.slice(2)) {
|
|
19
|
-
const [name, ...args] = argv;
|
|
20
|
-
// -- TS Defense --
|
|
21
|
-
if (!name) {
|
|
22
|
-
log.single.err("ARGS", "No Argument Supplied");
|
|
23
|
-
return;
|
|
24
|
-
}
|
|
25
|
-
if (["-h", "--help"].includes(name)) {
|
|
26
|
-
const multiLog: any[] = [];
|
|
27
|
-
multiLog.push({
|
|
28
|
-
t: "About",
|
|
29
|
-
m: config.about_text,
|
|
30
|
-
});
|
|
31
|
-
multiLog.push({
|
|
32
|
-
t: "Commands",
|
|
33
|
-
m: "Available Commands",
|
|
34
|
-
});
|
|
35
|
-
for (const cmd of commands.values()) {
|
|
36
|
-
multiLog.push({
|
|
37
|
-
t: cmd.name,
|
|
38
|
-
m: `${cmd.description}\n |-> [Instructions]: ${cmd.instructions}\n`,
|
|
39
|
-
});
|
|
40
|
-
}
|
|
41
|
-
multiLog.push({
|
|
42
|
-
t: "More Info",
|
|
43
|
-
m: config.more_info_text,
|
|
44
|
-
});
|
|
45
|
-
log.multi.info(multiLog);
|
|
46
|
-
return;
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
if (["-v", "--version"].includes(name)) {
|
|
50
|
-
const pkgText = await Bun.file(join(process.cwd(), "package.json")).text();
|
|
51
|
-
const pkg = JSON.parse(pkgText);
|
|
52
|
-
log.multi.info([
|
|
53
|
-
{
|
|
54
|
-
t: "Package Name",
|
|
55
|
-
m: pkg.name,
|
|
56
|
-
},
|
|
57
|
-
{
|
|
58
|
-
t: "Package Version",
|
|
59
|
-
m: pkg.version,
|
|
60
|
-
},
|
|
61
|
-
]);
|
|
62
|
-
return;
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
const command = commands.get(name);
|
|
66
|
-
if (!command) {
|
|
67
|
-
log.single.err("Command", "No Command Supplied");
|
|
68
|
-
process.exit(1);
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
try {
|
|
72
|
-
await command.run(args);
|
|
73
|
-
} catch (err) {
|
|
74
|
-
const multilog: any[] = [];
|
|
75
|
-
multilog.push({
|
|
76
|
-
t: "Panic",
|
|
77
|
-
m: `Failed to run ${name}`,
|
|
78
|
-
});
|
|
79
|
-
if (err instanceof Error) {
|
|
80
|
-
multilog.push({
|
|
81
|
-
t: "Error",
|
|
82
|
-
m: err.message,
|
|
83
|
-
});
|
|
84
|
-
} else {
|
|
85
|
-
multilog.push({
|
|
86
|
-
t: "Unknown Error",
|
|
87
|
-
m: JSON.stringify(err),
|
|
88
|
-
});
|
|
89
|
-
}
|
|
90
|
-
log.multi.err(multilog);
|
|
91
|
-
process.exit(1);
|
|
92
|
-
}
|
|
93
|
-
}
|
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
export function line(content: string, depth: number): string {
|
|
2
|
-
return `\n${"\t".repeat(depth)}${content}`;
|
|
3
|
-
}
|
|
4
|
-
|
|
5
|
-
export class FileBuilder {
|
|
6
|
-
private lines: string[] = [];
|
|
7
|
-
|
|
8
|
-
addLine(content: string, depth: number = 0): void {
|
|
9
|
-
this.lines.push(`${"\t".repeat(depth)}${content}`);
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
addEmptyLine(): void {
|
|
13
|
-
this.lines.push("");
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
build(): string {
|
|
17
|
-
return this.lines.join("\n");
|
|
18
|
-
}
|
|
19
|
-
}
|
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import { mkdir, realpath } from "node:fs/promises";
|
|
2
|
-
import { join } from "node:path";
|
|
3
|
-
|
|
4
|
-
const pathCache = new Map<string, string>();
|
|
5
|
-
|
|
6
|
-
export async function getRealPath(dir: string): Promise<string> {
|
|
7
|
-
if (!pathCache.has(dir)) {
|
|
8
|
-
const real = await realpath(dir);
|
|
9
|
-
pathCache.set(dir, real);
|
|
10
|
-
}
|
|
11
|
-
return pathCache.get(dir)!;
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
export async function writeFileTuple([targetDir, relativePath, content]: [string, string, string]): Promise<void> {
|
|
15
|
-
const realDir = await getRealPath(targetDir);
|
|
16
|
-
const fullPath = join(realDir, relativePath);
|
|
17
|
-
await mkdir(join(fullPath, ".."), { recursive: true });
|
|
18
|
-
await Bun.write(fullPath, content);
|
|
19
|
-
}
|
package/src/core/log.ts
DELETED
|
@@ -1,82 +0,0 @@
|
|
|
1
|
-
import figlet from "figlet";
|
|
2
|
-
|
|
3
|
-
const infoLogSingle = (title: string, message: string) => {
|
|
4
|
-
console.log("");
|
|
5
|
-
console.info(" [INFO]");
|
|
6
|
-
console.info(` [${title}]: ${message}`);
|
|
7
|
-
console.log("");
|
|
8
|
-
};
|
|
9
|
-
|
|
10
|
-
type MultiLogArgs = {
|
|
11
|
-
t: string;
|
|
12
|
-
m: string;
|
|
13
|
-
}[];
|
|
14
|
-
|
|
15
|
-
const infoLogMulti = (args: MultiLogArgs) => {
|
|
16
|
-
console.log("");
|
|
17
|
-
console.info(" [INFO]");
|
|
18
|
-
for (const arg of args) {
|
|
19
|
-
console.info(` [${arg.t}]: ${arg.m}`);
|
|
20
|
-
}
|
|
21
|
-
console.log("");
|
|
22
|
-
};
|
|
23
|
-
|
|
24
|
-
const warnLogSingle = (title: string, message: string) => {
|
|
25
|
-
console.log("");
|
|
26
|
-
console.warn(" [WARNING]");
|
|
27
|
-
console.warn(` [${title}]: ${message}`);
|
|
28
|
-
console.log("");
|
|
29
|
-
};
|
|
30
|
-
|
|
31
|
-
const warnLogMulti = (args: MultiLogArgs) => {
|
|
32
|
-
console.log("");
|
|
33
|
-
console.warn(" [WARNING]");
|
|
34
|
-
for (const arg of args) {
|
|
35
|
-
console.warn(` [${arg.t}]: ${arg.m}`);
|
|
36
|
-
}
|
|
37
|
-
console.log("");
|
|
38
|
-
};
|
|
39
|
-
|
|
40
|
-
const errLogSingle = (title: string, message: string) => {
|
|
41
|
-
console.log("");
|
|
42
|
-
console.error(" [ERROR]");
|
|
43
|
-
console.error(` [${title}]: ${message}`);
|
|
44
|
-
console.log("");
|
|
45
|
-
};
|
|
46
|
-
|
|
47
|
-
const errLogMulti = (args: MultiLogArgs) => {
|
|
48
|
-
console.log("");
|
|
49
|
-
console.error(" [ERROR]");
|
|
50
|
-
for (const arg of args) {
|
|
51
|
-
console.error(` [${arg.t}]: ${arg.m}`);
|
|
52
|
-
}
|
|
53
|
-
console.log("");
|
|
54
|
-
};
|
|
55
|
-
|
|
56
|
-
const title = (title: string, subtitle?: string) => {
|
|
57
|
-
console.clear();
|
|
58
|
-
console.log();
|
|
59
|
-
console.log(
|
|
60
|
-
figlet.textSync(title, {
|
|
61
|
-
font: "ANSI Regular",
|
|
62
|
-
}),
|
|
63
|
-
);
|
|
64
|
-
console.log(` [${subtitle}]`);
|
|
65
|
-
console.log();
|
|
66
|
-
};
|
|
67
|
-
|
|
68
|
-
const log = {
|
|
69
|
-
single: {
|
|
70
|
-
info: infoLogSingle,
|
|
71
|
-
warn: warnLogSingle,
|
|
72
|
-
err: errLogSingle,
|
|
73
|
-
},
|
|
74
|
-
multi: {
|
|
75
|
-
info: infoLogMulti,
|
|
76
|
-
warn: warnLogMulti,
|
|
77
|
-
err: errLogMulti,
|
|
78
|
-
},
|
|
79
|
-
title,
|
|
80
|
-
};
|
|
81
|
-
|
|
82
|
-
export default log;
|
package/src/data/init.ts
DELETED
|
@@ -1,102 +0,0 @@
|
|
|
1
|
-
import { FileBuilder } from "../core/helpers/file-builder";
|
|
2
|
-
|
|
3
|
-
export const commands_init = () => {
|
|
4
|
-
const file = new FileBuilder();
|
|
5
|
-
file.addLine(`import { registerCommand } from "../core/cli";`, 0);
|
|
6
|
-
file.addEmptyLine();
|
|
7
|
-
file.addLine(`export function registerCommands() {}`, 0);
|
|
8
|
-
return file.build();
|
|
9
|
-
};
|
|
10
|
-
|
|
11
|
-
export const config_init = (about: string) => {
|
|
12
|
-
const file = new FileBuilder();
|
|
13
|
-
file.addLine(`export const config = {`, 0);
|
|
14
|
-
file.addLine(`about_text:`, 2);
|
|
15
|
-
file.addLine(`"${about}",`, 1);
|
|
16
|
-
file.addLine(`more_info_text:`, 2);
|
|
17
|
-
file.addLine(
|
|
18
|
-
`"See https://github.com/mackenziebowes/mkcmd for more details.",`,
|
|
19
|
-
1,
|
|
20
|
-
);
|
|
21
|
-
file.addLine(`};`, 0);
|
|
22
|
-
return file.build();
|
|
23
|
-
};
|
|
24
|
-
|
|
25
|
-
export const package_init = (name: string) => {
|
|
26
|
-
const file = new FileBuilder();
|
|
27
|
-
file.addLine(`{`, 0);
|
|
28
|
-
file.addLine(`"name": "${name}",`, 1);
|
|
29
|
-
file.addLine(`"module": "index.ts",`, 1);
|
|
30
|
-
file.addLine(`"type": "module",`, 1);
|
|
31
|
-
file.addLine(`"private": true,`, 1);
|
|
32
|
-
file.addLine(`"bin": {`, 1);
|
|
33
|
-
file.addLine(`"${name.split(" ").join("")}": "./src/index.ts"`, 2);
|
|
34
|
-
file.addLine(`},`, 1);
|
|
35
|
-
file.addLine(`"devDependencies": {`, 1);
|
|
36
|
-
file.addLine(`"@types/bun": "latest"`, 2);
|
|
37
|
-
file.addLine(`},`, 1);
|
|
38
|
-
file.addLine(`"peerDependencies": {`, 1);
|
|
39
|
-
file.addLine(`"typescript": "^5"`, 2);
|
|
40
|
-
file.addLine(`},`, 1);
|
|
41
|
-
file.addLine(`"dependencies": {`, 1);
|
|
42
|
-
file.addLine(`"@clack/prompts": "^0.11.0",`, 2);
|
|
43
|
-
file.addLine(`"@types/figlet": "^1.7.0",`, 2);
|
|
44
|
-
file.addLine(`"figlet": "^1.9.4"`, 2);
|
|
45
|
-
file.addLine(`}`, 1);
|
|
46
|
-
file.addLine(`}`, 0);
|
|
47
|
-
return file.build();
|
|
48
|
-
};
|
|
49
|
-
|
|
50
|
-
export const readme_init = (name: string) => {
|
|
51
|
-
const file = new FileBuilder();
|
|
52
|
-
file.addLine(`# ${name}`);
|
|
53
|
-
file.addEmptyLine();
|
|
54
|
-
file.addLine(`To install dependencies:`);
|
|
55
|
-
file.addEmptyLine();
|
|
56
|
-
file.addLine("```bash");
|
|
57
|
-
file.addLine("bun install");
|
|
58
|
-
file.addLine("```");
|
|
59
|
-
file.addEmptyLine();
|
|
60
|
-
file.addLine("To run:");
|
|
61
|
-
file.addLine("```bash");
|
|
62
|
-
file.addLine("bun run index.ts");
|
|
63
|
-
file.addLine("```");
|
|
64
|
-
file.addLine(
|
|
65
|
-
"This project was created using `bun init` in bun v1.2.13. [Bun](https://bun.sh) is a fast all-in-one JavaScript runtime.",
|
|
66
|
-
);
|
|
67
|
-
return file.build();
|
|
68
|
-
};
|
|
69
|
-
|
|
70
|
-
export const tsconfig_init = () => {
|
|
71
|
-
const file = new FileBuilder();
|
|
72
|
-
file.addLine(`{`, 0);
|
|
73
|
-
file.addLine(`"compilerOptions": {`, 1);
|
|
74
|
-
file.addEmptyLine();
|
|
75
|
-
file.addLine(`// Environment setup & latest features`, 1);
|
|
76
|
-
file.addLine(`"lib": ["ESNext"],`, 1);
|
|
77
|
-
file.addLine(`"target": "ESNext",`, 1);
|
|
78
|
-
file.addLine(`"module": "ESNext",`, 1);
|
|
79
|
-
file.addLine(`"moduleDetection": "force",`, 1);
|
|
80
|
-
file.addLine(`"jsx": "react-jsx",`, 1);
|
|
81
|
-
file.addLine(`"allowJs": true,`, 1);
|
|
82
|
-
file.addEmptyLine();
|
|
83
|
-
file.addLine(`// Bundler mode`, 1);
|
|
84
|
-
file.addLine(`"moduleResolution": "bundler",`, 1);
|
|
85
|
-
file.addLine(`"allowImportingTsExtensions": true,`, 1);
|
|
86
|
-
file.addLine(`"verbatimModuleSyntax": true,`, 1);
|
|
87
|
-
file.addLine(`"noEmit": true,`, 1);
|
|
88
|
-
file.addEmptyLine();
|
|
89
|
-
file.addLine(`// Best practices`, 1);
|
|
90
|
-
file.addLine(`"strict": true,`, 1);
|
|
91
|
-
file.addLine(`"skipLibCheck": true,`, 1);
|
|
92
|
-
file.addLine(`"noFallthroughCasesInSwitch": true,`, 1);
|
|
93
|
-
file.addLine(`"noUncheckedIndexedAccess": true,`, 1);
|
|
94
|
-
file.addEmptyLine();
|
|
95
|
-
file.addLine(`// Some stricter flags (disabled by default)`, 1);
|
|
96
|
-
file.addLine(`"noUnusedLocals": false,`, 1);
|
|
97
|
-
file.addLine(`"noUnusedParameters": false,`, 1);
|
|
98
|
-
file.addLine(`"noPropertyAccessFromIndexSignature": false`, 1);
|
|
99
|
-
file.addLine(`}`, 1);
|
|
100
|
-
file.addLine(`}`, 0);
|
|
101
|
-
return file.build();
|
|
102
|
-
};
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import { promptProjectDetails, ProjectPrompts } from "./prompt-project";
|
|
2
|
-
import { scaffoldProject } from "./scaffold-project";
|
|
3
|
-
import { scaffoldCore } from "./scaffold-core";
|
|
4
|
-
import log from "../core/log";
|
|
5
|
-
import { config } from "../config";
|
|
6
|
-
|
|
7
|
-
export async function orchestrateScaffold() {
|
|
8
|
-
const prompts = await promptProjectDetails();
|
|
9
|
-
|
|
10
|
-
await scaffoldProject(prompts);
|
|
11
|
-
log.single.info("Project", "Project files created");
|
|
12
|
-
|
|
13
|
-
await scaffoldCore(prompts.targetDir);
|
|
14
|
-
log.single.info("Core", "Core files copied");
|
|
15
|
-
|
|
16
|
-
log.multi.info([
|
|
17
|
-
{ t: "Success", m: "Project scaffolded successfully!" },
|
|
18
|
-
{ t: "Location", m: prompts.targetDir },
|
|
19
|
-
{ t: "Next", m: `cd ${prompts.targetDir} && bun install` },
|
|
20
|
-
]);
|
|
21
|
-
}
|
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
import { text, intro, outro } from "@clack/prompts";
|
|
2
|
-
|
|
3
|
-
export interface ProjectPrompts {
|
|
4
|
-
projectName: string;
|
|
5
|
-
targetDir: string;
|
|
6
|
-
description: string;
|
|
7
|
-
}
|
|
8
|
-
|
|
9
|
-
export async function promptProjectDetails(): Promise<ProjectPrompts> {
|
|
10
|
-
intro("mkcmd - Scaffold a new CLI project");
|
|
11
|
-
|
|
12
|
-
const projectName = (await text({
|
|
13
|
-
message: "What is your project name?",
|
|
14
|
-
placeholder: "my-cli",
|
|
15
|
-
})) as string;
|
|
16
|
-
|
|
17
|
-
const targetDir = (await text({
|
|
18
|
-
message: "Where should the project be created?",
|
|
19
|
-
placeholder: "./my-cli",
|
|
20
|
-
initialValue: `./${projectName}`,
|
|
21
|
-
})) as string;
|
|
22
|
-
|
|
23
|
-
const description = (await text({
|
|
24
|
-
message: "What does this project do?",
|
|
25
|
-
placeholder: "A CLI tool that does amazing things",
|
|
26
|
-
})) as string;
|
|
27
|
-
|
|
28
|
-
outro("Project details collected!");
|
|
29
|
-
|
|
30
|
-
return { projectName, targetDir, description };
|
|
31
|
-
}
|
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
import { join } from "node:path";
|
|
2
|
-
import { readdir } from "node:fs/promises";
|
|
3
|
-
import { fileURLToPath } from "node:url";
|
|
4
|
-
import { writeFileTuple } from "../core/helpers/file-utils";
|
|
5
|
-
|
|
6
|
-
const currentDir = join(fileURLToPath(import.meta.url), "../..");
|
|
7
|
-
const sourceCoreDir = join(currentDir, "src", "core");
|
|
8
|
-
|
|
9
|
-
export async function scaffoldCore(targetDir: string) {
|
|
10
|
-
const files = await readdir(sourceCoreDir);
|
|
11
|
-
|
|
12
|
-
for (const file of files) {
|
|
13
|
-
if (file.endsWith(".ts")) {
|
|
14
|
-
const content = await Bun.file(join(sourceCoreDir, file)).text();
|
|
15
|
-
await writeFileTuple([targetDir, `src/core/${file}`, content]);
|
|
16
|
-
}
|
|
17
|
-
}
|
|
18
|
-
}
|
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import { type ProjectPrompts } from "./prompt-project";
|
|
2
|
-
import { writeFileTuple } from "../core/helpers/file-utils";
|
|
3
|
-
import {
|
|
4
|
-
commands_init,
|
|
5
|
-
config_init,
|
|
6
|
-
package_init,
|
|
7
|
-
readme_init,
|
|
8
|
-
tsconfig_init,
|
|
9
|
-
} from "../data/init";
|
|
10
|
-
|
|
11
|
-
export async function scaffoldProject(prompts: ProjectPrompts) {
|
|
12
|
-
const { projectName, targetDir, description } = prompts;
|
|
13
|
-
|
|
14
|
-
await writeFileTuple([targetDir, "src/commands/index.ts", commands_init()]);
|
|
15
|
-
await writeFileTuple([targetDir, "src/config.ts", config_init(description)]);
|
|
16
|
-
await writeFileTuple([targetDir, "package.json", package_init(projectName)]);
|
|
17
|
-
await writeFileTuple([targetDir, "README.md", readme_init(projectName)]);
|
|
18
|
-
await writeFileTuple([targetDir, "tsconfig.json", tsconfig_init()]);
|
|
19
|
-
}
|