paperlint 6.2.2 → 6.3.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.
- package/README.md +8 -1
- package/dist/adapters/hotcrp/index.d.ts +7 -0
- package/dist/adapters/hotcrp/index.d.ts.map +1 -0
- package/dist/adapters/hotcrp/index.js +7 -0
- package/dist/adapters/hotcrp/index.js.map +1 -0
- package/dist/adapters/hotcrp/portal.io.d.ts +20 -0
- package/dist/adapters/hotcrp/portal.io.d.ts.map +1 -0
- package/dist/adapters/hotcrp/portal.io.js +90 -0
- package/dist/adapters/hotcrp/portal.io.js.map +1 -0
- package/dist/adapters/hotcrp/response.d.ts +13 -0
- package/dist/adapters/hotcrp/response.d.ts.map +1 -0
- package/dist/adapters/hotcrp/response.js +138 -0
- package/dist/adapters/hotcrp/response.js.map +1 -0
- package/dist/cli.d.ts +3 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +109 -34
- package/dist/cli.js.map +1 -1
- package/dist/domain/result.d.ts +4 -0
- package/dist/domain/result.d.ts.map +1 -1
- package/dist/domain/result.js +2 -0
- package/dist/domain/result.js.map +1 -1
- package/dist/domain/submission.d.ts +106 -0
- package/dist/domain/submission.d.ts.map +1 -0
- package/dist/domain/submission.js +39 -0
- package/dist/domain/submission.js.map +1 -0
- package/dist/domain/venue-name.d.ts +38 -0
- package/dist/domain/venue-name.d.ts.map +1 -0
- package/dist/domain/venue-name.js +71 -0
- package/dist/domain/venue-name.js.map +1 -0
- package/dist/folder-venue-rule.d.ts +51 -0
- package/dist/folder-venue-rule.d.ts.map +1 -0
- package/dist/folder-venue-rule.js +96 -0
- package/dist/folder-venue-rule.js.map +1 -0
- package/dist/init.d.ts +6 -0
- package/dist/init.d.ts.map +1 -1
- package/dist/init.js +3 -3
- package/dist/init.js.map +1 -1
- package/dist/lib/paper-config.d.ts.map +1 -1
- package/dist/lib/paper-config.js +5 -1
- package/dist/lib/paper-config.js.map +1 -1
- package/dist/new-paper.d.ts +19 -5
- package/dist/new-paper.d.ts.map +1 -1
- package/dist/new-paper.js +23 -4
- package/dist/new-paper.js.map +1 -1
- package/dist/paper-settings.d.ts +3 -0
- package/dist/paper-settings.d.ts.map +1 -1
- package/dist/paper-settings.js +20 -4
- package/dist/paper-settings.js.map +1 -1
- package/dist/ports/submission-portal.d.ts +19 -0
- package/dist/ports/submission-portal.d.ts.map +1 -0
- package/dist/ports/submission-portal.js +2 -0
- package/dist/ports/submission-portal.js.map +1 -0
- package/dist/presets.d.ts +24 -0
- package/dist/presets.d.ts.map +1 -1
- package/dist/presets.js +35 -3
- package/dist/presets.js.map +1 -1
- package/dist/rules-config.js +1 -1
- package/dist/submission.d.ts +61 -0
- package/dist/submission.d.ts.map +1 -0
- package/dist/submission.js +211 -0
- package/dist/submission.js.map +1 -0
- package/dist/tex-requirements.d.ts +3 -0
- package/dist/tex-requirements.d.ts.map +1 -1
- package/dist/tex-requirements.js +3 -0
- package/dist/tex-requirements.js.map +1 -1
- package/dist/tex-venue-rules.d.ts +6 -7
- package/dist/tex-venue-rules.d.ts.map +1 -1
- package/dist/tex-venue-rules.js +10 -14
- package/dist/tex-venue-rules.js.map +1 -1
- package/dist/types.d.ts +13 -0
- package/dist/types.d.ts.map +1 -1
- package/docs/configuration.md +17 -10
- package/docs/rules/paper/folder-venue-leftover.md +104 -0
- package/docs/rules/talk/captions-cover.md +1 -1
- package/docs/rules/talk/duration-floor.md +1 -1
- package/docs/rules.md +44 -42
- package/docs/skills.md +5 -4
- package/docs/submission.md +64 -0
- package/docs/talk.md +1 -1
- package/lib/paper-config.ts +6 -1
- package/lib/skill-checks.d.mts +7 -0
- package/lib/skill-trigger-cases.mjs +11 -0
- package/package.json +2 -2
- package/presets/aidc.jsonc +6 -0
- package/presets/venue-profile.schema.json +17 -1
- package/skills/paper-pipeline/paper-pipeline.harness.mjs +4 -0
- package/skills/submission-portal/SKILL.md +69 -0
- package/skills/submission-portal/SKILL.md.spec.ts +71 -0
- package/skills/submission-portal/submission-portal.eval.mjs +15 -0
- package/skills/submission-portal/submission-portal.test.ts +81 -0
- package/skills/submit-paper/SKILL.md +2 -1
- package/skills/submit-paper/SKILL.md.spec.ts +1 -0
- package/skills/verify-citations/SKILL.md +8 -4
- package/skills/verify-citations/SKILL.md.spec.ts +7 -3
- package/skills/verify-citations/scripts/verify-cites.mjs +23 -5
- package/skills/verify-citations/scripts/verify-cites.test.mjs +76 -5
- package/src/adapters/hotcrp/cassette/README.md +24 -0
- package/src/adapters/hotcrp/cassette/get-noauth.json +10 -0
- package/src/adapters/hotcrp/cassette/get-paper.json +39 -0
- package/src/adapters/hotcrp/cassette/post-dot.json +21 -0
- package/src/adapters/hotcrp/cassette/post-ok.json +12 -0
- package/src/adapters/hotcrp/index.ts +11 -0
- package/src/adapters/hotcrp/portal.io.ts +130 -0
- package/src/adapters/hotcrp/portal.test.ts +503 -0
- package/src/adapters/hotcrp/response.ts +181 -0
- package/src/cli.test.ts +109 -0
- package/src/cli.ts +140 -21
- package/src/domain/result.test.ts +9 -1
- package/src/domain/result.ts +5 -0
- package/src/domain/submission.test.ts +45 -0
- package/src/domain/submission.ts +141 -0
- package/src/domain/venue-name.test.ts +115 -0
- package/src/domain/venue-name.ts +129 -0
- package/src/folder-venue-rule.test.ts +182 -0
- package/src/folder-venue-rule.ts +141 -0
- package/src/init.test.ts +22 -0
- package/src/init.ts +9 -2
- package/src/new-paper.harness.mjs +11 -9
- package/src/new-paper.test.ts +129 -8
- package/src/new-paper.ts +38 -7
- package/src/paper-settings.test.ts +12 -1
- package/src/paper-settings.ts +25 -5
- package/src/parse-args.test.ts +19 -0
- package/src/ports/submission-portal.ts +26 -0
- package/src/presets.test.ts +22 -0
- package/src/presets.ts +46 -3
- package/src/rule-cases.test.ts +19 -0
- package/src/rules-config.ts +1 -1
- package/src/submission.test.ts +496 -0
- package/src/submission.ts +311 -0
- package/src/tex-requirements.ts +8 -0
- package/src/tex-venue-rules.test.ts +1 -1
- package/src/tex-venue-rules.ts +12 -25
- package/src/types.ts +13 -0
package/README.md
CHANGED
|
@@ -103,9 +103,12 @@ REALM.
|
|
|
103
103
|
```
|
|
104
104
|
|
|
105
105
|
3. Create a paper. `--venue` names its venue preset from the table above, `--kind` which of its page
|
|
106
|
-
limits applies:
|
|
106
|
+
limits applies. Name the folder after the work, not the venue: a rejected paper moves to another
|
|
107
|
+
venue and keeps its folder, so `new` refuses a name like `aisec-2026` (`--allow-venue-name` when
|
|
108
|
+
the word really is the work's):
|
|
107
109
|
|
|
108
110
|
<!-- `vigiles:symbol src/new-paper.ts#newPaper` — `npm run check` fails if this function is renamed or removed. -->
|
|
111
|
+
<!-- `vigiles:symbol src/new-paper.ts#ALLOW_VENUE_NAME` — the flag's one spelling; `npm run check` fails if it is renamed or removed. -->
|
|
109
112
|
|
|
110
113
|
```sh
|
|
111
114
|
npx paperlint new my-paper --venue agenticdev --kind short
|
|
@@ -161,6 +164,8 @@ paperlint finds a paper by its folder: `<papersDir>/<name>/`, with the main file
|
|
|
161
164
|
| `npx paperlint lint` | runs every check over your papers; `--fix` fixes what can be fixed |
|
|
162
165
|
| `npx paperlint toolchain` | installs TeX Live with the packages your venues need (~270 MB, ~3 min, once) |
|
|
163
166
|
| `npx paperlint doctor` | checks the setup and exits non-zero if something is miswired |
|
|
167
|
+
| `npx paperlint submission show <paper>` | the paper's submission on the venue's portal, and whether it holds your build |
|
|
168
|
+
| `npx paperlint submission update <paper>` | checks a new PDF/abstract against the portal; `--save` sends it for real |
|
|
164
169
|
| `npx paperlint --help` | every command and flag |
|
|
165
170
|
|
|
166
171
|
## 🧠 Skills
|
|
@@ -175,6 +180,7 @@ what it does — "is this idea worth a paper?", "find me a venue for this". `ini
|
|
|
175
180
|
- **A hostile review before the real one.** `paper-adversarial-review`
|
|
176
181
|
- **A ready / not ready verdict before you submit**, worst problem first. `harden-paper`
|
|
177
182
|
- **Where your paper stands**, measured from the real build. `paper-status`
|
|
183
|
+
- **The PDF and abstract replaced on HotCRP**, dry run first, and proof the portal holds your build. `submission-portal`
|
|
178
184
|
|
|
179
185
|
Every skill, by stage: [`docs/skills.md`](docs/skills.md).
|
|
180
186
|
|
|
@@ -313,6 +319,7 @@ Only `paperlint lint --fix`, and only three rules: `paper/section-word` (`§`
|
|
|
313
319
|
- [`docs/configuration.md`](docs/configuration.md) — every setting, how `build` compiles, using your own ESLint
|
|
314
320
|
- [`docs/rules.md`](docs/rules.md) — every check, venue presets, recording a submitted PDF
|
|
315
321
|
- [`docs/references.md`](docs/references.md) — the reference check, and the cache file to commit
|
|
322
|
+
- [`docs/submission.md`](docs/submission.md) — reading and updating a submission on the venue's portal (HotCRP)
|
|
316
323
|
- [`docs/optional-rules.md`](docs/optional-rules.md) — checks only some venues need
|
|
317
324
|
- [`docs/toolchain.md`](docs/toolchain.md) — TeX Live, and Banal (HotCRP's page-geometry checker, GPL)
|
|
318
325
|
- [`CONTRIBUTING.md`](CONTRIBUTING.md) — how the package is tested and released, and adding a venue to it
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* HotCRP, as the `SubmissionPortal` port: its REST API read and written over `fetch`, its answers
|
|
3
|
+
* parsed here. Everything that changes if HotCRP's API does lives in this folder.
|
|
4
|
+
*/
|
|
5
|
+
export { CONTENT_FIELD, changeObject, hotcrpPortal, type HotcrpOptions, } from "./portal.io.ts";
|
|
6
|
+
export { parseShow, parseUpdate, sha256OfHash } from "./response.ts";
|
|
7
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/adapters/hotcrp/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,EACL,aAAa,EACb,YAAY,EACZ,YAAY,EACZ,KAAK,aAAa,GACnB,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,SAAS,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* HotCRP, as the `SubmissionPortal` port: its REST API read and written over `fetch`, its answers
|
|
3
|
+
* parsed here. Everything that changes if HotCRP's API does lives in this folder.
|
|
4
|
+
*/
|
|
5
|
+
export { CONTENT_FIELD, changeObject, hotcrpPortal, } from "./portal.io.js";
|
|
6
|
+
export { parseShow, parseUpdate, sha256OfHash } from "./response.js";
|
|
7
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/adapters/hotcrp/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,EACL,aAAa,EACb,YAAY,EACZ,YAAY,GAEb,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,SAAS,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { SubmissionChange } from "../../domain/submission.ts";
|
|
2
|
+
import type { SubmissionPortal } from "../../ports/submission-portal.ts";
|
|
3
|
+
/**
|
|
4
|
+
* The form field the PDF travels in, and the name the `json` object's `content_file` refers to it
|
|
5
|
+
* by. 🔴 NO DOT, SPACE OR BRACKET: HotCRP looks the name up in PHP's `$_FILES`, and PHP renames a
|
|
6
|
+
* dot or a space in a field name to `_`. The documented `-F paper.pdf=@paper.pdf` therefore arrives
|
|
7
|
+
* as `paper_pdf`, the lookup of `paper.pdf` misses, and HotCRP answers "Ignored attempt to upload
|
|
8
|
+
* document without any content" with `valid: false` — measured on a real HotCRP, 2026-10-03.
|
|
9
|
+
*/
|
|
10
|
+
export declare const CONTENT_FIELD = "paperlint_pdf";
|
|
11
|
+
export interface HotcrpOptions {
|
|
12
|
+
/** The site's base URL, no trailing slash: `https://example.org`. */
|
|
13
|
+
readonly url: string;
|
|
14
|
+
readonly token: string;
|
|
15
|
+
}
|
|
16
|
+
/** The submission object a change sends: only the fields it changes. */
|
|
17
|
+
export declare function changeObject(id: number, c: SubmissionChange): Readonly<Record<string, unknown>>;
|
|
18
|
+
/** HotCRP at `o.url`, read and changed with `o.token`. */
|
|
19
|
+
export declare function hotcrpPortal(o: HotcrpOptions): SubmissionPortal;
|
|
20
|
+
//# sourceMappingURL=portal.io.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"portal.io.d.ts","sourceRoot":"","sources":["../../../src/adapters/hotcrp/portal.io.ts"],"names":[],"mappings":"AAgBA,OAAO,KAAK,EAEV,gBAAgB,EACjB,MAAM,4BAA4B,CAAC;AACpC,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,kCAAkC,CAAC;AAGzE;;;;;;GAMG;AACH,eAAO,MAAM,aAAa,kBAAkB,CAAC;AAM7C,MAAM,WAAW,aAAa;IAC5B,qEAAqE;IACrE,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;CACxB;AAmCD,wEAAwE;AACxE,wBAAgB,YAAY,CAC1B,EAAE,EAAE,MAAM,EACV,CAAC,EAAE,gBAAgB,GAClB,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAQnC;AAmBD,0DAA0D;AAC1D,wBAAgB,YAAY,CAAC,CAAC,EAAE,aAAa,GAAG,gBAAgB,CAsB/D"}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* HotCRP's REST API (`<site>/api/paper`) as the `SubmissionPortal` port, over Node's `fetch`.
|
|
3
|
+
*
|
|
4
|
+
* Read: `GET /api/paper?p=<id>&word_limit=hard` (scope `submeta:read`; `word_limit=hard` returns the
|
|
5
|
+
* whole abstract instead of one cut at the soft limit).
|
|
6
|
+
*
|
|
7
|
+
* Change: `POST /api/paper?p=<id>` as multipart/form-data — a `json` field holding a submission
|
|
8
|
+
* object, and the PDF as a file part whose field name is the object's `submission.content_file`
|
|
9
|
+
* (the documented form: `curl -F "json=<data.json" -F paper.pdf=@paper.pdf SITEURL/api/paper`).
|
|
10
|
+
* Without `save` the request carries `dry_run=1`: HotCRP checks the change and keeps nothing.
|
|
11
|
+
*
|
|
12
|
+
* 🔴 THE TOKEN goes in the `Authorization` header and nowhere else: not into a URL, a message, or an
|
|
13
|
+
* error. A failure is described by HTTP status, HotCRP's own messages, or the network error's text.
|
|
14
|
+
*/
|
|
15
|
+
import { messageOf } from "../../domain/text.js";
|
|
16
|
+
import { err } from "../../domain/result.js";
|
|
17
|
+
import { parseShow, parseUpdate } from "./response.js";
|
|
18
|
+
/**
|
|
19
|
+
* The form field the PDF travels in, and the name the `json` object's `content_file` refers to it
|
|
20
|
+
* by. 🔴 NO DOT, SPACE OR BRACKET: HotCRP looks the name up in PHP's `$_FILES`, and PHP renames a
|
|
21
|
+
* dot or a space in a field name to `_`. The documented `-F paper.pdf=@paper.pdf` therefore arrives
|
|
22
|
+
* as `paper_pdf`, the lookup of `paper.pdf` misses, and HotCRP answers "Ignored attempt to upload
|
|
23
|
+
* document without any content" with `valid: false` — measured on a real HotCRP, 2026-10-03.
|
|
24
|
+
*/
|
|
25
|
+
export const CONTENT_FIELD = "paperlint_pdf";
|
|
26
|
+
/** Uploads take a while on a slow link; a read should not. */
|
|
27
|
+
const READ_TIMEOUT_MS = 60_000;
|
|
28
|
+
const WRITE_TIMEOUT_MS = 300_000;
|
|
29
|
+
/** One request → HTTP status and parsed JSON body, or why there is neither. */
|
|
30
|
+
async function call(url, init, token, timeoutMs) {
|
|
31
|
+
try {
|
|
32
|
+
const r = await fetch(url, {
|
|
33
|
+
...init,
|
|
34
|
+
headers: { Authorization: `bearer ${token}`, Accept: "application/json" },
|
|
35
|
+
signal: AbortSignal.timeout(timeoutMs),
|
|
36
|
+
});
|
|
37
|
+
const text = await r.text();
|
|
38
|
+
try {
|
|
39
|
+
return { ok: true, value: { status: r.status, body: JSON.parse(text) } };
|
|
40
|
+
}
|
|
41
|
+
catch {
|
|
42
|
+
return err({
|
|
43
|
+
kind: "malformed",
|
|
44
|
+
httpStatus: r.status,
|
|
45
|
+
detail: `the answer is not JSON (${r.headers.get("content-type") ?? "no content type"})`,
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
catch (e) {
|
|
50
|
+
return err({ kind: "unreachable", detail: messageOf(e) });
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
/** The submission object a change sends: only the fields it changes. */
|
|
54
|
+
export function changeObject(id, c) {
|
|
55
|
+
return {
|
|
56
|
+
object: "paper",
|
|
57
|
+
pid: id,
|
|
58
|
+
...(c.pdf === null ? {} : { submission: { content_file: CONTENT_FIELD } }),
|
|
59
|
+
...(c.abstract === null ? {} : { abstract: c.abstract }),
|
|
60
|
+
...(c.submit ? { status: "submitted" } : {}),
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
function formOf(id, c) {
|
|
64
|
+
const form = new FormData();
|
|
65
|
+
form.append("json", JSON.stringify(changeObject(id, c)));
|
|
66
|
+
if (c.pdf !== null)
|
|
67
|
+
form.append(CONTENT_FIELD, new Blob([new Uint8Array(c.pdf.bytes)], { type: "application/pdf" }), c.pdf.name);
|
|
68
|
+
return form;
|
|
69
|
+
}
|
|
70
|
+
const endpoint = (base, params) => `${base}/api/paper?${new URLSearchParams(params).toString()}`;
|
|
71
|
+
/** HotCRP at `o.url`, read and changed with `o.token`. */
|
|
72
|
+
export function hotcrpPortal(o) {
|
|
73
|
+
return {
|
|
74
|
+
async show(id) {
|
|
75
|
+
const url = endpoint(o.url, { p: String(id), word_limit: "hard" });
|
|
76
|
+
const a = await call(url, { method: "GET" }, o.token, READ_TIMEOUT_MS);
|
|
77
|
+
return a.ok ? parseShow(a.value.status, a.value.body) : a;
|
|
78
|
+
},
|
|
79
|
+
async update(id, change, { save }) {
|
|
80
|
+
const url = endpoint(o.url, {
|
|
81
|
+
p: String(id),
|
|
82
|
+
...(save ? {} : { dry_run: "1" }),
|
|
83
|
+
});
|
|
84
|
+
const body = formOf(id, change);
|
|
85
|
+
const a = await call(url, { method: "POST", body }, o.token, WRITE_TIMEOUT_MS);
|
|
86
|
+
return a.ok ? parseUpdate(a.value.status, a.value.body) : a;
|
|
87
|
+
},
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=portal.io.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"portal.io.js","sourceRoot":"","sources":["../../../src/adapters/hotcrp/portal.io.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AACH,OAAO,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AACjD,OAAO,EAAE,GAAG,EAAe,MAAM,wBAAwB,CAAC;AAM1D,OAAO,EAAE,SAAS,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAEvD;;;;;;GAMG;AACH,MAAM,CAAC,MAAM,aAAa,GAAG,eAAe,CAAC;AAE7C,8DAA8D;AAC9D,MAAM,eAAe,GAAG,MAAM,CAAC;AAC/B,MAAM,gBAAgB,GAAG,OAAO,CAAC;AAajC,+EAA+E;AAC/E,KAAK,UAAU,IAAI,CACjB,GAAW,EACX,IAAqE,EACrE,KAAa,EACb,SAAiB;IAEjB,IAAI,CAAC;QACH,MAAM,CAAC,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE;YACzB,GAAG,IAAI;YACP,OAAO,EAAE,EAAE,aAAa,EAAE,UAAU,KAAK,EAAE,EAAE,MAAM,EAAE,kBAAkB,EAAE;YACzE,MAAM,EAAE,WAAW,CAAC,OAAO,CAAC,SAAS,CAAC;SACvC,CAAC,CAAC;QACH,MAAM,IAAI,GAAG,MAAM,CAAC,CAAC,IAAI,EAAE,CAAC;QAC5B,IAAI,CAAC;YACH,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,IAAI,EAAE,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC;QAC3E,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,GAAG,CAAC;gBACT,IAAI,EAAE,WAAW;gBACjB,UAAU,EAAE,CAAC,CAAC,MAAM;gBACpB,MAAM,EAAE,2BAA2B,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC,IAAI,iBAAiB,GAAG;aACzF,CAAC,CAAC;QACL,CAAC;IACH,CAAC;IAAC,OAAO,CAAC,EAAE,CAAC;QACX,OAAO,GAAG,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,MAAM,EAAE,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;IAC5D,CAAC;AACH,CAAC;AAED,wEAAwE;AACxE,MAAM,UAAU,YAAY,CAC1B,EAAU,EACV,CAAmB;IAEnB,OAAO;QACL,MAAM,EAAE,OAAO;QACf,GAAG,EAAE,EAAE;QACP,GAAG,CAAC,CAAC,CAAC,GAAG,KAAK,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,UAAU,EAAE,EAAE,YAAY,EAAE,aAAa,EAAE,EAAE,CAAC;QAC1E,GAAG,CAAC,CAAC,CAAC,QAAQ,KAAK,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,CAAC,QAAQ,EAAE,CAAC;QACxD,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,WAAW,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC7C,CAAC;AACJ,CAAC;AAED,SAAS,MAAM,CAAC,EAAU,EAAE,CAAmB;IAC7C,MAAM,IAAI,GAAG,IAAI,QAAQ,EAAE,CAAC;IAC5B,IAAI,CAAC,MAAM,CAAC,MAAM,EAAE,IAAI,CAAC,SAAS,CAAC,YAAY,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IACzD,IAAI,CAAC,CAAC,GAAG,KAAK,IAAI;QAChB,IAAI,CAAC,MAAM,CACT,aAAa,EACb,IAAI,IAAI,CAAC,CAAC,IAAI,UAAU,CAAC,CAAC,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,IAAI,EAAE,iBAAiB,EAAE,CAAC,EACpE,CAAC,CAAC,GAAG,CAAC,IAAI,CACX,CAAC;IACJ,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,QAAQ,GAAG,CACf,IAAY,EACZ,MAAwC,EAChC,EAAE,CAAC,GAAG,IAAI,cAAc,IAAI,eAAe,CAAC,MAAM,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC;AAE3E,0DAA0D;AAC1D,MAAM,UAAU,YAAY,CAAC,CAAgB;IAC3C,OAAO;QACL,KAAK,CAAC,IAAI,CAAC,EAAE;YACX,MAAM,GAAG,GAAG,QAAQ,CAAC,CAAC,CAAC,GAAG,EAAE,EAAE,CAAC,EAAE,MAAM,CAAC,EAAE,CAAC,EAAE,UAAU,EAAE,MAAM,EAAE,CAAC,CAAC;YACnE,MAAM,CAAC,GAAG,MAAM,IAAI,CAAC,GAAG,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,EAAE,CAAC,CAAC,KAAK,EAAE,eAAe,CAAC,CAAC;YACvE,OAAO,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAC5D,CAAC;QACD,KAAK,CAAC,MAAM,CAAC,EAAE,EAAE,MAAM,EAAE,EAAE,IAAI,EAAE;YAC/B,MAAM,GAAG,GAAG,QAAQ,CAAC,CAAC,CAAC,GAAG,EAAE;gBAC1B,CAAC,EAAE,MAAM,CAAC,EAAE,CAAC;gBACb,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC;aAClC,CAAC,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,CAAC,EAAE,EAAE,MAAM,CAAC,CAAC;YAChC,MAAM,CAAC,GAAG,MAAM,IAAI,CAClB,GAAG,EACH,EAAE,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,EACxB,CAAC,CAAC,KAAK,EACP,gBAAgB,CACjB,CAAC;YACF,OAAO,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAC9D,CAAC;KACF,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { type Result } from "../../domain/result.ts";
|
|
2
|
+
import { type Sha256 } from "../../domain/sha256.ts";
|
|
3
|
+
import type { PortalFailure, SubmissionView, UpdateOutcome } from "../../domain/submission.ts";
|
|
4
|
+
/** HotCRP's `sha2-<hex>` → the sha256; null for any other hash it may name. */
|
|
5
|
+
export declare function sha256OfHash(hash: string): Sha256 | null;
|
|
6
|
+
/** `GET /api/paper` → the submission, or why there is none. */
|
|
7
|
+
export declare function parseShow(httpStatus: number, body: unknown): Result<SubmissionView, PortalFailure>;
|
|
8
|
+
/**
|
|
9
|
+
* `POST /api/paper` → the outcome, valid or not. A body carrying `valid` is HotCRP's verdict on
|
|
10
|
+
* the change whatever the HTTP status; the caller decides the exit from both.
|
|
11
|
+
*/
|
|
12
|
+
export declare function parseUpdate(httpStatus: number, body: unknown): Result<UpdateOutcome, PortalFailure>;
|
|
13
|
+
//# sourceMappingURL=response.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"response.d.ts","sourceRoot":"","sources":["../../../src/adapters/hotcrp/response.ts"],"names":[],"mappings":"AAUA,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,wBAAwB,CAAC;AAC9D,OAAO,EAAe,KAAK,MAAM,EAAE,MAAM,wBAAwB,CAAC;AAClE,OAAO,KAAK,EAEV,aAAa,EAEb,cAAc,EACd,aAAa,EACd,MAAM,4BAA4B,CAAC;AA6CpC,+EAA+E;AAC/E,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAGxD;AAkFD,+DAA+D;AAC/D,wBAAgB,SAAS,CACvB,UAAU,EAAE,MAAM,EAClB,IAAI,EAAE,OAAO,GACZ,MAAM,CAAC,cAAc,EAAE,aAAa,CAAC,CAMvC;AAED;;;GAGG;AACH,wBAAgB,WAAW,CACzB,UAAU,EAAE,MAAM,EAClB,IAAI,EAAE,OAAO,GACZ,MAAM,CAAC,aAAa,EAAE,aAAa,CAAC,CAYtC"}
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* HotCRP's answers, parsed at the boundary into paperlint's submission values. Pure.
|
|
3
|
+
*
|
|
4
|
+
* Only the fields the command uses are read; every other key HotCRP sends is dropped here. The field
|
|
5
|
+
* names are HotCRP's (`devel/openapi.json` and `devel/apidoc/submissions.md` in kohler/hotcrp):
|
|
6
|
+
* `GET /api/paper` answers `{ ok, paper, message_list? }`, `POST /api/paper` answers
|
|
7
|
+
* `{ ok, valid, change_list, message_list, dry_run?, pid }`. A document's `hash` is
|
|
8
|
+
* `sha2-<64 hex>` when HotCRP stored a sha256; timestamps are Unix seconds.
|
|
9
|
+
*/
|
|
10
|
+
import { z } from "zod";
|
|
11
|
+
import { err, ok } from "../../domain/result.js";
|
|
12
|
+
import { parseSha256 } from "../../domain/sha256.js";
|
|
13
|
+
const Message = z.object({
|
|
14
|
+
message: z.string().optional(),
|
|
15
|
+
field: z.string().optional(),
|
|
16
|
+
status: z.number().optional(),
|
|
17
|
+
});
|
|
18
|
+
const Messages = z.array(Message).optional();
|
|
19
|
+
const Document = z.object({
|
|
20
|
+
hash: z.string().optional(),
|
|
21
|
+
size: z.number().optional(),
|
|
22
|
+
mimetype: z.string().optional(),
|
|
23
|
+
timestamp: z.number().optional(),
|
|
24
|
+
});
|
|
25
|
+
const Paper = z.object({
|
|
26
|
+
pid: z.number(),
|
|
27
|
+
status: z.string(),
|
|
28
|
+
title: z.string().optional(),
|
|
29
|
+
abstract: z.string().optional(),
|
|
30
|
+
paper_type: z.unknown().optional(),
|
|
31
|
+
topics: z.array(z.string()).optional(),
|
|
32
|
+
submission: Document.nullable().optional(),
|
|
33
|
+
submitted_at: z.number().optional(),
|
|
34
|
+
modified_at: z.number().optional(),
|
|
35
|
+
});
|
|
36
|
+
const ShowBody = z.object({
|
|
37
|
+
ok: z.literal(true),
|
|
38
|
+
paper: Paper,
|
|
39
|
+
message_list: Messages,
|
|
40
|
+
});
|
|
41
|
+
const UpdateBody = z.object({
|
|
42
|
+
valid: z.boolean(),
|
|
43
|
+
change_list: z.array(z.string()).optional(),
|
|
44
|
+
message_list: Messages,
|
|
45
|
+
dry_run: z.boolean().optional(),
|
|
46
|
+
});
|
|
47
|
+
const Envelope = z.object({ message_list: Messages });
|
|
48
|
+
const SHA2 = /^sha2-([0-9a-f]{64})$/;
|
|
49
|
+
/** HotCRP's `sha2-<hex>` → the sha256; null for any other hash it may name. */
|
|
50
|
+
export function sha256OfHash(hash) {
|
|
51
|
+
const hex = SHA2.exec(hash)?.[1];
|
|
52
|
+
return hex === undefined ? null : parseSha256(hex);
|
|
53
|
+
}
|
|
54
|
+
/** HotCRP prefixes a message with its format (`<0>` plain text, `<5>` HTML); the text is the rest. */
|
|
55
|
+
const textOf = (message) => (message ?? "").replace(/^<\d+>/, "").trim();
|
|
56
|
+
/** The messages that say something: HotCRP also sends entries with no text, which print as blanks. */
|
|
57
|
+
const messagesOf = (list) => (list ?? [])
|
|
58
|
+
.map((m) => ({
|
|
59
|
+
message: textOf(m.message),
|
|
60
|
+
field: m.field ?? null,
|
|
61
|
+
status: m.status ?? null,
|
|
62
|
+
}))
|
|
63
|
+
.filter((m) => m.message !== "");
|
|
64
|
+
const documentOf = (d) => d?.hash === undefined
|
|
65
|
+
? null
|
|
66
|
+
: {
|
|
67
|
+
sha256: sha256OfHash(d.hash),
|
|
68
|
+
hash: d.hash,
|
|
69
|
+
size: d.size ?? null,
|
|
70
|
+
mimetype: d.mimetype ?? null,
|
|
71
|
+
uploadedAt: d.timestamp ?? null,
|
|
72
|
+
};
|
|
73
|
+
/** A paper type as text: HotCRP sends the option's name, or a value of another shape. */
|
|
74
|
+
const typeText = (v) => v === undefined || v === null
|
|
75
|
+
? null
|
|
76
|
+
: typeof v === "string"
|
|
77
|
+
? v
|
|
78
|
+
: JSON.stringify(v);
|
|
79
|
+
function viewOf(b) {
|
|
80
|
+
const p = b.paper;
|
|
81
|
+
return {
|
|
82
|
+
id: p.pid,
|
|
83
|
+
status: p.status,
|
|
84
|
+
title: p.title ?? null,
|
|
85
|
+
paperType: typeText(p.paper_type),
|
|
86
|
+
topics: p.topics ?? [],
|
|
87
|
+
abstract: p.abstract ?? null,
|
|
88
|
+
pdf: documentOf(p.submission),
|
|
89
|
+
submittedAt: p.submitted_at ?? null,
|
|
90
|
+
modifiedAt: p.modified_at ?? null,
|
|
91
|
+
messages: messagesOf(b.message_list),
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
const is2xx = (status) => status >= 200 && status < 300;
|
|
95
|
+
const StatusCode = z.object({ status_code: z.number() });
|
|
96
|
+
/**
|
|
97
|
+
* The status HotCRP meant. Its error envelope repeats the status in the body (`status_code: 401`
|
|
98
|
+
* beside `ok: false`, recorded in `cassette/get-noauth.json`); when something between us and HotCRP
|
|
99
|
+
* turns the transport status into a 2xx, the body's code still decides.
|
|
100
|
+
*/
|
|
101
|
+
function statusOf(transport, body) {
|
|
102
|
+
const c = StatusCode.safeParse(body);
|
|
103
|
+
return is2xx(transport) && c.success ? c.data.status_code : transport;
|
|
104
|
+
}
|
|
105
|
+
/** A body that is no answer of HotCRP's: the portal's messages when it sent any, else "malformed". */
|
|
106
|
+
function refusal(httpStatus, body, what) {
|
|
107
|
+
const e = Envelope.safeParse(body);
|
|
108
|
+
const messages = e.success ? messagesOf(e.data.message_list) : [];
|
|
109
|
+
return messages.length > 0 || !is2xx(httpStatus)
|
|
110
|
+
? { kind: "refused", httpStatus, messages }
|
|
111
|
+
: { kind: "malformed", httpStatus, detail: what };
|
|
112
|
+
}
|
|
113
|
+
/** `GET /api/paper` → the submission, or why there is none. */
|
|
114
|
+
export function parseShow(httpStatus, body) {
|
|
115
|
+
const status = statusOf(httpStatus, body);
|
|
116
|
+
const b = ShowBody.safeParse(body);
|
|
117
|
+
return b.success && is2xx(status)
|
|
118
|
+
? ok(viewOf(b.data))
|
|
119
|
+
: err(refusal(status, body, "the answer has no submission in `paper`"));
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* `POST /api/paper` → the outcome, valid or not. A body carrying `valid` is HotCRP's verdict on
|
|
123
|
+
* the change whatever the HTTP status; the caller decides the exit from both.
|
|
124
|
+
*/
|
|
125
|
+
export function parseUpdate(httpStatus, body) {
|
|
126
|
+
const status = statusOf(httpStatus, body);
|
|
127
|
+
const b = UpdateBody.safeParse(body);
|
|
128
|
+
if (!b.success)
|
|
129
|
+
return err(refusal(status, body, "the answer has no `valid`"));
|
|
130
|
+
return ok({
|
|
131
|
+
httpStatus: status,
|
|
132
|
+
valid: b.data.valid,
|
|
133
|
+
changes: b.data.change_list ?? [],
|
|
134
|
+
messages: messagesOf(b.data.message_list),
|
|
135
|
+
dryRun: b.data.dry_run ?? false,
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
//# sourceMappingURL=response.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"response.js","sourceRoot":"","sources":["../../../src/adapters/hotcrp/response.ts"],"names":[],"mappings":"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"}
|
package/dist/cli.d.ts
CHANGED
|
@@ -162,12 +162,14 @@ export declare function runHook(name: string | undefined, { err, run, resolve, }
|
|
|
162
162
|
* become two implementations. The lint runs on THAT folder, so the first thing printed after the
|
|
163
163
|
* file list is its verdict rather than the old "missing PIPELINE-STATUS.md".
|
|
164
164
|
*/
|
|
165
|
-
export declare function createPaperAt(papersRoot: string, name: string, format: PaperFormat, { log, err, cwd, venue, }: {
|
|
165
|
+
export declare function createPaperAt(papersRoot: string, name: string, format: PaperFormat, { log, err, cwd, venue, allowVenueName, }: {
|
|
166
166
|
log: typeof console.log;
|
|
167
167
|
err: typeof console.error;
|
|
168
168
|
cwd: string;
|
|
169
169
|
/** What `--venue` chose; null writes the template's `paperlint.json` as it is. */
|
|
170
170
|
venue?: VenueChoice | null;
|
|
171
|
+
/** `--allow-venue-name`: a name that names a venue is created, not refused. */
|
|
172
|
+
allowVenueName?: boolean;
|
|
171
173
|
}): Promise<number>;
|
|
172
174
|
/** A venue `paperlint new` will write, with what the messages need to say about it. */
|
|
173
175
|
export interface VenueChoice extends VenueSetting {
|
package/dist/cli.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AACA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,OAAO,EAAE,MAAM,EAAE,KAAK,MAAM,EAAE,MAAM,QAAQ,CAAC;AAS7C,OAAO,EAAE,MAAM,EAAE,MAAM,+CAA+C,CAAC;AAEvE,OAAO,EAAE,MAAM,EAAE,CAAC;AAClB,OAAO,KAAK,EAAE,IAAI,EAAE,eAAe,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AASpE,OAAO,EAAyB,YAAY,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
|