cornfield 0.5.0 → 0.7.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.
@@ -0,0 +1,259 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://github.com/popcorn245/CornField/blob/main/core/agent-contract.schema.json",
4
+ "title": "cornfield agent contract, version 1",
5
+ "description": "The JSON a cornfield-run fenced block holds: a request, a report or a stop request. docs/agent-contract.md says what each means. Checks the shape; a few rules are the validator's alone (the configured profile list, that a date is a real one), and are listed in the docs.",
6
+ "oneOf": [
7
+ {
8
+ "$ref": "#/$defs/request"
9
+ },
10
+ {
11
+ "$ref": "#/$defs/report"
12
+ },
13
+ {
14
+ "$ref": "#/$defs/stopRequest"
15
+ }
16
+ ],
17
+ "$defs": {
18
+ "runId": {
19
+ "description": "run- and a 26 character ULID in Crockford base32",
20
+ "type": "string",
21
+ "pattern": "^run-[0-7][0-9A-HJKMNP-TV-Z]{25}$"
22
+ },
23
+ "request": {
24
+ "description": "A request for a run. It carries no credential: a property named like a token, a secret or a password is refused.",
25
+ "type": "object",
26
+ "additionalProperties": false,
27
+ "required": [
28
+ "version",
29
+ "runId",
30
+ "kind",
31
+ "refs",
32
+ "brief",
33
+ "requestedBy",
34
+ "requestedAt"
35
+ ],
36
+ "propertyNames": {
37
+ "not": {
38
+ "pattern": "(?:[tT][oO][kK][eE][nN]|[sS][eE][cC][rR][eE][tT]|[pP][aA][sS][sS][wW]|[cC][rR][eE][dD][eE][nN][tT][iI][aA][lL]|[aA][pP][iI][_-]?[kK][eE][yY]|[aA][cC][cC][eE][sS][sS][_-]?[kK][eE][yY]|[pP][rR][iI][vV][aA][tT][eE][_-]?[kK][eE][yY]|[sS][sS][hH][_-]?[kK][eE][yY]|[aA][uU][tT][hH][oO][rR][iI][zZ][aA][tT][iI][oO][nN]|[bB][eE][aA][rR][eE][rR]|[cC][oO][oO][kK][iI][eE])"
39
+ }
40
+ },
41
+ "properties": {
42
+ "version": {
43
+ "const": 1
44
+ },
45
+ "runId": {
46
+ "$ref": "#/$defs/runId"
47
+ },
48
+ "kind": {
49
+ "enum": [
50
+ "code",
51
+ "summary",
52
+ "brief",
53
+ "proposal"
54
+ ]
55
+ },
56
+ "profile": {
57
+ "type": "string",
58
+ "maxLength": 64,
59
+ "not": {
60
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
61
+ },
62
+ "pattern": "^[A-Za-z0-9][A-Za-z0-9._-]{0,63}$",
63
+ "description": "A name the runner maps to a model, a machine and a budget. When the developer configured a list, only those names."
64
+ },
65
+ "refs": {
66
+ "type": "object",
67
+ "additionalProperties": false,
68
+ "properties": {
69
+ "issue": {
70
+ "type": "integer",
71
+ "minimum": 1,
72
+ "maximum": 2147483647
73
+ },
74
+ "proposal": {
75
+ "type": "string",
76
+ "maxLength": 120,
77
+ "not": {
78
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
79
+ },
80
+ "pattern": "^[A-Za-z0-9][A-Za-z0-9._-]{0,119}$"
81
+ },
82
+ "pull": {
83
+ "type": "integer",
84
+ "minimum": 1,
85
+ "maximum": 2147483647,
86
+ "description": "The spec pull request that holds the proposal; only with proposal."
87
+ },
88
+ "thread": {
89
+ "type": "integer",
90
+ "minimum": 1,
91
+ "maximum": 2147483647
92
+ }
93
+ },
94
+ "anyOf": [
95
+ {
96
+ "required": [
97
+ "issue"
98
+ ]
99
+ },
100
+ {
101
+ "required": [
102
+ "proposal"
103
+ ]
104
+ },
105
+ {
106
+ "required": [
107
+ "thread"
108
+ ]
109
+ }
110
+ ],
111
+ "dependentRequired": {
112
+ "pull": [
113
+ "proposal"
114
+ ]
115
+ }
116
+ },
117
+ "branch": {
118
+ "type": "string",
119
+ "maxLength": 200,
120
+ "not": {
121
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
122
+ },
123
+ "minLength": 1,
124
+ "description": "A hint: a safe git ref name.",
125
+ "allOf": [
126
+ {
127
+ "pattern": "^[A-Za-z0-9._/-]+$"
128
+ },
129
+ {
130
+ "not": {
131
+ "pattern": "^-|^/|/$|//|\\.\\.|\\.$|(^|/)\\.|\\.lock(/|$)"
132
+ }
133
+ }
134
+ ]
135
+ },
136
+ "brief": {
137
+ "type": "string",
138
+ "maxLength": 20000,
139
+ "not": {
140
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
141
+ }
142
+ },
143
+ "limits": {
144
+ "type": "object",
145
+ "additionalProperties": false,
146
+ "properties": {
147
+ "minutes": {
148
+ "type": "number",
149
+ "exclusiveMinimum": 0
150
+ },
151
+ "turns": {
152
+ "type": "integer",
153
+ "exclusiveMinimum": 0
154
+ },
155
+ "cost": {
156
+ "type": "number",
157
+ "exclusiveMinimum": 0
158
+ }
159
+ }
160
+ },
161
+ "nodes": {
162
+ "type": "array",
163
+ "maxItems": 100,
164
+ "items": {
165
+ "type": "string",
166
+ "maxLength": 200,
167
+ "not": {
168
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
169
+ },
170
+ "pattern": "^[A-Za-z0-9][A-Za-z0-9._:/-]{0,199}$"
171
+ }
172
+ },
173
+ "requestedBy": {
174
+ "type": "string",
175
+ "maxLength": 40,
176
+ "not": {
177
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
178
+ },
179
+ "pattern": "^[A-Za-z0-9][A-Za-z0-9._-]{0,39}$"
180
+ },
181
+ "requestedAt": {
182
+ "type": "string",
183
+ "pattern": "^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}(\\.\\d{1,3})?Z$"
184
+ }
185
+ }
186
+ },
187
+ "report": {
188
+ "description": "What a runner may say about a run it is doing.",
189
+ "type": "object",
190
+ "additionalProperties": false,
191
+ "required": [
192
+ "state"
193
+ ],
194
+ "properties": {
195
+ "state": {
196
+ "enum": [
197
+ "claimed",
198
+ "working",
199
+ "done",
200
+ "failed",
201
+ "stopped"
202
+ ]
203
+ },
204
+ "note": {
205
+ "type": "string",
206
+ "maxLength": 4000,
207
+ "not": {
208
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
209
+ }
210
+ },
211
+ "url": {
212
+ "type": "string",
213
+ "maxLength": 2000,
214
+ "not": {
215
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
216
+ },
217
+ "pattern": "^https?://[^\\s/@?#]+([/?#]\\S*)?$",
218
+ "description": "Where the runner keeps its logs.",
219
+ "allOf": [
220
+ {
221
+ "not": {
222
+ "pattern": "[?&#;](?:[^\\s=&#;]*(?:[tT][oO][kK][eE][nN]|[sS][eE][cC][rR][eE][tT]|[pP][aA][sS][sS][wW]|[kK][eE][yY]|[sS][iI][gG][nN][aA][tT][uU][rR][eE])[^\\s=&#;]*|[sS][iI][gG])="
223
+ }
224
+ }
225
+ ]
226
+ },
227
+ "tokens": {
228
+ "type": "integer",
229
+ "minimum": 0,
230
+ "maximum": 9007199254740991
231
+ },
232
+ "cost": {
233
+ "type": "number",
234
+ "minimum": 0
235
+ }
236
+ }
237
+ },
238
+ "stopRequest": {
239
+ "description": "cornfield asking a runner to stop. The runner decides what stopping means.",
240
+ "type": "object",
241
+ "additionalProperties": false,
242
+ "required": [
243
+ "state"
244
+ ],
245
+ "properties": {
246
+ "state": {
247
+ "const": "stop-requested"
248
+ },
249
+ "note": {
250
+ "type": "string",
251
+ "maxLength": 4000,
252
+ "not": {
253
+ "pattern": "(?<![A-Za-z0-9])gh[pousr]_[A-Za-z0-9]{30,}|(?<![A-Za-z0-9])github_pat_[A-Za-z0-9_]{20,}|(?<![A-Za-z0-9])glpat-[A-Za-z0-9_-]{15,}|(?<![A-Za-z0-9])gto-[A-Za-z0-9]{20,}|(?<![A-Za-z0-9])sk-(?=[A-Za-z0-9_-]{20})[A-Za-z_-]{0,40}[0-9]|(?<![A-Za-z0-9])AKIA[0-9A-Z]{16}|(?<![A-Za-z0-9])AIza[0-9A-Za-z_-]{35}|(?<![A-Za-z0-9])xox[abprs]-[A-Za-z0-9-]{10,}|(?<![A-Za-z0-9])eyJ[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{10,}\\.[A-Za-z0-9_-]{5,}|-----BEGIN [A-Z ]{0,40}PRIVATE KEY-----|(?<![A-Za-z0-9])[bB][eE][aA][rR][eE][rR][ \\t]+(?=[A-Za-z0-9._~+/=-]{20})[A-Za-z._~+/=-]{0,40}[0-9]|(?<![A-Za-z0-9+.-])[A-Za-z][A-Za-z0-9+.-]{0,31}://[^\\s/@:]+:[^\\s/@]+@"
254
+ }
255
+ }
256
+ }
257
+ }
258
+ }
259
+ }
package/core/config.js CHANGED
@@ -66,7 +66,7 @@ export const FORGE_TYPES = ['github', 'forgejo'];
66
66
  /** How a pull request cornfield lands is merged (`forge.mergeMethod`): the way the repo lands its pull requests */
67
67
  export const MERGE_METHODS = ['merge', 'squash', 'rebase'];
68
68
  /** The events a hook may ask for (`hooks[].events`), and what each one means: docs/config.md#hooks */
69
- export const HOOK_EVENTS = Object.freeze(['spec.ready', 'spec.approved', 'spec.sentBack', 'build.opened', 'pr.landed']);
69
+ export const HOOK_EVENTS = Object.freeze(['spec.ready', 'spec.approved', 'spec.sentBack', 'build.opened', 'pr.landed', 'session.expiring']);
70
70
  /** The most hooks a config lists */
71
71
  export const MAX_HOOKS = 20;
72
72
  /** The bounds of `hookPoll.specs` in milliseconds: not under a minute (the forge is not hammered), not over an hour */
package/core/defuse.js ADDED
@@ -0,0 +1,17 @@
1
+ /**
2
+ * @module core/defuse
3
+ *
4
+ * Breaking the mentions and references in text cornfield posts on the forge for someone else: `@user`, `@org/team`,
5
+ * `#1`, `owner/repo#1`, `GH-1`, and the links the forge would make of `https://…` or `www.…`. A zero-width space after
6
+ * the character keeps the text as it reads and stops it notifying anyone or linking anything. The pipeline's issues
7
+ * (server/pipeline.js), a review that came through the review API (server/reviews.js) and the agent contract
8
+ * (core/agent-contract.js) use it. It imports nothing, so Node and the browser can both load it.
9
+ */
10
+
11
+ /** A zero-width space: it ends a mention or a reference without showing */
12
+ export const ZW = '​';
13
+
14
+ /** Text with every mention, reference and auto-link broken (see the module's head) */
15
+ export function defuse(text) {
16
+ return String(text).replace(/[@#]/g, (c) => `${c}${ZW}`).replace(/\b(GH)-(?=\d)/gi, `$1${ZW}-`).replace(/:\/\//g, `:${ZW}//`).replace(/\b(www)\./gi, `$1${ZW}.`);
17
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "cornfield",
3
- "version": "0.5.0",
3
+ "version": "0.7.0",
4
4
  "description": "A self-hostable dev dashboard with the topology map at its centre: proposals on the map, scenarios, outages and what-if edits, for any repo.",
5
5
  "license": "MIT",
6
6
  "author": "popcorn245 (https://github.com/popcorn245)",
@@ -31,6 +31,7 @@
31
31
  "./plugins/*": "./plugins/*",
32
32
  "./deriver-kit": "./core/deriver-kit.js",
33
33
  "./server": "./server/server.js",
34
+ "./agent-contract.schema.json": "./core/agent-contract.schema.json",
34
35
  "./package.json": "./package.json"
35
36
  },
36
37
  "files": [