docs(conventions): the merge button is off for a reason, and the reason now lives in the repo
CONVENTIONS.md consolidates rules that already applied but were readable only to the maintainer: the charter (CLAUDE.md), versioning and vendoring (README.md), the reporting route (SECURITY.md), and file conventions visible only in the shape of the files. Two things stop being inferences. Why pull requests are off: this repository is vendored into runtimes that pin a tag, so a data change changes what they find, and that must be coordinated before it exists. And when a value may change: the three recorded mechanisms - re-extraction, retraction, owner-directed authoring - each tied to its source_fidelity key, with merit named as not among them. The four offline checks are included and were each proven to go red on a planted violation, not merely green on a clean tree. They are one-liners because a script would be .sh and check 4 would fail on it. No data file changed; a runtime passing 0.4.1 passes 0.4.2 unchanged. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KDRVXSFhKpFTzdoyjpjL17
This commit is contained in:
parent
2d86151e3b
commit
fe5e6b290b
3 changed files with 256 additions and 4 deletions
40
CHANGELOG.md
40
CHANGELOG.md
|
|
@ -9,6 +9,46 @@ Versioning note: the repository tag versions **the contract** (file set, key nam
|
||||||
case ids, disposition semantics). Each JSON file additionally carries its own
|
case ids, disposition semantics). Each JSON file additionally carries its own
|
||||||
`"version"` field, bumped when that file changes.
|
`"version"` field, bumped when that file changes.
|
||||||
|
|
||||||
|
## [0.4.2] — 2026-08-11
|
||||||
|
|
||||||
|
**No data file changed and no pattern moved.** A runtime that passes `0.4.1` passes `0.4.2`
|
||||||
|
unchanged; there is nothing here to re-measure. What the release adds is the rule set an outside
|
||||||
|
contributor could not previously read — including the reason the forge surface is shaped the way
|
||||||
|
it is.
|
||||||
|
|
||||||
|
### Added
|
||||||
|
|
||||||
|
- `CONVENTIONS.md` — the whole rule set a change here is held to, consolidated. **Not new
|
||||||
|
policy:** the charter lives in `CLAUDE.md`, the versioning and vendoring rules in `README.md`,
|
||||||
|
the reporting route in `SECURITY.md`, and the file conventions were visible only in the shape
|
||||||
|
of the files. Collected because a convention that exists only in the maintainer's head is not
|
||||||
|
one an outside reader can meet.
|
||||||
|
|
||||||
|
Two things in it were previously inferable at best. **Why pull requests are off:** this
|
||||||
|
repository is vendored into independent runtimes that pin a tag, so a change to detection data
|
||||||
|
changes what they *find*, and that has to be coordinated with each consumer **before it
|
||||||
|
exists** — which a merge button cannot do. `org-ops` reached that conclusion on 2026-08-11
|
||||||
|
from a README line, and the conclusion was right; this file is the ground it was missing.
|
||||||
|
**When a value may change:** the three mechanisms that have moved one so far — re-extraction,
|
||||||
|
retraction, and owner-directed authoring — each named with the `source_fidelity` key that
|
||||||
|
records it, and merit named explicitly as *not* on that list.
|
||||||
|
|
||||||
|
It also carries the four offline checks that stand in for the CI this organisation does not
|
||||||
|
have. Each was confirmed to go **red** on a violation, not merely green on a clean tree: a
|
||||||
|
JSON file with no `version`, a `spec/` file with no normative marker, and a planted `.sh` were
|
||||||
|
each detected. A check that cannot fail proves nothing. The checks are shell one-liners rather
|
||||||
|
than a script because a script would be `.sh`, and check 4 would fail on the tooling meant to
|
||||||
|
enforce it.
|
||||||
|
|
||||||
|
- `README.md` — a short **Contributing** section pointing at it, carrying the pull-request answer
|
||||||
|
inline so a reader who never opens the file still gets it. Same pattern the
|
||||||
|
**Reporting a wrong entry** section followed for `SECURITY.md` in `0.3.1`.
|
||||||
|
|
||||||
|
The four `v0.4.1` references in the install block and the layout table move to `v0.4.2`.
|
||||||
|
|
||||||
|
This closes the second half of what `org-ops` recorded as missing against the org standard on
|
||||||
|
2026-08-11. `SECURITY.md` was the first half, in `0.3.1`.
|
||||||
|
|
||||||
## [0.4.1] — 2026-08-11
|
## [0.4.1] — 2026-08-11
|
||||||
|
|
||||||
**No data file changed and no pattern moved. A number this repository published was wrong, and
|
**No data file changed and no pattern moved. A number this repository published was wrong, and
|
||||||
|
|
|
||||||
199
CONVENTIONS.md
Normal file
199
CONVENTIONS.md
Normal file
|
|
@ -0,0 +1,199 @@
|
||||||
|
# Conventions
|
||||||
|
|
||||||
|
The rules a change to this repository is held to, in one place.
|
||||||
|
|
||||||
|
Nothing here is new policy. Every rule below was already being applied — some of it stated in
|
||||||
|
[README.md](README.md), some in [SECURITY.md](SECURITY.md), some only visible in the shape of
|
||||||
|
the files themselves. It is collected here because a convention that only exists in the
|
||||||
|
maintainer's head is not a convention an outside reader can meet, and because two of the
|
||||||
|
decisions this repository makes — that nothing here runs, and that pull requests are switched
|
||||||
|
off — look arbitrary until the reason is written down next to them.
|
||||||
|
|
||||||
|
This file binds **contributions to this repository**. It does not bind the runtimes that read
|
||||||
|
the data; that is what `spec/` is for, and those files say `Status: normative` and mean it.
|
||||||
|
|
||||||
|
## The charter: nothing here runs
|
||||||
|
|
||||||
|
**This repository contains no executable code, and it will not acquire any.**
|
||||||
|
|
||||||
|
Not permitted, without exception:
|
||||||
|
|
||||||
|
- `.mjs`, `.js`, `.ts`, `.py`, `.sh` — or any other file that implements detection, scanning,
|
||||||
|
normalisation, scoring or I/O;
|
||||||
|
- `package.json`, `pyproject.toml`, lockfiles, dependencies, build steps;
|
||||||
|
- an import of, or knowledge of, any framework, SDK or runtime;
|
||||||
|
- network access, model calls, dependence on the clock, or randomness.
|
||||||
|
|
||||||
|
Permitted: JSON data, normative specifications in Markdown, and conformance fixtures
|
||||||
|
(`input.txt` plus `expected.json`).
|
||||||
|
|
||||||
|
The reason is `fork-and-own`. A consumer on a runtime nobody here has thought of should be able
|
||||||
|
to vendor this repository without inheriting a single technology choice. A build step is a
|
||||||
|
technology choice; so is a test runner. The moment one exists, the set of runtimes that can
|
||||||
|
adopt this core shrinks to the set that tolerates it.
|
||||||
|
|
||||||
|
The consequence is that **this repository cannot validate itself**. There is no CI in this
|
||||||
|
organisation and nothing runs on push. The checks below are yours to run, and they are the only
|
||||||
|
ones there are.
|
||||||
|
|
||||||
|
## How a change gets in — and why not by pull request
|
||||||
|
|
||||||
|
Pull requests are switched off on the canonical repository at
|
||||||
|
`git.fromaitochitta.com/open/llm-security-commons`, and issues are not the reporting channel
|
||||||
|
either. That is deliberate, and the reason is stronger than a preference about tooling.
|
||||||
|
|
||||||
|
This repository is **vendored into independent runtimes** — a Claude Code plugin on Node/ESM, a
|
||||||
|
Python guard, an advisory surface — each pinning a tag. The contract between them is semver, and
|
||||||
|
a change to detection data changes what those runtimes *find*. A patch to a pattern table is not
|
||||||
|
a contribution that can be merged and then socialised; it is a contract change that has to be
|
||||||
|
coordinated with every consumer **before it exists**, because the moment it is tagged, the next
|
||||||
|
consumer to pull it gets different findings than the one that pulled yesterday. A merge button
|
||||||
|
does not do that, and nothing downstream of a merge button can.
|
||||||
|
|
||||||
|
So the routes in are:
|
||||||
|
|
||||||
|
1. **Fork and own it.** MIT, and an intended use rather than a tolerated one. If you need a
|
||||||
|
different value in your runtime, this is the fast path and it is fully supported.
|
||||||
|
2. **Report it privately** — see [SECURITY.md](SECURITY.md). A wrong entry in a detection table
|
||||||
|
is a silent false negative in every runtime that reads it, so a report about one is a
|
||||||
|
security report even though nothing here executes. That file also explains why a confirmed
|
||||||
|
defect in extracted data is usually decided in the runtime it came from before it changes
|
||||||
|
here.
|
||||||
|
|
||||||
|
If you maintain a consumer, the coordination channel is direct contact with the maintainer, not
|
||||||
|
this repository's forge surface.
|
||||||
|
|
||||||
|
## Data files (JSON)
|
||||||
|
|
||||||
|
- **Every JSON file carries a top-level `"version"`** — a semver string. No exceptions.
|
||||||
|
- **Every JSON file states what it is and where its data came from**, in a top-level
|
||||||
|
`"$comment"` or `"description"`. Provenance is not optional metadata here; it is what makes
|
||||||
|
the difference between a table and a rumour.
|
||||||
|
- 2-space indentation, LF line endings, a trailing newline, UTF-8 without BOM.
|
||||||
|
- **Code points are written as strings** — `"U+200B"` — never as the raw invisible character.
|
||||||
|
Review cannot see what it cannot render, and a reviewer who cannot see a character cannot
|
||||||
|
check it. The single exception is `conformance/*/input.txt`, which by definition contains the
|
||||||
|
actual bytes.
|
||||||
|
- **Keys are stable identifiers.** Consumers match on them. **Changing a key is a breaking
|
||||||
|
change** and is versioned as one.
|
||||||
|
|
||||||
|
The four files that carry detection material — `codepoints/carriers.json`,
|
||||||
|
`signatures/secret-egress.json`, `signatures/malware-signatures.json`,
|
||||||
|
`signatures/active-content.json` — take one further rule, which is the most important line in
|
||||||
|
this document:
|
||||||
|
|
||||||
|
> **They are changed only from verified source data** — a dump from the owning repository, the
|
||||||
|
> Unicode standard, published vendor documentation. Never from memory, never "filled in for
|
||||||
|
> consistency". A guessed code point or a regex with wrong escaping is a silent false negative:
|
||||||
|
> a detector that looks like it is working and is not looking. If an entry cannot be verified,
|
||||||
|
> leave it out, or mark it explicitly unverified in its `$comment`.
|
||||||
|
|
||||||
|
## Specifications (Markdown)
|
||||||
|
|
||||||
|
- A normative specification carries **`Status: normative`** at the top and uses RFC 2119 terms
|
||||||
|
(MUST / MUST NOT / SHOULD / MAY) in uppercase, deliberately. These files bind the
|
||||||
|
implementations that read them.
|
||||||
|
- An informative document (`docs/`) carries **`Status: informative`** and is **never ground
|
||||||
|
truth**. It records measurements, history and open disagreements; a runtime is not wrong for
|
||||||
|
disagreeing with one.
|
||||||
|
- Naming a file that does not exist yet is allowed where the layout is part of the contract —
|
||||||
|
`spec/decode-pipeline.md` is named in README.md and marked **Planned**. It is not a link, and
|
||||||
|
nothing depends on it. A normative spec guessed at would be worse than an absent one.
|
||||||
|
|
||||||
|
## Conformance cases
|
||||||
|
|
||||||
|
- One directory per case: `conformance/<case-id>/input.txt` and
|
||||||
|
`conformance/<case-id>/expected.json`.
|
||||||
|
- `<case-id>` is stable and descriptive. **Changing a case id is a breaking change** — a
|
||||||
|
published conformance result names it.
|
||||||
|
- `expected.json` is **ground truth**. If a runtime disagrees with it, the runtime is wrong.
|
||||||
|
- The one way that reverses: the fixture is proven wrong. Then the fixture changes **in its own
|
||||||
|
commit, with the reason written down** — never folded into a change that does something else,
|
||||||
|
because a fixture edit is the one edit that can make every conforming runtime wrong
|
||||||
|
identically.
|
||||||
|
- A case declares the data files it is `scope`d to. A runtime that does not implement a scoped
|
||||||
|
table reports the case `not-applicable` — a third verdict beside pass and fail, and one that
|
||||||
|
must be reported rather than dropped from the denominator. See
|
||||||
|
[`spec/conformance-corpus.md`](spec/conformance-corpus.md).
|
||||||
|
|
||||||
|
## When a value may change
|
||||||
|
|
||||||
|
Detection values do not change here because someone here judged them wrong. Three mechanisms
|
||||||
|
have moved a value so far, and each is recorded in the file itself rather than only in the
|
||||||
|
changelog:
|
||||||
|
|
||||||
|
1. **Re-extraction** — the owning runtime changed its own value, and this repository re-read the
|
||||||
|
source at a pinned public commit. Recorded in `source_fidelity.post_extraction_drift`.
|
||||||
|
2. **Retraction** — this repository described its own provenance wrongly. The stored value may
|
||||||
|
have been right all along; the account of where it came from was not. Recorded in
|
||||||
|
`source_fidelity.retracted`.
|
||||||
|
3. **Owner-directed authoring** — the owning runtime decided a value and asked this repository
|
||||||
|
to carry it, because the dependency has inverted: the source now reads *this* file and holds
|
||||||
|
no literal to re-read. Recorded separately, in `source_fidelity.owner_directed_changes`,
|
||||||
|
precisely because calling it drift would assert that the source moved and commons followed —
|
||||||
|
which would be false in the one direction that matters.
|
||||||
|
|
||||||
|
What is **not** on that list is merit. Data extracted from an implementation is kept
|
||||||
|
behaviour-identical to it on purpose, because a copy that disagrees with its source is the exact
|
||||||
|
failure this repository exists to prevent. Producing one as a *fix* would be self-defeating. If
|
||||||
|
you believe an extracted value is wrong, say so — and expect the decision to be taken in the
|
||||||
|
runtime where the pattern is under test.
|
||||||
|
|
||||||
|
Data **authored here** rather than extracted — conformance payloads, flagged as
|
||||||
|
`authored_payloads` in `conformance/manifest.json` — is this repository's own to correct.
|
||||||
|
|
||||||
|
## Versioning
|
||||||
|
|
||||||
|
Two version numbers, and they are not locked to each other:
|
||||||
|
|
||||||
|
- **The repository tag** (`vX.Y.Z`) versions **the contract**: the file set, the key names, the
|
||||||
|
case ids, the disposition semantics.
|
||||||
|
- **Each JSON file's own `"version"`** is bumped when *that file* changes.
|
||||||
|
|
||||||
|
What counts as which:
|
||||||
|
|
||||||
|
| Change | Bump |
|
||||||
|
| --- | --- |
|
||||||
|
| New data field, new entry | minor |
|
||||||
|
| Changed or removed key, case id, or layout | **major** — consumers break |
|
||||||
|
| A change to what a conforming runtime *finds* | minor in 0.x, and the changelog says so |
|
||||||
|
|
||||||
|
That last row is why **the changelog entry is the thing to read before upgrading, not the
|
||||||
|
version number**. Pre-1.0, a release that changes findings is still a minor bump; only the entry
|
||||||
|
tells you whether your assertions move.
|
||||||
|
|
||||||
|
Consumers vendor **a tag, never `main`** — a conformance result can only be attributed to a tag.
|
||||||
|
Nothing polls for updates; when a change moves detection data, the maintainer notifies known
|
||||||
|
consumers directly, and their upgrade remains their own action on their own schedule.
|
||||||
|
|
||||||
|
## Checks to run before proposing a change
|
||||||
|
|
||||||
|
There is no CI. These four are the validation surface, they run offline in a second, and each
|
||||||
|
one has been confirmed to go red on a violation rather than merely green on a clean tree.
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 1. Every JSON file is well-formed
|
||||||
|
find . -name '*.json' -not -path './.git/*' -print0 \
|
||||||
|
| xargs -0 -n1 python3 -m json.tool > /dev/null && echo OK
|
||||||
|
|
||||||
|
# 2. Every JSON file outside conformance/ carries a top-level "version"
|
||||||
|
find . -name '*.json' -not -path './.git/*' -not -path './conformance/*' -print0 \
|
||||||
|
| xargs -0 python3 -c 'import json,sys
|
||||||
|
missing=[p for p in sys.argv[1:] if "version" not in json.load(open(p))]
|
||||||
|
print("\n".join("MISSING version: "+p for p in missing) or "OK")'
|
||||||
|
|
||||||
|
# 3. Every spec carries its normative marker (prints offending files, nothing = clean)
|
||||||
|
grep -L 'Status: normative' spec/*.md || echo OK
|
||||||
|
|
||||||
|
# 4. Charter guard: no executable code has crept in
|
||||||
|
find . -type f \( -name '*.mjs' -o -name '*.js' -o -name '*.ts' -o -name '*.py' -o -name '*.sh' \) \
|
||||||
|
-not -path './.git/*' | grep . && echo 'CHARTER VIOLATION' || echo OK
|
||||||
|
```
|
||||||
|
|
||||||
|
They are written as shell one-liners rather than shipped as a script because a script would be
|
||||||
|
`.sh`, and check 4 would then fail on the tooling meant to enforce it.
|
||||||
|
|
||||||
|
What they do **not** check: whether a value is *correct*. Nothing offline can. That is what the
|
||||||
|
conformance corpus is for, and it runs in each consumer's own test suite against a pinned tag —
|
||||||
|
constraining two of the seven data files, which is a real limit and is stated in
|
||||||
|
[README.md](README.md) under **Known limitations**.
|
||||||
21
README.md
21
README.md
|
|
@ -24,7 +24,7 @@ As a `git subtree` (recommended: history is preserved and upgrades are a single
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
git subtree add --prefix vendor/commons \
|
git subtree add --prefix vendor/commons \
|
||||||
https://git.fromaitochitta.com/open/llm-security-commons.git v0.4.1 --squash
|
https://git.fromaitochitta.com/open/llm-security-commons.git v0.4.2 --squash
|
||||||
|
|
||||||
# later, to move to a newer tag
|
# later, to move to a newer tag
|
||||||
git subtree pull --prefix vendor/commons \
|
git subtree pull --prefix vendor/commons \
|
||||||
|
|
@ -34,7 +34,7 @@ git subtree pull --prefix vendor/commons \
|
||||||
Or pin a tag and copy — `fork-and-own` is an explicitly supported path:
|
Or pin a tag and copy — `fork-and-own` is an explicitly supported path:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
git clone --depth 1 --branch v0.4.1 \
|
git clone --depth 1 --branch v0.4.2 \
|
||||||
https://git.fromaitochitta.com/open/llm-security-commons.git
|
https://git.fromaitochitta.com/open/llm-security-commons.git
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
@ -61,14 +61,14 @@ and keeping it that small is the point.
|
||||||
| [`schema/conformance-declaration.schema.json`](schema/conformance-declaration.schema.json) | **Normative.** The shape a runtime publishes alongside a conformance result: which commons tables it implements, the commons commit it measured, and the four verdict counts. Required by the corpus spec §1.1; not validated by anything here, because nothing here runs. |
|
| [`schema/conformance-declaration.schema.json`](schema/conformance-declaration.schema.json) | **Normative.** The shape a runtime publishes alongside a conformance result: which commons tables it implements, the commons commit it measured, and the four verdict counts. Required by the corpus spec §1.1; not validated by anything here, because nothing here runs. |
|
||||||
| [`spec/conformance-corpus.md`](spec/conformance-corpus.md) | **Normative.** How to read the corpus: what a case is, why `input.txt` is bytes rather than text, what `exact-within-scope` requires of a runtime, and how a runtime declares its table set so a case scoped outside it reads as `not-applicable` rather than as a failure. |
|
| [`spec/conformance-corpus.md`](spec/conformance-corpus.md) | **Normative.** How to read the corpus: what a case is, why `input.txt` is bytes rather than text, what `exact-within-scope` requires of a runtime, and how a runtime declares its table set so a case scoped outside it reads as `not-applicable` rather than as a failure. |
|
||||||
| [`conformance/`](conformance/) | 90 cases. One directory per case: `input.txt` in, `expected.json` out. Ground truth. 84 cover the injection lexicon — 83 one per pattern, both seeding runtimes measured producing the same verdict on all 83, plus one variant case gating a pattern form against its predecessor. Six cover active content and are measured against the one runtime that implements that table — `not-applicable` for the other, not failing. See [`conformance/manifest.json`](conformance/manifest.json). |
|
| [`conformance/`](conformance/) | 90 cases. One directory per case: `input.txt` in, `expected.json` out. Ground truth. 84 cover the injection lexicon — 83 one per pattern, both seeding runtimes measured producing the same verdict on all 83, plus one variant case gating a pattern form against its predecessor. Six cover active content and are measured against the one runtime that implements that table — `not-applicable` for the other, not failing. See [`conformance/manifest.json`](conformance/manifest.json). |
|
||||||
| `spec/decode-pipeline.md` | **Planned, still not shipped as of v0.4.1.** The decode order, in RFC 2119 language. Two runtimes that decode in different orders will disagree on identical input. Writing it needs the decode implementation, which is engine code and has not been supplied — and a normative spec guessed from a data dump would be worse than an absent one. |
|
| `spec/decode-pipeline.md` | **Planned, still not shipped as of v0.4.2.** The decode order, in RFC 2119 language. Two runtimes that decode in different orders will disagree on identical input. Writing it needs the decode implementation, which is engine code and has not been supplied — and a normative spec guessed from a data dump would be worse than an absent one. |
|
||||||
| [`docs/extraction-plan.md`](docs/extraction-plan.md) | Informative: where each file was seeded from, and what v0.1.0 promised. |
|
| [`docs/extraction-plan.md`](docs/extraction-plan.md) | Informative: where each file was seeded from, and what v0.1.0 promised. |
|
||||||
| [`docs/lexicon-port-divergence.md`](docs/lexicon-port-divergence.md) | Informative: a measured disagreement between two ports of the injection lexicon — 13 patterns that behave differently, in both directions. Most of it is still open, and the two rows that closed in v0.4.0 closed because the runtime that owns the value decided, not because this document found them wrong. |
|
| [`docs/lexicon-port-divergence.md`](docs/lexicon-port-divergence.md) | Informative: a measured disagreement between two ports of the injection lexicon — 13 patterns that behave differently, in both directions. Most of it is still open, and the two rows that closed in v0.4.0 closed because the runtime that owns the value decided, not because this document found them wrong. |
|
||||||
|
|
||||||
Every JSON file carries a top-level `version`. Every normative specification carries a
|
Every JSON file carries a top-level `version`. Every normative specification carries a
|
||||||
`Status: normative` marker. Rows marked **Planned** are named here because the layout is
|
`Status: normative` marker. Rows marked **Planned** are named here because the layout is
|
||||||
part of the contract, but the file does not exist yet — they are not links, and nothing in
|
part of the contract, but the file does not exist yet — they are not links, and nothing in
|
||||||
v0.4.1 depends on them.
|
v0.4.2 depends on them.
|
||||||
|
|
||||||
Each data file records its own provenance and, in `verified`, how strongly it is backed.
|
Each data file records its own provenance and, in `verified`, how strongly it is backed.
|
||||||
`calibration/calibration.json` is currently the one file that says `false`: it was
|
`calibration/calibration.json` is currently the one file that says `false`: it was
|
||||||
|
|
@ -150,6 +150,19 @@ so the gap is visible rather than inferred.
|
||||||
- **The homoglyph map is finite.** Confusable coverage is a long tail; absence from the map
|
- **The homoglyph map is finite.** Confusable coverage is a long tail; absence from the map
|
||||||
is not evidence a character is safe.
|
is not evidence a character is safe.
|
||||||
|
|
||||||
|
## Contributing
|
||||||
|
|
||||||
|
[CONVENTIONS.md](CONVENTIONS.md) is the whole rule set a change here is held to: the charter
|
||||||
|
(nothing runs, and why that is load-bearing rather than fussy), the file conventions, when a
|
||||||
|
detection value is allowed to move, how the two version numbers work, and the four offline
|
||||||
|
checks that stand in for the CI this organisation does not have.
|
||||||
|
|
||||||
|
It also answers the question the forge surface raises on its own: **pull requests are switched
|
||||||
|
off, deliberately.** This repository is vendored into independent runtimes that pin a tag, so a
|
||||||
|
change to detection data changes what they *find* — that has to be coordinated with each
|
||||||
|
consumer before it exists, which a merge button cannot do. Fork-and-own is the supported path;
|
||||||
|
a wrong entry is reported privately.
|
||||||
|
|
||||||
## Reporting a wrong entry
|
## Reporting a wrong entry
|
||||||
|
|
||||||
A wrong code point or a mis-escaped regex here is a silent false negative in every runtime
|
A wrong code point or a mis-escaped regex here is a silent false negative in every runtime
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue