@warpgogol/forge 4.1.3 → 4.1.5
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/os/mission/handlers/archive.test.ts +54 -0
- package/os/mission/handlers/archive.ts +25 -0
- package/package.json +1 -1
- package/skills/fo/fo-session-retro/SKILL.md +1 -1
- package/src/compass/contract-registry.test.ts +11 -0
- package/src/compass/types.test.ts +11 -0
- package/src/config/forge-config.test.ts +11 -0
- package/src/forge-module.test.ts +11 -0
- package/src/knowledge/budgets.test.ts +11 -0
- package/src/knowledge/compact.test.ts +11 -0
- package/src/knowledge/parse.test.ts +11 -0
- package/src/knowledge/schema.test.ts +60 -0
- package/src/onboarding/create.test.ts +11 -0
- package/src/onboarding/doctor.test.ts +11 -0
- package/src/onboarding/init.test.ts +11 -0
- package/src/onboarding/scaffold.test.ts +11 -0
- package/src/onboarding/upgrade.test.ts +11 -0
- package/src/plugin/forge-plugin-manifest.test.ts +12 -0
- package/src/types/werkstatt-engine-shims.d.ts +4 -0
- package/src/types/werkstatt-shared-shims.d.ts +133 -4
- package/src/types.test.ts +11 -0
- package/src/utils/fs-atomic.test.ts +11 -0
- package/src/utils/fs-trash-sync.test.ts +11 -0
- package/src/utils/fs.test.ts +11 -0
- package/src/utils/generated-marker.test.ts +11 -0
- package/src/utils/hash.test.ts +25 -0
- package/src/utils/string-utils.test.ts +23 -0
|
@@ -131,6 +131,60 @@ describe("mission.archive", () => {
|
|
|
131
131
|
expect(existsSync(path.join(missionsDir, "archive", "closed", "test-m006"))).toBe(false);
|
|
132
132
|
});
|
|
133
133
|
|
|
134
|
+
test("closed mission without releaseId → warns in pretty mode", async () => {
|
|
135
|
+
await writeMissionManifest(missionsDir, "test-m007", "closed");
|
|
136
|
+
const warnSpy = vi.fn();
|
|
137
|
+
const ctx: ForgeRuntimeContext = {
|
|
138
|
+
workspaceRoot: tmpDir,
|
|
139
|
+
logger: {
|
|
140
|
+
info: () => {},
|
|
141
|
+
success: () => {},
|
|
142
|
+
warn: warnSpy,
|
|
143
|
+
error: () => {},
|
|
144
|
+
debug: () => {},
|
|
145
|
+
},
|
|
146
|
+
outputFormat: "pretty",
|
|
147
|
+
dryRun: false,
|
|
148
|
+
} as unknown as ForgeRuntimeContext;
|
|
149
|
+
|
|
150
|
+
await runMissionArchive(makeInput(), ctx);
|
|
151
|
+
|
|
152
|
+
expect(warnSpy).toHaveBeenCalledWith(
|
|
153
|
+
expect.stringContaining("test-m007: closed mission has no releaseId"),
|
|
154
|
+
);
|
|
155
|
+
});
|
|
156
|
+
|
|
157
|
+
test("closed mission with releaseId → no warning", async () => {
|
|
158
|
+
const missionDir = path.join(missionsDir, "test-m008");
|
|
159
|
+
await fs.mkdir(missionDir, { recursive: true });
|
|
160
|
+
await fs.writeFile(
|
|
161
|
+
path.join(missionDir, "mission.yaml"),
|
|
162
|
+
`missionId: test-m008\nstate: closed\nreleaseId: test-r000001\n`,
|
|
163
|
+
);
|
|
164
|
+
const warnSpy = vi.fn();
|
|
165
|
+
const ctx: ForgeRuntimeContext = {
|
|
166
|
+
workspaceRoot: tmpDir,
|
|
167
|
+
logger: {
|
|
168
|
+
info: () => {},
|
|
169
|
+
success: () => {},
|
|
170
|
+
warn: warnSpy,
|
|
171
|
+
error: () => {},
|
|
172
|
+
debug: () => {},
|
|
173
|
+
},
|
|
174
|
+
outputFormat: "pretty",
|
|
175
|
+
dryRun: false,
|
|
176
|
+
} as unknown as ForgeRuntimeContext;
|
|
177
|
+
|
|
178
|
+
await runMissionArchive(makeInput(), ctx);
|
|
179
|
+
|
|
180
|
+
expect(
|
|
181
|
+
warnSpy.mock.calls.some(
|
|
182
|
+
(c) =>
|
|
183
|
+
typeof c[0] === "string" && c[0].includes("test-m008: closed mission has no releaseId"),
|
|
184
|
+
),
|
|
185
|
+
).toBe(false);
|
|
186
|
+
});
|
|
187
|
+
|
|
134
188
|
test("destination exists → skipped with 'destination exists' reason", async () => {
|
|
135
189
|
await writeMissionManifest(missionsDir, "test-m007", "closed");
|
|
136
190
|
const archiveDir = path.join(missionsDir, "archive", "closed", "test-m007");
|
|
@@ -69,6 +69,19 @@ function isCacheEntry(name: string): boolean {
|
|
|
69
69
|
return name.startsWith(".") || name === "node_modules" || name === "dist";
|
|
70
70
|
}
|
|
71
71
|
|
|
72
|
+
async function readMissionReleaseId(missionDir: string): Promise<string | null> {
|
|
73
|
+
const manifestPath = path.join(missionDir, "mission.yaml");
|
|
74
|
+
try {
|
|
75
|
+
const raw = await fs.readFile(manifestPath, "utf8");
|
|
76
|
+
const parsed = parseYaml(raw) as Record<string, unknown>;
|
|
77
|
+
const releaseId = parsed?.releaseId;
|
|
78
|
+
if (typeof releaseId === "string" && releaseId.trim()) return releaseId.trim();
|
|
79
|
+
} catch {
|
|
80
|
+
// fall through
|
|
81
|
+
}
|
|
82
|
+
return null;
|
|
83
|
+
}
|
|
84
|
+
|
|
72
85
|
async function readMissionState(missionDir: string): Promise<string | null> {
|
|
73
86
|
const manifestPath = path.join(missionDir, "mission.yaml");
|
|
74
87
|
try {
|
|
@@ -337,6 +350,18 @@ export async function runMissionArchive(
|
|
|
337
350
|
continue;
|
|
338
351
|
}
|
|
339
352
|
|
|
353
|
+
// Warn when archiving a closed mission without a release — operator likely
|
|
354
|
+
// forgot to run release.prepare before archiving. Non-blocking: some missions
|
|
355
|
+
// (e.g. aborted, content-only) legitimately have no release.
|
|
356
|
+
if (state === "closed" && !dryRun) {
|
|
357
|
+
const releaseId = await readMissionReleaseId(missionDir);
|
|
358
|
+
if (!releaseId && outputFormat === "pretty") {
|
|
359
|
+
logger.warn(
|
|
360
|
+
` ⚠ ${missionId}: closed mission has no releaseId — run release.prepare before archiving if this mission needs deployment`,
|
|
361
|
+
);
|
|
362
|
+
}
|
|
363
|
+
}
|
|
364
|
+
|
|
340
365
|
const targetDir = path.join(missionsPath, ARCHIVE_DIR_NAME, state);
|
|
341
366
|
const targetPath = path.join(targetDir, missionId);
|
|
342
367
|
const targetRel = `${MISSIONS_DIR}/${ARCHIVE_DIR_NAME}/${state}/${missionId}`;
|
package/package.json
CHANGED
|
@@ -9,7 +9,7 @@ languagePolicy: ref(PREFERENCES.md)
|
|
|
9
9
|
bindings:
|
|
10
10
|
requires: []
|
|
11
11
|
optional: [paths.invariantsFile]
|
|
12
|
-
triggers: ["session retrospective", "capture insights from this session", "triage session discoveries", "Завершаем сессию", "/session-end"]
|
|
12
|
+
triggers: ["session retrospective", "capture insights from this session", "triage session discoveries", "Завершаем сессию", "Завершаем эту сессию", "Заканчиваем сессию", "Завершить сессию", "End session", "Wrap up", "Session end", "/session-end"]
|
|
13
13
|
---
|
|
14
14
|
|
|
15
15
|
# Session Retro
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./contract-registry.ts";
|
|
6
|
+
|
|
7
|
+
describe("contract-registry (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./types.ts";
|
|
6
|
+
|
|
7
|
+
describe("compass types (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./forge-config.ts";
|
|
6
|
+
|
|
7
|
+
describe("forge-config (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./forge-module.ts";
|
|
6
|
+
|
|
7
|
+
describe("forge-module (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./budgets.ts";
|
|
6
|
+
|
|
7
|
+
describe("knowledge budgets (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./compact.ts";
|
|
6
|
+
|
|
7
|
+
describe("knowledge compact (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./parse.ts";
|
|
6
|
+
|
|
7
|
+
describe("knowledge parse (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import { knowledgeEntryMetaSchema } from "./schema.ts";
|
|
6
|
+
|
|
7
|
+
describe("knowledgeEntryMetaSchema", () => {
|
|
8
|
+
it("parses a valid L0 entry", () => {
|
|
9
|
+
const result = knowledgeEntryMetaSchema.safeParse({
|
|
10
|
+
id: "K-0001",
|
|
11
|
+
layer: "L0",
|
|
12
|
+
created: "2026-01-01",
|
|
13
|
+
status: "active",
|
|
14
|
+
});
|
|
15
|
+
expect(result.success).toBe(true);
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
it("parses a valid L2 entry with confirmations and lastConfirmedAt", () => {
|
|
19
|
+
const result = knowledgeEntryMetaSchema.safeParse({
|
|
20
|
+
id: "K-0002",
|
|
21
|
+
layer: "L2",
|
|
22
|
+
created: "2026-01-01",
|
|
23
|
+
lastConfirmedAt: "2026-06-01",
|
|
24
|
+
confirmations: 3,
|
|
25
|
+
status: "active",
|
|
26
|
+
});
|
|
27
|
+
expect(result.success).toBe(true);
|
|
28
|
+
});
|
|
29
|
+
|
|
30
|
+
it("rejects L0 entries with confirmations", () => {
|
|
31
|
+
const result = knowledgeEntryMetaSchema.safeParse({
|
|
32
|
+
id: "K-0003",
|
|
33
|
+
layer: "L0",
|
|
34
|
+
created: "2026-01-01",
|
|
35
|
+
confirmations: 1,
|
|
36
|
+
status: "active",
|
|
37
|
+
});
|
|
38
|
+
expect(result.success).toBe(false);
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
it("rejects L2 entries without confirmations", () => {
|
|
42
|
+
const result = knowledgeEntryMetaSchema.safeParse({
|
|
43
|
+
id: "K-0004",
|
|
44
|
+
layer: "L2",
|
|
45
|
+
created: "2026-01-01",
|
|
46
|
+
status: "active",
|
|
47
|
+
});
|
|
48
|
+
expect(result.success).toBe(false);
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
it("rejects invalid id format", () => {
|
|
52
|
+
const result = knowledgeEntryMetaSchema.safeParse({
|
|
53
|
+
id: "K-001",
|
|
54
|
+
layer: "L0",
|
|
55
|
+
created: "2026-01-01",
|
|
56
|
+
status: "active",
|
|
57
|
+
});
|
|
58
|
+
expect(result.success).toBe(false);
|
|
59
|
+
});
|
|
60
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./create.ts";
|
|
6
|
+
|
|
7
|
+
describe("onboarding/create (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./doctor.ts";
|
|
6
|
+
|
|
7
|
+
describe("onboarding/doctor (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./init.ts";
|
|
6
|
+
|
|
7
|
+
describe("onboarding/init (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./scaffold.ts";
|
|
6
|
+
|
|
7
|
+
describe("onboarding/scaffold (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./upgrade.ts";
|
|
6
|
+
|
|
7
|
+
describe("onboarding/upgrade (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./forge-plugin-manifest.ts";
|
|
6
|
+
|
|
7
|
+
describe("forge-plugin-manifest (load verification)", () => {
|
|
8
|
+
it("module loads and exports schema", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
expect(mod.forgePluginManifestSchema).toBeDefined();
|
|
11
|
+
});
|
|
12
|
+
});
|
|
@@ -882,6 +882,10 @@ declare module "@warpgogol/werkstatt-engine/fleet-module" {
|
|
|
882
882
|
export function createFleetModule(...args: any[]): any;
|
|
883
883
|
}
|
|
884
884
|
|
|
885
|
+
declare module "@warpgogol/werkstatt-engine/lagebild-module" {
|
|
886
|
+
export function createLagebildModule(...args: any[]): any;
|
|
887
|
+
}
|
|
888
|
+
|
|
885
889
|
declare module "@warpgogol/werkstatt-engine/subdomain-module" {
|
|
886
890
|
export function createSubdomainModule(...args: any[]): any;
|
|
887
891
|
}
|
|
@@ -215,6 +215,7 @@ declare module "@warpgogol/werkstatt-shared/integration" {
|
|
|
215
215
|
export const IngressOrigin: any;
|
|
216
216
|
export const ExplicitPolicyAssertion: any;
|
|
217
217
|
export const PolicyAssertionKind: any;
|
|
218
|
+
export const lagebildDestinationAdapter: any;
|
|
218
219
|
}
|
|
219
220
|
|
|
220
221
|
declare module "@warpgogol/werkstatt-shared/integration/port" {
|
|
@@ -552,11 +553,13 @@ declare module "@warpgogol/werkstatt-shared/share" {
|
|
|
552
553
|
export function splitMarkdownSections(...args: any[]): any;
|
|
553
554
|
export function extractParagraphs(...args: any[]): any;
|
|
554
555
|
export function splitSentences(...args: any[]): any;
|
|
556
|
+
export function extractLists(...args: any[]): any;
|
|
555
557
|
export function extractListFacts(...args: any[]): any;
|
|
556
558
|
export function extractEmail(...args: any[]): any;
|
|
557
559
|
export function extractPostalAddress(...args: any[]): any;
|
|
558
560
|
export function mergePeople(...args: any[]): any;
|
|
559
561
|
export type MarkdownSection = any;
|
|
562
|
+
export type MarkdownList = any;
|
|
560
563
|
export function getBaseUrl(...args: any[]): any;
|
|
561
564
|
export function toCanonicalUrl(...args: any[]): any;
|
|
562
565
|
export function toAbsoluteUrl(...args: any[]): any;
|
|
@@ -585,8 +588,11 @@ declare module "@warpgogol/werkstatt-shared/share" {
|
|
|
585
588
|
export function projectPeople(...args: any[]): any;
|
|
586
589
|
export function projectLocation(...args: any[]): any;
|
|
587
590
|
export function projectServices(...args: any[]): any;
|
|
591
|
+
export function projectClaims(...args: any[]): any;
|
|
588
592
|
export function projectWeb(...args: any[]): any;
|
|
589
593
|
export const BUSINESS_DOMAIN_VISIBILITY: any;
|
|
594
|
+
export interface SemanticClaimProvenance {}
|
|
595
|
+
export interface SemanticEvidenceRef {}
|
|
590
596
|
export type BusinessDomain = any;
|
|
591
597
|
export type BusinessVisibility = any;
|
|
592
598
|
export function buildOrganizationProfile(...args: any[]): any;
|
|
@@ -652,6 +658,15 @@ declare module "@warpgogol/werkstatt-shared/share" {
|
|
|
652
658
|
export const PRICE_MARKER_RE: any;
|
|
653
659
|
export const AMOUNT_MARKER_RE: any;
|
|
654
660
|
export interface DerivedPriceEntry {}
|
|
661
|
+
export function deriveCanonicalUri(...args: any[]): any;
|
|
662
|
+
export type CanonicalEntityType = any;
|
|
663
|
+
export function normalizeFactValue(...args: any[]): any;
|
|
664
|
+
export interface CanonicalFact {}
|
|
665
|
+
export function calculateAgeDays(...args: any[]): any;
|
|
666
|
+
export function isAssessmentStale(...args: any[]): any;
|
|
667
|
+
export function isItemStale(...args: any[]): any;
|
|
668
|
+
export const DEFAULT_FRESHNESS_WINDOW_DAYS: any;
|
|
669
|
+
export interface FreshnessViolation {}
|
|
655
670
|
export function createLanguageRedirectMiddleware(...args: any[]): any;
|
|
656
671
|
export function resolvePseoBudget(...args: any[]): any;
|
|
657
672
|
export function isValidFeature(...args: any[]): any;
|
|
@@ -1080,6 +1095,7 @@ declare module "@warpgogol/werkstatt-shared/share/agent" {
|
|
|
1080
1095
|
export const AGENT_SURFACE_VERSION: any;
|
|
1081
1096
|
export interface AgentKnowledgeRef {}
|
|
1082
1097
|
export interface AgentActionRef {}
|
|
1098
|
+
export interface AgentClaimRef {}
|
|
1083
1099
|
export interface AgentSurfaceManifest {}
|
|
1084
1100
|
export interface AgentSurfaceManifestInput {}
|
|
1085
1101
|
export function isAgentKnowledgeDomain(...args: any[]): any;
|
|
@@ -1507,8 +1523,10 @@ declare module "@warpgogol/werkstatt-shared/share/page" {
|
|
|
1507
1523
|
}
|
|
1508
1524
|
|
|
1509
1525
|
declare module "@warpgogol/werkstatt-shared/share/redirects" {
|
|
1526
|
+
export function buildPageRouteExclusionAlternation(...args: any[]): any;
|
|
1510
1527
|
export function parseRedirectRules(...args: any[]): any;
|
|
1511
1528
|
export function extractRedirectTarget(...args: any[]): any;
|
|
1529
|
+
export const PAGE_ROUTE_EXCLUDED_EXTENSIONS: any;
|
|
1512
1530
|
export type RedirectRule = any;
|
|
1513
1531
|
}
|
|
1514
1532
|
|
|
@@ -1518,6 +1536,17 @@ declare module "@warpgogol/werkstatt-shared/share/remediation" {
|
|
|
1518
1536
|
export interface RemediationPattern {}
|
|
1519
1537
|
}
|
|
1520
1538
|
|
|
1539
|
+
declare module "@warpgogol/werkstatt-shared/share/pbt" {
|
|
1540
|
+
export function fcAssert(...args: any[]): any;
|
|
1541
|
+
export function letterString(...args: any[]): any;
|
|
1542
|
+
export function composeWord(...args: any[]): any;
|
|
1543
|
+
export function safeText(...args: any[]): any;
|
|
1544
|
+
export const DEFAULT_NUM_RUNS: any;
|
|
1545
|
+
export const DEFAULT_MAX_SKIPS_PER_RUN: any;
|
|
1546
|
+
export interface FcAssertOptions {}
|
|
1547
|
+
export interface ComposeWordOptions {}
|
|
1548
|
+
}
|
|
1549
|
+
|
|
1521
1550
|
declare module "@warpgogol/werkstatt-shared/share/rfc0042-utils" {
|
|
1522
1551
|
export function need(...args: any[]): any;
|
|
1523
1552
|
export function cast(...args: any[]): any;
|
|
@@ -1958,11 +1987,13 @@ declare module "@warpgogol/werkstatt-shared/share/semantic" {
|
|
|
1958
1987
|
export function splitMarkdownSections(...args: any[]): any;
|
|
1959
1988
|
export function extractParagraphs(...args: any[]): any;
|
|
1960
1989
|
export function splitSentences(...args: any[]): any;
|
|
1990
|
+
export function extractLists(...args: any[]): any;
|
|
1961
1991
|
export function extractListFacts(...args: any[]): any;
|
|
1962
1992
|
export function extractEmail(...args: any[]): any;
|
|
1963
1993
|
export function extractPostalAddress(...args: any[]): any;
|
|
1964
1994
|
export function mergePeople(...args: any[]): any;
|
|
1965
1995
|
export type MarkdownSection = any;
|
|
1996
|
+
export type MarkdownList = any;
|
|
1966
1997
|
export function getBaseUrl(...args: any[]): any;
|
|
1967
1998
|
export function toCanonicalUrl(...args: any[]): any;
|
|
1968
1999
|
export function toAbsoluteUrl(...args: any[]): any;
|
|
@@ -1991,8 +2022,11 @@ declare module "@warpgogol/werkstatt-shared/share/semantic" {
|
|
|
1991
2022
|
export function projectPeople(...args: any[]): any;
|
|
1992
2023
|
export function projectLocation(...args: any[]): any;
|
|
1993
2024
|
export function projectServices(...args: any[]): any;
|
|
2025
|
+
export function projectClaims(...args: any[]): any;
|
|
1994
2026
|
export function projectWeb(...args: any[]): any;
|
|
1995
2027
|
export const BUSINESS_DOMAIN_VISIBILITY: any;
|
|
2028
|
+
export interface SemanticClaimProvenance {}
|
|
2029
|
+
export interface SemanticEvidenceRef {}
|
|
1996
2030
|
export type BusinessDomain = any;
|
|
1997
2031
|
export type BusinessVisibility = any;
|
|
1998
2032
|
export function buildOrganizationProfile(...args: any[]): any;
|
|
@@ -2058,12 +2092,39 @@ declare module "@warpgogol/werkstatt-shared/share/semantic" {
|
|
|
2058
2092
|
export const PRICE_MARKER_RE: any;
|
|
2059
2093
|
export const AMOUNT_MARKER_RE: any;
|
|
2060
2094
|
export interface DerivedPriceEntry {}
|
|
2095
|
+
export function deriveCanonicalUri(...args: any[]): any;
|
|
2096
|
+
export type CanonicalEntityType = any;
|
|
2097
|
+
export function normalizeFactValue(...args: any[]): any;
|
|
2098
|
+
export interface CanonicalFact {}
|
|
2099
|
+
export function calculateAgeDays(...args: any[]): any;
|
|
2100
|
+
export function isAssessmentStale(...args: any[]): any;
|
|
2101
|
+
export function isItemStale(...args: any[]): any;
|
|
2102
|
+
export const DEFAULT_FRESHNESS_WINDOW_DAYS: any;
|
|
2103
|
+
export interface FreshnessViolation {}
|
|
2061
2104
|
}
|
|
2062
2105
|
|
|
2063
2106
|
declare module "@warpgogol/werkstatt-shared/share/semantic/derived-prices-loader" {
|
|
2064
2107
|
export function loadDerivedPrices(...args: any[]): any;
|
|
2065
2108
|
}
|
|
2066
2109
|
|
|
2110
|
+
declare module "@warpgogol/werkstatt-shared/share/semantic/canonical-uri" {
|
|
2111
|
+
export function deriveCanonicalUri(...args: any[]): any;
|
|
2112
|
+
export type CanonicalEntityType = any;
|
|
2113
|
+
}
|
|
2114
|
+
|
|
2115
|
+
declare module "@warpgogol/werkstatt-shared/share/semantic/fact-extraction" {
|
|
2116
|
+
export function normalizeFactValue(...args: any[]): any;
|
|
2117
|
+
export interface CanonicalFact {}
|
|
2118
|
+
}
|
|
2119
|
+
|
|
2120
|
+
declare module "@warpgogol/werkstatt-shared/share/semantic/freshness" {
|
|
2121
|
+
export function calculateAgeDays(...args: any[]): any;
|
|
2122
|
+
export function isAssessmentStale(...args: any[]): any;
|
|
2123
|
+
export function isItemStale(...args: any[]): any;
|
|
2124
|
+
export const DEFAULT_FRESHNESS_WINDOW_DAYS: any;
|
|
2125
|
+
export interface FreshnessViolation {}
|
|
2126
|
+
}
|
|
2127
|
+
|
|
2067
2128
|
declare module "@warpgogol/werkstatt-shared/share/shared-context" {
|
|
2068
2129
|
export function buildSharedContextPageOrder(...args: any[]): any;
|
|
2069
2130
|
export function collectSharedContextCandidatesByLevel(...args: any[]): any;
|
|
@@ -2109,6 +2170,37 @@ declare module "@warpgogol/werkstatt-shared/share/text-normalize" {
|
|
|
2109
2170
|
export type NormalizableKind = any;
|
|
2110
2171
|
}
|
|
2111
2172
|
|
|
2173
|
+
declare module "@warpgogol/werkstatt-shared/share/typography" {
|
|
2174
|
+
export const extractTextSurface: any;
|
|
2175
|
+
export const TECHNICAL_KEYS: any;
|
|
2176
|
+
export const deriveFileLocale: any;
|
|
2177
|
+
export const TextSegment: any;
|
|
2178
|
+
export const TextSegmentSource: any;
|
|
2179
|
+
export const TextSurfaceOptions: any;
|
|
2180
|
+
export const YamlError: any;
|
|
2181
|
+
export const ExtractTextSurfaceResult: any;
|
|
2182
|
+
export const TIER1_RULES: any;
|
|
2183
|
+
export const DEFAULT_ALLOWED_TOKENS: any;
|
|
2184
|
+
export const createTypographyContext: any;
|
|
2185
|
+
export const TypographyRuleId: any;
|
|
2186
|
+
export const TypographyRuleFamily: any;
|
|
2187
|
+
export const TypographyFinding: any;
|
|
2188
|
+
export const TypographyRule: any;
|
|
2189
|
+
export const TypographyContext: any;
|
|
2190
|
+
export const TIER2_STRUCTURE_RULES: any;
|
|
2191
|
+
export const TIER2_LOCALE_RULES: any;
|
|
2192
|
+
export const Tier2LocaleRuleId: any;
|
|
2193
|
+
export const TIER3_ADVISORY_RULES: any;
|
|
2194
|
+
export const Tier3AdvisoryRuleId: any;
|
|
2195
|
+
export const LOCALE_DEFAULTS: any;
|
|
2196
|
+
export const getLocaleDefaults: any;
|
|
2197
|
+
export const LocaleTypographyDefaults: any;
|
|
2198
|
+
export const FixAction: any;
|
|
2199
|
+
export const FIXABLE_RULE_IDS: any;
|
|
2200
|
+
export const isFixable: any;
|
|
2201
|
+
export const applyFixes: any;
|
|
2202
|
+
}
|
|
2203
|
+
|
|
2112
2204
|
declare module "@warpgogol/werkstatt-shared/share/text-position" {
|
|
2113
2205
|
export function getLineColumn(...args: any[]): any;
|
|
2114
2206
|
}
|
|
@@ -2288,8 +2380,6 @@ declare module "@warpgogol/werkstatt-shared/index" {
|
|
|
2288
2380
|
declare module "@warpgogol/werkstatt-shared/integration/adapters" {
|
|
2289
2381
|
export const telegramChannelAdapter: any;
|
|
2290
2382
|
export const whatsappChannelAdapter: any;
|
|
2291
|
-
export const pipedriveCrmAdapter: any;
|
|
2292
|
-
export const pipedriveDestinationAdapter: any;
|
|
2293
2383
|
}
|
|
2294
2384
|
|
|
2295
2385
|
declare module "@warpgogol/werkstatt-shared/integration/dispatch" {
|
|
@@ -2421,6 +2511,7 @@ declare module "@warpgogol/werkstatt-shared/integration/index" {
|
|
|
2421
2511
|
export const IngressOrigin: any;
|
|
2422
2512
|
export const ExplicitPolicyAssertion: any;
|
|
2423
2513
|
export const PolicyAssertionKind: any;
|
|
2514
|
+
export const lagebildDestinationAdapter: any;
|
|
2424
2515
|
}
|
|
2425
2516
|
|
|
2426
2517
|
declare module "@warpgogol/werkstatt-shared/integration/lifecycle" {
|
|
@@ -2960,6 +3051,7 @@ declare module "@warpgogol/werkstatt-shared/ontology/schemas/system/release" {
|
|
|
2960
3051
|
declare module "@warpgogol/werkstatt-shared/ontology/schemas/system/text" {
|
|
2961
3052
|
export const systemTextNormalizeSignalsSchema: any;
|
|
2962
3053
|
export const systemTextNormalizeSchema: any;
|
|
3054
|
+
export const systemTypographySchema: any;
|
|
2963
3055
|
export const systemTextSchema: any;
|
|
2964
3056
|
export type SystemText = any;
|
|
2965
3057
|
}
|
|
@@ -3107,6 +3199,7 @@ declare module "@warpgogol/werkstatt-shared/share/agent/index" {
|
|
|
3107
3199
|
export const AGENT_SURFACE_VERSION: any;
|
|
3108
3200
|
export interface AgentKnowledgeRef {}
|
|
3109
3201
|
export interface AgentActionRef {}
|
|
3202
|
+
export interface AgentClaimRef {}
|
|
3110
3203
|
export interface AgentSurfaceManifest {}
|
|
3111
3204
|
export interface AgentSurfaceManifestInput {}
|
|
3112
3205
|
export function isAgentKnowledgeDomain(...args: any[]): any;
|
|
@@ -3185,6 +3278,7 @@ declare module "@warpgogol/werkstatt-shared/share/agent/manifest" {
|
|
|
3185
3278
|
export const AGENT_SURFACE_VERSION: any;
|
|
3186
3279
|
export interface AgentKnowledgeRef {}
|
|
3187
3280
|
export interface AgentActionRef {}
|
|
3281
|
+
export interface AgentClaimRef {}
|
|
3188
3282
|
export interface AgentSurfaceManifest {}
|
|
3189
3283
|
export interface AgentSurfaceManifestInput {}
|
|
3190
3284
|
}
|
|
@@ -3330,8 +3424,6 @@ declare module "@warpgogol/werkstatt-shared/share/env.d" {
|
|
|
3330
3424
|
export const INTEGRATION_WHATSAPP_TOKEN: any;
|
|
3331
3425
|
export const INTEGRATION_WHATSAPP_PHONE_ID: any;
|
|
3332
3426
|
export const INTEGRATION_WHATSAPP_TO: any;
|
|
3333
|
-
export const INTEGRATION_PIPEDRIVE_API_TOKEN: any;
|
|
3334
|
-
export const INTEGRATION_PIPEDRIVE_DOMAIN: any;
|
|
3335
3427
|
export const INTEGRATION_INBOUND_SECRET: any;
|
|
3336
3428
|
export const UPSTASH_QSTASH_URL: any;
|
|
3337
3429
|
export const UPSTASH_QSTASH_TOKEN: any;
|
|
@@ -3408,11 +3500,13 @@ declare module "@warpgogol/werkstatt-shared/share/index" {
|
|
|
3408
3500
|
export function splitMarkdownSections(...args: any[]): any;
|
|
3409
3501
|
export function extractParagraphs(...args: any[]): any;
|
|
3410
3502
|
export function splitSentences(...args: any[]): any;
|
|
3503
|
+
export function extractLists(...args: any[]): any;
|
|
3411
3504
|
export function extractListFacts(...args: any[]): any;
|
|
3412
3505
|
export function extractEmail(...args: any[]): any;
|
|
3413
3506
|
export function extractPostalAddress(...args: any[]): any;
|
|
3414
3507
|
export function mergePeople(...args: any[]): any;
|
|
3415
3508
|
export type MarkdownSection = any;
|
|
3509
|
+
export type MarkdownList = any;
|
|
3416
3510
|
export function getBaseUrl(...args: any[]): any;
|
|
3417
3511
|
export function toCanonicalUrl(...args: any[]): any;
|
|
3418
3512
|
export function toAbsoluteUrl(...args: any[]): any;
|
|
@@ -3441,8 +3535,11 @@ declare module "@warpgogol/werkstatt-shared/share/index" {
|
|
|
3441
3535
|
export function projectPeople(...args: any[]): any;
|
|
3442
3536
|
export function projectLocation(...args: any[]): any;
|
|
3443
3537
|
export function projectServices(...args: any[]): any;
|
|
3538
|
+
export function projectClaims(...args: any[]): any;
|
|
3444
3539
|
export function projectWeb(...args: any[]): any;
|
|
3445
3540
|
export const BUSINESS_DOMAIN_VISIBILITY: any;
|
|
3541
|
+
export interface SemanticClaimProvenance {}
|
|
3542
|
+
export interface SemanticEvidenceRef {}
|
|
3446
3543
|
export type BusinessDomain = any;
|
|
3447
3544
|
export type BusinessVisibility = any;
|
|
3448
3545
|
export function buildOrganizationProfile(...args: any[]): any;
|
|
@@ -3508,6 +3605,15 @@ declare module "@warpgogol/werkstatt-shared/share/index" {
|
|
|
3508
3605
|
export const PRICE_MARKER_RE: any;
|
|
3509
3606
|
export const AMOUNT_MARKER_RE: any;
|
|
3510
3607
|
export interface DerivedPriceEntry {}
|
|
3608
|
+
export function deriveCanonicalUri(...args: any[]): any;
|
|
3609
|
+
export type CanonicalEntityType = any;
|
|
3610
|
+
export function normalizeFactValue(...args: any[]): any;
|
|
3611
|
+
export interface CanonicalFact {}
|
|
3612
|
+
export function calculateAgeDays(...args: any[]): any;
|
|
3613
|
+
export function isAssessmentStale(...args: any[]): any;
|
|
3614
|
+
export function isItemStale(...args: any[]): any;
|
|
3615
|
+
export const DEFAULT_FRESHNESS_WINDOW_DAYS: any;
|
|
3616
|
+
export interface FreshnessViolation {}
|
|
3511
3617
|
export function createLanguageRedirectMiddleware(...args: any[]): any;
|
|
3512
3618
|
export function resolvePseoBudget(...args: any[]): any;
|
|
3513
3619
|
export function isValidFeature(...args: any[]): any;
|
|
@@ -4443,6 +4549,8 @@ declare module "@warpgogol/werkstatt-shared/share/scripts/index" {
|
|
|
4443
4549
|
export function initLenis(...args: any[]): any;
|
|
4444
4550
|
export type LenisInstance = any;
|
|
4445
4551
|
export type InitLenisOptions = any;
|
|
4552
|
+
export function initScrollSpy(...args: any[]): any;
|
|
4553
|
+
export interface ScrollSpyOptions {}
|
|
4446
4554
|
export function runStandardLayoutOrchestration(...args: any[]): any;
|
|
4447
4555
|
export interface OrchestrationOptions {}
|
|
4448
4556
|
}
|
|
@@ -4521,8 +4629,11 @@ declare module "@warpgogol/werkstatt-shared/share/semantic/business-projection"
|
|
|
4521
4629
|
export function projectPeople(...args: any[]): any;
|
|
4522
4630
|
export function projectLocation(...args: any[]): any;
|
|
4523
4631
|
export function projectServices(...args: any[]): any;
|
|
4632
|
+
export function projectClaims(...args: any[]): any;
|
|
4524
4633
|
export function projectWeb(...args: any[]): any;
|
|
4525
4634
|
export const BUSINESS_DOMAIN_VISIBILITY: any;
|
|
4635
|
+
export interface SemanticClaimProvenance {}
|
|
4636
|
+
export interface SemanticEvidenceRef {}
|
|
4526
4637
|
export type BusinessDomain = any;
|
|
4527
4638
|
export type BusinessVisibility = any;
|
|
4528
4639
|
}
|
|
@@ -4532,11 +4643,13 @@ declare module "@warpgogol/werkstatt-shared/share/semantic/extract" {
|
|
|
4532
4643
|
export function splitMarkdownSections(...args: any[]): any;
|
|
4533
4644
|
export function extractParagraphs(...args: any[]): any;
|
|
4534
4645
|
export function splitSentences(...args: any[]): any;
|
|
4646
|
+
export function extractLists(...args: any[]): any;
|
|
4535
4647
|
export function extractListFacts(...args: any[]): any;
|
|
4536
4648
|
export function extractEmail(...args: any[]): any;
|
|
4537
4649
|
export function extractPostalAddress(...args: any[]): any;
|
|
4538
4650
|
export function mergePeople(...args: any[]): any;
|
|
4539
4651
|
export type MarkdownSection = any;
|
|
4652
|
+
export type MarkdownList = any;
|
|
4540
4653
|
}
|
|
4541
4654
|
|
|
4542
4655
|
declare module "@warpgogol/werkstatt-shared/share/semantic/feed" {
|
|
@@ -4607,11 +4720,13 @@ declare module "@warpgogol/werkstatt-shared/share/semantic/index" {
|
|
|
4607
4720
|
export function splitMarkdownSections(...args: any[]): any;
|
|
4608
4721
|
export function extractParagraphs(...args: any[]): any;
|
|
4609
4722
|
export function splitSentences(...args: any[]): any;
|
|
4723
|
+
export function extractLists(...args: any[]): any;
|
|
4610
4724
|
export function extractListFacts(...args: any[]): any;
|
|
4611
4725
|
export function extractEmail(...args: any[]): any;
|
|
4612
4726
|
export function extractPostalAddress(...args: any[]): any;
|
|
4613
4727
|
export function mergePeople(...args: any[]): any;
|
|
4614
4728
|
export type MarkdownSection = any;
|
|
4729
|
+
export type MarkdownList = any;
|
|
4615
4730
|
export function getBaseUrl(...args: any[]): any;
|
|
4616
4731
|
export function toCanonicalUrl(...args: any[]): any;
|
|
4617
4732
|
export function toAbsoluteUrl(...args: any[]): any;
|
|
@@ -4640,8 +4755,11 @@ declare module "@warpgogol/werkstatt-shared/share/semantic/index" {
|
|
|
4640
4755
|
export function projectPeople(...args: any[]): any;
|
|
4641
4756
|
export function projectLocation(...args: any[]): any;
|
|
4642
4757
|
export function projectServices(...args: any[]): any;
|
|
4758
|
+
export function projectClaims(...args: any[]): any;
|
|
4643
4759
|
export function projectWeb(...args: any[]): any;
|
|
4644
4760
|
export const BUSINESS_DOMAIN_VISIBILITY: any;
|
|
4761
|
+
export interface SemanticClaimProvenance {}
|
|
4762
|
+
export interface SemanticEvidenceRef {}
|
|
4645
4763
|
export type BusinessDomain = any;
|
|
4646
4764
|
export type BusinessVisibility = any;
|
|
4647
4765
|
export function buildOrganizationProfile(...args: any[]): any;
|
|
@@ -4707,6 +4825,15 @@ declare module "@warpgogol/werkstatt-shared/share/semantic/index" {
|
|
|
4707
4825
|
export const PRICE_MARKER_RE: any;
|
|
4708
4826
|
export const AMOUNT_MARKER_RE: any;
|
|
4709
4827
|
export interface DerivedPriceEntry {}
|
|
4828
|
+
export function deriveCanonicalUri(...args: any[]): any;
|
|
4829
|
+
export type CanonicalEntityType = any;
|
|
4830
|
+
export function normalizeFactValue(...args: any[]): any;
|
|
4831
|
+
export interface CanonicalFact {}
|
|
4832
|
+
export function calculateAgeDays(...args: any[]): any;
|
|
4833
|
+
export function isAssessmentStale(...args: any[]): any;
|
|
4834
|
+
export function isItemStale(...args: any[]): any;
|
|
4835
|
+
export const DEFAULT_FRESHNESS_WINDOW_DAYS: any;
|
|
4836
|
+
export interface FreshnessViolation {}
|
|
4710
4837
|
}
|
|
4711
4838
|
|
|
4712
4839
|
declare module "@warpgogol/werkstatt-shared/share/semantic/jsonld/article" {
|
|
@@ -5536,6 +5663,8 @@ declare module "@warpgogol/werkstatt-shared/share/scripts" {
|
|
|
5536
5663
|
export function initLenis(...args: any[]): any;
|
|
5537
5664
|
export type LenisInstance = any;
|
|
5538
5665
|
export type InitLenisOptions = any;
|
|
5666
|
+
export function initScrollSpy(...args: any[]): any;
|
|
5667
|
+
export interface ScrollSpyOptions {}
|
|
5539
5668
|
export function runStandardLayoutOrchestration(...args: any[]): any;
|
|
5540
5669
|
export interface OrchestrationOptions {}
|
|
5541
5670
|
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./fs-atomic.ts";
|
|
6
|
+
|
|
7
|
+
describe("utils/fs-atomic (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./fs-trash-sync.ts";
|
|
6
|
+
|
|
7
|
+
describe("utils/fs-trash-sync (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import * as mod from "./generated-marker.ts";
|
|
6
|
+
|
|
7
|
+
describe("utils/generated-marker (load verification)", () => {
|
|
8
|
+
it("module loads successfully", () => {
|
|
9
|
+
expect(mod).toBeDefined();
|
|
10
|
+
});
|
|
11
|
+
});
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import { byteHash } from "./hash.ts";
|
|
6
|
+
|
|
7
|
+
describe("byteHash", () => {
|
|
8
|
+
it("produces a sha256-prefixed hex digest for a string", () => {
|
|
9
|
+
const hash = byteHash("test");
|
|
10
|
+
expect(hash).toMatch(/^sha256:[0-9a-f]{64}$/);
|
|
11
|
+
});
|
|
12
|
+
|
|
13
|
+
it("produces a sha256-prefixed hex digest for bytes", () => {
|
|
14
|
+
const hash = byteHash(new Uint8Array([1, 2, 3]));
|
|
15
|
+
expect(hash).toMatch(/^sha256:[0-9a-f]{64}$/);
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
it("is deterministic for same input", () => {
|
|
19
|
+
expect(byteHash("abc")).toBe(byteHash("abc"));
|
|
20
|
+
});
|
|
21
|
+
|
|
22
|
+
it("produces different hashes for different inputs", () => {
|
|
23
|
+
expect(byteHash("abc")).not.toBe(byteHash("abd"));
|
|
24
|
+
});
|
|
25
|
+
});
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
// @vitest-environment node
|
|
2
|
+
|
|
3
|
+
import { describe, expect, it } from "vitest";
|
|
4
|
+
|
|
5
|
+
import { toKebabCase } from "./string-utils.ts";
|
|
6
|
+
|
|
7
|
+
describe("toKebabCase", () => {
|
|
8
|
+
it("converts spaces to hyphens", () => {
|
|
9
|
+
expect(toKebabCase("hello world")).toBe("hello-world");
|
|
10
|
+
});
|
|
11
|
+
|
|
12
|
+
it("removes special characters", () => {
|
|
13
|
+
expect(toKebabCase("hello!@#world")).toBe("hello-world");
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
it("trims leading and trailing hyphens", () => {
|
|
17
|
+
expect(toKebabCase("---hello---")).toBe("hello");
|
|
18
|
+
});
|
|
19
|
+
|
|
20
|
+
it("handles empty string", () => {
|
|
21
|
+
expect(toKebabCase("")).toBe("");
|
|
22
|
+
});
|
|
23
|
+
});
|