arkgate 2.1.0

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.
Files changed (64) hide show
  1. package/CHANGELOG.md +1249 -0
  2. package/LICENSE +21 -0
  3. package/README.md +218 -0
  4. package/SECURITY.md +39 -0
  5. package/bin/ark-check.mjs +5204 -0
  6. package/bin/ark-mcp.mjs +898 -0
  7. package/bin/ark-shared.mjs +1520 -0
  8. package/bin/ark.mjs +491 -0
  9. package/dist/eslint/index.cjs +222 -0
  10. package/dist/eslint/index.cjs.map +1 -0
  11. package/dist/eslint/index.d.cts +42 -0
  12. package/dist/eslint/index.d.ts +40 -0
  13. package/dist/eslint/index.js +193 -0
  14. package/dist/eslint/index.js.map +1 -0
  15. package/dist/index.cjs +3080 -0
  16. package/dist/index.cjs.map +1 -0
  17. package/dist/index.d.cts +577 -0
  18. package/dist/index.d.ts +577 -0
  19. package/dist/index.js +2998 -0
  20. package/dist/index.js.map +1 -0
  21. package/dist/nestjs/index.cjs +2332 -0
  22. package/dist/nestjs/index.cjs.map +1 -0
  23. package/dist/nestjs/index.d.cts +22 -0
  24. package/dist/nestjs/index.d.ts +22 -0
  25. package/dist/nestjs/index.js +2308 -0
  26. package/dist/nestjs/index.js.map +1 -0
  27. package/dist/types-DpdVN7Lm.d.cts +1023 -0
  28. package/dist/types-DpdVN7Lm.d.ts +1023 -0
  29. package/docs/agent-guide.md +490 -0
  30. package/docs/ai-gates.md +337 -0
  31. package/docs/ark-check-example.json +87 -0
  32. package/docs/assets/ark-write-gate.svg +28 -0
  33. package/docs/brownfield-adoption.md +87 -0
  34. package/docs/demos/01-write-gate-self-correction.md +74 -0
  35. package/docs/demos/02-brownfield-baseline-adoption.md +71 -0
  36. package/docs/demos/03-copilot-autopilot.md +83 -0
  37. package/docs/enthusiast/README.md +62 -0
  38. package/docs/enthusiast/explanation-application-shape.md +29 -0
  39. package/docs/enthusiast/how-to-agent-gates.md +36 -0
  40. package/docs/enthusiast/how-to-gallery-starter.md +27 -0
  41. package/docs/enthusiast/how-to-pick-shape.md +45 -0
  42. package/docs/enthusiast/how-to-policy-pack.md +37 -0
  43. package/docs/enthusiast/reference-archetypes.md +36 -0
  44. package/docs/enthusiast/reference-commands.md +50 -0
  45. package/docs/enthusiast/tutorial-first-project.md +86 -0
  46. package/docs/production-hardening.md +59 -0
  47. package/package.json +125 -0
  48. package/server.json +39 -0
  49. package/templates/architecture-playbook.json +339 -0
  50. package/templates/policy-packs/enthusiast-feature-sliced.json +20 -0
  51. package/templates/policy-packs/enthusiast-hexagonal.json +18 -0
  52. package/templates/policy-packs/enthusiast-layered.json +18 -0
  53. package/templates/policy-packs/enthusiast-monorepo.json +18 -0
  54. package/templates/skills/ark-adopt.md +103 -0
  55. package/templates/skills/ark-architect.md +90 -0
  56. package/templates/skills/ark-autopilot.md +95 -0
  57. package/templates/skills/ark-contract.md +98 -0
  58. package/templates/skills/ark-coverage.md +96 -0
  59. package/templates/skills/ark-explain.md +78 -0
  60. package/templates/skills/ark-fix.md +96 -0
  61. package/templates/skills/ark-loop.md +69 -0
  62. package/templates/skills/ark-place.md +68 -0
  63. package/templates/skills/ark-runtime.md +62 -0
  64. package/templates/skills/ark-upgrade.md +109 -0
@@ -0,0 +1,222 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/eslint/index.ts
21
+ var eslint_exports = {};
22
+ __export(eslint_exports, {
23
+ default: () => eslint_default,
24
+ noDomainInfraImports: () => noDomainInfraImports,
25
+ noForbiddenGlobals: () => noForbiddenGlobals,
26
+ noRawEventPublish: () => noRawEventPublish,
27
+ plugin: () => plugin,
28
+ requirePublishSource: () => requirePublishSource
29
+ });
30
+ module.exports = __toCommonJS(eslint_exports);
31
+ function stringValue(node) {
32
+ return typeof node?.value === "string" ? node.value : void 0;
33
+ }
34
+ function propertyName(node) {
35
+ return node?.name ?? stringValue(node);
36
+ }
37
+ function calleePropertyName(node) {
38
+ return propertyName(node.callee?.property);
39
+ }
40
+ function objectProperty(node, name) {
41
+ return node?.properties?.find((property) => propertyName(property.key) === name);
42
+ }
43
+ function objectHasProperty(node, name) {
44
+ return objectProperty(node, name) !== void 0;
45
+ }
46
+ function objectHasMetadataSource(node) {
47
+ const metadata = objectProperty(node, "metadata")?.value;
48
+ return objectHasProperty(metadata, "source");
49
+ }
50
+ function looksLikeIntent(value) {
51
+ return /^(Domain|Application|Adapter|Workflow|Job|Presentation|Reporting|Metadata|Security|Audit|Observability|Kernel)\.[A-Za-z0-9_.]+$/.test(value);
52
+ }
53
+ function isDomainFile(context) {
54
+ const filename = context.getFilename?.() ?? "";
55
+ const normalized = filename.split("\\").join("/").toLowerCase();
56
+ return normalized.includes("/domain/") || normalized.endsWith("/domain.ts");
57
+ }
58
+ function isInfraImport(specifier) {
59
+ const normalized = specifier.toLowerCase();
60
+ return [
61
+ "adapter",
62
+ "adapters",
63
+ "infrastructure",
64
+ "persistence",
65
+ "repository",
66
+ "repositories",
67
+ "integration",
68
+ "database",
69
+ "db"
70
+ ].some((token) => normalized.includes(token));
71
+ }
72
+ function isPublishCall(node) {
73
+ return calleePropertyName(node) === "publish";
74
+ }
75
+ var noDomainInfraImports = {
76
+ meta: {
77
+ type: "problem",
78
+ docs: {
79
+ description: "Disallow importing infrastructure or adapters from domain files."
80
+ },
81
+ messages: {
82
+ forbiddenImport: "Domain code must not import infrastructure, adapters, repositories, or database modules."
83
+ },
84
+ schema: []
85
+ },
86
+ create(context) {
87
+ const check = (node) => {
88
+ if (!isDomainFile(context)) return;
89
+ const source = stringValue(node.source);
90
+ if (source && isInfraImport(source)) {
91
+ context.report({ node, messageId: "forbiddenImport" });
92
+ }
93
+ };
94
+ return {
95
+ ImportDeclaration: check,
96
+ ExportNamedDeclaration: check,
97
+ ExportAllDeclaration: check
98
+ };
99
+ }
100
+ };
101
+ var noRawEventPublish = {
102
+ meta: {
103
+ type: "problem",
104
+ docs: {
105
+ description: "Require event bus publish calls to use registered intent creators instead of raw event objects or intent strings."
106
+ },
107
+ messages: {
108
+ rawPublish: "Publish through a registered intent creator; raw event objects or intent strings bypass Ark contracts."
109
+ },
110
+ schema: []
111
+ },
112
+ create(context) {
113
+ return {
114
+ CallExpression(node) {
115
+ if (!isPublishCall(node)) return;
116
+ const firstArg = node.arguments?.[0];
117
+ const firstValue = stringValue(firstArg);
118
+ if (firstValue && looksLikeIntent(firstValue) || objectHasProperty(firstArg, "intent")) {
119
+ context.report({ node, messageId: "rawPublish" });
120
+ }
121
+ }
122
+ };
123
+ }
124
+ };
125
+ var requirePublishSource = {
126
+ meta: {
127
+ type: "problem",
128
+ docs: {
129
+ description: "Require event bus publish calls to include source metadata."
130
+ },
131
+ messages: {
132
+ missingSource: "Strict Ark publish calls must include metadata.source."
133
+ },
134
+ schema: []
135
+ },
136
+ create(context) {
137
+ return {
138
+ CallExpression(node) {
139
+ if (!isPublishCall(node)) return;
140
+ const firstArg = node.arguments?.[0];
141
+ const metadataArg = node.arguments?.[2];
142
+ if (objectHasMetadataSource(firstArg) || objectHasProperty(metadataArg, "source")) {
143
+ return;
144
+ }
145
+ context.report({ node, messageId: "missingSource" });
146
+ }
147
+ };
148
+ }
149
+ };
150
+ var DEFAULT_FORBIDDEN_GLOBALS = ["fetch", "process", "Date.now", "Math.random"];
151
+ var noForbiddenGlobals = {
152
+ meta: {
153
+ type: "problem",
154
+ docs: {
155
+ description: 'Disallow ambient globals (e.g. fetch, Date.now) in architecture-governed code; scope the rule to layer directories via ESLint "files" patterns.'
156
+ },
157
+ messages: {
158
+ forbiddenGlobal: 'Ambient global "{{name}}" is forbidden here; inject the capability through a port instead.'
159
+ },
160
+ schema: [
161
+ {
162
+ type: "object",
163
+ properties: {
164
+ globals: { type: "array", items: { type: "string" } }
165
+ },
166
+ additionalProperties: false
167
+ }
168
+ ]
169
+ },
170
+ create(context) {
171
+ const option = context.options?.[0];
172
+ const globals = new Set(option?.globals ?? DEFAULT_FORBIDDEN_GLOBALS);
173
+ const report = (node, name) => context.report({ node, messageId: "forbiddenGlobal", data: { name } });
174
+ return {
175
+ // Same positional detection as ark-check's FORBIDDEN_GLOBAL: property accesses on a
176
+ // forbidden base (console.log, Date.now), direct calls, and constructions. Bare
177
+ // identifier mentions elsewhere are not flagged (avoids shadowed-local false positives).
178
+ MemberExpression(node) {
179
+ const base = node.object?.type === "Identifier" ? node.object.name : void 0;
180
+ if (!base) return;
181
+ const dotted = `${base}.${propertyName(node.property) ?? ""}`;
182
+ if (globals.has(dotted)) report(node, dotted);
183
+ else if (globals.has(base)) report(node, base);
184
+ },
185
+ CallExpression(node) {
186
+ const callee = node.callee?.type === "Identifier" ? node.callee.name : void 0;
187
+ if (callee && globals.has(callee)) report(node, callee);
188
+ },
189
+ NewExpression(node) {
190
+ const callee = node.callee?.type === "Identifier" ? node.callee.name : void 0;
191
+ if (callee && globals.has(callee)) report(node, callee);
192
+ }
193
+ };
194
+ }
195
+ };
196
+ var rules = {
197
+ "no-domain-infra-imports": noDomainInfraImports,
198
+ "no-raw-event-publish": noRawEventPublish,
199
+ "require-publish-source": requirePublishSource,
200
+ "no-forbidden-globals": noForbiddenGlobals
201
+ };
202
+ var plugin = { rules };
203
+ plugin.configs = {
204
+ recommended: {
205
+ plugins: { ark: plugin },
206
+ rules: {
207
+ "ark/no-domain-infra-imports": "error",
208
+ "ark/no-raw-event-publish": "error",
209
+ "ark/require-publish-source": "error"
210
+ }
211
+ }
212
+ };
213
+ var eslint_default = plugin;
214
+ // Annotate the CommonJS export names for ESM import in node:
215
+ 0 && (module.exports = {
216
+ noDomainInfraImports,
217
+ noForbiddenGlobals,
218
+ noRawEventPublish,
219
+ plugin,
220
+ requirePublishSource
221
+ });
222
+ //# sourceMappingURL=index.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/eslint/index.ts"],"sourcesContent":["type RuleContext = {\n report(descriptor: Record<string, unknown>): void;\n getFilename?: () => string;\n options?: unknown[];\n};\n\ntype RuleListener = Record<string, (node: AstNode) => void>;\n\ntype AstNode = {\n type?: string;\n name?: string;\n value?: unknown;\n source?: AstNode;\n callee?: AstNode;\n object?: AstNode;\n property?: AstNode;\n key?: AstNode;\n arguments?: AstNode[];\n properties?: AstNode[];\n};\n\ntype ArkRule = {\n meta: {\n type: 'problem';\n docs: { description: string };\n messages: Record<string, string>;\n schema: unknown[];\n };\n create(context: RuleContext): RuleListener;\n};\n\ntype ArkEslintPlugin = {\n rules: Record<string, ArkRule>;\n configs?: Record<string, unknown>;\n};\n\nfunction stringValue(node: AstNode | undefined): string | undefined {\n return typeof node?.value === 'string' ? node.value : undefined;\n}\n\nfunction propertyName(node: AstNode | undefined): string | undefined {\n return node?.name ?? stringValue(node);\n}\n\nfunction calleePropertyName(node: AstNode): string | undefined {\n return propertyName(node.callee?.property);\n}\n\nfunction objectProperty(node: AstNode | undefined, name: string): AstNode | undefined {\n return node?.properties?.find((property) => propertyName(property.key) === name);\n}\n\nfunction objectHasProperty(node: AstNode | undefined, name: string): boolean {\n return objectProperty(node, name) !== undefined;\n}\n\nfunction objectHasMetadataSource(node: AstNode | undefined): boolean {\n const metadata = objectProperty(node, 'metadata')?.value as AstNode | undefined;\n return objectHasProperty(metadata, 'source');\n}\n\nfunction looksLikeIntent(value: string): boolean {\n return /^(Domain|Application|Adapter|Workflow|Job|Presentation|Reporting|Metadata|Security|Audit|Observability|Kernel)\\.[A-Za-z0-9_.]+$/.test(value);\n}\n\nfunction isDomainFile(context: RuleContext): boolean {\n const filename = context.getFilename?.() ?? '';\n const normalized = filename.split('\\\\').join('/').toLowerCase();\n return normalized.includes('/domain/') || normalized.endsWith('/domain.ts');\n}\n\nfunction isInfraImport(specifier: string): boolean {\n const normalized = specifier.toLowerCase();\n return [\n 'adapter',\n 'adapters',\n 'infrastructure',\n 'persistence',\n 'repository',\n 'repositories',\n 'integration',\n 'database',\n 'db',\n ].some((token) => normalized.includes(token));\n}\n\nfunction isPublishCall(node: AstNode): boolean {\n return calleePropertyName(node) === 'publish';\n}\n\nexport const noDomainInfraImports: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description: 'Disallow importing infrastructure or adapters from domain files.',\n },\n messages: {\n forbiddenImport: 'Domain code must not import infrastructure, adapters, repositories, or database modules.',\n },\n schema: [],\n },\n create(context) {\n const check = (node: AstNode) => {\n if (!isDomainFile(context)) return;\n const source = stringValue(node.source);\n if (source && isInfraImport(source)) {\n context.report({ node, messageId: 'forbiddenImport' });\n }\n };\n\n return {\n ImportDeclaration: check,\n ExportNamedDeclaration: check,\n ExportAllDeclaration: check,\n };\n },\n};\n\nexport const noRawEventPublish: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description: 'Require event bus publish calls to use registered intent creators instead of raw event objects or intent strings.',\n },\n messages: {\n rawPublish: 'Publish through a registered intent creator; raw event objects or intent strings bypass Ark contracts.',\n },\n schema: [],\n },\n create(context) {\n return {\n CallExpression(node) {\n if (!isPublishCall(node)) return;\n const firstArg = node.arguments?.[0];\n const firstValue = stringValue(firstArg);\n if (\n firstValue && looksLikeIntent(firstValue) ||\n objectHasProperty(firstArg, 'intent')\n ) {\n context.report({ node, messageId: 'rawPublish' });\n }\n },\n };\n },\n};\n\nexport const requirePublishSource: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description: 'Require event bus publish calls to include source metadata.',\n },\n messages: {\n missingSource: 'Strict Ark publish calls must include metadata.source.',\n },\n schema: [],\n },\n create(context) {\n return {\n CallExpression(node) {\n if (!isPublishCall(node)) return;\n const firstArg = node.arguments?.[0];\n const metadataArg = node.arguments?.[2];\n if (objectHasMetadataSource(firstArg) || objectHasProperty(metadataArg, 'source')) {\n return;\n }\n context.report({ node, messageId: 'missingSource' });\n },\n };\n },\n};\n\nconst DEFAULT_FORBIDDEN_GLOBALS = ['fetch', 'process', 'Date.now', 'Math.random'];\n\nexport const noForbiddenGlobals: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description:\n 'Disallow ambient globals (e.g. fetch, Date.now) in architecture-governed code; scope the rule to layer directories via ESLint \"files\" patterns.',\n },\n messages: {\n forbiddenGlobal: 'Ambient global \"{{name}}\" is forbidden here; inject the capability through a port instead.',\n },\n schema: [\n {\n type: 'object',\n properties: {\n globals: { type: 'array', items: { type: 'string' } },\n },\n additionalProperties: false,\n },\n ],\n },\n create(context) {\n const option = context.options?.[0] as { globals?: string[] } | undefined;\n const globals = new Set(option?.globals ?? DEFAULT_FORBIDDEN_GLOBALS);\n const report = (node: AstNode, name: string) =>\n context.report({ node, messageId: 'forbiddenGlobal', data: { name } });\n\n return {\n // Same positional detection as ark-check's FORBIDDEN_GLOBAL: property accesses on a\n // forbidden base (console.log, Date.now), direct calls, and constructions. Bare\n // identifier mentions elsewhere are not flagged (avoids shadowed-local false positives).\n MemberExpression(node) {\n const base = node.object?.type === 'Identifier' ? node.object.name : undefined;\n if (!base) return;\n const dotted = `${base}.${propertyName(node.property) ?? ''}`;\n if (globals.has(dotted)) report(node, dotted);\n else if (globals.has(base)) report(node, base);\n },\n CallExpression(node) {\n const callee = node.callee?.type === 'Identifier' ? node.callee.name : undefined;\n if (callee && globals.has(callee)) report(node, callee);\n },\n NewExpression(node) {\n const callee = node.callee?.type === 'Identifier' ? node.callee.name : undefined;\n if (callee && globals.has(callee)) report(node, callee);\n },\n };\n },\n};\n\nconst rules = {\n 'no-domain-infra-imports': noDomainInfraImports,\n 'no-raw-event-publish': noRawEventPublish,\n 'require-publish-source': requirePublishSource,\n 'no-forbidden-globals': noForbiddenGlobals,\n};\n\nconst plugin: ArkEslintPlugin = { rules };\n\nplugin.configs = {\n recommended: {\n plugins: { ark: plugin },\n rules: {\n 'ark/no-domain-infra-imports': 'error',\n 'ark/no-raw-event-publish': 'error',\n 'ark/require-publish-source': 'error',\n },\n },\n};\n\nexport { plugin };\nexport default plugin;\n"],"mappings":"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","names":[]}
@@ -0,0 +1,42 @@
1
+ type RuleContext = {
2
+ report(descriptor: Record<string, unknown>): void;
3
+ getFilename?: () => string;
4
+ options?: unknown[];
5
+ };
6
+ type RuleListener = Record<string, (node: AstNode) => void>;
7
+ type AstNode = {
8
+ type?: string;
9
+ name?: string;
10
+ value?: unknown;
11
+ source?: AstNode;
12
+ callee?: AstNode;
13
+ object?: AstNode;
14
+ property?: AstNode;
15
+ key?: AstNode;
16
+ arguments?: AstNode[];
17
+ properties?: AstNode[];
18
+ };
19
+ type ArkRule = {
20
+ meta: {
21
+ type: 'problem';
22
+ docs: {
23
+ description: string;
24
+ };
25
+ messages: Record<string, string>;
26
+ schema: unknown[];
27
+ };
28
+ create(context: RuleContext): RuleListener;
29
+ };
30
+ type ArkEslintPlugin = {
31
+ rules: Record<string, ArkRule>;
32
+ configs?: Record<string, unknown>;
33
+ };
34
+ declare const noDomainInfraImports: ArkRule;
35
+ declare const noRawEventPublish: ArkRule;
36
+ declare const requirePublishSource: ArkRule;
37
+ declare const noForbiddenGlobals: ArkRule;
38
+ declare const plugin: ArkEslintPlugin;
39
+
40
+ // @ts-ignore
41
+ export = plugin;
42
+ export { noDomainInfraImports, noForbiddenGlobals, noRawEventPublish, plugin, requirePublishSource };
@@ -0,0 +1,40 @@
1
+ type RuleContext = {
2
+ report(descriptor: Record<string, unknown>): void;
3
+ getFilename?: () => string;
4
+ options?: unknown[];
5
+ };
6
+ type RuleListener = Record<string, (node: AstNode) => void>;
7
+ type AstNode = {
8
+ type?: string;
9
+ name?: string;
10
+ value?: unknown;
11
+ source?: AstNode;
12
+ callee?: AstNode;
13
+ object?: AstNode;
14
+ property?: AstNode;
15
+ key?: AstNode;
16
+ arguments?: AstNode[];
17
+ properties?: AstNode[];
18
+ };
19
+ type ArkRule = {
20
+ meta: {
21
+ type: 'problem';
22
+ docs: {
23
+ description: string;
24
+ };
25
+ messages: Record<string, string>;
26
+ schema: unknown[];
27
+ };
28
+ create(context: RuleContext): RuleListener;
29
+ };
30
+ type ArkEslintPlugin = {
31
+ rules: Record<string, ArkRule>;
32
+ configs?: Record<string, unknown>;
33
+ };
34
+ declare const noDomainInfraImports: ArkRule;
35
+ declare const noRawEventPublish: ArkRule;
36
+ declare const requirePublishSource: ArkRule;
37
+ declare const noForbiddenGlobals: ArkRule;
38
+ declare const plugin: ArkEslintPlugin;
39
+
40
+ export { plugin as default, noDomainInfraImports, noForbiddenGlobals, noRawEventPublish, plugin, requirePublishSource };
@@ -0,0 +1,193 @@
1
+ // src/eslint/index.ts
2
+ function stringValue(node) {
3
+ return typeof node?.value === "string" ? node.value : void 0;
4
+ }
5
+ function propertyName(node) {
6
+ return node?.name ?? stringValue(node);
7
+ }
8
+ function calleePropertyName(node) {
9
+ return propertyName(node.callee?.property);
10
+ }
11
+ function objectProperty(node, name) {
12
+ return node?.properties?.find((property) => propertyName(property.key) === name);
13
+ }
14
+ function objectHasProperty(node, name) {
15
+ return objectProperty(node, name) !== void 0;
16
+ }
17
+ function objectHasMetadataSource(node) {
18
+ const metadata = objectProperty(node, "metadata")?.value;
19
+ return objectHasProperty(metadata, "source");
20
+ }
21
+ function looksLikeIntent(value) {
22
+ return /^(Domain|Application|Adapter|Workflow|Job|Presentation|Reporting|Metadata|Security|Audit|Observability|Kernel)\.[A-Za-z0-9_.]+$/.test(value);
23
+ }
24
+ function isDomainFile(context) {
25
+ const filename = context.getFilename?.() ?? "";
26
+ const normalized = filename.split("\\").join("/").toLowerCase();
27
+ return normalized.includes("/domain/") || normalized.endsWith("/domain.ts");
28
+ }
29
+ function isInfraImport(specifier) {
30
+ const normalized = specifier.toLowerCase();
31
+ return [
32
+ "adapter",
33
+ "adapters",
34
+ "infrastructure",
35
+ "persistence",
36
+ "repository",
37
+ "repositories",
38
+ "integration",
39
+ "database",
40
+ "db"
41
+ ].some((token) => normalized.includes(token));
42
+ }
43
+ function isPublishCall(node) {
44
+ return calleePropertyName(node) === "publish";
45
+ }
46
+ var noDomainInfraImports = {
47
+ meta: {
48
+ type: "problem",
49
+ docs: {
50
+ description: "Disallow importing infrastructure or adapters from domain files."
51
+ },
52
+ messages: {
53
+ forbiddenImport: "Domain code must not import infrastructure, adapters, repositories, or database modules."
54
+ },
55
+ schema: []
56
+ },
57
+ create(context) {
58
+ const check = (node) => {
59
+ if (!isDomainFile(context)) return;
60
+ const source = stringValue(node.source);
61
+ if (source && isInfraImport(source)) {
62
+ context.report({ node, messageId: "forbiddenImport" });
63
+ }
64
+ };
65
+ return {
66
+ ImportDeclaration: check,
67
+ ExportNamedDeclaration: check,
68
+ ExportAllDeclaration: check
69
+ };
70
+ }
71
+ };
72
+ var noRawEventPublish = {
73
+ meta: {
74
+ type: "problem",
75
+ docs: {
76
+ description: "Require event bus publish calls to use registered intent creators instead of raw event objects or intent strings."
77
+ },
78
+ messages: {
79
+ rawPublish: "Publish through a registered intent creator; raw event objects or intent strings bypass Ark contracts."
80
+ },
81
+ schema: []
82
+ },
83
+ create(context) {
84
+ return {
85
+ CallExpression(node) {
86
+ if (!isPublishCall(node)) return;
87
+ const firstArg = node.arguments?.[0];
88
+ const firstValue = stringValue(firstArg);
89
+ if (firstValue && looksLikeIntent(firstValue) || objectHasProperty(firstArg, "intent")) {
90
+ context.report({ node, messageId: "rawPublish" });
91
+ }
92
+ }
93
+ };
94
+ }
95
+ };
96
+ var requirePublishSource = {
97
+ meta: {
98
+ type: "problem",
99
+ docs: {
100
+ description: "Require event bus publish calls to include source metadata."
101
+ },
102
+ messages: {
103
+ missingSource: "Strict Ark publish calls must include metadata.source."
104
+ },
105
+ schema: []
106
+ },
107
+ create(context) {
108
+ return {
109
+ CallExpression(node) {
110
+ if (!isPublishCall(node)) return;
111
+ const firstArg = node.arguments?.[0];
112
+ const metadataArg = node.arguments?.[2];
113
+ if (objectHasMetadataSource(firstArg) || objectHasProperty(metadataArg, "source")) {
114
+ return;
115
+ }
116
+ context.report({ node, messageId: "missingSource" });
117
+ }
118
+ };
119
+ }
120
+ };
121
+ var DEFAULT_FORBIDDEN_GLOBALS = ["fetch", "process", "Date.now", "Math.random"];
122
+ var noForbiddenGlobals = {
123
+ meta: {
124
+ type: "problem",
125
+ docs: {
126
+ description: 'Disallow ambient globals (e.g. fetch, Date.now) in architecture-governed code; scope the rule to layer directories via ESLint "files" patterns.'
127
+ },
128
+ messages: {
129
+ forbiddenGlobal: 'Ambient global "{{name}}" is forbidden here; inject the capability through a port instead.'
130
+ },
131
+ schema: [
132
+ {
133
+ type: "object",
134
+ properties: {
135
+ globals: { type: "array", items: { type: "string" } }
136
+ },
137
+ additionalProperties: false
138
+ }
139
+ ]
140
+ },
141
+ create(context) {
142
+ const option = context.options?.[0];
143
+ const globals = new Set(option?.globals ?? DEFAULT_FORBIDDEN_GLOBALS);
144
+ const report = (node, name) => context.report({ node, messageId: "forbiddenGlobal", data: { name } });
145
+ return {
146
+ // Same positional detection as ark-check's FORBIDDEN_GLOBAL: property accesses on a
147
+ // forbidden base (console.log, Date.now), direct calls, and constructions. Bare
148
+ // identifier mentions elsewhere are not flagged (avoids shadowed-local false positives).
149
+ MemberExpression(node) {
150
+ const base = node.object?.type === "Identifier" ? node.object.name : void 0;
151
+ if (!base) return;
152
+ const dotted = `${base}.${propertyName(node.property) ?? ""}`;
153
+ if (globals.has(dotted)) report(node, dotted);
154
+ else if (globals.has(base)) report(node, base);
155
+ },
156
+ CallExpression(node) {
157
+ const callee = node.callee?.type === "Identifier" ? node.callee.name : void 0;
158
+ if (callee && globals.has(callee)) report(node, callee);
159
+ },
160
+ NewExpression(node) {
161
+ const callee = node.callee?.type === "Identifier" ? node.callee.name : void 0;
162
+ if (callee && globals.has(callee)) report(node, callee);
163
+ }
164
+ };
165
+ }
166
+ };
167
+ var rules = {
168
+ "no-domain-infra-imports": noDomainInfraImports,
169
+ "no-raw-event-publish": noRawEventPublish,
170
+ "require-publish-source": requirePublishSource,
171
+ "no-forbidden-globals": noForbiddenGlobals
172
+ };
173
+ var plugin = { rules };
174
+ plugin.configs = {
175
+ recommended: {
176
+ plugins: { ark: plugin },
177
+ rules: {
178
+ "ark/no-domain-infra-imports": "error",
179
+ "ark/no-raw-event-publish": "error",
180
+ "ark/require-publish-source": "error"
181
+ }
182
+ }
183
+ };
184
+ var eslint_default = plugin;
185
+ export {
186
+ eslint_default as default,
187
+ noDomainInfraImports,
188
+ noForbiddenGlobals,
189
+ noRawEventPublish,
190
+ plugin,
191
+ requirePublishSource
192
+ };
193
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/eslint/index.ts"],"sourcesContent":["type RuleContext = {\n report(descriptor: Record<string, unknown>): void;\n getFilename?: () => string;\n options?: unknown[];\n};\n\ntype RuleListener = Record<string, (node: AstNode) => void>;\n\ntype AstNode = {\n type?: string;\n name?: string;\n value?: unknown;\n source?: AstNode;\n callee?: AstNode;\n object?: AstNode;\n property?: AstNode;\n key?: AstNode;\n arguments?: AstNode[];\n properties?: AstNode[];\n};\n\ntype ArkRule = {\n meta: {\n type: 'problem';\n docs: { description: string };\n messages: Record<string, string>;\n schema: unknown[];\n };\n create(context: RuleContext): RuleListener;\n};\n\ntype ArkEslintPlugin = {\n rules: Record<string, ArkRule>;\n configs?: Record<string, unknown>;\n};\n\nfunction stringValue(node: AstNode | undefined): string | undefined {\n return typeof node?.value === 'string' ? node.value : undefined;\n}\n\nfunction propertyName(node: AstNode | undefined): string | undefined {\n return node?.name ?? stringValue(node);\n}\n\nfunction calleePropertyName(node: AstNode): string | undefined {\n return propertyName(node.callee?.property);\n}\n\nfunction objectProperty(node: AstNode | undefined, name: string): AstNode | undefined {\n return node?.properties?.find((property) => propertyName(property.key) === name);\n}\n\nfunction objectHasProperty(node: AstNode | undefined, name: string): boolean {\n return objectProperty(node, name) !== undefined;\n}\n\nfunction objectHasMetadataSource(node: AstNode | undefined): boolean {\n const metadata = objectProperty(node, 'metadata')?.value as AstNode | undefined;\n return objectHasProperty(metadata, 'source');\n}\n\nfunction looksLikeIntent(value: string): boolean {\n return /^(Domain|Application|Adapter|Workflow|Job|Presentation|Reporting|Metadata|Security|Audit|Observability|Kernel)\\.[A-Za-z0-9_.]+$/.test(value);\n}\n\nfunction isDomainFile(context: RuleContext): boolean {\n const filename = context.getFilename?.() ?? '';\n const normalized = filename.split('\\\\').join('/').toLowerCase();\n return normalized.includes('/domain/') || normalized.endsWith('/domain.ts');\n}\n\nfunction isInfraImport(specifier: string): boolean {\n const normalized = specifier.toLowerCase();\n return [\n 'adapter',\n 'adapters',\n 'infrastructure',\n 'persistence',\n 'repository',\n 'repositories',\n 'integration',\n 'database',\n 'db',\n ].some((token) => normalized.includes(token));\n}\n\nfunction isPublishCall(node: AstNode): boolean {\n return calleePropertyName(node) === 'publish';\n}\n\nexport const noDomainInfraImports: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description: 'Disallow importing infrastructure or adapters from domain files.',\n },\n messages: {\n forbiddenImport: 'Domain code must not import infrastructure, adapters, repositories, or database modules.',\n },\n schema: [],\n },\n create(context) {\n const check = (node: AstNode) => {\n if (!isDomainFile(context)) return;\n const source = stringValue(node.source);\n if (source && isInfraImport(source)) {\n context.report({ node, messageId: 'forbiddenImport' });\n }\n };\n\n return {\n ImportDeclaration: check,\n ExportNamedDeclaration: check,\n ExportAllDeclaration: check,\n };\n },\n};\n\nexport const noRawEventPublish: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description: 'Require event bus publish calls to use registered intent creators instead of raw event objects or intent strings.',\n },\n messages: {\n rawPublish: 'Publish through a registered intent creator; raw event objects or intent strings bypass Ark contracts.',\n },\n schema: [],\n },\n create(context) {\n return {\n CallExpression(node) {\n if (!isPublishCall(node)) return;\n const firstArg = node.arguments?.[0];\n const firstValue = stringValue(firstArg);\n if (\n firstValue && looksLikeIntent(firstValue) ||\n objectHasProperty(firstArg, 'intent')\n ) {\n context.report({ node, messageId: 'rawPublish' });\n }\n },\n };\n },\n};\n\nexport const requirePublishSource: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description: 'Require event bus publish calls to include source metadata.',\n },\n messages: {\n missingSource: 'Strict Ark publish calls must include metadata.source.',\n },\n schema: [],\n },\n create(context) {\n return {\n CallExpression(node) {\n if (!isPublishCall(node)) return;\n const firstArg = node.arguments?.[0];\n const metadataArg = node.arguments?.[2];\n if (objectHasMetadataSource(firstArg) || objectHasProperty(metadataArg, 'source')) {\n return;\n }\n context.report({ node, messageId: 'missingSource' });\n },\n };\n },\n};\n\nconst DEFAULT_FORBIDDEN_GLOBALS = ['fetch', 'process', 'Date.now', 'Math.random'];\n\nexport const noForbiddenGlobals: ArkRule = {\n meta: {\n type: 'problem',\n docs: {\n description:\n 'Disallow ambient globals (e.g. fetch, Date.now) in architecture-governed code; scope the rule to layer directories via ESLint \"files\" patterns.',\n },\n messages: {\n forbiddenGlobal: 'Ambient global \"{{name}}\" is forbidden here; inject the capability through a port instead.',\n },\n schema: [\n {\n type: 'object',\n properties: {\n globals: { type: 'array', items: { type: 'string' } },\n },\n additionalProperties: false,\n },\n ],\n },\n create(context) {\n const option = context.options?.[0] as { globals?: string[] } | undefined;\n const globals = new Set(option?.globals ?? DEFAULT_FORBIDDEN_GLOBALS);\n const report = (node: AstNode, name: string) =>\n context.report({ node, messageId: 'forbiddenGlobal', data: { name } });\n\n return {\n // Same positional detection as ark-check's FORBIDDEN_GLOBAL: property accesses on a\n // forbidden base (console.log, Date.now), direct calls, and constructions. Bare\n // identifier mentions elsewhere are not flagged (avoids shadowed-local false positives).\n MemberExpression(node) {\n const base = node.object?.type === 'Identifier' ? node.object.name : undefined;\n if (!base) return;\n const dotted = `${base}.${propertyName(node.property) ?? ''}`;\n if (globals.has(dotted)) report(node, dotted);\n else if (globals.has(base)) report(node, base);\n },\n CallExpression(node) {\n const callee = node.callee?.type === 'Identifier' ? node.callee.name : undefined;\n if (callee && globals.has(callee)) report(node, callee);\n },\n NewExpression(node) {\n const callee = node.callee?.type === 'Identifier' ? node.callee.name : undefined;\n if (callee && globals.has(callee)) report(node, callee);\n },\n };\n },\n};\n\nconst rules = {\n 'no-domain-infra-imports': noDomainInfraImports,\n 'no-raw-event-publish': noRawEventPublish,\n 'require-publish-source': requirePublishSource,\n 'no-forbidden-globals': noForbiddenGlobals,\n};\n\nconst plugin: ArkEslintPlugin = { rules };\n\nplugin.configs = {\n recommended: {\n plugins: { ark: plugin },\n rules: {\n 'ark/no-domain-infra-imports': 'error',\n 'ark/no-raw-event-publish': 'error',\n 'ark/require-publish-source': 'error',\n },\n },\n};\n\nexport { plugin };\nexport default plugin;\n"],"mappings":";AAoCA,SAAS,YAAY,MAA+C;AAClE,SAAO,OAAO,MAAM,UAAU,WAAW,KAAK,QAAQ;AACxD;AAEA,SAAS,aAAa,MAA+C;AACnE,SAAO,MAAM,QAAQ,YAAY,IAAI;AACvC;AAEA,SAAS,mBAAmB,MAAmC;AAC7D,SAAO,aAAa,KAAK,QAAQ,QAAQ;AAC3C;AAEA,SAAS,eAAe,MAA2B,MAAmC;AACpF,SAAO,MAAM,YAAY,KAAK,CAAC,aAAa,aAAa,SAAS,GAAG,MAAM,IAAI;AACjF;AAEA,SAAS,kBAAkB,MAA2B,MAAuB;AAC3E,SAAO,eAAe,MAAM,IAAI,MAAM;AACxC;AAEA,SAAS,wBAAwB,MAAoC;AACnE,QAAM,WAAW,eAAe,MAAM,UAAU,GAAG;AACnD,SAAO,kBAAkB,UAAU,QAAQ;AAC7C;AAEA,SAAS,gBAAgB,OAAwB;AAC/C,SAAO,kIAAkI,KAAK,KAAK;AACrJ;AAEA,SAAS,aAAa,SAA+B;AACnD,QAAM,WAAW,QAAQ,cAAc,KAAK;AAC5C,QAAM,aAAa,SAAS,MAAM,IAAI,EAAE,KAAK,GAAG,EAAE,YAAY;AAC9D,SAAO,WAAW,SAAS,UAAU,KAAK,WAAW,SAAS,YAAY;AAC5E;AAEA,SAAS,cAAc,WAA4B;AACjD,QAAM,aAAa,UAAU,YAAY;AACzC,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF,EAAE,KAAK,CAAC,UAAU,WAAW,SAAS,KAAK,CAAC;AAC9C;AAEA,SAAS,cAAc,MAAwB;AAC7C,SAAO,mBAAmB,IAAI,MAAM;AACtC;AAEO,IAAM,uBAAgC;AAAA,EAC3C,MAAM;AAAA,IACJ,MAAM;AAAA,IACN,MAAM;AAAA,MACJ,aAAa;AAAA,IACf;AAAA,IACA,UAAU;AAAA,MACR,iBAAiB;AAAA,IACnB;AAAA,IACA,QAAQ,CAAC;AAAA,EACX;AAAA,EACA,OAAO,SAAS;AACd,UAAM,QAAQ,CAAC,SAAkB;AAC/B,UAAI,CAAC,aAAa,OAAO,EAAG;AAC5B,YAAM,SAAS,YAAY,KAAK,MAAM;AACtC,UAAI,UAAU,cAAc,MAAM,GAAG;AACnC,gBAAQ,OAAO,EAAE,MAAM,WAAW,kBAAkB,CAAC;AAAA,MACvD;AAAA,IACF;AAEA,WAAO;AAAA,MACL,mBAAmB;AAAA,MACnB,wBAAwB;AAAA,MACxB,sBAAsB;AAAA,IACxB;AAAA,EACF;AACF;AAEO,IAAM,oBAA6B;AAAA,EACxC,MAAM;AAAA,IACJ,MAAM;AAAA,IACN,MAAM;AAAA,MACJ,aAAa;AAAA,IACf;AAAA,IACA,UAAU;AAAA,MACR,YAAY;AAAA,IACd;AAAA,IACA,QAAQ,CAAC;AAAA,EACX;AAAA,EACA,OAAO,SAAS;AACd,WAAO;AAAA,MACL,eAAe,MAAM;AACnB,YAAI,CAAC,cAAc,IAAI,EAAG;AAC1B,cAAM,WAAW,KAAK,YAAY,CAAC;AACnC,cAAM,aAAa,YAAY,QAAQ;AACvC,YACE,cAAc,gBAAgB,UAAU,KACxC,kBAAkB,UAAU,QAAQ,GACpC;AACA,kBAAQ,OAAO,EAAE,MAAM,WAAW,aAAa,CAAC;AAAA,QAClD;AAAA,MACF;AAAA,IACF;AAAA,EACF;AACF;AAEO,IAAM,uBAAgC;AAAA,EAC3C,MAAM;AAAA,IACJ,MAAM;AAAA,IACN,MAAM;AAAA,MACJ,aAAa;AAAA,IACf;AAAA,IACA,UAAU;AAAA,MACR,eAAe;AAAA,IACjB;AAAA,IACA,QAAQ,CAAC;AAAA,EACX;AAAA,EACA,OAAO,SAAS;AACd,WAAO;AAAA,MACL,eAAe,MAAM;AACnB,YAAI,CAAC,cAAc,IAAI,EAAG;AAC1B,cAAM,WAAW,KAAK,YAAY,CAAC;AACnC,cAAM,cAAc,KAAK,YAAY,CAAC;AACtC,YAAI,wBAAwB,QAAQ,KAAK,kBAAkB,aAAa,QAAQ,GAAG;AACjF;AAAA,QACF;AACA,gBAAQ,OAAO,EAAE,MAAM,WAAW,gBAAgB,CAAC;AAAA,MACrD;AAAA,IACF;AAAA,EACF;AACF;AAEA,IAAM,4BAA4B,CAAC,SAAS,WAAW,YAAY,aAAa;AAEzE,IAAM,qBAA8B;AAAA,EACzC,MAAM;AAAA,IACJ,MAAM;AAAA,IACN,MAAM;AAAA,MACJ,aACE;AAAA,IACJ;AAAA,IACA,UAAU;AAAA,MACR,iBAAiB;AAAA,IACnB;AAAA,IACA,QAAQ;AAAA,MACN;AAAA,QACE,MAAM;AAAA,QACN,YAAY;AAAA,UACV,SAAS,EAAE,MAAM,SAAS,OAAO,EAAE,MAAM,SAAS,EAAE;AAAA,QACtD;AAAA,QACA,sBAAsB;AAAA,MACxB;AAAA,IACF;AAAA,EACF;AAAA,EACA,OAAO,SAAS;AACd,UAAM,SAAS,QAAQ,UAAU,CAAC;AAClC,UAAM,UAAU,IAAI,IAAI,QAAQ,WAAW,yBAAyB;AACpE,UAAM,SAAS,CAAC,MAAe,SAC7B,QAAQ,OAAO,EAAE,MAAM,WAAW,mBAAmB,MAAM,EAAE,KAAK,EAAE,CAAC;AAEvE,WAAO;AAAA;AAAA;AAAA;AAAA,MAIL,iBAAiB,MAAM;AACrB,cAAM,OAAO,KAAK,QAAQ,SAAS,eAAe,KAAK,OAAO,OAAO;AACrE,YAAI,CAAC,KAAM;AACX,cAAM,SAAS,GAAG,IAAI,IAAI,aAAa,KAAK,QAAQ,KAAK,EAAE;AAC3D,YAAI,QAAQ,IAAI,MAAM,EAAG,QAAO,MAAM,MAAM;AAAA,iBACnC,QAAQ,IAAI,IAAI,EAAG,QAAO,MAAM,IAAI;AAAA,MAC/C;AAAA,MACA,eAAe,MAAM;AACnB,cAAM,SAAS,KAAK,QAAQ,SAAS,eAAe,KAAK,OAAO,OAAO;AACvE,YAAI,UAAU,QAAQ,IAAI,MAAM,EAAG,QAAO,MAAM,MAAM;AAAA,MACxD;AAAA,MACA,cAAc,MAAM;AAClB,cAAM,SAAS,KAAK,QAAQ,SAAS,eAAe,KAAK,OAAO,OAAO;AACvE,YAAI,UAAU,QAAQ,IAAI,MAAM,EAAG,QAAO,MAAM,MAAM;AAAA,MACxD;AAAA,IACF;AAAA,EACF;AACF;AAEA,IAAM,QAAQ;AAAA,EACZ,2BAA2B;AAAA,EAC3B,wBAAwB;AAAA,EACxB,0BAA0B;AAAA,EAC1B,wBAAwB;AAC1B;AAEA,IAAM,SAA0B,EAAE,MAAM;AAExC,OAAO,UAAU;AAAA,EACf,aAAa;AAAA,IACX,SAAS,EAAE,KAAK,OAAO;AAAA,IACvB,OAAO;AAAA,MACL,+BAA+B;AAAA,MAC/B,4BAA4B;AAAA,MAC5B,8BAA8B;AAAA,IAChC;AAAA,EACF;AACF;AAGA,IAAO,iBAAQ;","names":[]}