skillwiki 0.9.18 → 0.9.20
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/dist/cli.js +171 -25
- package/package.json +1 -1
- package/skills/.claude-plugin/plugin.json +1 -1
- package/skills/.codex-plugin/plugin.json +1 -1
- package/skills/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -2866,9 +2866,9 @@ ${content}
|
|
|
2866
2866
|
|
|
2867
2867
|
// src/commands/lint.ts
|
|
2868
2868
|
import { existsSync as existsSync6 } from "fs";
|
|
2869
|
-
import { readFile as readFile17 } from "fs/promises";
|
|
2869
|
+
import { readFile as readFile17, readdir as readdir5 } from "fs/promises";
|
|
2870
2870
|
import { createHash as createHash5 } from "crypto";
|
|
2871
|
-
import { join as join23 } from "path";
|
|
2871
|
+
import { join as join23, relative as relative3, sep as sep3 } from "path";
|
|
2872
2872
|
|
|
2873
2873
|
// src/commands/sparse-community.ts
|
|
2874
2874
|
async function runSparseCommunity(input) {
|
|
@@ -3714,6 +3714,7 @@ var ERROR_ORDER = ["sensitive_content", "broken_wikilinks", "invalid_frontmatter
|
|
|
3714
3714
|
var WARNING_ORDER = ["raw_body_duplicate", "raw_subdirectory_duplicate", "file_source_url", "index_incomplete", "index_link_format", "stale_page", "page_too_large", "log_rotate_needed", "orphans", "compound_refs", "legacy_citation_style", "orphaned_citations", "duplicate_frontmatter", "work_item_health", "orphaned_project_pages", "missing_overview", "missing_diagram"];
|
|
3715
3715
|
var INFO_ORDER = ["bridges", "sparse_community", "page_structure", "topic_map_recommended", "frontmatter_wikilink", "wikilink_citation", "missing_tldr", "stale_sections", "cli_refs"];
|
|
3716
3716
|
var KNOWN_BUCKETS = [...ERROR_ORDER, ...WARNING_ORDER, ...INFO_ORDER];
|
|
3717
|
+
var CLI_REFS_TYPED_DIRS = ["entities", "concepts", "comparisons", "queries", "meta"];
|
|
3717
3718
|
function shellQuote(value) {
|
|
3718
3719
|
return `'${value.replace(/'/g, `'\\''`)}'`;
|
|
3719
3720
|
}
|
|
@@ -3786,6 +3787,63 @@ function summarizeLintOutput(output, examplesLimit = 3) {
|
|
|
3786
3787
|
humanHint: lines.join("\n")
|
|
3787
3788
|
};
|
|
3788
3789
|
}
|
|
3790
|
+
async function walkMarkdownFiles(absDir, vaultRoot) {
|
|
3791
|
+
const entries = await readdir5(absDir, { withFileTypes: true });
|
|
3792
|
+
const pages = [];
|
|
3793
|
+
for (const entry of entries) {
|
|
3794
|
+
const absPath = join23(absDir, entry.name);
|
|
3795
|
+
if (entry.isDirectory()) {
|
|
3796
|
+
if (entry.name === ".git" || entry.name === "node_modules") continue;
|
|
3797
|
+
pages.push(...await walkMarkdownFiles(absPath, vaultRoot));
|
|
3798
|
+
} else if (entry.isFile() && entry.name.endsWith(".md")) {
|
|
3799
|
+
pages.push({ absPath, relPath: relative3(vaultRoot, absPath).split(sep3).join("/") });
|
|
3800
|
+
}
|
|
3801
|
+
}
|
|
3802
|
+
return pages;
|
|
3803
|
+
}
|
|
3804
|
+
async function collectCliRefsPages(vault) {
|
|
3805
|
+
if (!existsSync6(join23(vault, "SCHEMA.md"))) {
|
|
3806
|
+
return err("VAULT_PATH_INVALID", { root: vault, reason: "SCHEMA.md missing" });
|
|
3807
|
+
}
|
|
3808
|
+
const pages = [];
|
|
3809
|
+
for (const dir of CLI_REFS_TYPED_DIRS) {
|
|
3810
|
+
const absDir = join23(vault, dir);
|
|
3811
|
+
if (!existsSync6(absDir)) continue;
|
|
3812
|
+
pages.push(...await walkMarkdownFiles(absDir, vault));
|
|
3813
|
+
}
|
|
3814
|
+
return ok(pages);
|
|
3815
|
+
}
|
|
3816
|
+
async function runCliRefsOnly(input) {
|
|
3817
|
+
const pages = await collectCliRefsPages(input.vault);
|
|
3818
|
+
if (!pages.ok) {
|
|
3819
|
+
return { exitCode: ExitCode.VAULT_PATH_INVALID, result: pages };
|
|
3820
|
+
}
|
|
3821
|
+
const cliRefFlags = [];
|
|
3822
|
+
const cliSurface = buildCliSurface();
|
|
3823
|
+
for (const page of pages.data) {
|
|
3824
|
+
const text = await readPage(page);
|
|
3825
|
+
const violations = validateCliRefs(text, page.relPath, cliSurface);
|
|
3826
|
+
for (const v of violations) {
|
|
3827
|
+
cliRefFlags.push(`${v.page}: ${v.ref} (${v.reason})`);
|
|
3828
|
+
}
|
|
3829
|
+
}
|
|
3830
|
+
const infoOut = cliRefFlags.length > 0 ? [{ kind: "cli_refs", items: cliRefFlags }] : [];
|
|
3831
|
+
const summary = { errors: 0, warnings: 0, info: cliRefFlags.length };
|
|
3832
|
+
const exitCode = cliRefFlags.length > 0 ? ExitCode.LINT_HAS_WARNINGS : ExitCode.OK;
|
|
3833
|
+
const output = {
|
|
3834
|
+
vault: { path: input.vault, source: input.source ?? "resolved" },
|
|
3835
|
+
summary,
|
|
3836
|
+
by_severity: { error: [], warning: [], info: infoOut },
|
|
3837
|
+
fixed: [],
|
|
3838
|
+
unresolved: [],
|
|
3839
|
+
humanHint: `--only cli_refs
|
|
3840
|
+
${cliRefFlags.length === 0 ? "0 violations" : ` cli_refs: ${cliRefFlags.length}`}`
|
|
3841
|
+
};
|
|
3842
|
+
return {
|
|
3843
|
+
exitCode,
|
|
3844
|
+
result: ok(input.summary ? summarizeLintOutput(output, input.examplesLimit) : output)
|
|
3845
|
+
};
|
|
3846
|
+
}
|
|
3789
3847
|
async function runLint(input) {
|
|
3790
3848
|
if (input.only && !KNOWN_BUCKETS.includes(input.only)) {
|
|
3791
3849
|
return {
|
|
@@ -3793,6 +3851,9 @@ async function runLint(input) {
|
|
|
3793
3851
|
result: { ok: false, error: "UNKNOWN_BUCKET", detail: `Unknown bucket "${input.only}". Valid: ${KNOWN_BUCKETS.join(", ")}` }
|
|
3794
3852
|
};
|
|
3795
3853
|
}
|
|
3854
|
+
if (input.only === "cli_refs") {
|
|
3855
|
+
return runCliRefsOnly(input);
|
|
3856
|
+
}
|
|
3796
3857
|
const shouldFix = (bucket) => !!input.fix && (!input.only || input.only === bucket);
|
|
3797
3858
|
const buckets = {};
|
|
3798
3859
|
const fixed = [];
|
|
@@ -5806,6 +5867,8 @@ function checkVaultGitAhead(resolvedPath) {
|
|
|
5806
5867
|
);
|
|
5807
5868
|
}
|
|
5808
5869
|
function checkVaultGitBehind(resolvedPath) {
|
|
5870
|
+
const staleRemote = checkStaleRemoteMain(resolvedPath);
|
|
5871
|
+
if (staleRemote) return staleRemote;
|
|
5809
5872
|
return checkVaultGitComparison(
|
|
5810
5873
|
resolvedPath,
|
|
5811
5874
|
"vault_git_behind",
|
|
@@ -5815,6 +5878,47 @@ function checkVaultGitBehind(resolvedPath) {
|
|
|
5815
5878
|
"0 commits behind origin/main"
|
|
5816
5879
|
);
|
|
5817
5880
|
}
|
|
5881
|
+
function gitRefHash(resolvedPath, ref) {
|
|
5882
|
+
try {
|
|
5883
|
+
const out = execSync2(`git rev-parse --verify ${ref}`, {
|
|
5884
|
+
cwd: resolvedPath,
|
|
5885
|
+
encoding: "utf8",
|
|
5886
|
+
stdio: ["pipe", "pipe", "pipe"],
|
|
5887
|
+
timeout: 2e3
|
|
5888
|
+
}).trim();
|
|
5889
|
+
return out || void 0;
|
|
5890
|
+
} catch {
|
|
5891
|
+
return void 0;
|
|
5892
|
+
}
|
|
5893
|
+
}
|
|
5894
|
+
function remoteMainHash(resolvedPath) {
|
|
5895
|
+
try {
|
|
5896
|
+
const out = execSync2("git ls-remote origin refs/heads/main", {
|
|
5897
|
+
cwd: resolvedPath,
|
|
5898
|
+
encoding: "utf8",
|
|
5899
|
+
stdio: ["pipe", "pipe", "pipe"],
|
|
5900
|
+
timeout: 3e3
|
|
5901
|
+
}).trim();
|
|
5902
|
+
const hash = out.split(/\s+/)[0];
|
|
5903
|
+
return /^[0-9a-f]{40}$/i.test(hash) ? hash : void 0;
|
|
5904
|
+
} catch {
|
|
5905
|
+
return void 0;
|
|
5906
|
+
}
|
|
5907
|
+
}
|
|
5908
|
+
function checkStaleRemoteMain(resolvedPath) {
|
|
5909
|
+
if (resolvedPath === void 0) return void 0;
|
|
5910
|
+
if (!existsSync11(join29(resolvedPath, ".git"))) return void 0;
|
|
5911
|
+
const localOrigin = gitRefHash(resolvedPath, "origin/main");
|
|
5912
|
+
if (!localOrigin) return void 0;
|
|
5913
|
+
const remoteMain = remoteMainHash(resolvedPath);
|
|
5914
|
+
if (!remoteMain || remoteMain === localOrigin) return void 0;
|
|
5915
|
+
return check(
|
|
5916
|
+
"warn",
|
|
5917
|
+
"vault_git_behind",
|
|
5918
|
+
"Vault commits behind",
|
|
5919
|
+
`Remote main differs from local origin/main (${remoteMain.slice(0, 8)} != ${localOrigin.slice(0, 8)}) \u2014 run git fetch before trusting behind count`
|
|
5920
|
+
);
|
|
5921
|
+
}
|
|
5818
5922
|
function checkVaultGitComparison(resolvedPath, id, label, range, nonZeroSuffix, zeroDetail) {
|
|
5819
5923
|
if (resolvedPath === void 0) {
|
|
5820
5924
|
return check("pass", id, label, "No vault path \u2014 check skipped");
|
|
@@ -6254,6 +6358,53 @@ function vaultSyncChecks(input) {
|
|
|
6254
6358
|
const packagedSnapshotPath = join29(shareDir, "wiki-snapshot.sh");
|
|
6255
6359
|
const legacySnapshotPath = "/root/.hermes/scripts/wiki-snapshot-v3.sh";
|
|
6256
6360
|
const snapshotPath = input.snapshotScriptPath ?? (existsSync11(packagedSnapshotPath) ? packagedSnapshotPath : legacySnapshotPath);
|
|
6361
|
+
function snapshotLastStatusCheck() {
|
|
6362
|
+
const snapshotLog = join29(logDir, "wiki-snapshot.log");
|
|
6363
|
+
try {
|
|
6364
|
+
const logContent = readFileSync7(snapshotLog, "utf8");
|
|
6365
|
+
const lines = logContent.trim().split("\n").filter(Boolean);
|
|
6366
|
+
if (lines.length === 0) {
|
|
6367
|
+
return check(
|
|
6368
|
+
"warn",
|
|
6369
|
+
"vault_sync_last_push_age",
|
|
6370
|
+
"Vault sync last snapshot status",
|
|
6371
|
+
"Snapshot log file is empty"
|
|
6372
|
+
);
|
|
6373
|
+
}
|
|
6374
|
+
const lastLine = [...lines].reverse().find(
|
|
6375
|
+
(line) => /ERROR|Status: complete|Push successful|No changes to commit/.test(line)
|
|
6376
|
+
) ?? lines[lines.length - 1];
|
|
6377
|
+
if (/ERROR/.test(lastLine)) {
|
|
6378
|
+
return check(
|
|
6379
|
+
"error",
|
|
6380
|
+
"vault_sync_last_push_age",
|
|
6381
|
+
"Vault sync last snapshot status",
|
|
6382
|
+
`Last snapshot failed: ${lastLine.slice(0, 160)}`
|
|
6383
|
+
);
|
|
6384
|
+
}
|
|
6385
|
+
if (/Status: complete|Push successful|No changes to commit/.test(lastLine)) {
|
|
6386
|
+
return check(
|
|
6387
|
+
"pass",
|
|
6388
|
+
"vault_sync_last_push_age",
|
|
6389
|
+
"Vault sync last snapshot status",
|
|
6390
|
+
lastLine.slice(0, 160)
|
|
6391
|
+
);
|
|
6392
|
+
}
|
|
6393
|
+
return check(
|
|
6394
|
+
"warn",
|
|
6395
|
+
"vault_sync_last_push_age",
|
|
6396
|
+
"Vault sync last snapshot status",
|
|
6397
|
+
`Last snapshot log entry: ${lastLine.slice(0, 160)}`
|
|
6398
|
+
);
|
|
6399
|
+
} catch {
|
|
6400
|
+
return check(
|
|
6401
|
+
"warn",
|
|
6402
|
+
"vault_sync_last_push_age",
|
|
6403
|
+
"Vault sync last snapshot status",
|
|
6404
|
+
`Snapshot log not found at ${snapshotLog}`
|
|
6405
|
+
);
|
|
6406
|
+
}
|
|
6407
|
+
}
|
|
6257
6408
|
if (input.vaultSyncRole === "snapshotter") {
|
|
6258
6409
|
const c12 = existsSync11(snapshotPath) ? check("pass", "vault_sync_installed", "Vault sync installed", `Found snapshot script: ${snapshotPath}`) : check("error", "vault_sync_installed", "Vault sync installed", `Snapshot script not found at ${snapshotPath}`);
|
|
6259
6410
|
const serviceScope = input.vaultSyncServiceScope ?? "user";
|
|
@@ -6279,12 +6430,7 @@ function vaultSyncChecks(input) {
|
|
|
6279
6430
|
c22 = check("error", "vault_sync_jobs_enabled", "Vault sync jobs enabled", `wiki-snapshot.timer check failed (${serviceScope})`);
|
|
6280
6431
|
}
|
|
6281
6432
|
}
|
|
6282
|
-
const c32 =
|
|
6283
|
-
"pass",
|
|
6284
|
-
"vault_sync_last_push_age",
|
|
6285
|
-
"Vault sync last push recency",
|
|
6286
|
-
"Snapshotter host \u2014 leaf wiki-push log not applicable"
|
|
6287
|
-
);
|
|
6433
|
+
const c32 = snapshotLastStatusCheck();
|
|
6288
6434
|
const cFetch2 = check(
|
|
6289
6435
|
"pass",
|
|
6290
6436
|
"vault_sync_last_fetch_status",
|
|
@@ -7916,13 +8062,13 @@ async function runSelfUpdate(input) {
|
|
|
7916
8062
|
}
|
|
7917
8063
|
|
|
7918
8064
|
// src/commands/transcripts.ts
|
|
7919
|
-
import { readdir as
|
|
8065
|
+
import { readdir as readdir6, stat as stat8, readFile as readFile22 } from "fs/promises";
|
|
7920
8066
|
import { join as join34 } from "path";
|
|
7921
8067
|
async function runTranscripts(input) {
|
|
7922
8068
|
const dir = join34(input.vault, "raw", "transcripts");
|
|
7923
8069
|
let entries;
|
|
7924
8070
|
try {
|
|
7925
|
-
entries = await
|
|
8071
|
+
entries = await readdir6(dir, { withFileTypes: true });
|
|
7926
8072
|
} catch {
|
|
7927
8073
|
return { exitCode: ExitCode.VAULT_PATH_INVALID, result: { ok: false, error: "VAULT_PATH_INVALID", detail: `raw/transcripts/ not found: ${dir}` } };
|
|
7928
8074
|
}
|
|
@@ -7947,14 +8093,14 @@ async function runTranscripts(input) {
|
|
|
7947
8093
|
}
|
|
7948
8094
|
|
|
7949
8095
|
// src/commands/project-index.ts
|
|
7950
|
-
import { readdir as
|
|
8096
|
+
import { readdir as readdir7, readFile as readFile23, writeFile as writeFile11, mkdir as mkdir10 } from "fs/promises";
|
|
7951
8097
|
import { join as join35, dirname as dirname13 } from "path";
|
|
7952
8098
|
var LAYER2_DIRS = ["entities", "concepts", "comparisons", "queries", "meta"];
|
|
7953
8099
|
async function runProjectIndex(input) {
|
|
7954
8100
|
const slug = input.slug;
|
|
7955
8101
|
const projectDir = join35(input.vault, "projects", slug);
|
|
7956
8102
|
try {
|
|
7957
|
-
await
|
|
8103
|
+
await readdir7(projectDir);
|
|
7958
8104
|
} catch {
|
|
7959
8105
|
return {
|
|
7960
8106
|
exitCode: ExitCode.PROJECT_NOT_FOUND,
|
|
@@ -7965,7 +8111,7 @@ async function runProjectIndex(input) {
|
|
|
7965
8111
|
const entries = [];
|
|
7966
8112
|
const compoundDir = join35(input.vault, "projects", slug, "compound");
|
|
7967
8113
|
try {
|
|
7968
|
-
const compoundFiles = await
|
|
8114
|
+
const compoundFiles = await readdir7(compoundDir, { withFileTypes: true });
|
|
7969
8115
|
for (const entry of compoundFiles) {
|
|
7970
8116
|
if (!entry.isFile() || !entry.name.endsWith(".md")) continue;
|
|
7971
8117
|
const filePath = join35(compoundDir, entry.name);
|
|
@@ -7988,7 +8134,7 @@ async function runProjectIndex(input) {
|
|
|
7988
8134
|
for (const dir of LAYER2_DIRS) {
|
|
7989
8135
|
let files;
|
|
7990
8136
|
try {
|
|
7991
|
-
files = await
|
|
8137
|
+
files = await readdir7(join35(input.vault, dir), { withFileTypes: true });
|
|
7992
8138
|
} catch {
|
|
7993
8139
|
continue;
|
|
7994
8140
|
}
|
|
@@ -8091,7 +8237,7 @@ ${entries.map((e) => ` ${e.type}: [[${e.page.replace(/\.md$/, "")}]] \u2014 ${e
|
|
|
8091
8237
|
}
|
|
8092
8238
|
|
|
8093
8239
|
// src/commands/compound.ts
|
|
8094
|
-
import { writeFile as writeFile12, mkdir as mkdir11, readdir as
|
|
8240
|
+
import { writeFile as writeFile12, mkdir as mkdir11, readdir as readdir8, unlink as unlink4 } from "fs/promises";
|
|
8095
8241
|
import { join as join36 } from "path";
|
|
8096
8242
|
import { existsSync as existsSync14 } from "fs";
|
|
8097
8243
|
import { readFile as readFile24 } from "fs/promises";
|
|
@@ -8328,7 +8474,7 @@ no compound directory found`
|
|
|
8328
8474
|
}
|
|
8329
8475
|
let dirents;
|
|
8330
8476
|
try {
|
|
8331
|
-
dirents = await
|
|
8477
|
+
dirents = await readdir8(compoundDir, { withFileTypes: true });
|
|
8332
8478
|
} catch {
|
|
8333
8479
|
return {
|
|
8334
8480
|
exitCode: ExitCode.OK,
|
|
@@ -8460,7 +8606,7 @@ ${input.text.trim()}
|
|
|
8460
8606
|
|
|
8461
8607
|
// src/commands/session-brief.ts
|
|
8462
8608
|
import { mkdir as mkdir13, readFile as readFile25, writeFile as writeFile14 } from "fs/promises";
|
|
8463
|
-
import { join as join38, relative as
|
|
8609
|
+
import { join as join38, relative as relative4, sep as sep4 } from "path";
|
|
8464
8610
|
var MAX_WORDS = 900;
|
|
8465
8611
|
async function runSessionBrief(input) {
|
|
8466
8612
|
const scan = await scanVault(input.vault);
|
|
@@ -8564,7 +8710,7 @@ async function readProjectSlug(file) {
|
|
|
8564
8710
|
return void 0;
|
|
8565
8711
|
}
|
|
8566
8712
|
function inferProjectFromPath(vault, cwd) {
|
|
8567
|
-
const rel =
|
|
8713
|
+
const rel = relative4(vault, cwd).split(sep4).join("/");
|
|
8568
8714
|
const match = rel.match(/^projects\/([^/]+)(?:\/|$)/);
|
|
8569
8715
|
return match?.[1];
|
|
8570
8716
|
}
|
|
@@ -8853,8 +8999,8 @@ function dateFromPath(path) {
|
|
|
8853
8999
|
|
|
8854
9000
|
// src/commands/memory.ts
|
|
8855
9001
|
import { createHash as createHash8 } from "crypto";
|
|
8856
|
-
import { mkdir as mkdir14, readFile as readFile26, readdir as
|
|
8857
|
-
import { basename as basename2, extname, join as join39, relative as
|
|
9002
|
+
import { mkdir as mkdir14, readFile as readFile26, readdir as readdir9, stat as stat9, writeFile as writeFile15 } from "fs/promises";
|
|
9003
|
+
import { basename as basename2, extname, join as join39, relative as relative5, sep as sep5 } from "path";
|
|
8858
9004
|
async function runMemoryTopics(input) {
|
|
8859
9005
|
const scan = await scanVault(input.vault);
|
|
8860
9006
|
if (!scan.ok) return { exitCode: ExitCode.VAULT_PATH_INVALID, result: scan };
|
|
@@ -9041,7 +9187,7 @@ async function collectImportFiles(source) {
|
|
|
9041
9187
|
return files.sort((a, b) => a.localeCompare(b));
|
|
9042
9188
|
}
|
|
9043
9189
|
async function walkImportFiles(dir, out) {
|
|
9044
|
-
const entries = await
|
|
9190
|
+
const entries = await readdir9(dir, { withFileTypes: true });
|
|
9045
9191
|
for (const entry of entries) {
|
|
9046
9192
|
if (entry.name === ".git" || entry.name === "node_modules") continue;
|
|
9047
9193
|
const path = join39(dir, entry.name);
|
|
@@ -9094,7 +9240,7 @@ async function buildImportEntry(file, sourceRoot, project, today, maxBytes) {
|
|
|
9094
9240
|
const redacted = redactSensitiveContent(extracted, { file });
|
|
9095
9241
|
const privacy = redacted.findings.length > 0 ? "sensitive" : "local";
|
|
9096
9242
|
const sourceSlug = slugify3(basename2(file, extname(file)));
|
|
9097
|
-
const relSource =
|
|
9243
|
+
const relSource = relative5(sourceRoot, file).split(sep5).join("/");
|
|
9098
9244
|
const entry = {
|
|
9099
9245
|
...baseEntry,
|
|
9100
9246
|
status: "ready",
|
|
@@ -9166,7 +9312,7 @@ function hiddenString(entry, key) {
|
|
|
9166
9312
|
return entry[key] ?? "";
|
|
9167
9313
|
}
|
|
9168
9314
|
function classifyImportSource(file) {
|
|
9169
|
-
const rel = file.split(
|
|
9315
|
+
const rel = file.split(sep5).join("/");
|
|
9170
9316
|
const name = basename2(file);
|
|
9171
9317
|
if (rel.includes("/.codex/memories/")) return "codex-memory";
|
|
9172
9318
|
if (rel.includes("/.codex/rules/")) return "codex-rule";
|
|
@@ -10413,7 +10559,7 @@ function runSyncUnlock(input) {
|
|
|
10413
10559
|
|
|
10414
10560
|
// src/commands/backup.ts
|
|
10415
10561
|
import { statSync as statSync5, readdirSync as readdirSync3, readFileSync as readFileSync12, mkdirSync as mkdirSync7, writeFileSync as writeFileSync8 } from "fs";
|
|
10416
|
-
import { join as join43, relative as
|
|
10562
|
+
import { join as join43, relative as relative6, dirname as dirname14 } from "path";
|
|
10417
10563
|
import { PutObjectCommand, HeadObjectCommand, ListObjectsV2Command, GetObjectCommand, DeleteObjectsCommand } from "@aws-sdk/client-s3";
|
|
10418
10564
|
|
|
10419
10565
|
// src/utils/s3-client.ts
|
|
@@ -10441,7 +10587,7 @@ function* walkMarkdown(dir, base) {
|
|
|
10441
10587
|
if (entry.isDirectory()) {
|
|
10442
10588
|
yield* walkMarkdown(full, base);
|
|
10443
10589
|
} else if (entry.name.endsWith(".md")) {
|
|
10444
|
-
yield
|
|
10590
|
+
yield relative6(base, full).replace(/\\/g, "/");
|
|
10445
10591
|
}
|
|
10446
10592
|
}
|
|
10447
10593
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "skillwiki",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.20",
|
|
4
4
|
"skills": "./",
|
|
5
5
|
"description": "Project-aware Karpathy-style knowledge base for Claude Code: 18 prompt-only skills (wiki-*, proj-*, using-skillwiki) backed by the deterministic `skillwiki` CLI.",
|
|
6
6
|
"author": {
|