paperlint 7.1.0 → 8.0.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 (261) hide show
  1. package/.github/workflows/ci.yml +3 -0
  2. package/.github/workflows/deadlines.yml +100 -0
  3. package/README.md +6 -0
  4. package/dist/adapters/hotcrp/deadlines.d.ts +8 -0
  5. package/dist/adapters/hotcrp/deadlines.d.ts.map +1 -0
  6. package/dist/adapters/hotcrp/deadlines.io.d.ts +6 -0
  7. package/dist/adapters/hotcrp/deadlines.io.d.ts.map +1 -0
  8. package/dist/adapters/hotcrp/deadlines.io.js +26 -0
  9. package/dist/adapters/hotcrp/deadlines.io.js.map +1 -0
  10. package/dist/adapters/hotcrp/deadlines.js +134 -0
  11. package/dist/adapters/hotcrp/deadlines.js.map +1 -0
  12. package/dist/adapters/hotcrp/index.d.ts +2 -0
  13. package/dist/adapters/hotcrp/index.d.ts.map +1 -1
  14. package/dist/adapters/hotcrp/index.js +2 -0
  15. package/dist/adapters/hotcrp/index.js.map +1 -1
  16. package/dist/build.d.ts.map +1 -1
  17. package/dist/build.js +1 -6
  18. package/dist/build.js.map +1 -1
  19. package/dist/cli.d.ts +3 -4
  20. package/dist/cli.d.ts.map +1 -1
  21. package/dist/cli.js +53 -47
  22. package/dist/cli.js.map +1 -1
  23. package/dist/cycle-rules.d.ts +24 -0
  24. package/dist/cycle-rules.d.ts.map +1 -0
  25. package/dist/cycle-rules.js +212 -0
  26. package/dist/cycle-rules.js.map +1 -0
  27. package/dist/domain/cycle.d.ts +148 -0
  28. package/dist/domain/cycle.d.ts.map +1 -0
  29. package/dist/domain/cycle.js +281 -0
  30. package/dist/domain/cycle.js.map +1 -0
  31. package/dist/domain/deadline.d.ts +128 -0
  32. package/dist/domain/deadline.d.ts.map +1 -0
  33. package/dist/domain/deadline.js +281 -0
  34. package/dist/domain/deadline.js.map +1 -0
  35. package/dist/eslint-rules/cycle-stage.d.ts +39 -0
  36. package/dist/eslint-rules/cycle-stage.d.ts.map +1 -0
  37. package/dist/eslint-rules/cycle-stage.js +119 -0
  38. package/dist/eslint-rules/cycle-stage.js.map +1 -0
  39. package/dist/eslint-rules/latex-language.d.ts.map +1 -1
  40. package/dist/eslint-rules/latex-language.js +10 -13
  41. package/dist/eslint-rules/latex-language.js.map +1 -1
  42. package/dist/eslint-rules/paper-context.js +2 -2
  43. package/dist/eslint-rules/paper-typography.d.ts.map +1 -1
  44. package/dist/eslint-rules/paper-typography.js +22 -91
  45. package/dist/eslint-rules/paper-typography.js.map +1 -1
  46. package/dist/eslint-rules/papers.d.ts +1 -3
  47. package/dist/eslint-rules/papers.d.ts.map +1 -1
  48. package/dist/eslint-rules/papers.js +2 -4
  49. package/dist/eslint-rules/papers.js.map +1 -1
  50. package/dist/eslint-rules/tex-build.d.ts.map +1 -1
  51. package/dist/eslint-rules/tex-build.js +8 -25
  52. package/dist/eslint-rules/tex-build.js.map +1 -1
  53. package/dist/init.d.ts +1 -4
  54. package/dist/init.d.ts.map +1 -1
  55. package/dist/init.js +3 -9
  56. package/dist/init.js.map +1 -1
  57. package/dist/lib/markdown.d.ts +5 -81
  58. package/dist/lib/markdown.d.ts.map +1 -1
  59. package/dist/lib/markdown.js +5 -116
  60. package/dist/lib/markdown.js.map +1 -1
  61. package/dist/lib/paper-config.d.ts.map +1 -1
  62. package/dist/lib/paper-config.js +2 -2
  63. package/dist/lib/paper-config.js.map +1 -1
  64. package/dist/lib/skill-eval-fixture.d.ts +6 -4
  65. package/dist/lib/skill-eval-fixture.d.ts.map +1 -1
  66. package/dist/lib/skill-eval-fixture.js +25 -18
  67. package/dist/lib/skill-eval-fixture.js.map +1 -1
  68. package/dist/new-paper.d.ts +5 -11
  69. package/dist/new-paper.d.ts.map +1 -1
  70. package/dist/new-paper.js +12 -23
  71. package/dist/new-paper.js.map +1 -1
  72. package/dist/paper-files.d.ts +4 -4
  73. package/dist/paper-prose.d.ts +17 -0
  74. package/dist/paper-prose.d.ts.map +1 -0
  75. package/dist/paper-prose.js +46 -0
  76. package/dist/paper-prose.js.map +1 -0
  77. package/dist/paper-settings.d.ts +7 -0
  78. package/dist/paper-settings.d.ts.map +1 -1
  79. package/dist/paper-settings.js +61 -8
  80. package/dist/paper-settings.js.map +1 -1
  81. package/dist/ports/venue-deadlines.d.ts +14 -0
  82. package/dist/ports/venue-deadlines.d.ts.map +1 -0
  83. package/dist/ports/venue-deadlines.js +2 -0
  84. package/dist/ports/venue-deadlines.js.map +1 -0
  85. package/dist/presets.d.ts +12 -0
  86. package/dist/presets.d.ts.map +1 -1
  87. package/dist/presets.js +19 -11
  88. package/dist/presets.js.map +1 -1
  89. package/dist/structure.d.ts.map +1 -1
  90. package/dist/structure.js +4 -3
  91. package/dist/structure.js.map +1 -1
  92. package/dist/submission.d.ts +8 -0
  93. package/dist/submission.d.ts.map +1 -1
  94. package/dist/submission.js +41 -10
  95. package/dist/submission.js.map +1 -1
  96. package/dist/tex-requirements.d.ts +3 -0
  97. package/dist/tex-requirements.d.ts.map +1 -1
  98. package/dist/tex-requirements.js +19 -0
  99. package/dist/tex-requirements.js.map +1 -1
  100. package/dist/tex-venue-rules.d.ts +19 -0
  101. package/dist/tex-venue-rules.d.ts.map +1 -1
  102. package/dist/tex-venue-rules.js +69 -0
  103. package/dist/tex-venue-rules.js.map +1 -1
  104. package/dist/types.d.ts +0 -2
  105. package/dist/types.d.ts.map +1 -1
  106. package/dist/venue-rules.d.ts +10 -0
  107. package/dist/venue-rules.d.ts.map +1 -1
  108. package/dist/venue-rules.js +26 -10
  109. package/dist/venue-rules.js.map +1 -1
  110. package/docs/configuration.md +146 -20
  111. package/docs/e2e.md +4 -6
  112. package/docs/prior-art/paper-folder-scaffolding.md +24 -29
  113. package/docs/rules/cycle/evidence.md +87 -0
  114. package/docs/rules/cycle/port-done.md +75 -0
  115. package/docs/rules/cycle/record.md +152 -0
  116. package/docs/rules/cycle/stage.md +85 -0
  117. package/docs/rules/tex/claim-provenance.md +0 -1
  118. package/docs/rules.md +48 -47
  119. package/docs/submission.md +5 -0
  120. package/eslint-rules/cycle-stage.test.mjs +131 -0
  121. package/eslint-rules/cycle-stage.ts +141 -0
  122. package/eslint-rules/latex-language.harness.mjs +3 -3
  123. package/eslint-rules/latex-language.ts +10 -13
  124. package/eslint-rules/paper-context.ts +2 -2
  125. package/eslint-rules/paper-typography.test.mjs +17 -85
  126. package/eslint-rules/paper-typography.ts +22 -98
  127. package/eslint-rules/papers.harness.mjs +1 -1
  128. package/eslint-rules/papers.ts +2 -4
  129. package/eslint-rules/tex-build.harness.mjs +2 -2
  130. package/eslint-rules/tex-build.ts +8 -25
  131. package/eslint.config.mjs +41 -2
  132. package/hooks/hooks.harness.ts +15 -15
  133. package/hooks/paper-edit-guard.hook.mjs +5 -8
  134. package/hooks/paper-edit-guard.test.ts +12 -3
  135. package/hooks/paper-skills-nudge.hook.mjs +2 -3
  136. package/hooks/paper-skills-nudge.test.ts +13 -3
  137. package/hooks/paper-status-gates.hook.mjs +2 -2
  138. package/hooks/paper-status-gates.test.ts +14 -2
  139. package/lib/markdown.test.mjs +5 -60
  140. package/lib/markdown.ts +9 -136
  141. package/lib/paper-config.ts +3 -2
  142. package/lib/skill-checks.test.mjs +4 -1
  143. package/lib/skill-eval-fixture.ts +25 -18
  144. package/package.json +1 -3
  145. package/presets/aidc.jsonc +24 -3
  146. package/presets/aidc.md +6 -3
  147. package/presets/msr.jsonc +25 -1
  148. package/presets/msr.md +5 -1
  149. package/presets/realm.jsonc +1 -1
  150. package/presets/venue-profile.schema.json +39 -0
  151. package/scripts/check.ts +4 -0
  152. package/scripts/harness-api.frozen.json +0 -5
  153. package/scripts/refresh-deadlines.test.ts +431 -0
  154. package/scripts/refresh-deadlines.ts +387 -0
  155. package/skills/cold-read-diff/SKILL.md +3 -3
  156. package/skills/cold-read-diff/SKILL.md.spec.ts +2 -2
  157. package/skills/grade-paper-writing/SKILL.md +14 -22
  158. package/skills/grade-paper-writing/SKILL.md.spec.ts +13 -21
  159. package/skills/grade-paper-writing/__snapshots__/prose-lint.test.ts.snap +40 -26
  160. package/skills/grade-paper-writing/prose-lint.mjs +108 -278
  161. package/skills/grade-paper-writing/prose-lint.test.ts +184 -81
  162. package/skills/paper-adversarial-review/SKILL.md +2 -2
  163. package/skills/paper-adversarial-review/SKILL.md.spec.ts +1 -1
  164. package/skills/paper-pipeline/SKILL.md +9 -12
  165. package/skills/paper-pipeline/SKILL.md.spec.ts +8 -11
  166. package/skills/paper-pipeline/description-language.eval.mjs +25 -15
  167. package/skills/paper-pipeline/framing-vs-vocabulary.eval.mjs +25 -15
  168. package/skills/paper-pipeline/grade-paper-writing-ablation.eval.mjs +25 -15
  169. package/skills/paper-pipeline/pipeline-firing.eval.mjs +27 -16
  170. package/skills/paper-pipeline/pipeline-language.eval.mjs +25 -15
  171. package/skills/paper-pipeline/references/acceptance-gate.md +16 -20
  172. package/skills/paper-pipeline/references/artifact-checklist.md +4 -5
  173. package/skills/paper-pipeline/references/pipeline-status-template.md +1 -1
  174. package/skills/paper-pipeline/scripts/README.md +0 -4
  175. package/skills/paper-pipeline/scripts/extract-ref-facts.harness.mjs +8 -72
  176. package/skills/paper-pipeline/scripts/extract-ref-facts.mjs +48 -156
  177. package/skills/paper-pipeline/scripts/extract-ref-facts.test.mjs +81 -75
  178. package/skills/paper-pipeline/scripts/generated-code.harness.mjs +3 -3
  179. package/skills/paper-status/SKILL.md +2 -2
  180. package/skills/paper-status/SKILL.md.spec.ts +1 -1
  181. package/skills/render-paper/SKILL.md +2 -2
  182. package/skills/render-paper/SKILL.md.spec.ts +1 -1
  183. package/skills/render-paper/extract-pdf-facts.mjs +2 -2
  184. package/skills/tighten-paper/SKILL.md +29 -42
  185. package/skills/tighten-paper/SKILL.md.spec.ts +28 -41
  186. package/skills/verify-citations/scripts/bib-authors.check.test.mjs +0 -13
  187. package/skills/verify-citations/scripts/bib-authors.cli.test.ts +23 -11
  188. package/skills/verify-citations/scripts/bib-authors.mjs +8 -93
  189. package/skills/verify-citations/scripts/bib-authors.test.mjs +1 -44
  190. package/src/adapters/hotcrp/cassette/README.md +22 -0
  191. package/src/adapters/hotcrp/cassette/deadlines-aidc26.html +17 -0
  192. package/src/adapters/hotcrp/cassette/deadlines-fse2027.html +24 -0
  193. package/src/adapters/hotcrp/cassette/deadlines-icse2027.html +25 -0
  194. package/src/adapters/hotcrp/cassette/deadlines-msr2027.html +25 -0
  195. package/src/adapters/hotcrp/cassette/deadlines-nosuch.html +18 -0
  196. package/src/adapters/hotcrp/cassette/deadlines-sosp26.html +26 -0
  197. package/src/adapters/hotcrp/deadlines.io.test.ts +86 -0
  198. package/src/adapters/hotcrp/deadlines.io.ts +27 -0
  199. package/src/adapters/hotcrp/deadlines.test.ts +170 -0
  200. package/src/adapters/hotcrp/deadlines.ts +161 -0
  201. package/src/adapters/hotcrp/index.ts +2 -0
  202. package/src/build.harness.mjs +2 -2
  203. package/src/build.test.ts +1 -1
  204. package/src/build.ts +1 -6
  205. package/src/cli.harness.mjs +26 -46
  206. package/src/cli.test.ts +41 -40
  207. package/src/cli.ts +57 -58
  208. package/src/cycle-rules.test.ts +278 -0
  209. package/src/cycle-rules.ts +273 -0
  210. package/src/domain/cycle.test.ts +456 -0
  211. package/src/domain/cycle.ts +432 -0
  212. package/src/domain/deadline.test.ts +386 -0
  213. package/src/domain/deadline.ts +472 -0
  214. package/src/folder-venue-rule.test.ts +1 -1
  215. package/src/init.test.ts +6 -7
  216. package/src/init.ts +3 -22
  217. package/src/lint-fix.test.ts +10 -4
  218. package/src/new-paper.harness.mjs +9 -28
  219. package/src/new-paper.test.ts +7 -6
  220. package/src/new-paper.ts +11 -30
  221. package/src/paper-files.test.ts +5 -4
  222. package/src/paper-files.ts +4 -4
  223. package/src/paper-prose.test.ts +49 -0
  224. package/src/paper-prose.ts +67 -0
  225. package/src/paper-settings.test.ts +167 -0
  226. package/src/paper-settings.ts +85 -11
  227. package/src/parse-args.test.ts +0 -1
  228. package/src/ports/venue-deadlines.ts +14 -0
  229. package/src/presets.test.ts +105 -0
  230. package/src/presets.ts +43 -10
  231. package/src/rule-cases.test.ts +144 -0
  232. package/src/structure.harness.ts +5 -11
  233. package/src/structure.ts +4 -3
  234. package/src/submission.test.ts +105 -1
  235. package/src/submission.ts +73 -12
  236. package/src/tex-requirements.ts +31 -0
  237. package/src/tex-venue-rules.test.ts +76 -0
  238. package/src/tex-venue-rules.ts +85 -0
  239. package/src/types.ts +0 -2
  240. package/src/venue-rules.test.ts +82 -0
  241. package/src/venue-rules.ts +44 -12
  242. package/fixtures/real-markdown-paper/baseline.json +0 -22
  243. package/fixtures/real-markdown-paper/baseline.ts +0 -70
  244. package/skills/paper-pipeline/PIPELINE-MAP.md +0 -381
  245. package/skills/paper-pipeline/pipeline-firing.baseline.json +0 -270
  246. package/skills/paper-pipeline/references/sweep-2026-08-09-ideal-pipeline.md +0 -585
  247. package/skills/paper-pipeline/scripts/artifact-coverage.harness.mjs +0 -492
  248. package/skills/paper-pipeline/scripts/artifact-coverage.mjs +0 -397
  249. package/skills/paper-pipeline/scripts/artifact-coverage.test.ts +0 -86
  250. package/skills/paper-pipeline/scripts/check-provenance.mjs +0 -184
  251. package/skills/paper-pipeline/scripts/population-map.harness.mjs +0 -135
  252. package/skills/paper-pipeline/scripts/population-map.mjs +0 -188
  253. package/skills/paper-pipeline/scripts/population-map.test.mjs +0 -154
  254. package/skills/paper-pipeline/scripts/provenance.harness.mjs +0 -266
  255. package/skills/paper-pipeline/scripts/round-diff.harness.ts +0 -907
  256. package/skills/paper-pipeline/scripts/round-diff.mjs +0 -583
  257. package/skills/paper-pipeline/scripts/round-diff.test.mjs +0 -159
  258. package/skills/tighten-paper/__snapshots__/structure.test.ts.snap +0 -133
  259. package/skills/tighten-paper/structure.mjs +0 -364
  260. package/skills/tighten-paper/structure.test.ts +0 -117
  261. package/templates/paper/paper.md +0 -4
@@ -10,54 +10,61 @@
10
10
  * and the zero was an artifact of the empty directory, not a fact about the skill.
11
11
  *
12
12
  * Extracted from `paper-pipeline/pipeline-firing.eval.mjs`, which had it right
13
- * from the start, so the two runners cannot drift apart on what the model sees.
13
+ * from the start; the `paper-pipeline/*.eval.mjs` experiments carry the same
14
+ * block, byte for byte.
14
15
  *
15
16
  * ⚠️ AND THE PRICE, so this file is not a one-sided story (measured 2026-08-12).
16
17
  * With a fixture present the model OPENS THE PAPER and looks around, so the number
17
18
  * stops being "did the DESCRIPTION fire" and becomes "did the model go investigate
18
19
  * and then fire". A different quantity, and a costlier one: ~590k → ~780k tokens
19
- * per skill (+190k) and 67s → 84s, while this whole fixture is 1,537 characters
20
- * ≈ 384 tokens. The growth is reading, not input size (`cache` 470k → 652k).
20
+ * per skill (+190k) and 67s → 84s, while the fixture measured then was 1,537
21
+ * characters ≈ 384 tokens. The growth is reading, not input size (`cache`
22
+ * 470k → 652k).
21
23
  * Cite the trigger numbers with that caveat attached — it is written out in
22
24
  * `vigiles/repro/skill-trigger-2026-08-11/README.md` under "How to read".
23
25
  */
24
26
  export const FIXTURE = {
25
- "paper/paper.md": [
26
- "# Prose Isn't Policy: Measuring Whether Agent-Config Rules Are Enforceable",
27
+ "paper/paper.tex": [
28
+ "\\documentclass{article}",
29
+ "\\title{Prose Isn't Policy: Measuring Whether Agent-Config Rules Are Enforceable}",
30
+ "\\begin{document}",
31
+ "\\maketitle",
27
32
  "",
28
- "## Abstract",
33
+ "\\begin{abstract}",
29
34
  "Agent configuration files state rules in prose and assume the model obeys them. We compile a",
30
- "corpus of real rules and measure what fraction can be mechanically enforced. We find that 84%",
35
+ "corpus of real rules and measure what fraction can be mechanically enforced. We find that 84\\%",
31
36
  "of rules in our corpus are enforceable, and that LLM-authored checkers for the remainder leak",
32
- "silently in 84-96% of adversarial cases \\cite{greshake2023}.",
37
+ "silently in 84--96\\% of adversarial cases~\\cite{greshake2023}.",
38
+ "\\end{abstract}",
33
39
  "",
34
- "## 1 Introduction",
40
+ "\\section{Introduction}",
35
41
  "Every agent harness ships a natural-language rulebook. Nothing checks it. This is the same",
36
- "mistake as a code comment that claims an invariant no test enforces \\cite{thompson1984}.",
42
+ "mistake as a code comment that claims an invariant no test enforces~\\cite{thompson1984}.",
37
43
  "",
38
- "## 2 Method",
44
+ "\\section{Method}",
39
45
  "We gather rules from public repositories, classify each by enforceability, and build a",
40
46
  "two-stage adversarial gate that validates a synthesized rule against a blind gold set.",
41
47
  "",
42
- "## 3 Results",
43
- "See Table 1. The headline number is 84%.",
48
+ "\\section{Results}",
49
+ "See Table~1. The headline number is 84\\%.",
44
50
  "",
45
- "## 4 Discussion",
51
+ "\\section{Discussion}",
46
52
  "The result generalizes beyond our corpus in the sense that the mechanism is not corpus-specific,",
47
53
  "though of course the specific percentages are, and it is important to note in this context that",
48
54
  "the framing itself may be what carries, rather than the measurement.",
49
55
  "",
50
- "## 5 Threats to Validity",
56
+ "\\section{Threats to Validity}",
51
57
  "Our corpus is drawn from public repositories and may not represent private configurations.",
52
58
  "",
53
- "## 6 Related Work",
59
+ "\\section{Related Work}",
54
60
  "TODO",
55
61
  "",
56
- "## 7 Conclusion",
62
+ "\\section{Conclusion}",
57
63
  "Prose is not policy.",
64
+ "\\end{document}",
58
65
  ].join("\n"),
59
66
  "paper/repro/README.md":
60
- "# Reproduction artifact\n\n`python3 paper_numbers.py` recomputes every bolded figure in paper.md.\n",
67
+ "# Reproduction artifact\n\n`python3 paper_numbers.py` recomputes every bolded figure in paper.tex.\n",
61
68
  "paper/PIPELINE-STATUS.md":
62
69
  "# Pipeline status\n\n| gate | state |\n|---|---|\n| numbers | pass |\n| structure | not run |\n| citations | not run |\n",
63
70
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "paperlint",
3
- "version": "7.1.0",
3
+ "version": "8.0.0",
4
4
  "description": "A linter for scientific papers written in LaTeX: catches mistakes before you submit to a conference or journal.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -114,8 +114,6 @@
114
114
  "eslint.config.mjs",
115
115
  "fixtures",
116
116
  "!fixtures/accepted-papers",
117
- "!fixtures/real-markdown-paper",
118
- "fixtures/real-markdown-paper/baseline.*",
119
117
  "hooks",
120
118
  "lib",
121
119
  "presets",
@@ -13,10 +13,12 @@
13
13
  // and appendices.»
14
14
  // «Submissions must be properly anonymized for double-blind review.»
15
15
  //
16
- // THE DEADLINE PEOPLE GET WRONG (not a lint fact): the HotCRP portal closes 2026-10-02 11:59:59 UTC
16
+ // THE DEADLINE PEOPLE GET WRONG: the HotCRP portal closed 2026-10-02 11:59:59 UTC first
17
17
  // (`"sub":1790942399` on https://aidc.submit.acsac.org/deadlines, recorded in paperlint#90), while
18
- // the workshop page says «October 2, 2026 (Anywhere-on-Earth, AoE)» — a day later. The portal is
19
- // what refuses the upload.
18
+ // the workshop page said «October 2, 2026 (Anywhere-on-Earth, AoE)» — a day later; by 2026-10-05
19
+ // the portal had moved it a day (`"sub":1791028799`). The portal is what refuses the upload, so its
20
+ // readings are `deadlines` below, rewritten by the scheduled refresh in paperlint's repository
21
+ // (.github/workflows/deadlines.yml) when the portal changes them.
20
22
  //
21
23
  // THE REVIEW IS DOUBLE-BLIND: `"blind":true` in the same portal data, and the call above.
22
24
  //
@@ -38,6 +40,25 @@
38
40
  // the HotCRP API, there.
39
41
  "portal": { "kind": "hotcrp", "url": "https://aidc.submit.acsac.org" },
40
42
 
43
+ // Read from the portal's public deadlines page; the camera-ready only in its status object
44
+ // (`"final":{"done":1793447999}`).
45
+ "deadlines": [
46
+ {
47
+ "what": "submission",
48
+ "at": "2026-10-03T11:59:59Z",
49
+ "source": "portal",
50
+ "url": "https://aidc.submit.acsac.org/deadlines",
51
+ "read": "2026-10-05",
52
+ },
53
+ {
54
+ "what": "camera-ready",
55
+ "at": "2026-10-31T11:59:59Z",
56
+ "source": "portal",
57
+ "url": "https://aidc.submit.acsac.org/deadlines",
58
+ "read": "2026-10-05",
59
+ },
60
+ ],
61
+
41
62
  // What the venue is called in a paper's text (tex/venue-leftover): the workshop, and the
42
63
  // conference it is held at.
43
64
  "aliases": ["AIDC", "ACSAC"],
package/presets/aidc.md CHANGED
@@ -21,9 +21,12 @@ from it. The `submit-paper` skill reads this card for the venue's specifics.
21
21
  - **Double-blind**: «Submissions must be properly anonymized for double-blind review.», and
22
22
  `"blind":true` in the portal's data.
23
23
  - **Portal**: HotCRP at `https://aidc.submit.acsac.org`.
24
- - 🔴 **The deadline people get wrong**: the HotCRP portal closes 2026-10-02 11:59:59 UTC
25
- (`"sub":1790942399` on `https://aidc.submit.acsac.org/deadlines`), while the workshop page says
26
- «October 2, 2026 (Anywhere-on-Earth, AoE)» — a day later. The portal is what refuses the upload.
24
+ - 🔴 **The deadline people get wrong**: the HotCRP portal closed 2026-10-02 11:59:59 UTC first
25
+ (`"sub":1790942399` on `https://aidc.submit.acsac.org/deadlines`), while the workshop page said
26
+ «October 2, 2026 (Anywhere-on-Earth, AoE)» — a day later; on 2026-10-05 the portal read
27
+ 2026-10-03 11:59:59 UTC (`"sub":1791028799`). The portal is what refuses the upload. The preset
28
+ carries its readings as `deadlines`, refreshed by paperlint's scheduled workflow when the portal
29
+ changes them.
27
30
 
28
31
  ## Paper kinds and limits
29
32
 
package/presets/msr.jsonc CHANGED
@@ -15,7 +15,10 @@
15
15
  // camera-ready version.»
16
16
  // «The MSR 2027 Technical Track will employ a double-anonymous review process.»
17
17
  //
18
- // The dates are not lint facts; they are in the card, msr.md beside this file.
18
+ // THE DEADLINES ARE THE PORTAL'S, as read: `deadlines` below is rewritten by the scheduled refresh
19
+ // in paperlint's repository (.github/workflows/deadlines.yml) when the portal changes them, and a
20
+ // paper reaches the new dates through its normal update of paperlint. The call's own wording
21
+ // (abstract and paper days, AoE) is in the card, msr.md beside this file.
19
22
  {
20
23
  "type": "venue",
21
24
  "name": "MSR",
@@ -34,6 +37,27 @@
34
37
  // token — the HotCRP API, there.
35
38
  "portal": { "kind": "hotcrp", "url": "https://msr2027.hotcrp.com" },
36
39
 
40
+ // Read from the portal's public deadlines page (no account) by the adapter in src/adapters/hotcrp/.
41
+ // «Submissions must be completed by this deadline» is the `submission`: on the CALL's abstract
42
+ // day, 04:00 UTC — four days before the call's paper day. «Completed submissions may be updated
43
+ // until this deadline» is the `resubmission`.
44
+ "deadlines": [
45
+ {
46
+ "what": "submission",
47
+ "at": "2026-10-20T04:00:00Z",
48
+ "source": "portal",
49
+ "url": "https://msr2027.hotcrp.com/deadlines",
50
+ "read": "2026-10-05",
51
+ },
52
+ {
53
+ "what": "resubmission",
54
+ "at": "2026-10-23T04:00:00Z",
55
+ "source": "portal",
56
+ "url": "https://msr2027.hotcrp.com/deadlines",
57
+ "read": "2026-10-05",
58
+ },
59
+ ],
60
+
37
61
  // What the venue is called in a paper's text (tex/venue-leftover) — and only beside a year
38
62
  // («MSR 2027», «MSR'27»): «MSR» is also Microsoft Research, and an acronym papers define for
39
63
  // themselves («Manual Speech Recognition (MSR)», in an accepted ACSAC paper of
package/presets/msr.md CHANGED
@@ -28,7 +28,11 @@ whereas last year it was ACM format.»), and limits and dates change between edi
28
28
  (`"sub":1792468800`, 2026-10-20 04:00 UTC) and «Resubmission deadline: Friday Oct 23, 2026, 12 AM
29
29
  EDT» («Completed submissions may be updated until this deadline»). Midnight EDT at the start of
30
30
  each day is about a day and a half before the end of that day AoE. The portal is what refuses the
31
- upload: plan for its times, and re-read the page, since chairs change them.
31
+ upload: plan for its times. The preset carries them as `deadlines` (`source: "portal"`, with the
32
+ day read), refreshed by paperlint's scheduled workflow when the portal changes them; a paper whose
33
+ current cycle names `paperlint:msr` derives them. Recording the call's days in the paper's own
34
+ cycle maps «abstract» to `registration` and «paper» to `submission` — and the portal's earlier
35
+ `submission` is then the one in force.
32
36
  - **Format**, verbatim from the call: «LaTeX users must use \documentclass[10pt,conference]{IEEEtran}
33
37
  without including the compsoc or compsocconf options», «title in 24pt font and full text in 10pt
34
38
  type», and «Alterations of spacing, font size, and other changes that deviate from the
@@ -72,7 +72,7 @@
72
72
  //
73
73
  // A gate on banal's number would give 13 against a limit of 8 and would redden on a paper that
74
74
  // is within the limit. For an `error`-level rule that is the worst outcome. The limit stays
75
- // owned by the counter inside `build-submission.sh`: it reads the markdown source and therefore
75
+ // owned by the counter inside `build-submission.sh`: it reads the paper's source and therefore
76
76
  // KNOWS where the body ends, which the PDF does not.
77
77
  //
78
78
  // The numbers below are DATA for that counter and for humans, not an input to the rule. Source:
@@ -78,6 +78,45 @@
78
78
  }
79
79
  }
80
80
  },
81
+ "deadlines": {
82
+ "description": "The edition's deadlines as they were READ — the portal's readings, rewritten by the scheduled refresh in paperlint's repository when the portal changes them (a patch release), each with the page and the day it was read. A paper whose current cycle names this preset derives them; its own record adds the call's readings and overrides on top, and the earlier reading binds. `what`: registration (abstract registration — a call's \"abstract\" date), submission (the full paper), resubmission (updates to a completed submission), notification, camera-ready. At most one reading per kind and source. A child's list replaces its parent's.",
83
+ "type": "array",
84
+ "items": {
85
+ "type": "object",
86
+ "additionalProperties": false,
87
+ "required": ["what", "at", "source", "url", "read"],
88
+ "properties": {
89
+ "what": {
90
+ "type": "string",
91
+ "enum": [
92
+ "registration",
93
+ "submission",
94
+ "resubmission",
95
+ "notification",
96
+ "camera-ready"
97
+ ]
98
+ },
99
+ "at": {
100
+ "description": "An instant in UTC, as the portal publishes it: 2026-10-20T04:00:00Z.",
101
+ "type": "string",
102
+ "pattern": "^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}Z$"
103
+ },
104
+ "source": {
105
+ "type": "string",
106
+ "enum": ["portal", "call"]
107
+ },
108
+ "url": {
109
+ "type": "string",
110
+ "pattern": "^https?://[^\\s/]+[^\\s]*$"
111
+ },
112
+ "read": {
113
+ "description": "The day the page was read, YYYY-MM-DD.",
114
+ "type": "string",
115
+ "pattern": "^\\d{4}-\\d{2}-\\d{2}$"
116
+ }
117
+ }
118
+ }
119
+ },
81
120
  "required_sections": {
82
121
  "description": "Sections the venue requires, read by `tex/required-section`. Each is a `\\section` or `\\section*` whose title equals `title` once whitespace is collapsed. `position: \"last\"`: after every section of the body (the ones before the appendix and the bibliography); it may stand after the bibliography. A child preset's list replaces its parent's.",
83
122
  "type": "array",
package/scripts/check.ts CHANGED
@@ -202,6 +202,10 @@ export const NOT_COVERED: Readonly<Record<string, string>> = {
202
202
  validate:
203
203
  "pr-title.yml checks the pull request's TITLE (the squash commit semantic-release reads), " +
204
204
  "which exists only on GitHub, not in the tree.",
205
+ refresh:
206
+ "deadlines.yml reads the venue presets' portals over the network once a day and opens a pull " +
207
+ "request when a deadline moved; npm test replays the recorded portal pages through " +
208
+ "scripts/refresh-deadlines.test.ts, and nothing local should read the live portals on every check.",
205
209
  };
206
210
 
207
211
  /**
@@ -10,7 +10,6 @@
10
10
  "eslint-rules/pdf-last-page-balance.harness.mjs",
11
11
  "eslint-rules/temp-root-realpath.harness.mjs",
12
12
  "eslint-rules/tex-build.harness.mjs",
13
- "fixtures/real-markdown-paper/real-markdown-paper.harness.ts",
14
13
  "lib/agent-cli-version.harness.mjs",
15
14
  "lib/paper-config.harness.mjs",
16
15
  "lib/skill-trigger-cases.harness.mjs",
@@ -30,13 +29,9 @@
30
29
  "skills/osf-artifact-upload/osf-artifact-upload.harness.ts",
31
30
  "skills/paper-adversarial-review/paper-adversarial-review.harness.mjs",
32
31
  "skills/paper-pipeline/paper-pipeline.harness.mjs",
33
- "skills/paper-pipeline/scripts/artifact-coverage.harness.mjs",
34
32
  "skills/paper-pipeline/scripts/consumer.harness.mjs",
35
33
  "skills/paper-pipeline/scripts/extract-ref-facts.harness.mjs",
36
34
  "skills/paper-pipeline/scripts/generated-code.harness.mjs",
37
- "skills/paper-pipeline/scripts/population-map.harness.mjs",
38
- "skills/paper-pipeline/scripts/provenance.harness.mjs",
39
- "skills/paper-pipeline/scripts/round-diff.harness.ts",
40
35
  "skills/paper-status/paper-status.harness.mjs",
41
36
  "skills/pc-panel-review/pc-panel-review.harness.mjs",
42
37
  "skills/plan-paper-timeline/plan-paper-timeline.harness.mjs",