cngkit 1.1.17 → 1.1.18
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/README.md +19 -1
- package/dist/{chunk-K36DKQWH.js → chunk-C7HFDK4S.js} +70 -4
- package/dist/chunk-C7HFDK4S.js.map +1 -0
- package/dist/{chunk-WYJTGGMN.js → chunk-CBIVTEZP.js} +2 -2
- package/dist/{chunk-WYJTGGMN.js.map → chunk-CBIVTEZP.js.map} +1 -1
- package/dist/{chunk-HRFI2IEP.js → chunk-FJ34NVQ4.js} +350 -2
- package/dist/chunk-FJ34NVQ4.js.map +1 -0
- package/dist/{chunk-5ZNV3FDG.js → chunk-IB5B3BLY.js} +3 -3
- package/dist/{chunk-BL3XMLIH.js → chunk-KSW6QT5Q.js} +57 -2
- package/dist/chunk-KSW6QT5Q.js.map +1 -0
- package/dist/{chunk-GT2MTS6E.js → chunk-TWQDLZ6F.js} +2 -2
- package/dist/{chunk-VCWNKNUE.js → chunk-ZA4YOWPB.js} +9 -1
- package/dist/chunk-ZA4YOWPB.js.map +1 -0
- package/dist/cli.js +31 -6
- package/dist/cli.js.map +1 -1
- package/dist/commands/coderoom/index.js +4 -4
- package/dist/commands/coderoom/join.js +5 -5
- package/dist/commands/coderoom/share.js +5 -5
- package/dist/commands/hookify/index.js +25 -0
- package/dist/commands/hookify/index.js.map +1 -0
- package/dist/commands/hookify/ingest.js +88 -0
- package/dist/commands/hookify/ingest.js.map +1 -0
- package/dist/commands/index.js +3 -3
- package/dist/commands/knowledges/audiences.js +6 -6
- package/dist/commands/knowledges/files.js +6 -6
- package/dist/commands/knowledges/glob.js +6 -6
- package/dist/commands/knowledges/grep.js +6 -6
- package/dist/commands/knowledges/index.js +4 -4
- package/dist/commands/knowledges/list.js +6 -6
- package/dist/commands/knowledges/ls.js +31 -0
- package/dist/commands/knowledges/ls.js.map +1 -0
- package/dist/commands/knowledges/read.js +6 -6
- package/dist/commands/knowledges/search.js +6 -6
- package/dist/commands/knowledges/status.js +6 -6
- package/dist/commands/login.js +3 -3
- package/dist/commands/scrub.js +3 -3
- package/dist/commands/transcripts.js +4 -4
- package/package.json +2 -2
- package/dist/chunk-BL3XMLIH.js.map +0 -1
- package/dist/chunk-HRFI2IEP.js.map +0 -1
- package/dist/chunk-K36DKQWH.js.map +0 -1
- package/dist/chunk-VCWNKNUE.js.map +0 -1
- /package/dist/{chunk-5ZNV3FDG.js.map → chunk-IB5B3BLY.js.map} +0 -0
- /package/dist/{chunk-GT2MTS6E.js.map → chunk-TWQDLZ6F.js.map} +0 -0
package/README.md
CHANGED
|
@@ -43,14 +43,16 @@ cngkit scrub [path]
|
|
|
43
43
|
cngkit transcripts list --limit 12
|
|
44
44
|
cngkit knowledges search Cloudflare --limit 3
|
|
45
45
|
cngkit knowledges read /libraries/lib-cloudflare/SUBSKILL.md --limit 80
|
|
46
|
+
printf '{"hook":"PreToolUse"}' | cngkit hookify ingest --event PreToolUse
|
|
46
47
|
```
|
|
47
48
|
|
|
48
|
-
The CLI currently has
|
|
49
|
+
The CLI currently has five main jobs:
|
|
49
50
|
|
|
50
51
|
- **Coderoom**: start or join a live shared working-tree room.
|
|
51
52
|
- **Scrub**: scan local files for secrets and optionally mask them inline.
|
|
52
53
|
- **Transcripts**: inspect local Claude and Codex transcript files from the terminal.
|
|
53
54
|
- **Knowledges**: search and read the hosted Harness knowledge catalog.
|
|
55
|
+
- **Hookify**: forward local hook events to Curly.ng for server-side hook processing.
|
|
54
56
|
|
|
55
57
|
## Coderoom
|
|
56
58
|
|
|
@@ -168,6 +170,20 @@ Safety notes:
|
|
|
168
170
|
- Raw secret values are never printed.
|
|
169
171
|
- `--mask` is accepted as a compatibility alias, but inline changes still require `--yes`.
|
|
170
172
|
|
|
173
|
+
## Hookify
|
|
174
|
+
|
|
175
|
+
`hookify` is the Curly.ng hook processing surface. The first command is intentionally
|
|
176
|
+
small: it reads stdin and forwards the raw payload to the backend.
|
|
177
|
+
|
|
178
|
+
```bash
|
|
179
|
+
cngkit hookify ingest --event PreToolUse < hook-payload.json
|
|
180
|
+
cngkit hookify ingest --event Stop --async < hook-payload.json
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
The backend response controls stdout and the process exit code. If the backend request
|
|
184
|
+
fails, the command falls back to exit code `0` so local hooks do not block work because
|
|
185
|
+
the remote service is unavailable.
|
|
186
|
+
|
|
171
187
|
## Local Agent Transcripts
|
|
172
188
|
|
|
173
189
|
`transcripts` reads local JSONL files from:
|
|
@@ -235,6 +251,8 @@ cngkit help knowledges
|
|
|
235
251
|
cngkit coderoom --help
|
|
236
252
|
cngkit knowledges read --help
|
|
237
253
|
cngkit transcripts --help
|
|
254
|
+
cngkit hookify --help
|
|
255
|
+
cngkit hookify ingest --help
|
|
238
256
|
```
|
|
239
257
|
|
|
240
258
|
Help uses terminal Markdown rendering in interactive terminals and pipes. Status, warnings,
|
|
@@ -7,10 +7,10 @@ import {
|
|
|
7
7
|
} from "./chunk-XQGLUQFM.js";
|
|
8
8
|
import {
|
|
9
9
|
createCngApiClient
|
|
10
|
-
} from "./chunk-
|
|
10
|
+
} from "./chunk-FJ34NVQ4.js";
|
|
11
11
|
import {
|
|
12
12
|
resolveOutputFormat
|
|
13
|
-
} from "./chunk-
|
|
13
|
+
} from "./chunk-CBIVTEZP.js";
|
|
14
14
|
|
|
15
15
|
// src/features/knowledges/knowledges-api.ts
|
|
16
16
|
function createKnowledgesApi(options) {
|
|
@@ -44,6 +44,13 @@ function createKnowledgesApi(options) {
|
|
|
44
44
|
glob: ({ pattern, path }) => client.harnessFilesystem.getHarnessFilesystemGlob({
|
|
45
45
|
pattern,
|
|
46
46
|
path
|
|
47
|
+
}),
|
|
48
|
+
listDirectory: ({ path, limit }) => client.harnessFilesystem.getHarnessFilesystemLs({
|
|
49
|
+
path,
|
|
50
|
+
limit
|
|
51
|
+
}),
|
|
52
|
+
statPath: ({ path }) => client.harnessFilesystem.getHarnessFilesystemStat({
|
|
53
|
+
path
|
|
47
54
|
})
|
|
48
55
|
};
|
|
49
56
|
}
|
|
@@ -95,6 +102,13 @@ function normalizeCatalogPath(value) {
|
|
|
95
102
|
return relativePath;
|
|
96
103
|
}
|
|
97
104
|
}
|
|
105
|
+
function normalizeFilesystemCatalogPath(value) {
|
|
106
|
+
const trimmed = value.trim();
|
|
107
|
+
if (trimmed === "/" || trimmed === "") {
|
|
108
|
+
return "skills/knowledges/subskills";
|
|
109
|
+
}
|
|
110
|
+
return normalizeCatalogPath(trimmed);
|
|
111
|
+
}
|
|
98
112
|
function normalizeGrepMode(value) {
|
|
99
113
|
if (value === void 0) {
|
|
100
114
|
return "content";
|
|
@@ -313,6 +327,57 @@ async function runKnowGlobCommand(pattern, options, output, dependencies) {
|
|
|
313
327
|
output.warning(`[truncated: ${response.data.total_files} total files]`);
|
|
314
328
|
}
|
|
315
329
|
}
|
|
330
|
+
async function runKnowLsCommand(path, options, output, dependencies) {
|
|
331
|
+
const api = dependencies?.api ?? createKnowledgesApi(options);
|
|
332
|
+
const response = await api.listDirectory({
|
|
333
|
+
path: normalizeFilesystemCatalogPath(path ?? "/"),
|
|
334
|
+
limit: coerceLimit(options.limit, 100, 1e3)
|
|
335
|
+
});
|
|
336
|
+
if (shouldPrintJson(options)) {
|
|
337
|
+
output.raw(formatJson(response.data));
|
|
338
|
+
return;
|
|
339
|
+
}
|
|
340
|
+
const entries = [...response.data.entries].sort(compareFilesystemEntries);
|
|
341
|
+
const lines = entries.map(formatFilesystemEntryLine);
|
|
342
|
+
if (lines.length > 0) {
|
|
343
|
+
output.raw(lines.join("\n"));
|
|
344
|
+
} else {
|
|
345
|
+
output.warning(`No entries under ${response.data.path}.`);
|
|
346
|
+
}
|
|
347
|
+
if (response.data.truncated) {
|
|
348
|
+
output.warning(`[truncated: ${response.data.total_entries} total entries]`);
|
|
349
|
+
}
|
|
350
|
+
}
|
|
351
|
+
function compareFilesystemEntries(left, right) {
|
|
352
|
+
if (left.type !== right.type) {
|
|
353
|
+
return left.type === "directory" ? -1 : 1;
|
|
354
|
+
}
|
|
355
|
+
return left.path.localeCompare(right.path);
|
|
356
|
+
}
|
|
357
|
+
function formatFilesystemEntryLine(entry) {
|
|
358
|
+
const fields = [
|
|
359
|
+
entry.type,
|
|
360
|
+
entry.path,
|
|
361
|
+
...formatOptionalEntryFields([
|
|
362
|
+
["size", entry.size],
|
|
363
|
+
["files", entry.file_count],
|
|
364
|
+
["children", entry.child_count],
|
|
365
|
+
["total_size", entry.total_size],
|
|
366
|
+
["sha256", entry.sha256],
|
|
367
|
+
["asset_kind", entry.asset_kind],
|
|
368
|
+
["subskill", entry.subskill_name]
|
|
369
|
+
])
|
|
370
|
+
];
|
|
371
|
+
return fields.join(" ");
|
|
372
|
+
}
|
|
373
|
+
function formatOptionalEntryFields(fields) {
|
|
374
|
+
return fields.flatMap(([key, value]) => {
|
|
375
|
+
if (value === null || value === "") {
|
|
376
|
+
return [];
|
|
377
|
+
}
|
|
378
|
+
return [`${key}=${value}`];
|
|
379
|
+
});
|
|
380
|
+
}
|
|
316
381
|
|
|
317
382
|
export {
|
|
318
383
|
runKnowStatusCommand,
|
|
@@ -322,6 +387,7 @@ export {
|
|
|
322
387
|
runKnowFilesCommand,
|
|
323
388
|
runKnowReadCommand,
|
|
324
389
|
runKnowGrepCommand,
|
|
325
|
-
runKnowGlobCommand
|
|
390
|
+
runKnowGlobCommand,
|
|
391
|
+
runKnowLsCommand
|
|
326
392
|
};
|
|
327
|
-
//# sourceMappingURL=chunk-
|
|
393
|
+
//# sourceMappingURL=chunk-C7HFDK4S.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/features/knowledges/knowledges-api.ts","../src/features/knowledges/knowledges-input.ts","../src/features/knowledges/run-knowledges-command.ts"],"sourcesContent":["import type { CngApi } from \"@cng/client\";\n\nimport { createCngApiClient } from \"../../shared/api-client.js\";\nimport type { GlobalCommandOptions } from \"../../shared/config.js\";\n\nexport type KnowCommandDependencies = {\n api?: KnowledgesApi;\n};\n\nexport type KnowledgesApi = {\n getCatalog(): Promise<CngApi.HarnessCatalogSummaryApiResponse>;\n listAudiences(): Promise<CngApi.HarnessAudiencesApiResponse>;\n search(query: string, limit: number): Promise<CngApi.HarnessSemanticSearchApiResponse>;\n listSubskills(): Promise<CngApi.HarnessSubskillsApiResponse>;\n listFiles(options: {\n query?: string;\n audience?: CngApi.HarnessAudienceId;\n limit: number;\n }): Promise<CngApi.HarnessSubskillAssetsApiResponse>;\n read(options: {\n filePath: string;\n offset?: number;\n limit: number;\n }): Promise<CngApi.HarnessReadApiResponse>;\n grep(options: {\n pattern: string;\n path: string;\n include: string;\n mode: CngApi.HarnessGrepOutputMode;\n context: number;\n ignoreCase: boolean;\n }): Promise<CngApi.HarnessGrepApiResponse>;\n glob(options: { pattern: string; path: string }): Promise<CngApi.HarnessGlobApiResponse>;\n listDirectory(options: {\n path: string;\n limit: number;\n }): Promise<CngApi.HarnessFilesystemLsApiResponse>;\n statPath(options: { path: string }): Promise<CngApi.HarnessFilesystemStatApiResponse>;\n};\n\nexport function createKnowledgesApi(options: GlobalCommandOptions): KnowledgesApi {\n const client = createCngApiClient(options);\n\n return {\n getCatalog: () => client.harnessKnowledges.getHarnessKnowledgesCatalog(),\n listAudiences: () => client.harnessKnowledges.listHarnessKnowledgesAudiences(),\n search: (query, limit) =>\n client.harnessKnowledges.searchHarnessKnowledges({\n q: query,\n limit,\n }),\n listSubskills: () => client.harnessKnowledges.listHarnessKnowledgesSubskills(),\n listFiles: ({ query, audience, limit }) =>\n client.harnessKnowledges.listHarnessSubskillAssets({\n ...(query ? { q: query } : {}),\n ...(audience ? { audience } : {}),\n limit,\n }),\n read: ({ filePath, offset, limit }) =>\n client.harnessFilesystem.getHarnessFilesystemRead({\n file_path: filePath,\n offset,\n limit,\n }),\n grep: ({ pattern, path, include, mode, context, ignoreCase }) =>\n client.harnessFilesystem.getHarnessFilesystemGrep({\n pattern,\n path,\n include,\n output_mode: mode,\n context,\n case_insensitive: ignoreCase ? \"true\" : undefined,\n }),\n glob: ({ pattern, path }) =>\n client.harnessFilesystem.getHarnessFilesystemGlob({\n pattern,\n path,\n }),\n listDirectory: ({ path, limit }) =>\n client.harnessFilesystem.getHarnessFilesystemLs({\n path,\n limit,\n }),\n statPath: ({ path }) =>\n client.harnessFilesystem.getHarnessFilesystemStat({\n path,\n }),\n };\n}\n","import type { CngApi } from \"@cng/client\";\n\nexport function normalizeAudienceId(value: string | undefined): CngApi.HarnessAudienceId | undefined {\n if (value === undefined) {\n return undefined;\n }\n\n switch (value) {\n case \"all\":\n case \"operators\":\n case \"builders\":\n case \"researchers\":\n case \"agent-makers\":\n return value;\n default:\n throw new Error(\n `Unknown audience \"${value}\". Run cngkit knowledges audiences to see supported values.`\n );\n }\n}\n\nexport function normalizeCatalogPath(value: string): string {\n const trimmed = value.trim();\n if (trimmed === \"/\" || trimmed === \"\") {\n return \"skills\";\n }\n\n const relativePath = trimmed.replace(/^\\/+/, \"\");\n if (relativePath.startsWith(\"skills/knowledges/\")) {\n return relativePath;\n }\n\n const [firstSegment, ...restSegments] = relativePath.split(\"/\");\n if (!firstSegment) {\n return relativePath;\n }\n\n switch (firstSegment) {\n case \"concepts\":\n case \"domains\":\n case \"formats\":\n case \"languages\":\n case \"libraries\":\n case \"patterns\":\n case \"platforms\":\n case \"procedures\":\n case \"protocols\":\n case \"tools\":\n return `skills/knowledges/subskills/${firstSegment}${restSegments.length > 0 ? `/${restSegments.join(\"/\")}` : \"\"}`;\n default:\n return relativePath;\n }\n}\n\nexport function normalizeFilesystemCatalogPath(value: string): string {\n const trimmed = value.trim();\n if (trimmed === \"/\" || trimmed === \"\") {\n return \"skills/knowledges/subskills\";\n }\n\n return normalizeCatalogPath(trimmed);\n}\n\nexport function normalizeGrepMode(value: string | undefined): CngApi.HarnessGrepOutputMode {\n if (value === undefined) {\n return \"content\";\n }\n\n switch (value) {\n case \"content\":\n case \"files_with_matches\":\n case \"count\":\n return value;\n default:\n throw new Error(\"Unknown grep mode. Use one of: content, files_with_matches, count.\");\n }\n}\n","import { formatKnowledgesHelp } from \"../../cli/help-specs.js\";\nimport type { CngApi } from \"@cng/client\";\nimport {\n coerceLimit,\n coerceOptionalNumber,\n formatJson,\n optionalJoinedArgument,\n shouldPrintJson,\n singleLine,\n type JsonOutputOptions,\n type NumberOption,\n} from \"../../shared/command-utils.js\";\nimport { resolveOutputFormat } from \"../../shared/config.js\";\nimport type { GlobalCommandOptions } from \"../../shared/config.js\";\nimport type { CommandOutput } from \"../../shared/output.js\";\nimport { createKnowledgesApi, type KnowCommandDependencies } from \"./knowledges-api.js\";\nimport {\n normalizeAudienceId,\n normalizeCatalogPath,\n normalizeFilesystemCatalogPath,\n normalizeGrepMode,\n} from \"./knowledges-input.js\";\n\nexport type KnowStatusCommandOptions = GlobalCommandOptions & JsonOutputOptions;\n\nexport type KnowAudiencesCommandOptions = GlobalCommandOptions & JsonOutputOptions;\n\nexport type KnowSearchCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n limit?: NumberOption;\n };\n\nexport type KnowListCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n limit?: NumberOption;\n };\n\nexport type KnowFilesCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n audience?: string;\n limit?: NumberOption;\n };\n\nexport type KnowReadCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n offset?: NumberOption;\n limit?: NumberOption;\n };\n\nexport type KnowGrepCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n path?: string;\n include?: string;\n outputMode?: string;\n context?: NumberOption;\n caseInsensitive?: boolean;\n limit?: NumberOption;\n };\n\nexport type KnowGlobCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n path?: string;\n limit?: NumberOption;\n };\n\nexport type KnowLsCommandOptions = GlobalCommandOptions &\n JsonOutputOptions & {\n limit?: NumberOption;\n };\n\nexport type KnowStatCommandOptions = GlobalCommandOptions & JsonOutputOptions;\n\nexport type KnowRealpathCommandOptions = GlobalCommandOptions & JsonOutputOptions;\n\nexport type KnowledgesCliOptions = KnowFilesCommandOptions &\n KnowGlobCommandOptions &\n KnowGrepCommandOptions &\n KnowReadCommandOptions &\n KnowSearchCommandOptions &\n KnowLsCommandOptions;\n\nexport async function runKnowledgesCommand(\n args: string[] | undefined,\n options: KnowledgesCliOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const [subcommand, ...subcommandArgs] = args ?? [];\n\n if (subcommand === undefined || subcommand === \"help\") {\n output.markdown(formatKnowledgesHelp(subcommandArgs[0]));\n return;\n }\n\n switch (subcommand) {\n case \"status\":\n return runKnowStatusCommand(options, output, dependencies);\n case \"audiences\":\n return runKnowAudiencesCommand(options, output, dependencies);\n case \"search\":\n return runKnowSearchCommand(optionalJoinedArgument(subcommandArgs), options, output, dependencies);\n case \"list\":\n return runKnowListCommand(optionalJoinedArgument(subcommandArgs), options, output, dependencies);\n case \"files\":\n return runKnowFilesCommand(optionalJoinedArgument(subcommandArgs), options, output, dependencies);\n case \"read\":\n return runKnowReadCommand(subcommandArgs[0], options, output, dependencies);\n case \"grep\":\n return runKnowGrepCommand(optionalJoinedArgument(subcommandArgs), options, output, dependencies);\n case \"glob\":\n return runKnowGlobCommand(optionalJoinedArgument(subcommandArgs), options, output, dependencies);\n case \"ls\":\n return runKnowLsCommand(subcommandArgs[0], options, output, dependencies);\n case \"stat\":\n return runKnowStatCommand(subcommandArgs[0], options, output, dependencies);\n case \"realpath\":\n return runKnowRealpathCommand(subcommandArgs[0], options, output);\n default:\n throw new Error(\n \"Missing knowledges command. Usage: cngkit knowledges <status|audiences|search|list|files|read|grep|glob|ls|stat|realpath>\"\n );\n }\n}\n\nexport async function runKnowStatusCommand(\n options: KnowStatusCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.getCatalog();\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n const latestRun = response.data.latestRun;\n const lines = [\n `Catalog: ${response.data.name}`,\n `Files: ${response.data.files}`,\n `Blobs: ${response.data.blobs}`,\n `Database: ${response.data.database.engine} (${response.data.database.binding})`,\n ];\n\n if (latestRun) {\n lines.push(`Latest run: ${latestRun.status} (${latestRun.id})`);\n if (latestRun.updated_at) {\n lines.push(`Updated: ${latestRun.updated_at}`);\n }\n } else {\n lines.push(\"Latest run: none\");\n }\n\n output.info(lines.join(\"\\n\"));\n}\n\nexport async function runKnowAudiencesCommand(\n options: KnowAudiencesCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.listAudiences();\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n const lines = response.data.audiences.flatMap((audience) => [\n `${audience.id} - ${audience.label}`,\n ` ${singleLine(audience.help)}`,\n ]);\n\n output.info(lines.length > 0 ? lines.join(\"\\n\") : \"No audiences available.\");\n}\n\nexport async function runKnowSearchCommand(\n query: string | undefined,\n options: KnowSearchCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n if (!query) {\n throw new Error(\"Missing search query. Usage: cngkit knowledges search <query>\");\n }\n\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.search(query, coerceLimit(options.limit, 5));\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n const lines = response.data.results.flatMap((result, index) => [\n `${index + 1}. ${result.title} (${result.subskillName})`,\n ` score ${result.score.toFixed(3)} | ${result.path}`,\n ` ${singleLine(result.description || result.contentPreview)}`,\n ]);\n\n if (lines.length > 0) {\n output.info(lines.join(\"\\n\"));\n return;\n }\n\n output.warning(`No results for \"${query}\".`);\n}\n\nexport async function runKnowListCommand(\n query: string | undefined,\n options: KnowListCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.listSubskills();\n const limit = coerceLimit(options.limit, 25);\n const normalizedQuery = query?.toLowerCase();\n const subskills = response.data.subskills\n .filter((subskill) => {\n if (!normalizedQuery) {\n return true;\n }\n return [subskill.name, subskill.title, subskill.description, subskill.type]\n .join(\" \")\n .toLowerCase()\n .includes(normalizedQuery);\n })\n .slice(0, limit);\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson({ subskills, total: subskills.length }));\n return;\n }\n\n const lines = subskills.flatMap((subskill) => [\n `${subskill.name} [${subskill.type}]`,\n ` ${subskill.title} | files ${subskill.fileCount} | rating ${subskill.rating}`,\n ` ${singleLine(subskill.description)}`,\n ]);\n\n if (lines.length > 0) {\n output.info(lines.join(\"\\n\"));\n return;\n }\n\n output.warning(\"No matching subskills.\");\n}\n\nexport async function runKnowFilesCommand(\n query: string | undefined,\n options: KnowFilesCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.listFiles({\n query,\n audience: normalizeAudienceId(options.audience),\n limit: coerceLimit(options.limit, 25),\n });\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n const lines = response.data.files.map((file) => {\n const title = file.display_title ?? file.title ?? file.subskill_name ?? \"Untitled\";\n return `${file.path}\\n ${title}`;\n });\n\n if (lines.length > 0) {\n output.info(lines.join(\"\\n\"));\n return;\n }\n\n output.warning(\"No matching files.\");\n}\n\nexport async function runKnowReadCommand(\n filePath: string | undefined,\n options: KnowReadCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n if (!filePath) {\n throw new Error(\"Missing file_path. Usage: cngkit knowledges read <file_path>\");\n }\n\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.read({\n filePath: normalizeCatalogPath(filePath),\n offset: coerceOptionalNumber(options.offset),\n limit: coerceLimit(options.limit, 200, 2000),\n });\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n if (resolveOutputFormat() === \"markdown\" || !response.data.file_path.endsWith(\".md\")) {\n output.raw(response.data.content);\n } else {\n output.markdown(response.data.content);\n }\n\n if (response.data.truncated) {\n output.warning(\n `[truncated: showing ${response.data.limit} lines from offset ${response.data.offset} of ${response.data.total_lines}]`\n );\n }\n}\n\nexport async function runKnowGrepCommand(\n pattern: string | undefined,\n options: KnowGrepCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n if (!pattern) {\n throw new Error(\"Missing pattern. Usage: cngkit knowledges grep <pattern>\");\n }\n\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const limit = options.limit !== undefined ? coerceOptionalNumber(options.limit) : undefined;\n const response = await api.grep({\n pattern,\n path: normalizeCatalogPath(options.path ?? \"/\"),\n include: options.include ?? \"*\",\n mode: normalizeGrepMode(options.outputMode),\n context: coerceLimit(options.context, 0, 20),\n ignoreCase: options.caseInsensitive === true,\n });\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n if (response.data.mode === \"files_with_matches\") {\n const files = limit ? response.data.files.slice(0, limit) : response.data.files;\n if (files.length > 0) {\n output.raw(files.join(\"\\n\"));\n return;\n }\n\n output.warning(`No files matched \"${pattern}\".`);\n return;\n }\n\n if (response.data.mode === \"count\") {\n const counts = limit ? response.data.counts.slice(0, limit) : response.data.counts;\n const lines = counts.map((count) => `${count.file_path}: ${count.match_count}`);\n if (lines.length > 0) {\n output.raw(lines.join(\"\\n\"));\n return;\n }\n\n output.warning(`No matches for \"${pattern}\".`);\n return;\n }\n\n const matches = limit ? response.data.matches.slice(0, limit) : response.data.matches;\n const lines = matches.flatMap((match) => [\n `${match.file_path}:${match.line_number}`,\n ...match.context_before.map((line) => ` ${line}`),\n `> ${match.line}`,\n ...match.context_after.map((line) => ` ${line}`),\n ]);\n\n if (lines.length > 0) {\n output.raw(lines.join(\"\\n\"));\n return;\n }\n\n output.warning(`No matches for \"${pattern}\".`);\n}\n\nexport async function runKnowGlobCommand(\n pattern: string | undefined,\n options: KnowGlobCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const limit = options.limit !== undefined ? coerceOptionalNumber(options.limit) : undefined;\n const response = await api.glob({\n pattern: pattern ?? \"**/*.md\",\n path: normalizeCatalogPath(options.path ?? \"/\"),\n });\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n const files = limit ? response.data.files.slice(0, limit) : response.data.files;\n const wasClientTruncated = limit ? response.data.files.length > limit : false;\n\n if (files.length > 0) {\n output.raw(files.join(\"\\n\"));\n } else {\n output.warning(\"No matching files.\");\n }\n if (response.data.truncated || wasClientTruncated) {\n output.warning(`[truncated: ${response.data.total_files} total files]`);\n }\n}\n\nexport async function runKnowLsCommand(\n path: string | undefined,\n options: KnowLsCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.listDirectory({\n path: normalizeFilesystemCatalogPath(path ?? \"/\"),\n limit: coerceLimit(options.limit, 100, 1000),\n });\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n const entries = [...response.data.entries].sort(compareFilesystemEntries);\n const lines = entries.map(formatFilesystemEntryLine);\n\n if (lines.length > 0) {\n output.raw(lines.join(\"\\n\"));\n } else {\n output.warning(`No entries under ${response.data.path}.`);\n }\n\n if (response.data.truncated) {\n output.warning(`[truncated: ${response.data.total_entries} total entries]`);\n }\n}\n\nexport async function runKnowStatCommand(\n path: string | undefined,\n options: KnowStatCommandOptions,\n output: CommandOutput,\n dependencies?: KnowCommandDependencies\n): Promise<void> {\n if (!path) {\n throw new Error(\"Missing path. Usage: cngkit knowledges stat <path>\");\n }\n\n const api = dependencies?.api ?? createKnowledgesApi(options);\n const response = await api.statPath({\n path: normalizeFilesystemCatalogPath(path),\n });\n\n if (shouldPrintJson(options)) {\n output.raw(formatJson(response.data));\n return;\n }\n\n output.raw(formatFilesystemStat(response.data));\n}\n\nexport async function runKnowRealpathCommand(\n path: string | undefined,\n options: KnowRealpathCommandOptions,\n output: CommandOutput\n): Promise<void> {\n if (!path) {\n throw new Error(\"Missing path. Usage: cngkit knowledges realpath <path>\");\n }\n\n const resolvedPath = normalizeFilesystemCatalogPath(path);\n if (shouldPrintJson(options)) {\n output.raw(formatJson({ path: resolvedPath }));\n return;\n }\n\n output.raw(resolvedPath);\n}\n\nfunction compareFilesystemEntries(\n left: CngApi.HarnessFilesystemEntry,\n right: CngApi.HarnessFilesystemEntry\n): number {\n if (left.type !== right.type) {\n return left.type === \"directory\" ? -1 : 1;\n }\n\n return left.path.localeCompare(right.path);\n}\n\nfunction formatFilesystemEntryLine(entry: CngApi.HarnessFilesystemEntry): string {\n const fields = [\n entry.type,\n entry.path,\n ...formatOptionalEntryFields([\n [\"size\", entry.size],\n [\"files\", entry.file_count],\n [\"children\", entry.child_count],\n [\"total_size\", entry.total_size],\n [\"sha256\", entry.sha256],\n [\"asset_kind\", entry.asset_kind],\n [\"subskill\", entry.subskill_name],\n ]),\n ];\n\n return fields.join(\"\\t\");\n}\n\nfunction formatFilesystemStat(entry: CngApi.HarnessFilesystemStatResponse): string {\n const fields: Array<[string, string | number | null]> = [\n [\"path\", entry.path],\n [\"type\", entry.type],\n [\"name\", entry.name],\n [\"depth\", entry.depth],\n [\"size\", entry.size],\n [\"files\", entry.file_count],\n [\"children\", entry.child_count],\n [\"total_size\", entry.total_size],\n [\"sha256\", entry.sha256],\n [\"asset_kind\", entry.asset_kind],\n [\"title\", entry.title],\n [\"subskill\", entry.subskill_name],\n [\"updated_at\", entry.updated_at],\n ];\n\n return formatOptionalEntryFields(fields).join(\"\\n\");\n}\n\nfunction formatOptionalEntryFields(fields: Array<[string, string | number | null]>): string[] {\n return fields.flatMap(([key, value]) => {\n if (value === null || value === \"\") {\n return [];\n }\n\n return [`${key}=${value}`];\n });\n}\n"],"mappings":"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","names":["lines"]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
// src/shared/config.ts
|
|
2
2
|
import { randomBytes, randomUUID } from "crypto";
|
|
3
3
|
import process from "process";
|
|
4
|
-
var packageVersion = "1.1.
|
|
4
|
+
var packageVersion = "1.1.18";
|
|
5
5
|
var defaultApiBaseUrl = "https://curly.ng";
|
|
6
6
|
function resolveApiBaseUrl(options) {
|
|
7
7
|
void options;
|
|
@@ -219,4 +219,4 @@ export {
|
|
|
219
219
|
createCommandOutput,
|
|
220
220
|
formatError
|
|
221
221
|
};
|
|
222
|
-
//# sourceMappingURL=chunk-
|
|
222
|
+
//# sourceMappingURL=chunk-CBIVTEZP.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/shared/config.ts","../src/shared/output.ts","../src/shared/theme.ts"],"sourcesContent":["import { randomBytes, randomUUID } from \"node:crypto\";\nimport process from \"node:process\";\n\nexport const packageVersion = \"1.1.17\";\nexport const defaultApiBaseUrl = \"https://curly.ng\";\nexport const outputFormats = [\"text\", \"json\", \"markdown\"] as const;\n\nexport type OutputFormat = (typeof outputFormats)[number];\n\nexport type GlobalCommandOptions = {\n readonly apiBaseUrl?: never;\n};\n\nexport function resolveApiBaseUrl(options: GlobalCommandOptions): string {\n void options;\n return defaultApiBaseUrl;\n}\n\nexport function resolveOutputFormat(): OutputFormat {\n const value = process.env.CNGKIT_FORMAT?.toLowerCase();\n if (value === \"json\" || value === \"markdown\") {\n return value;\n }\n\n return \"text\";\n}\n\nexport function parseOutputFormat(value: string): OutputFormat {\n const normalizedValue = value.toLowerCase();\n if (normalizedValue === \"text\" || normalizedValue === \"json\" || normalizedValue === \"markdown\") {\n return normalizedValue;\n }\n\n throw new Error(\"Unknown --format value. Use one of: text, json, markdown.\");\n}\n\nexport function createRoomCode(): string {\n return randomBytes(4).toString(\"hex\").toUpperCase();\n}\n\nexport function createPeerId(): string {\n return randomUUID();\n}\n","import process from \"node:process\";\nimport { createElement } from \"react\";\nimport { renderToString, Text } from \"ink\";\nimport Markdown from \"@inkkit/ink-markdown\";\nimport stripAnsi from \"strip-ansi\";\nimport {\n createMarkdownTheme,\n statusStylePropsByOutputStyle,\n type OutputStyle,\n} from \"./theme.js\";\nimport { resolveOutputFormat } from \"./config.js\";\n\ntype OutputStream = NodeJS.WriteStream & {\n isTTY?: boolean;\n columns?: number;\n};\n\nexport type CommandOutput = {\n info(message: string): void;\n success(message: string): void;\n warning(message: string): void;\n muted(message: string): void;\n markdown(message: string): void;\n raw(message: string): void;\n error(message: string): void;\n};\n\nexport const consoleOutput = createCommandOutput(process.stdout, process.stderr);\n\nexport function createCommandOutput(stdout: OutputStream, stderr: OutputStream): CommandOutput {\n return {\n info(message) {\n writeStyledMessage(stdout, \"info\", message);\n },\n success(message) {\n writeStyledMessage(stdout, \"success\", message);\n },\n warning(message) {\n writeStyledMessage(stdout, \"warning\", message);\n },\n muted(message) {\n writeStyledMessage(stdout, \"muted\", message);\n },\n markdown(message) {\n stdout.write(`${formatMarkdownMessage(stdout, message)}\\n`);\n },\n raw(message) {\n stdout.write(`${message}\\n`);\n },\n error(message) {\n writeStyledMessage(stderr, \"error\", message);\n },\n };\n}\n\nexport function formatError(error: unknown): string {\n return error instanceof Error ? error.message : String(error);\n}\n\nfunction writeStyledMessage(stream: OutputStream, style: OutputStyle, message: string): void {\n stream.write(`${formatStyledMessage(stream, style, message)}\\n`);\n}\n\nfunction formatStyledMessage(stream: OutputStream, style: OutputStyle, message: string): string {\n if (!shouldRenderColor(stream)) {\n return message;\n }\n\n return renderToString(\n createElement(\n Text,\n {\n ...statusStylePropsByOutputStyle[style],\n wrap: \"wrap\",\n },\n message\n ),\n {\n columns: 10_000,\n }\n );\n}\n\nfunction formatMarkdownMessage(stream: OutputStream, markdown: string): string {\n if (resolveOutputFormat() === \"markdown\") {\n return markdown;\n }\n\n const useColor = shouldRenderColor(stream);\n const markdownWidth = clampMarkdownWidth(stream.columns);\n const preparedMarkdown = prepareMarkdownForTerminal(markdown);\n const renderedMarkdown = renderToString(\n createElement(\n Markdown,\n {\n ...createMarkdownTheme(useColor),\n children: preparedMarkdown,\n width: markdownWidth,\n }\n ),\n {\n columns: markdownWidth,\n }\n );\n\n return useColor ? renderedMarkdown.trimEnd() : stripAnsi(renderedMarkdown).trimEnd();\n}\n\nfunction prepareMarkdownForTerminal(markdown: string): string {\n if (!markdown.startsWith(\"---\\n\")) {\n return markdown;\n }\n\n const frontmatterEndIndex = markdown.indexOf(\"\\n---\", 4);\n if (frontmatterEndIndex < 0) {\n return formatFrontmatterForTerminal(markdown.slice(4).trimEnd());\n }\n\n const frontmatter = markdown.slice(4, frontmatterEndIndex).trimEnd();\n const body = markdown.slice(frontmatterEndIndex + \"\\n---\".length).replace(/^\\n+/, \"\");\n\n return `${formatFrontmatterForTerminal(frontmatter)}\\n\\n${body}`;\n}\n\nfunction formatFrontmatterForTerminal(frontmatter: string): string {\n return `## Metadata\\n\\n\\`\\`\\`yaml\\n${frontmatter}\\n\\`\\`\\``;\n}\n\nfunction shouldRenderColor(stream: OutputStream): boolean {\n if (process.env.CNGKIT_NO_COLOR === \"1\") {\n return false;\n }\n\n const colorMode = process.env.CNGKIT_COLOR?.toLowerCase();\n\n if (colorMode === \"never\" || colorMode === \"0\" || colorMode === \"false\") {\n return false;\n }\n\n if (colorMode === \"always\" || colorMode === \"1\" || colorMode === \"true\") {\n return true;\n }\n\n if (process.env.FORCE_COLOR !== undefined && process.env.FORCE_COLOR !== \"0\") {\n return true;\n }\n\n if (process.env.NO_COLOR !== undefined) {\n return false;\n }\n\n return stream.isTTY === true;\n}\n\nfunction clampMarkdownWidth(columns: number | undefined): number {\n if (columns === undefined) {\n return 100;\n }\n\n return Math.max(72, Math.min(columns, 120));\n}\n","import { Chalk } from \"chalk\";\nimport type { TextProps } from \"ink\";\n\nexport type OutputStyle = \"info\" | \"success\" | \"warning\" | \"muted\" | \"error\";\n\nexport const statusStylePropsByOutputStyle = {\n info: {\n color: \"cyan\",\n },\n success: {\n color: \"green\",\n bold: true,\n },\n warning: {\n color: \"yellow\",\n bold: true,\n },\n muted: {\n dimColor: true,\n },\n error: {\n color: \"red\",\n bold: true,\n },\n} satisfies Record<OutputStyle, TextProps>;\n\nexport function createMarkdownTheme(useColor: boolean) {\n const chalk = new Chalk({ level: useColor ? 1 : 0 });\n const identity = (value: string) => value;\n\n return {\n code: chalk.green,\n blockquote: chalk.dim.italic,\n html: chalk.gray,\n heading: chalk.blueBright.bold,\n firstHeading: chalk.magentaBright.bold,\n hr: chalk.gray,\n listitem: identity,\n table: identity,\n paragraph: identity,\n strong: chalk.bold,\n em: chalk.italic,\n codespan: chalk.cyanBright,\n del: chalk.dim.strikethrough,\n link: chalk.blueBright,\n href: chalk.blue.underline,\n text: identity,\n showSectionPrefix: false,\n reflowText: true,\n unescape: true,\n emoji: false,\n tab: 2,\n };\n}\n"],"mappings":";AAAA,SAAS,aAAa,kBAAkB;AACxC,OAAO,aAAa;AAEb,IAAM,iBAAiB;AACvB,IAAM,oBAAoB;AAS1B,SAAS,kBAAkB,SAAuC;AACvE,OAAK;AACL,SAAO;AACT;AAEO,SAAS,sBAAoC;AAClD,QAAM,QAAQ,QAAQ,IAAI,eAAe,YAAY;AACrD,MAAI,UAAU,UAAU,UAAU,YAAY;AAC5C,WAAO;AAAA,EACT;AAEA,SAAO;AACT;AAEO,SAAS,kBAAkB,OAA6B;AAC7D,QAAM,kBAAkB,MAAM,YAAY;AAC1C,MAAI,oBAAoB,UAAU,oBAAoB,UAAU,oBAAoB,YAAY;AAC9F,WAAO;AAAA,EACT;AAEA,QAAM,IAAI,MAAM,2DAA2D;AAC7E;AAEO,SAAS,iBAAyB;AACvC,SAAO,YAAY,CAAC,EAAE,SAAS,KAAK,EAAE,YAAY;AACpD;AAEO,SAAS,eAAuB;AACrC,SAAO,WAAW;AACpB;;;AC1CA,OAAOA,cAAa;AACpB,SAAS,qBAAqB;AAC9B,SAAS,gBAAgB,YAAY;AACrC,OAAO,cAAc;AACrB,OAAO,eAAe;;;ACJtB,SAAS,aAAa;AAKf,IAAM,gCAAgC;AAAA,EAC3C,MAAM;AAAA,IACJ,OAAO;AAAA,EACT;AAAA,EACA,SAAS;AAAA,IACP,OAAO;AAAA,IACP,MAAM;AAAA,EACR;AAAA,EACA,SAAS;AAAA,IACP,OAAO;AAAA,IACP,MAAM;AAAA,EACR;AAAA,EACA,OAAO;AAAA,IACL,UAAU;AAAA,EACZ;AAAA,EACA,OAAO;AAAA,IACL,OAAO;AAAA,IACP,MAAM;AAAA,EACR;AACF;AAEO,SAAS,oBAAoB,UAAmB;AACrD,QAAM,QAAQ,IAAI,MAAM,EAAE,OAAO,WAAW,IAAI,EAAE,CAAC;AACnD,QAAM,WAAW,CAAC,UAAkB;AAEpC,SAAO;AAAA,IACL,MAAM,MAAM;AAAA,IACZ,YAAY,MAAM,IAAI;AAAA,IACtB,MAAM,MAAM;AAAA,IACZ,SAAS,MAAM,WAAW;AAAA,IAC1B,cAAc,MAAM,cAAc;AAAA,IAClC,IAAI,MAAM;AAAA,IACV,UAAU;AAAA,IACV,OAAO;AAAA,IACP,WAAW;AAAA,IACX,QAAQ,MAAM;AAAA,IACd,IAAI,MAAM;AAAA,IACV,UAAU,MAAM;AAAA,IAChB,KAAK,MAAM,IAAI;AAAA,IACf,MAAM,MAAM;AAAA,IACZ,MAAM,MAAM,KAAK;AAAA,IACjB,MAAM;AAAA,IACN,mBAAmB;AAAA,IACnB,YAAY;AAAA,IACZ,UAAU;AAAA,IACV,OAAO;AAAA,IACP,KAAK;AAAA,EACP;AACF;;;AD1BO,IAAM,gBAAgB,oBAAoBC,SAAQ,QAAQA,SAAQ,MAAM;AAExE,SAAS,oBAAoB,QAAsB,QAAqC;AAC7F,SAAO;AAAA,IACL,KAAK,SAAS;AACZ,yBAAmB,QAAQ,QAAQ,OAAO;AAAA,IAC5C;AAAA,IACA,QAAQ,SAAS;AACf,yBAAmB,QAAQ,WAAW,OAAO;AAAA,IAC/C;AAAA,IACA,QAAQ,SAAS;AACf,yBAAmB,QAAQ,WAAW,OAAO;AAAA,IAC/C;AAAA,IACA,MAAM,SAAS;AACb,yBAAmB,QAAQ,SAAS,OAAO;AAAA,IAC7C;AAAA,IACA,SAAS,SAAS;AAChB,aAAO,MAAM,GAAG,sBAAsB,QAAQ,OAAO,CAAC;AAAA,CAAI;AAAA,IAC5D;AAAA,IACA,IAAI,SAAS;AACX,aAAO,MAAM,GAAG,OAAO;AAAA,CAAI;AAAA,IAC7B;AAAA,IACA,MAAM,SAAS;AACb,yBAAmB,QAAQ,SAAS,OAAO;AAAA,IAC7C;AAAA,EACF;AACF;AAEO,SAAS,YAAY,OAAwB;AAClD,SAAO,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK;AAC9D;AAEA,SAAS,mBAAmB,QAAsB,OAAoB,SAAuB;AAC3F,SAAO,MAAM,GAAG,oBAAoB,QAAQ,OAAO,OAAO,CAAC;AAAA,CAAI;AACjE;AAEA,SAAS,oBAAoB,QAAsB,OAAoB,SAAyB;AAC9F,MAAI,CAAC,kBAAkB,MAAM,GAAG;AAC9B,WAAO;AAAA,EACT;AAEA,SAAO;AAAA,IACL;AAAA,MACE;AAAA,MACA;AAAA,QACE,GAAG,8BAA8B,KAAK;AAAA,QACtC,MAAM;AAAA,MACR;AAAA,MACA;AAAA,IACF;AAAA,IACA;AAAA,MACE,SAAS;AAAA,IACX;AAAA,EACF;AACF;AAEA,SAAS,sBAAsB,QAAsB,UAA0B;AAC7E,MAAI,oBAAoB,MAAM,YAAY;AACxC,WAAO;AAAA,EACT;AAEA,QAAM,WAAW,kBAAkB,MAAM;AACzC,QAAM,gBAAgB,mBAAmB,OAAO,OAAO;AACvD,QAAM,mBAAmB,2BAA2B,QAAQ;AAC5D,QAAM,mBAAmB;AAAA,IACvB;AAAA,MACE;AAAA,MACA;AAAA,QACE,GAAG,oBAAoB,QAAQ;AAAA,QAC/B,UAAU;AAAA,QACV,OAAO;AAAA,MACT;AAAA,IACF;AAAA,IACA;AAAA,MACE,SAAS;AAAA,IACX;AAAA,EACF;AAEA,SAAO,WAAW,iBAAiB,QAAQ,IAAI,UAAU,gBAAgB,EAAE,QAAQ;AACrF;AAEA,SAAS,2BAA2B,UAA0B;AAC5D,MAAI,CAAC,SAAS,WAAW,OAAO,GAAG;AACjC,WAAO;AAAA,EACT;AAEA,QAAM,sBAAsB,SAAS,QAAQ,SAAS,CAAC;AACvD,MAAI,sBAAsB,GAAG;AAC3B,WAAO,6BAA6B,SAAS,MAAM,CAAC,EAAE,QAAQ,CAAC;AAAA,EACjE;AAEA,QAAM,cAAc,SAAS,MAAM,GAAG,mBAAmB,EAAE,QAAQ;AACnE,QAAM,OAAO,SAAS,MAAM,sBAAsB,QAAQ,MAAM,EAAE,QAAQ,QAAQ,EAAE;AAEpF,SAAO,GAAG,6BAA6B,WAAW,CAAC;AAAA;AAAA,EAAO,IAAI;AAChE;AAEA,SAAS,6BAA6B,aAA6B;AACjE,SAAO;AAAA;AAAA;AAAA,EAA8B,WAAW;AAAA;AAClD;AAEA,SAAS,kBAAkB,QAA+B;AACxD,MAAIA,SAAQ,IAAI,oBAAoB,KAAK;AACvC,WAAO;AAAA,EACT;AAEA,QAAM,YAAYA,SAAQ,IAAI,cAAc,YAAY;AAExD,MAAI,cAAc,WAAW,cAAc,OAAO,cAAc,SAAS;AACvE,WAAO;AAAA,EACT;AAEA,MAAI,cAAc,YAAY,cAAc,OAAO,cAAc,QAAQ;AACvE,WAAO;AAAA,EACT;AAEA,MAAIA,SAAQ,IAAI,gBAAgB,UAAaA,SAAQ,IAAI,gBAAgB,KAAK;AAC5E,WAAO;AAAA,EACT;AAEA,MAAIA,SAAQ,IAAI,aAAa,QAAW;AACtC,WAAO;AAAA,EACT;AAEA,SAAO,OAAO,UAAU;AAC1B;AAEA,SAAS,mBAAmB,SAAqC;AAC/D,MAAI,YAAY,QAAW;AACzB,WAAO;AAAA,EACT;AAEA,SAAO,KAAK,IAAI,IAAI,KAAK,IAAI,SAAS,GAAG,CAAC;AAC5C;","names":["process","process"]}
|
|
1
|
+
{"version":3,"sources":["../src/shared/config.ts","../src/shared/output.ts","../src/shared/theme.ts"],"sourcesContent":["import { randomBytes, randomUUID } from \"node:crypto\";\nimport process from \"node:process\";\n\nexport const packageVersion = \"1.1.18\";\nexport const defaultApiBaseUrl = \"https://curly.ng\";\nexport const outputFormats = [\"text\", \"json\", \"markdown\"] as const;\n\nexport type OutputFormat = (typeof outputFormats)[number];\n\nexport type GlobalCommandOptions = {\n readonly apiBaseUrl?: never;\n};\n\nexport function resolveApiBaseUrl(options: GlobalCommandOptions): string {\n void options;\n return defaultApiBaseUrl;\n}\n\nexport function resolveOutputFormat(): OutputFormat {\n const value = process.env.CNGKIT_FORMAT?.toLowerCase();\n if (value === \"json\" || value === \"markdown\") {\n return value;\n }\n\n return \"text\";\n}\n\nexport function parseOutputFormat(value: string): OutputFormat {\n const normalizedValue = value.toLowerCase();\n if (normalizedValue === \"text\" || normalizedValue === \"json\" || normalizedValue === \"markdown\") {\n return normalizedValue;\n }\n\n throw new Error(\"Unknown --format value. Use one of: text, json, markdown.\");\n}\n\nexport function createRoomCode(): string {\n return randomBytes(4).toString(\"hex\").toUpperCase();\n}\n\nexport function createPeerId(): string {\n return randomUUID();\n}\n","import process from \"node:process\";\nimport { createElement } from \"react\";\nimport { renderToString, Text } from \"ink\";\nimport Markdown from \"@inkkit/ink-markdown\";\nimport stripAnsi from \"strip-ansi\";\nimport {\n createMarkdownTheme,\n statusStylePropsByOutputStyle,\n type OutputStyle,\n} from \"./theme.js\";\nimport { resolveOutputFormat } from \"./config.js\";\n\ntype OutputStream = NodeJS.WriteStream & {\n isTTY?: boolean;\n columns?: number;\n};\n\nexport type CommandOutput = {\n info(message: string): void;\n success(message: string): void;\n warning(message: string): void;\n muted(message: string): void;\n markdown(message: string): void;\n raw(message: string): void;\n error(message: string): void;\n};\n\nexport const consoleOutput = createCommandOutput(process.stdout, process.stderr);\n\nexport function createCommandOutput(stdout: OutputStream, stderr: OutputStream): CommandOutput {\n return {\n info(message) {\n writeStyledMessage(stdout, \"info\", message);\n },\n success(message) {\n writeStyledMessage(stdout, \"success\", message);\n },\n warning(message) {\n writeStyledMessage(stdout, \"warning\", message);\n },\n muted(message) {\n writeStyledMessage(stdout, \"muted\", message);\n },\n markdown(message) {\n stdout.write(`${formatMarkdownMessage(stdout, message)}\\n`);\n },\n raw(message) {\n stdout.write(`${message}\\n`);\n },\n error(message) {\n writeStyledMessage(stderr, \"error\", message);\n },\n };\n}\n\nexport function formatError(error: unknown): string {\n return error instanceof Error ? error.message : String(error);\n}\n\nfunction writeStyledMessage(stream: OutputStream, style: OutputStyle, message: string): void {\n stream.write(`${formatStyledMessage(stream, style, message)}\\n`);\n}\n\nfunction formatStyledMessage(stream: OutputStream, style: OutputStyle, message: string): string {\n if (!shouldRenderColor(stream)) {\n return message;\n }\n\n return renderToString(\n createElement(\n Text,\n {\n ...statusStylePropsByOutputStyle[style],\n wrap: \"wrap\",\n },\n message\n ),\n {\n columns: 10_000,\n }\n );\n}\n\nfunction formatMarkdownMessage(stream: OutputStream, markdown: string): string {\n if (resolveOutputFormat() === \"markdown\") {\n return markdown;\n }\n\n const useColor = shouldRenderColor(stream);\n const markdownWidth = clampMarkdownWidth(stream.columns);\n const preparedMarkdown = prepareMarkdownForTerminal(markdown);\n const renderedMarkdown = renderToString(\n createElement(\n Markdown,\n {\n ...createMarkdownTheme(useColor),\n children: preparedMarkdown,\n width: markdownWidth,\n }\n ),\n {\n columns: markdownWidth,\n }\n );\n\n return useColor ? renderedMarkdown.trimEnd() : stripAnsi(renderedMarkdown).trimEnd();\n}\n\nfunction prepareMarkdownForTerminal(markdown: string): string {\n if (!markdown.startsWith(\"---\\n\")) {\n return markdown;\n }\n\n const frontmatterEndIndex = markdown.indexOf(\"\\n---\", 4);\n if (frontmatterEndIndex < 0) {\n return formatFrontmatterForTerminal(markdown.slice(4).trimEnd());\n }\n\n const frontmatter = markdown.slice(4, frontmatterEndIndex).trimEnd();\n const body = markdown.slice(frontmatterEndIndex + \"\\n---\".length).replace(/^\\n+/, \"\");\n\n return `${formatFrontmatterForTerminal(frontmatter)}\\n\\n${body}`;\n}\n\nfunction formatFrontmatterForTerminal(frontmatter: string): string {\n return `## Metadata\\n\\n\\`\\`\\`yaml\\n${frontmatter}\\n\\`\\`\\``;\n}\n\nfunction shouldRenderColor(stream: OutputStream): boolean {\n if (process.env.CNGKIT_NO_COLOR === \"1\") {\n return false;\n }\n\n const colorMode = process.env.CNGKIT_COLOR?.toLowerCase();\n\n if (colorMode === \"never\" || colorMode === \"0\" || colorMode === \"false\") {\n return false;\n }\n\n if (colorMode === \"always\" || colorMode === \"1\" || colorMode === \"true\") {\n return true;\n }\n\n if (process.env.FORCE_COLOR !== undefined && process.env.FORCE_COLOR !== \"0\") {\n return true;\n }\n\n if (process.env.NO_COLOR !== undefined) {\n return false;\n }\n\n return stream.isTTY === true;\n}\n\nfunction clampMarkdownWidth(columns: number | undefined): number {\n if (columns === undefined) {\n return 100;\n }\n\n return Math.max(72, Math.min(columns, 120));\n}\n","import { Chalk } from \"chalk\";\nimport type { TextProps } from \"ink\";\n\nexport type OutputStyle = \"info\" | \"success\" | \"warning\" | \"muted\" | \"error\";\n\nexport const statusStylePropsByOutputStyle = {\n info: {\n color: \"cyan\",\n },\n success: {\n color: \"green\",\n bold: true,\n },\n warning: {\n color: \"yellow\",\n bold: true,\n },\n muted: {\n dimColor: true,\n },\n error: {\n color: \"red\",\n bold: true,\n },\n} satisfies Record<OutputStyle, TextProps>;\n\nexport function createMarkdownTheme(useColor: boolean) {\n const chalk = new Chalk({ level: useColor ? 1 : 0 });\n const identity = (value: string) => value;\n\n return {\n code: chalk.green,\n blockquote: chalk.dim.italic,\n html: chalk.gray,\n heading: chalk.blueBright.bold,\n firstHeading: chalk.magentaBright.bold,\n hr: chalk.gray,\n listitem: identity,\n table: identity,\n paragraph: identity,\n strong: chalk.bold,\n em: chalk.italic,\n codespan: chalk.cyanBright,\n del: chalk.dim.strikethrough,\n link: chalk.blueBright,\n href: chalk.blue.underline,\n text: identity,\n showSectionPrefix: false,\n reflowText: true,\n unescape: true,\n emoji: false,\n tab: 2,\n };\n}\n"],"mappings":"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","names":["process","process"]}
|