A derived PDF is a folder since raw derive; the raw/CONTRACT.md example was adapted when the command shipped, the raw pending record and its generated copies were not. Files changed: - CHANGES.md - VERSION - docs/reference/commands/raw-material-and-uploads.md - tools/CONTRACT.md - tools/chemenu/commands/raw_cmd.py Co-Authored-By: Claude Code <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01SnAJ7Z3CpVD3PRbN73QtU2
35 KiB
Raw material and uploads
Bringing new material into raw/: fetching and capturing it, seeing what is waiting, accepting it, and reviewing what an MCP client uploaded.
Contents
raw fetchraw deriveraw captureraw statusraw pendingraw acceptupload listupload showupload acceptupload reject
raw fetch
Capture a web page the user names into incoming/: the HTML as received plus a derived text, for raw accept to promote.
Synopsis
wikitool raw fetch <url> [--name <stem>]- Fetch the page and writeincoming/<stem>.htmlandincoming/<stem>.mdwikitool raw fetch --html incoming/<file>.html --url <url>- Derive the.mdfrom a page a human saved from their browser - no network access
Options
Arguments:
url The http(s) URL to fetch
Options:
--html <path> Derive the text from this HTML file under incoming/ (saved from
a browser) instead of fetching - no network access
--url <str> With --html: the page's URL, for the header and relative links
--name <str> File stem in incoming/ instead of the one computed from the URL
-h, --help Show this message and exit.
Examples
tools/wikitool raw fetch https://example.org/blog/post
tools/wikitool raw fetch https://example.org/ --name example-start
tools/wikitool raw fetch --html incoming/post.html --url https://example.org/blog/post
Behaviour
- Writes into
incoming/only, never intoraw/:raw acceptpromotes both files afterwards, in one call, as one bundle underraw/<YYYY>/<MM>/<stem>/. - The
.htmlholds the response body byte for byte. The.mdstarts with a fixed header block (fetched_by,url,final_url,retrieved,http_status,content_type,charset,title,derived_from) followed by the derived text. - Character set, in this order: byte-order mark, the HTTP
Content-Typecharset, a<meta>declaration in the first 4 KiB, UTF-8. Undecodable bytes are replaced with U+FFFD and reported; the header names the charset and where it came from. - Derived text: the content root is
<main>, else the single<article>, else<body>;script,style,noscript,nav,header,footer,aside,form,templateandsvgare dropped below it. Headings, lists, code, tables and links (made absolute) become Markdown. The same bytes always give the same text. - The stem is the URL's last path segment without its extension, else its host name - ASCII, lowercase,
--separated, at most 60 characters;--nameoverrides it. - A
text/plainortext/markdownresponse is stored as received as.txt/.md; any other non-HTML response (PDF, image, ...) as received under the extension of its content type. Neither gets a derived file or a header. - Only
http/https, on every redirect hop too. 30 s for the whole transfer, 25 MiB at most. No cookies, no JavaScript: a derived text under 200 characters is written, with a warning to read it before accepting. --htmlderives the.mdbeside a page saved toincoming/from a logged-in browser - the way past a paywall or a script-rendered page. Its header carriesderived(when the text was derived) instead ofretrieved,final_url,http_statusandcontent_type, and the.htmlis left untouched.- Success prints the
raw acceptline for the written files and thesource_urlfor the source page.
Properties
- Changes files: yes
- Idempotent: no
- Atomic: Yes for what it leaves behind - one or two new files in
incoming/, created exclusively; a failure on the second removes the first - Counts toward the session call budget: yes
- Can reach the network: yes
Exit codes
0- success1- The URL is nothttp/https(also after a redirect), or neither or both of<url>and--htmlwere given1- A target file already exists inincoming/1- The server answered with an HTTP error, could not be reached, took longer than 30 s, or sent more than 25 MiB1- raw fetch --html:--urlis missing, the file is not directly inincoming/or does not exist, orincoming/<stem>.mdalready exists
See also
raw/CONTRACT.md"Getting a URL in:raw fetch" - the rules and whywikitool raw accept- promotes the written files intoraw/instructions/wiki-ingest/SKILL.md- where a URL to ingest starts
raw derive
Derive reading text from a PDF, e-mail, Office file or web page in incoming/, or unpack a ZIP, and leave the original beside it, for raw accept to promote.
Synopsis
wikitool raw derive incoming/<file> [--name <stem>]- Move the file into the new folderincoming/<stem>/asoriginal.<ext>and writeincoming/<stem>/derived.mdwikitool raw derive incoming/<folder>- Write a<stem>.mdbeside every file in the folder that has a filter
Options
Arguments:
path A file or a folder directly in incoming/ [required]
Options:
--name <str> Folder stem for a single file instead of the file's own stem
-h, --help Show this message and exit.
Examples
tools/wikitool raw derive incoming/report.docx
tools/wikitool raw derive incoming/Angebot-XYZ.xlsx --name angebot-xyz
tools/wikitool raw derive incoming/meeting-files
tools/wikitool raw derive incoming/scans.zip
Behaviour
- Writes into
incoming/only, never intoraw/, and reads no network:raw acceptpromotes the folder afterwards as one source underraw/<YYYY>/<MM>/<stem>/. - A single file directly in
incoming/becomes a folder named after its stem (or--name) holdingoriginal.<ext>- the original bytes, moved - andderived.md. The fixed names keep the path inside the path budget; the header ofderived.mdrecords the file's own name asoriginal_name. - A folder is derived in place: each file with a filter gets
<stem>.mdbeside it, nothing is renamed, and the files without a filter are named in the output. derived.mdstarts with a fixed header (derived_by,filter,engine,derived,derived_from,original_namefor a renamed file,title, then the fields of the format) followed by the derived text. The same bytes always give the same text; onlyderiveddiffers between runs.enginenames the tool version and, where a package reads the format, its version.- Formats: web pages (
.html), Word (.docx), PowerPoint (.pptx), Excel (.xlsx,.xlsm), e-mail (.eml) and ZIP archives (.zip), read with the standard library only; PDF (.pdf,pypdf) and Outlook messages (.msg,olefile), each read by a package intools/requirements.txtthat is imported only when such a file is derived. A missing package refuses that format alone, with the preflight hint;wikitool doctorshows oneimport-filter-<name>line per package-backed format. A PDF gets<!-- page N -->markers and a WARN when it yields almost no text (a scan; there is no OCR); an encrypted PDF is refused. A.msgis a container like an.eml; an embedded message inside it is named, not read. - A ZIP and a mail are containers. A ZIP at the top of
incoming/becomes the folderincoming/<stem>/holding its files under their own names, each with a<stem>.mdwhere a filter reads it; the ZIP is removed and the output names it with its sha256. A mail becomes a folder withoriginal.eml,derived.mdand its attachments under their own names; a ZIP attached to it is unpacked once into a folder of its own, and an attached mail is quoted inderived.md, not unpacked. A ZIP inside a ZIP, an absolute or..path, a symbolic link, an encrypted entry, more than 1000 entries, a file over 25 MiB or more than 250 MiB in total refuse the whole call. Hidden entries (__MACOSX/,.DS_Store, anything starting with a dot) are named, not written. A name taken twice, or reserved (original.*andderived.mdat the top of a mail's folder,_capture.jsonanywhere), gets-2,-3before its extension, and the output lists each rename. - A name already taken under
raw/is a WARN, not a refusal: whether the folder is a later edition of that source or a separate one is the human's call. A later edition of a derived source is replaced file by file withraw accept --replaces; there is no--replaces-bundlefor it. - After a success the output prints the warnings the filters raised, at most three
CHECKlines per format that was derived in this run - what to look at before the text is trusted - and theraw acceptline for the result. - Never edit
derived.mdby hand: a better derivation is a newraw deriveof the original.
Properties
- Changes files: yes
- Idempotent: no
- Atomic: Yes for what it leaves behind - everything is read, derived and checked before the first write; the files are created exclusively, and a failure part-way puts back what this call changed
- Counts toward the session call budget: yes
- Can reach the network: no
Exit codes
0- success1- The path is not directly inincoming/, does not exist, or no filter reads the file's extension1- The target folder or a.mdalready exists, or the path would be over the path budget1- The document cannot be read (damaged, encrypted), a container breaks one of its rules (a ZIP inside a ZIP, an unsafe path, a limit) or the filter's package is not installed
See also
raw/CONTRACT.md"Getting a document in:raw derive" - the rules and whywikitool raw accept- promotes the folder intoraw/instructions/wiki-ingest/SKILL.md- where a PDF, mail or Office file to ingest starts
raw capture
Capture documentation from a git repository into incoming/<bundle>/, with a manifest naming the repository, ref rule and commit, for raw accept to promote.
Synopsis
wikitool raw capture <repo-url> --ref <branch|tag-pattern> --path <glob> [--path <glob> ...] --name <bundle> --fidelity <v> --authority <v>- First capture of a repositorywikitool raw capture --update <raw-bundle> [--fidelity <v>] [--authority <v>]- Capture the current state of an already-accepted bundle, forraw accept --replaces-bundle
Options
Arguments:
repo_url The repository URL (ssh://, https:// or user@host:path)
Options:
--ref <str> A branch name (main) or a tag pattern (v*)
--path <str> A glob over the repository's paths; repeatable
--name <str> The bundle name - the folder in incoming/ and under raw/
--fidelity <str> How faithful the capture is (see `wikitool types describe
source`)
--authority <str> What the material may claim about its subject (see
`wikitool types describe source`)
--update <path> Capture the current state of this captured bundle under
raw/, from its own manifest
-h, --help Show this message and exit.
Examples
tools/wikitool raw capture ssh://git@example.org/team/service.git --ref main --path 'docs/**/*.md' --path README.md --name service-docs --fidelity verbatim --authority normative
tools/wikitool raw capture https://example.org/team/lib.git --ref 'v*' --path docs --name lib-docs --fidelity verbatim --authority reporting
tools/wikitool raw capture --update raw/2026/10/service-docs
Behaviour
- Writes into
incoming/<bundle>/only, never intoraw/:raw accept incoming/<bundle>promotes it, as one folder, toraw/<YYYY>/<MM>/<bundle>/. --refis a branch name (main) or a tag pattern (v*, any of*?[), which names the newest matching tag by version order. It resolves to one commit - for an annotated tag, the commit it points at.- The commit is fetched by ref name, shallowly, into a bare cache repository per URL under
tools/.wikitool_capture/(gitignored). Files are read from it as blobs, never through a checkout, so they are byte-identical to the repository's - no line-ending conversion, no filter. --pathglobs (repeatable) select files by their path in the repository, as git's:(glob)pathspec does:*,?and[...]do not cross/;**as a whole segment spans any number of directories; a glob without wildcards also takes everything below it as a directory. Files keep their repository paths inside the bundle.- Never captured, each named in the output with its reason: a file whose first line starts with
<!-- wikitool:export, a symlink, a submodule, a file over 25 MiB, a path with a segment starting with., a file named_capture.json, and a Git LFS pointer. incoming/<bundle>/_capture.jsonrecordsschema,repo,ref,commit,paths,captured(UTC),fidelity,authorityandfiles. It is the only declaration that and how this instance follows the repository.- Only
ssh://,https://and the scp formuser@host:path; a URL with a password or token in it is refused, since the manifest is committed. Git runs with the host's own credentials and configuration, restricted to those protocols, and never prompts: a repository that asks for credentials is reported as unreachable. Each git call times out after 120 s. --update <raw-bundle>takes URL, ref rule and globs from that bundle's manifest and writes the current state toincoming/<same bundle name>/;--fidelity/--authoritydefault to the manifest's values, and passing one is the way to correct it.- Refused before anything is written:
incoming/<bundle>already exists, the name is already taken underraw/(a first capture), nothing matches the globs, or a target path - measured at its later place underraw/- is over the path budget. - Success prints the commit and the
raw acceptline that comes next.
Properties
- Changes files: yes
- Idempotent: no
- Atomic: Yes for what it leaves in
incoming/- the bundle is written into a hidden staging directory and renamed into place in one step; a failure removes the staging directory. The git cache undertools/.wikitool_capture/is updated either way - Counts toward the session call budget: yes
- Can reach the network: yes
Exit codes
0- success1- The URL is notssh://,https://oruser@host:path, or carries a password; the--refrule, a--pathglob or--nameis unusable; or an argument of the other variant was mixed in1---fidelity/--authorityis missing on a first capture, or namesunknownor a value outside the schema's enum1- The repository could not be reached, asked for credentials, or timed out; or no branch or tag matches--ref1-incoming/<bundle>already exists, the name is already taken underraw/, nothing matches the globs, or a path would be over the budget1- raw capture --update: The path is not a bundle underraw/with a readable_capture.json, or its manifest names a URL that is refused
See also
raw/CONTRACT.md"Getting a repository in:raw capture" - the rules and whywikitool raw accept- promotes the bundle;--replaces-bundlefor a new editionwikitool raw status- which captured bundles have fallen behind their repository
raw status
Report which captured bundles under raw/ have fallen behind their repository, with each changed file as A/M/D.
Synopsis
wikitool raw status [--json]
Options
--json Print one JSON object per captured bundle
-h, --help Show this message and exit.
Examples
tools/wikitool raw status
tools/wikitool raw status --json
Behaviour
- Reads every
_capture.jsonunderraw/and resolves its ref rule withgit ls-remote. Only where the commit moved is the new commit fetched, and compared - with the same globs and exclusionsraw captureapplies - against the bundle's files underraw/. - A bundle whose commit moved without a change inside its globs is reported as unchanged, not listed. A tag pattern follows new matching tags only, never new commits on a branch.
- Each changed bundle prints
old -> newand its files asA/M/D, grouped by owning source page with its citing pages, followed by theraw capture --updateandraw accept --replaces-bundlelines that take the new edition in. - An unreachable repository, a refused URL or an unreadable manifest is one line beside the others, never an abort; the exit status is 0 as long as the command itself ran.
--jsonprints one object per bundle:bundle,repo,ref,old,new,changed,files([{path, status}]),error(or null).- Git runs exactly as for
raw capture: the host's credentials, onlyssh/https, never a prompt, 120 s per call.
Properties
- Changes files: no
- Idempotent: yes
- Atomic: Read-only for the tree - writes nothing but the git cache under
tools/.wikitool_capture/ - Counts toward the session call budget: yes
- Can reach the network: yes
Exit codes
0- success0- A repository could not be reached, its manifest or URL was refused, or no ref matches its rule
See also
wikitool raw capture---updatecaptures the new editionwikitool raw accept---replaces-bundletakes it inraw/CONTRACT.md"Getting a repository in:raw capture"
raw pending
List what waits in incoming/, oldest first, and name the entry an ingest without an argument takes next.
Synopsis
wikitool raw pending [--json]
Options
--json Print the candidates as JSON
-h, --help Show this message and exit.
Examples
tools/wikitool raw pending
tools/wikitool raw pending --json
Behaviour
- A candidate is a top-level entry of
incoming/: a singlefile, abundleof top-level files sharing a stem (araw fetchpair), or afolderwith every file below it. Dotfiles, empty directories and their contents are none;mcp-upload/is outsideincoming/and never listed. - Order: oldest first by modification time. A bundle or folder counts as new as its newest file; a tie goes by name. The mtime is when a document last changed only if it was copied with its timestamps kept (
cp -p,rsync -a, an unpacked archive) - for a download or araw fetchit is merely when it was dropped. - Each candidate shows its path(s), kind, file count and mtime, and whether
raw acceptwould take it as it stands - the same checks, minus--fidelity/--authority. One it would refuse is listed with the reason and skipped: it needs a human. - The default is the first candidate
raw acceptwould take, and the output names it. --jsonprints the same candidates in the same order:kind,paths,files,mtime,acceptable,reason,default,hint.- A lone file that a
raw derivefilter reads (a PDF, mail, Office file or web page) is listed with theraw deriveline for it, in text output and ashintin JSON (nullfor every other candidate). The hint changes nothing about the order or the default. - Reads directory listings and
lstatonly, never a file's content; an emptyincoming/is exit 0 with nothing to do.
Properties
- Changes files: no
- Idempotent: yes
- Atomic: Read-only
- Counts toward the session call budget: yes
- Can reach the network: no
Exit codes
0- success
See also
wikitool raw accept- promotes the chosen candidateinstructions/wiki-ingest/SKILL.md- ingest without an argument starts hereraw/CONTRACT.md"Getting a file in: incoming/" - candidates and order, and why
raw accept
Promote one or more files, or one folder, from incoming/ into raw/.
Synopsis
wikitool raw accept <file> [<file> ...] --fidelity <v> --authority <v> [--page "<Title>"] [--dry-run]- Promote one or more files fromincoming/into today'sraw/<YYYY>/<MM>/shardwikitool raw accept incoming/<folder> --fidelity <v> --authority <v> [--dry-run]- Promote a whole folder as one source, its structure kept, intoraw/<YYYY>/<MM>/<folder>/wikitool raw accept <file> --replaces <raw-path> [--fidelity <v>] [--authority <v>] [--dry-run]- Overwrite one existing raw file in place with a new editionwikitool raw accept incoming/<bundle> --replaces-bundle <raw-bundle> [--dry-run]- Replace a captured bundle as a whole with the new editionraw capture --updatewrote
Options
Arguments:
files... One or more files directly in incoming/, all belonging to the same
source - or one folder in incoming/, accepted whole as one source
[required]
Options:
--fidelity <str> How faithful the capture is (see `wikitool types
describe source`). Required unless --replaces is
given, where it is the optional, sanctioned way to
correct an already-set value
--authority <str> What the material may claim about its subject (see
`wikitool types describe source`). Required unless
--replaces is given, where it is the optional,
sanctioned way to correct an already-set value
--page <str> Extend this existing source page's raw_files: with
the promoted file(s), folding in its already-
promoted file if this raises it past one
--replaces <path> Overwrite this existing raw/ file in place with the
single incoming/ file passed alongside it - the only
sanctioned way past the stem-uniqueness rule below
--dry-run List what would move without writing
--replaces-bundle <path> Replace this captured bundle under raw/ as a whole
with the new edition in the incoming/ folder passed
alongside it (written by raw capture --update)
-h, --help Show this message and exit.
Examples
tools/wikitool raw accept incoming/docker-cheatsheet.md --fidelity verbatim --authority reporting
tools/wikitool raw accept incoming/part-2.md --fidelity verbatim --authority reporting --page "Source - Docker Cheatsheet"
tools/wikitool raw accept incoming/projekt-x --fidelity verbatim --authority reporting
tools/wikitool raw accept incoming/cluster.md --replaces raw/documents/cluster.md
tools/wikitool raw accept incoming/chemenu --replaces-bundle raw/2026/10/chemenu
Behaviour
- Promotes files from
incoming/intoraw/<YYYY>/<MM>/, computed from the accept date rather than chosen by hand. A file argument must sit directly inincoming/; a file inside a subdirectory is refused, since a subdirectory is a source of its own. - A folder argument (
incoming/<folder>) is one source: every file below it moves toraw/<YYYY>/<MM>/<folder>/at the same relative path, and the directories left empty are removed -incoming/<folder>no longer exists afterwards. The folder name is the bundle name; twoREADME.mdin different subfolders are no conflict. - A folder is accepted alone - no other argument, no
--page, no--replaces- with one--fidelity/--authoritypair for all of it. It is refused, before anything moves, if it is empty, or if a hidden entry (name starting with.), a symlink or a special file sits anywhere below it; the refusal names each one. - One file promoted alone lands with no directory of its own; several files in one call nest under
raw/<YYYY>/<MM>/<stem>/, named after the first file's stem. --fidelity/--authorityare required on a plain accept (types describe sourcelists the values);unknownis refused - it is backfill-only.--page "<Title>"additionally extends that existing source page'sraw_files:in the same call and writes both capture fields onto it - refused if it already carries a different value, since a capture field is fixed once.- If
--pageraises the page past one file, its already-promoted file is folded into a bundle at its own parent directory, not today's shard, so a bundle never mixes an old and a new capture date - after checking that file has no other owner. - Every name occupied anywhere under
raw/- file stems and bundle directory names alike, old type directories and date shards together - stays unique: a promote whose target name already belongs to something this call does not itself own is refused, naming--replacesand renaming inincoming/as the two routes, without recommending either. --replaces <raw-path>overwrites that file in place with the single incoming file (same filename required), leaves every page'sraw_files:untouched and writes nokb/page; the previous edition survives only ingit log --follow <raw-path>.- With
--replaces,--fidelity/--authorityare optional, and passing one overwrites the owning page's already-set value - the one path the fixed-once rule does not block. --replacesrefuses a target with more than one owning source page; with none, it replaces anyway and says so. It cannot be combined with--pageor with more than one incoming file.--replacesprints the source page (if any) and its citing pages, so their update lands in the same commit as the replacement.- A file already at its computed destination is what "already exists" reports, not a partial prior run to resume - safe to retry as-is once a cause is fixed.
- A folder carrying
_capture.jsonat its top is a captured bundle (raw capture):--fidelity/--authoritycome from that manifest only and are refused on the command line; the folder must hold exactly the files the manifest lists._capture.jsongoes in noraw_files:. --replaces-bundle <raw-bundle>replaces a captured bundle underraw/with the new edition inincoming/<bundle>at the same address: files gone from the new edition are removed, emptied directoriesrmdired, and afterwards the bundle holds exactly the new manifest's files plus_capture.json.raw_files:is left untouched; an owning source page'sfidelity/authorityis overwritten where the new manifest differs.--replaces-bundleprints each changed file asA/M/D, grouped by owning source page with its citing pages, and thetouch --page ... --add/--remove raw_files=lines that follow;git diffon the bundle shows theMandDfiles, theAfiles appear only in that list because they are still untracked.--replacesand--pagerefuse a target inside a captured bundle; the refusal namesraw capture --updateand--replaces-bundle. A file named_capture.jsonanywhere but at a captured folder's top is refused - the name is reserved.--dry-runreports the moves without making them.
Properties
- Changes files: yes
- Idempotent: no
- Atomic:
raw accept: No - one filesystem move per file, then (with--page) one page write. With a folder: No - one move per file, then onermdirper emptied directory; a half-accepted folder is not resumed.raw accept --replaces: No - oneunlink()+ onerename(), plus (if--fidelity/--authoritywas given) one page write.raw accept --replaces-bundle: No - oneunlink()per removed file, onerename()per added or modified file, then the manifest, then onermdirper emptied directory, plus one page write per owning page whose capture fields change; a half-replaced bundle is not resumed - Counts toward the session call budget: yes
- Can reach the network: no
Exit codes
0- success1- raw accept: A file does not exist or is not directly inincoming/; two files in one call share a filename; a target path already exists; or a target path would be over the path budget (160 UTF-16 code units below the instance root)1- raw accept incoming/: The folder is not directly inincoming/, is combined with another argument,--pageor--replaces, holds no file, or holds a hidden entry, a symlink or a special file; a target path is over the budget; or the folder name is already occupied underraw/1- A file - given directly, inside a folder, or as--replaces/--replaces-bundlematerial - is a guideline export: its first line, after an optional BOM, starts with<!-- wikitool:export1- raw accept:--fidelity/--authorityis missing, or namesunknownor a value outside the schema's enum1- raw accept: The target name is already occupied anywhere underraw/by something the call does not own1- raw accept:--pagenames an unknown page or one with noraw_files:yet, an existingraw_files:entry is missing on disk, a file to be moved has more than one owning page, or--pagewould overwrite an already-setfidelity/authoritywith a different value1- raw accept --replaces: More than one incoming file, or--pagealso given1- raw accept --replaces: The incoming file does not exist or is not directly inincoming/, its filename differs from the target's, or the target does not lie underraw/or does not exist1- raw accept --replaces:--fidelity/--authoritynamesunknownor a value outside the schema's enum, or the target has more than one owning source page1- raw accept --replaces / --page: The target, or a file the page already has, lies in a captured bundle1- raw accept incoming/: A captured folder is given--fidelity/--authority, its_capture.jsoncannot be read or names an invalid value, or its files differ from the ones the manifest lists1- raw accept --replaces-bundle: Either side has no_capture.json, the two manifests name different repositories, the folder's name differs from the bundle's,--page,--replaces,--fidelityor--authoritywas also given, the folder does not match its manifest, a new path is over the budget, or a file of the bundle has more than one owning source page
See also
raw/CONTRACT.md"Getting a file in: incoming/" - the rules and whywikitool raw pending- what is waiting inincoming/, and which entry is nextwikitool raw capture- writes a captured bundle, or its new edition, intoincoming/wikitool types describe source- the capture field valueswikitool new source- the source page for a promoted file
upload list
List every MCP submission currently waiting in the quarantine (mcp-upload/).
Synopsis
wikitool upload list [--json]
Options
--json Print every waiting submission as JSON
-h, --help Show this message and exit.
Examples
tools/wikitool upload list
tools/wikitool upload list --json
Behaviour
- Lists every submission waiting in
mcp-upload/, oldest id first: id, filename, size, submitter. - Only ever non-empty when
.wikitool-upload.jsonopts the checkout into the MCP server'ssubmittool. - A submission directory with a corrupt manifest is silently skipped.
- Never fails; read-only and safe to retry freely.
Properties
- Changes files: no
- Idempotent: yes
- Atomic: Read-only
- Counts toward the session call budget: yes
- Can reach the network: no
Exit codes
0- success
See also
wikitool upload show- one submission's manifestdocs/how-to/set-up-the-mcp-server.md§ "Optional: the submit path"
upload show
Print one submission's manifest in full.
Synopsis
wikitool upload show <id> [--json]
Options
Arguments:
submission_id A submission id from `upload list` [required]
Options:
--json
-h, --help Show this message and exit.
Examples
tools/wikitool upload show <id>
Behaviour
- Prints one submission's manifest in full: filename, size, sha256, submitter, submitter source (the header name, not a claim the header was honest), submission time.
- What a reviewer reads before
upload accept. - Read-only.
Properties
- Changes files: no
- Idempotent: yes
- Atomic: Read-only
- Counts toward the session call budget: yes
- Can reach the network: no
Exit codes
0- success1- Unknown or malformed submission id
See also
wikitool upload accept- promotes it after reviewwikitool upload reject- declines it
upload accept
Upload Review Gate: promote a submission's file from quarantine into incoming/.
Synopsis
wikitool upload accept <id> [--confirm TOKEN]
Options
Arguments:
submission_id A submission id from `upload list` [required]
Options:
--confirm <str> The token from a prior refusal, once a human has reviewed it
-h, --help Show this message and exit.
Examples
tools/wikitool upload accept <id>
tools/wikitool upload accept <id> --confirm <token> # re-run after exit 42, once the user approved the manifest
Behaviour
- Promotes a submission's file from
mcp-upload/<id>/intoincoming/, deletes the quarantine directory, and appends anacceptedevent tomcp-upload/ledger.jsonl. - Upload Review Gate: without a matching
--confirm, exits 42 and prints the manifest in full plus the exact re-run line - one submission at a time. The gate check runs before anything is moved. - The token digests id, filename, size, sha256 and submitter, so an edited or superseded manifest invalidates it.
- An occupied
incoming/<filename>is an ordinary validation error, not the gate.
Properties
- Changes files: yes
- Idempotent: no
- Atomic: No - one filesystem move, one directory delete, one ledger append; the gate check runs first, before any of them
- Counts toward the session call budget: yes
- Can reach the network: no
- Gates: upload-review - see exit codes and gates
Exit codes
0- success1- Unknown or malformed submission id, or the submission's file is missing frommcp-upload/<id>/1-incoming/<filename>already exists42- Upload Review Gate:--confirmis absent or does not match the manifest's current token
See also
wikitool upload show- the manifest to reviewwikitool raw accept- the next step for the file inincoming/instructions/gates.md- the gate procedure
upload reject
Delete a submission's material, keeping only its ledger trail.
Synopsis
wikitool upload reject <id> --reason "<why>"
Options
Arguments:
submission_id A submission id from `upload list` [required]
Options:
--reason <str> Why this submission was declined [required]
-h, --help Show this message and exit.
Examples
tools/wikitool upload reject <id> --reason "duplicate of raw/articles/llm-wiki.md"
Behaviour
- Appends an append-only
rejectedevent naming the reason and the sha256 of what was declined, then deletes the submission's material. - The ledger write happens first, so an interruption still leaves the reason on record.
- No gate - rejecting needs no clearance, only accepting does.
- Not idempotent: a second call with the same id reports "unknown id", which confirms the first call worked.
Properties
- Changes files: yes
- Idempotent: no
- Atomic: No - one ledger append, then one recursive delete; the ledger write happens first, so an interruption still leaves the reason on record
- Counts toward the session call budget: yes
- Can reach the network: no
Exit codes
0- success1- Unknown or malformed submission id, or an empty--reason
See also
wikitool upload show- the manifest to review