@grainulation/mill 1.0.0 → 1.0.1
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/CODE_OF_CONDUCT.md +25 -0
- package/CONTRIBUTING.md +101 -0
- package/README.md +90 -42
- package/bin/mill.js +233 -67
- package/lib/exporters/csv.js +35 -30
- package/lib/exporters/json-ld.js +19 -13
- package/lib/exporters/markdown.js +83 -44
- package/lib/exporters/pdf.js +15 -15
- package/lib/formats/bibtex.js +41 -34
- package/lib/formats/changelog.js +27 -26
- package/lib/formats/confluence-adf.js +312 -0
- package/lib/formats/csv.js +41 -37
- package/lib/formats/dot.js +45 -34
- package/lib/formats/evidence-matrix.js +17 -16
- package/lib/formats/executive-summary.js +89 -41
- package/lib/formats/github-issues.js +40 -33
- package/lib/formats/graphml.js +45 -32
- package/lib/formats/html-report.js +110 -63
- package/lib/formats/jira-csv.js +30 -29
- package/lib/formats/json-ld.js +6 -6
- package/lib/formats/markdown.js +53 -36
- package/lib/formats/ndjson.js +6 -6
- package/lib/formats/obsidian.js +43 -35
- package/lib/formats/opml.js +38 -28
- package/lib/formats/ris.js +29 -23
- package/lib/formats/rss.js +31 -28
- package/lib/formats/sankey.js +16 -15
- package/lib/formats/slide-deck.js +145 -57
- package/lib/formats/sql.js +57 -53
- package/lib/formats/static-site.js +64 -52
- package/lib/formats/treemap.js +16 -15
- package/lib/formats/typescript-defs.js +79 -76
- package/lib/formats/yaml.js +58 -40
- package/lib/formats.js +16 -16
- package/lib/index.js +5 -5
- package/lib/json-ld-common.js +37 -31
- package/lib/publishers/clipboard.js +21 -19
- package/lib/publishers/static.js +27 -12
- package/lib/serve-mcp.js +158 -83
- package/lib/server.js +252 -142
- package/package.json +7 -3
|
@@ -7,10 +7,11 @@
|
|
|
7
7
|
* Zero dependencies — node built-in only.
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
|
-
export const name =
|
|
11
|
-
export const extension =
|
|
12
|
-
export const mimeType =
|
|
13
|
-
export const description =
|
|
10
|
+
export const name = "static-site";
|
|
11
|
+
export const extension = ".json";
|
|
12
|
+
export const mimeType = "application/json; charset=utf-8";
|
|
13
|
+
export const description =
|
|
14
|
+
"Hugo-compatible static site manifest (file tree as JSON)";
|
|
14
15
|
|
|
15
16
|
/**
|
|
16
17
|
* Convert a compilation object to a static site manifest.
|
|
@@ -22,148 +23,159 @@ export function convert(compilation) {
|
|
|
22
23
|
const meta = compilation.meta || {};
|
|
23
24
|
const certificate = compilation.certificate || {};
|
|
24
25
|
|
|
25
|
-
const sprintName = meta.sprint ||
|
|
26
|
-
const question = meta.question ||
|
|
27
|
-
const audience = meta.audience ||
|
|
26
|
+
const sprintName = meta.sprint || "sprint";
|
|
27
|
+
const question = meta.question || "";
|
|
28
|
+
const audience = meta.audience || "";
|
|
28
29
|
|
|
29
30
|
const files = {};
|
|
30
31
|
|
|
31
32
|
// Hugo config
|
|
32
|
-
files[
|
|
33
|
+
files["config.yaml"] = buildConfig(sprintName, question);
|
|
33
34
|
|
|
34
35
|
// Index page
|
|
35
|
-
files[
|
|
36
|
+
files["content/_index.md"] = buildIndex(
|
|
37
|
+
sprintName,
|
|
38
|
+
question,
|
|
39
|
+
audience,
|
|
40
|
+
claims,
|
|
41
|
+
);
|
|
36
42
|
|
|
37
43
|
// Per-type section pages
|
|
38
44
|
const groups = {};
|
|
39
45
|
for (const claim of claims) {
|
|
40
|
-
const type = claim.type ||
|
|
46
|
+
const type = claim.type || "other";
|
|
41
47
|
if (!groups[type]) groups[type] = [];
|
|
42
48
|
groups[type].push(claim);
|
|
43
49
|
}
|
|
44
50
|
|
|
45
51
|
for (const [type, group] of Object.entries(groups)) {
|
|
46
|
-
files[`content/claims/${type}/_index.md`] = buildSectionIndex(
|
|
52
|
+
files[`content/claims/${type}/_index.md`] = buildSectionIndex(
|
|
53
|
+
type,
|
|
54
|
+
group.length,
|
|
55
|
+
);
|
|
47
56
|
|
|
48
57
|
for (const claim of group) {
|
|
49
|
-
const id = claim.id ||
|
|
58
|
+
const id = claim.id || "unknown";
|
|
50
59
|
files[`content/claims/${type}/${id}.md`] = buildClaimPage(claim);
|
|
51
60
|
}
|
|
52
61
|
}
|
|
53
62
|
|
|
54
63
|
// Data file: full claims array
|
|
55
|
-
files[
|
|
64
|
+
files["data/claims.json"] = JSON.stringify(claims, null, 2);
|
|
56
65
|
|
|
57
66
|
// Data file: certificate
|
|
58
67
|
if (Object.keys(certificate).length > 0) {
|
|
59
|
-
files[
|
|
68
|
+
files["data/certificate.json"] = JSON.stringify(certificate, null, 2);
|
|
60
69
|
}
|
|
61
70
|
|
|
62
71
|
// Data file: meta
|
|
63
|
-
files[
|
|
72
|
+
files["data/meta.json"] = JSON.stringify(meta, null, 2);
|
|
64
73
|
|
|
65
74
|
const manifest = {
|
|
66
|
-
generator:
|
|
75
|
+
generator: "mill",
|
|
67
76
|
sprint: sprintName,
|
|
68
77
|
claimCount: claims.length,
|
|
69
78
|
files,
|
|
70
79
|
};
|
|
71
80
|
|
|
72
|
-
return JSON.stringify(manifest, null, 2) +
|
|
81
|
+
return JSON.stringify(manifest, null, 2) + "\n";
|
|
73
82
|
}
|
|
74
83
|
|
|
75
84
|
function buildConfig(sprintName, question) {
|
|
76
85
|
const lines = [];
|
|
77
|
-
lines.push(
|
|
86
|
+
lines.push(
|
|
87
|
+
`baseURL: "https://your-site.example.com/${sanitizeSlug(sprintName)}/" # Update with your domain`,
|
|
88
|
+
);
|
|
78
89
|
lines.push(`title: "${escYaml(sprintName)}"`);
|
|
79
90
|
lines.push(`theme: "mill-default"`);
|
|
80
91
|
lines.push('languageCode: "en-us"');
|
|
81
|
-
lines.push(
|
|
82
|
-
lines.push(
|
|
92
|
+
lines.push("");
|
|
93
|
+
lines.push("params:");
|
|
83
94
|
lines.push(` question: "${escYaml(question)}"`);
|
|
84
95
|
lines.push(` generator: "mill"`);
|
|
85
|
-
return lines.join(
|
|
96
|
+
return lines.join("\n") + "\n";
|
|
86
97
|
}
|
|
87
98
|
|
|
88
99
|
function buildIndex(sprintName, question, audience, claims) {
|
|
89
100
|
const lines = [];
|
|
90
|
-
lines.push(
|
|
101
|
+
lines.push("---");
|
|
91
102
|
lines.push(`title: "${escYaml(sprintName)}"`);
|
|
92
103
|
lines.push(`description: "${escYaml(question)}"`);
|
|
93
104
|
lines.push('type: "index"');
|
|
94
|
-
lines.push(
|
|
95
|
-
lines.push(
|
|
105
|
+
lines.push("---");
|
|
106
|
+
lines.push("");
|
|
96
107
|
lines.push(`# ${sprintName}`);
|
|
97
|
-
lines.push(
|
|
108
|
+
lines.push("");
|
|
98
109
|
if (question) lines.push(`**Question:** ${question}`);
|
|
99
110
|
if (audience) lines.push(`**Audience:** ${audience}`);
|
|
100
|
-
lines.push(
|
|
111
|
+
lines.push("");
|
|
101
112
|
lines.push(`**Total claims:** ${claims.length}`);
|
|
102
113
|
|
|
103
114
|
// Type summary
|
|
104
115
|
const typeCounts = {};
|
|
105
116
|
for (const c of claims) {
|
|
106
|
-
const t = c.type ||
|
|
117
|
+
const t = c.type || "other";
|
|
107
118
|
typeCounts[t] = (typeCounts[t] || 0) + 1;
|
|
108
119
|
}
|
|
109
|
-
lines.push(
|
|
120
|
+
lines.push("");
|
|
110
121
|
for (const [type, count] of Object.entries(typeCounts)) {
|
|
111
122
|
lines.push(`- ${type}: ${count}`);
|
|
112
123
|
}
|
|
113
124
|
|
|
114
|
-
return lines.join(
|
|
125
|
+
return lines.join("\n") + "\n";
|
|
115
126
|
}
|
|
116
127
|
|
|
117
128
|
function buildSectionIndex(type, count) {
|
|
118
129
|
const lines = [];
|
|
119
|
-
lines.push(
|
|
130
|
+
lines.push("---");
|
|
120
131
|
lines.push(`title: "${escYaml(type)}"`);
|
|
121
132
|
lines.push(`type: "section"`);
|
|
122
|
-
lines.push(
|
|
123
|
-
lines.push(
|
|
124
|
-
lines.push(`${count} ${type} claim${count !== 1 ?
|
|
125
|
-
return lines.join(
|
|
133
|
+
lines.push("---");
|
|
134
|
+
lines.push("");
|
|
135
|
+
lines.push(`${count} ${type} claim${count !== 1 ? "s" : ""}.`);
|
|
136
|
+
return lines.join("\n") + "\n";
|
|
126
137
|
}
|
|
127
138
|
|
|
128
139
|
function buildClaimPage(claim) {
|
|
129
|
-
const id = claim.id ||
|
|
130
|
-
const type = claim.type ||
|
|
131
|
-
const content = claim.content || claim.text ||
|
|
140
|
+
const id = claim.id || "unknown";
|
|
141
|
+
const type = claim.type || "";
|
|
142
|
+
const content = claim.content || claim.text || "";
|
|
132
143
|
const evidence = getEvidence(claim);
|
|
133
|
-
const status = claim.status ||
|
|
144
|
+
const status = claim.status || "";
|
|
134
145
|
const tags = Array.isArray(claim.tags) ? claim.tags : [];
|
|
135
|
-
const confidence = claim.confidence != null ? claim.confidence :
|
|
146
|
+
const confidence = claim.confidence != null ? claim.confidence : "";
|
|
136
147
|
|
|
137
148
|
const lines = [];
|
|
138
|
-
lines.push(
|
|
149
|
+
lines.push("---");
|
|
139
150
|
lines.push(`title: "${escYaml(id)}"`);
|
|
140
151
|
lines.push(`type: "${escYaml(type)}"`);
|
|
141
152
|
lines.push(`evidence: "${escYaml(evidence)}"`);
|
|
142
153
|
lines.push(`status: "${escYaml(status)}"`);
|
|
143
|
-
if (confidence !==
|
|
144
|
-
if (tags.length > 0)
|
|
145
|
-
|
|
146
|
-
lines.push(
|
|
154
|
+
if (confidence !== "") lines.push(`confidence: ${confidence}`);
|
|
155
|
+
if (tags.length > 0)
|
|
156
|
+
lines.push(`tags: [${tags.map((t) => `"${escYaml(t)}"`).join(", ")}]`);
|
|
157
|
+
lines.push("---");
|
|
158
|
+
lines.push("");
|
|
147
159
|
lines.push(content);
|
|
148
|
-
return lines.join(
|
|
160
|
+
return lines.join("\n") + "\n";
|
|
149
161
|
}
|
|
150
162
|
|
|
151
163
|
function getEvidence(claim) {
|
|
152
|
-
if (typeof claim.evidence ===
|
|
153
|
-
if (typeof claim.evidence ===
|
|
154
|
-
return claim.evidence.tier || claim.evidence_tier ||
|
|
164
|
+
if (typeof claim.evidence === "string") return claim.evidence;
|
|
165
|
+
if (typeof claim.evidence === "object" && claim.evidence !== null) {
|
|
166
|
+
return claim.evidence.tier || claim.evidence_tier || "";
|
|
155
167
|
}
|
|
156
|
-
return claim.evidence_tier ||
|
|
168
|
+
return claim.evidence_tier || "";
|
|
157
169
|
}
|
|
158
170
|
|
|
159
171
|
function escYaml(str) {
|
|
160
|
-
if (str == null) return
|
|
172
|
+
if (str == null) return "";
|
|
161
173
|
return String(str).replace(/"/g, '\\"');
|
|
162
174
|
}
|
|
163
175
|
|
|
164
176
|
function sanitizeSlug(str) {
|
|
165
177
|
return String(str)
|
|
166
178
|
.toLowerCase()
|
|
167
|
-
.replace(/[^a-z0-9]+/g,
|
|
168
|
-
.replace(/^-+|-+$/g,
|
|
179
|
+
.replace(/[^a-z0-9]+/g, "-")
|
|
180
|
+
.replace(/^-+|-+$/g, "");
|
|
169
181
|
}
|
package/lib/formats/treemap.js
CHANGED
|
@@ -6,10 +6,11 @@
|
|
|
6
6
|
* Zero dependencies — node built-in only.
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
|
-
export const name =
|
|
10
|
-
export const extension =
|
|
11
|
-
export const mimeType =
|
|
12
|
-
export const description =
|
|
9
|
+
export const name = "treemap";
|
|
10
|
+
export const extension = ".json";
|
|
11
|
+
export const mimeType = "application/json; charset=utf-8";
|
|
12
|
+
export const description =
|
|
13
|
+
"Claims as nested JSON for D3 treemap visualization (grouped by type)";
|
|
13
14
|
|
|
14
15
|
/**
|
|
15
16
|
* Convert a compilation object to D3 treemap JSON.
|
|
@@ -18,12 +19,12 @@ export const description = 'Claims as nested JSON for D3 treemap visualization (
|
|
|
18
19
|
*/
|
|
19
20
|
export function convert(compilation) {
|
|
20
21
|
const claims = compilation.claims || [];
|
|
21
|
-
const sprintName = compilation.meta?.sprint ||
|
|
22
|
+
const sprintName = compilation.meta?.sprint || "sprint";
|
|
22
23
|
|
|
23
24
|
// Group claims by type
|
|
24
25
|
const groups = {};
|
|
25
26
|
for (const claim of claims) {
|
|
26
|
-
const type = claim.type ||
|
|
27
|
+
const type = claim.type || "other";
|
|
27
28
|
if (!groups[type]) groups[type] = [];
|
|
28
29
|
groups[type].push(claim);
|
|
29
30
|
}
|
|
@@ -32,17 +33,17 @@ export function convert(compilation) {
|
|
|
32
33
|
name: sprintName,
|
|
33
34
|
children: Object.entries(groups).map(([type, group]) => ({
|
|
34
35
|
name: type,
|
|
35
|
-
children: group.map(claim => {
|
|
36
|
+
children: group.map((claim) => {
|
|
36
37
|
const node = {
|
|
37
|
-
name: claim.id ||
|
|
38
|
+
name: claim.id || "",
|
|
38
39
|
value: claim.confidence != null ? claim.confidence : 1,
|
|
39
40
|
evidence: getEvidence(claim),
|
|
40
41
|
};
|
|
41
42
|
|
|
42
|
-
const content = claim.content || claim.text ||
|
|
43
|
+
const content = claim.content || claim.text || "";
|
|
43
44
|
if (content) node.content = content;
|
|
44
45
|
|
|
45
|
-
const status = claim.status ||
|
|
46
|
+
const status = claim.status || "";
|
|
46
47
|
if (status) node.status = status;
|
|
47
48
|
|
|
48
49
|
const tags = Array.isArray(claim.tags) ? claim.tags : [];
|
|
@@ -53,13 +54,13 @@ export function convert(compilation) {
|
|
|
53
54
|
})),
|
|
54
55
|
};
|
|
55
56
|
|
|
56
|
-
return JSON.stringify(tree, null, 2) +
|
|
57
|
+
return JSON.stringify(tree, null, 2) + "\n";
|
|
57
58
|
}
|
|
58
59
|
|
|
59
60
|
function getEvidence(claim) {
|
|
60
|
-
if (typeof claim.evidence ===
|
|
61
|
-
if (typeof claim.evidence ===
|
|
62
|
-
return claim.evidence.tier || claim.evidence_tier ||
|
|
61
|
+
if (typeof claim.evidence === "string") return claim.evidence;
|
|
62
|
+
if (typeof claim.evidence === "object" && claim.evidence !== null) {
|
|
63
|
+
return claim.evidence.tier || claim.evidence_tier || "";
|
|
63
64
|
}
|
|
64
|
-
return claim.evidence_tier ||
|
|
65
|
+
return claim.evidence_tier || "";
|
|
65
66
|
}
|
|
@@ -6,10 +6,11 @@
|
|
|
6
6
|
* Zero dependencies — node built-in only.
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
|
-
export const name =
|
|
10
|
-
export const extension =
|
|
11
|
-
export const mimeType =
|
|
12
|
-
export const description =
|
|
9
|
+
export const name = "typescript-defs";
|
|
10
|
+
export const extension = ".d.ts";
|
|
11
|
+
export const mimeType = "text/plain; charset=utf-8";
|
|
12
|
+
export const description =
|
|
13
|
+
"TypeScript type definitions derived from compilation data";
|
|
13
14
|
|
|
14
15
|
/**
|
|
15
16
|
* Convert a compilation object to TypeScript .d.ts definitions.
|
|
@@ -22,106 +23,108 @@ export function convert(compilation) {
|
|
|
22
23
|
const conflicts = compilation.conflicts || [];
|
|
23
24
|
const certificate = compilation.certificate || {};
|
|
24
25
|
|
|
25
|
-
const claimTypes = uniqueSorted(claims.map(c => c.type).filter(Boolean));
|
|
26
|
+
const claimTypes = uniqueSorted(claims.map((c) => c.type).filter(Boolean));
|
|
26
27
|
const evidenceTiers = uniqueSorted(
|
|
27
|
-
claims
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
28
|
+
claims
|
|
29
|
+
.map((c) => {
|
|
30
|
+
if (typeof c.evidence === "string") return c.evidence;
|
|
31
|
+
return c.evidence?.tier ?? c.evidence_tier ?? null;
|
|
32
|
+
})
|
|
33
|
+
.filter(Boolean),
|
|
31
34
|
);
|
|
32
|
-
const statuses = uniqueSorted(claims.map(c => c.status).filter(Boolean));
|
|
35
|
+
const statuses = uniqueSorted(claims.map((c) => c.status).filter(Boolean));
|
|
33
36
|
|
|
34
37
|
const lines = [];
|
|
35
38
|
|
|
36
|
-
lines.push(
|
|
37
|
-
lines.push(
|
|
38
|
-
lines.push(
|
|
39
|
+
lines.push("// Auto-generated by mill typescript-defs format");
|
|
40
|
+
lines.push("// Derived from compilation data — do not edit manually");
|
|
41
|
+
lines.push("");
|
|
39
42
|
|
|
40
43
|
// ClaimType union
|
|
41
44
|
lines.push(`export type ClaimType = ${unionType(claimTypes)};`);
|
|
42
|
-
lines.push(
|
|
45
|
+
lines.push("");
|
|
43
46
|
|
|
44
47
|
// EvidenceTier union
|
|
45
48
|
lines.push(`export type EvidenceTier = ${unionType(evidenceTiers)};`);
|
|
46
|
-
lines.push(
|
|
49
|
+
lines.push("");
|
|
47
50
|
|
|
48
51
|
// ClaimStatus union
|
|
49
52
|
lines.push(`export type ClaimStatus = ${unionType(statuses)};`);
|
|
50
|
-
lines.push(
|
|
53
|
+
lines.push("");
|
|
51
54
|
|
|
52
55
|
// Evidence interface
|
|
53
|
-
lines.push(
|
|
54
|
-
lines.push(
|
|
55
|
-
lines.push(
|
|
56
|
-
lines.push(
|
|
57
|
-
lines.push(
|
|
56
|
+
lines.push("export interface Evidence {");
|
|
57
|
+
lines.push(" tier: EvidenceTier;");
|
|
58
|
+
lines.push(" source?: string;");
|
|
59
|
+
lines.push("}");
|
|
60
|
+
lines.push("");
|
|
58
61
|
|
|
59
62
|
// Source interface
|
|
60
|
-
lines.push(
|
|
61
|
-
lines.push(
|
|
62
|
-
lines.push(
|
|
63
|
-
lines.push(
|
|
64
|
-
lines.push(
|
|
63
|
+
lines.push("export interface ClaimSource {");
|
|
64
|
+
lines.push(" origin?: string;");
|
|
65
|
+
lines.push(" artifact?: string;");
|
|
66
|
+
lines.push("}");
|
|
67
|
+
lines.push("");
|
|
65
68
|
|
|
66
69
|
// Claim interface
|
|
67
|
-
lines.push(
|
|
68
|
-
lines.push(
|
|
69
|
-
lines.push(
|
|
70
|
-
lines.push(
|
|
71
|
-
lines.push(
|
|
72
|
-
lines.push(
|
|
73
|
-
lines.push(
|
|
74
|
-
lines.push(
|
|
75
|
-
lines.push(
|
|
76
|
-
lines.push(
|
|
77
|
-
lines.push(
|
|
78
|
-
lines.push(
|
|
70
|
+
lines.push("export interface Claim {");
|
|
71
|
+
lines.push(" id: string;");
|
|
72
|
+
lines.push(" type: ClaimType;");
|
|
73
|
+
lines.push(" content: string;");
|
|
74
|
+
lines.push(" evidence: EvidenceTier | Evidence;");
|
|
75
|
+
lines.push(" status: ClaimStatus;");
|
|
76
|
+
lines.push(" confidence?: number;");
|
|
77
|
+
lines.push(" source?: string | ClaimSource;");
|
|
78
|
+
lines.push(" tags?: string[];");
|
|
79
|
+
lines.push(" created?: string;");
|
|
80
|
+
lines.push("}");
|
|
81
|
+
lines.push("");
|
|
79
82
|
|
|
80
83
|
// Meta interface
|
|
81
|
-
lines.push(
|
|
82
|
-
lines.push(
|
|
83
|
-
lines.push(
|
|
84
|
-
lines.push(
|
|
84
|
+
lines.push("export interface Meta {");
|
|
85
|
+
lines.push(" sprint?: string;");
|
|
86
|
+
lines.push(" question?: string;");
|
|
87
|
+
lines.push(" audience?: string;");
|
|
85
88
|
for (const key of Object.keys(meta)) {
|
|
86
|
-
if (![
|
|
89
|
+
if (!["sprint", "question", "audience"].includes(key)) {
|
|
87
90
|
lines.push(` ${sanitizeKey(key)}?: ${inferTsType(meta[key])};`);
|
|
88
91
|
}
|
|
89
92
|
}
|
|
90
|
-
lines.push(
|
|
91
|
-
lines.push(
|
|
93
|
+
lines.push("}");
|
|
94
|
+
lines.push("");
|
|
92
95
|
|
|
93
96
|
// Conflict interface
|
|
94
|
-
lines.push(
|
|
95
|
-
lines.push(
|
|
96
|
-
lines.push(
|
|
97
|
-
lines.push(
|
|
98
|
-
lines.push(
|
|
99
|
-
lines.push(
|
|
100
|
-
lines.push(
|
|
97
|
+
lines.push("export interface Conflict {");
|
|
98
|
+
lines.push(" ids?: string[];");
|
|
99
|
+
lines.push(" description?: string;");
|
|
100
|
+
lines.push(" reason?: string;");
|
|
101
|
+
lines.push(" resolution?: string;");
|
|
102
|
+
lines.push("}");
|
|
103
|
+
lines.push("");
|
|
101
104
|
|
|
102
105
|
// Certificate interface
|
|
103
|
-
lines.push(
|
|
104
|
-
lines.push(
|
|
105
|
-
lines.push(
|
|
106
|
-
lines.push(
|
|
106
|
+
lines.push("export interface Certificate {");
|
|
107
|
+
lines.push(" compiled_at?: string;");
|
|
108
|
+
lines.push(" sha256?: string;");
|
|
109
|
+
lines.push(" claim_count?: number;");
|
|
107
110
|
for (const key of Object.keys(certificate)) {
|
|
108
|
-
if (![
|
|
111
|
+
if (!["compiled_at", "sha256", "claim_count"].includes(key)) {
|
|
109
112
|
lines.push(` ${sanitizeKey(key)}?: ${inferTsType(certificate[key])};`);
|
|
110
113
|
}
|
|
111
114
|
}
|
|
112
|
-
lines.push(
|
|
113
|
-
lines.push(
|
|
115
|
+
lines.push("}");
|
|
116
|
+
lines.push("");
|
|
114
117
|
|
|
115
118
|
// Compilation interface
|
|
116
|
-
lines.push(
|
|
117
|
-
lines.push(
|
|
118
|
-
lines.push(
|
|
119
|
-
lines.push(
|
|
120
|
-
lines.push(
|
|
121
|
-
lines.push(
|
|
122
|
-
lines.push(
|
|
123
|
-
|
|
124
|
-
return lines.join(
|
|
119
|
+
lines.push("export interface Compilation {");
|
|
120
|
+
lines.push(" meta: Meta;");
|
|
121
|
+
lines.push(" claims: Claim[];");
|
|
122
|
+
lines.push(" conflicts: Conflict[];");
|
|
123
|
+
lines.push(" certificate: Certificate;");
|
|
124
|
+
lines.push("}");
|
|
125
|
+
lines.push("");
|
|
126
|
+
|
|
127
|
+
return lines.join("\n");
|
|
125
128
|
}
|
|
126
129
|
|
|
127
130
|
function uniqueSorted(arr) {
|
|
@@ -129,8 +132,8 @@ function uniqueSorted(arr) {
|
|
|
129
132
|
}
|
|
130
133
|
|
|
131
134
|
function unionType(values) {
|
|
132
|
-
if (values.length === 0) return
|
|
133
|
-
return values.map(v => `'${v}'`).join(
|
|
135
|
+
if (values.length === 0) return "string";
|
|
136
|
+
return values.map((v) => `'${v}'`).join(" | ");
|
|
134
137
|
}
|
|
135
138
|
|
|
136
139
|
function sanitizeKey(key) {
|
|
@@ -138,10 +141,10 @@ function sanitizeKey(key) {
|
|
|
138
141
|
}
|
|
139
142
|
|
|
140
143
|
function inferTsType(value) {
|
|
141
|
-
if (value === null || value === undefined) return
|
|
142
|
-
if (typeof value ===
|
|
143
|
-
if (typeof value ===
|
|
144
|
-
if (typeof value ===
|
|
145
|
-
if (Array.isArray(value)) return
|
|
146
|
-
return
|
|
144
|
+
if (value === null || value === undefined) return "unknown";
|
|
145
|
+
if (typeof value === "number") return "number";
|
|
146
|
+
if (typeof value === "boolean") return "boolean";
|
|
147
|
+
if (typeof value === "string") return "string";
|
|
148
|
+
if (Array.isArray(value)) return "unknown[]";
|
|
149
|
+
return "Record<string, unknown>";
|
|
147
150
|
}
|