Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
# Changelog

## Unreleased
## 1.0.0 — unpublished candidate

- Prepare stable/latest and preview channel checks, exact-archive qualification and a best-effort support policy. Runtime and wire v1 remain unchanged; npm publication is a separate step.
- Fix the public API contract for 1.0 preparation and document alpha.3 upgrade/rollback without changing wire v1. No stable version is published by this change.
- Check the exact candidate archive against integrity-pinned npm alpha.3 and beta.2: all nine writer/reader pairs, historical and Billetsys vectors, errors, exports and strict TypeScript consumers.
- Reject canonical-reader regressions for case/whitespace as well as grouping, and verify the documented exception classes across all three packages.
Expand Down
17 changes: 8 additions & 9 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,15 +23,14 @@ Do not replace their pins or regenerate historical vectors to hide a break.
Keep the TypeScript consumer and both writer/reader directions covered.
Temporary consumers and archives are removed even after failures.

## Publishing a prerelease

Use a clean, reviewed commit and verify that its CI passed. Keep the version, changelog and evidence version in sync. A published npm name/version cannot be reused. For the beta candidate, keep both `publishConfig.tag` and the explicit publication tag set to `beta`. Do not move the existing `alpha` or `latest` tags.

1. Run `pnpm check`, `pnpm test:demo`, `pnpm test:comparison`, `pnpm test:workflows` and `pnpm test:package`; the matching CI must also cover browsers, PDF extraction/lookup and the supported Node/OS matrix.
2. Pack with `pnpm pack --pack-destination artifacts`. Record the commit, package SHA-256 and npm SHA-512 integrity. Inspect the file inventory and install this exact archive into an isolated consumer before publication.
3. Authenticate to `https://registry.npmjs.org` with `npm login --auth-type=web`. Enter passwords and second-factor challenges only in npm's login flow. Never commit credentials or put them in an issue/PR. Direct publication requires account 2FA or another authentication method supported by npm; prefer the interactive account flow for the first release.
4. Run `npm publish ./artifacts/refmint-VERSION.tgz --dry-run --ignore-scripts --tag beta --access public --registry=https://registry.npmjs.org`, substituting the actual version. Inspect the name, version, files and integrity. Then publish the same archive by removing only `--dry-run`.
5. Read the public registry metadata back. Check the version, `beta` tag and tarball integrity, then install `refmint@beta` in a fresh consumer and exercise both `refmint` and `refmint/codec`. Download the registry tarball and compare it with the published archive. Keep the proof with the release record.
## Preparing and publishing a release

Follow [the release procedure](docs/releasing.md) and [support policy](docs/support.md).
Stable versions use `latest`; alpha uses `alpha`; beta/RC uses `beta`. Both
`publishConfig.tag` and the explicit publication tag must agree. The package gate
checks the channel. Use `pnpm test:package /absolute/path/to/candidate.tgz` to
qualify an existing final archive without rebuilding it. Publication is a separate
owner decision on a clean, reviewed commit with successful CI.

The first npm alpha.2 archive has updated README, changelog and contributor documentation. All other files match the original GitHub alpha.2 archive; the original tag, download and checksums remain intact. Future releases should prepare registry instructions before creating either archive.

Expand Down
7 changes: 5 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,11 @@ npm install --save-exact refmint@0.1.0-beta.2
[API compatibility and frozen v1 format](docs/beta-contract.md) · [Verified npm installation](docs/evidence/release-beta2.json).

[API contract for 1.0 preparation](docs/stable-contract.md) ·
[Upgrade checks from alpha.3](docs/migration-alpha3-to-1.md). The package remains in beta;
the compatibility matrix compares published releases with an unpublished archive.
[Upgrade checks from alpha.3](docs/migration-alpha3-to-1.md) ·
[Release channels](docs/releasing.md) · [Support policy](docs/support.md).
This checkout prepares an **unpublished 1.0.0 candidate**; the installation above
still selects the published beta. The compatibility matrix compares both old
releases with the exact candidate archive.

**Try an invoice lookup.** The [sample PDF](https://github.com/PerchAnton/refmint/blob/v0.1.0-beta.2/examples/workflows/sample-invoice.pdf)
shows `INV-2026-000042`, the short alias `D1042` and the 21-character printed
Expand Down
3 changes: 2 additions & 1 deletion SECURITY.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,5 @@ Keep a unique database constraint, retry conflicts with a limit, authorize looku

Do not attempt to repair an invalid code automatically: a guessed correction can select the wrong record. The parser only normalizes the presentation differences documented in SPEC.md.

For a potential vulnerability, use GitHub's private vulnerability reporting if available, or contact the repository owner through their GitHub profile without disclosing exploit details in a public issue. Ordinary reproducible bugs belong in issues. The current beta has not had an independent security audit. See the [beta scope](docs/beta-contract.md) and [stability criteria](docs/stability.md); a beta label is not a security assurance.
For a potential vulnerability, use GitHub's private vulnerability reporting if available, or contact the repository owner through their GitHub profile without disclosing exploit details in a public issue. Ordinary reproducible bugs belong in issues. The current package has not had an independent security audit. See the
[maintenance and support policy](docs/support.md). See the [beta scope](docs/beta-contract.md) and [stability criteria](docs/stability.md); a beta label is not a security assurance.
7 changes: 6 additions & 1 deletion docs/evidence.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"generated_at": "2026-10-27T13:21:13.955Z",
"version": "0.1.0-beta.2",
"version": "1.0.0",
"environment": {
"node": "v24.19.0",
"platform": "darwin",
Expand Down Expand Up @@ -114,5 +114,10 @@
"carried_forward": {
"reason": "Runtime JavaScript bytes are unchanged; original alpha.2 measurement timestamps, environment and samples are retained.",
"verified_date": "2026-11-05"
},
"release_preparation": {
"previousVersion": "0.1.0-beta.2",
"runtimeUnchanged": true,
"note": "Version metadata carried forward for the unpublished 1.0.0 candidate; original measurement timestamps, environment and hashes are unchanged."
}
}
90 changes: 90 additions & 0 deletions docs/releasing.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
# Release channels and exact-archive qualification

This branch prepares **1.0.0**. It does not publish it, move registry tags, or
approve a consumer dependency update. Use the published beta until a stable
release is explicitly announced. Package versions and wire v1 are independent.

## Channels

| Version | `publishConfig.tag` and explicit npm `--tag` | Intended use |
| --- | --- | --- |
| `X.Y.Z-alpha.N` | `alpha` | Experimental previews |
| `X.Y.Z-beta.N` or `X.Y.Z-rc.N` | `beta` | Compatibility/release trials |
| `X.Y.Z`, major at least 1 | `latest` | Reviewed stable releases |

`latest` is npm's default install channel; there is no separate `stable` alias.
Never send a prerelease to `latest`, or a stable build to a preview tag. The
package gate checks this policy in both the checkout and installed archive.
It intentionally rejects unsupported prerelease labels, leading-zero numeric
identifiers and build metadata; this is our release policy, not a SemVer parser.
A dist-tag is mutable routing, not an integrity or compatibility guarantee.
Consumers should use an exact version and retain their lockfile.

A beta publication changes only `beta`; a stable publication changes only
`latest`. Preserve `alpha` and the previous `beta` for explicit trials. Record
all registry tags immediately before and after publication. Never reassign a
published name/version or relabel an old beta archive as 1.0.0. See npm's
[publish](https://docs.npmjs.com/cli/v11/commands/npm-publish/) and
[dist-tag](https://docs.npmjs.com/cli/v11/commands/npm-dist-tag/) documentation.

## Before publication

The owner approves release separately from merging a preparation PR. No workflow
in this repository publishes automatically. Use a clean, reviewed commit whose
CI passed on that exact head, including Node/OS, browser and PDF jobs.

1. Update version, channel, changelog and evidence version together. Keep old
measurement dates and environments when the runtime is unchanged; label the
carry-forward. Runtime changes require fresh evidence and compatibility checks.
2. Run `pnpm check`, `pnpm test:demo`, `pnpm test:comparison`,
`pnpm test:workflows` and `pnpm test:package`. Review known bugs/security reports,
the [support policy](support.md), [API contract](stable-contract.md), and
[migration checks](migration-alpha3-to-1.md). Preserve all frozen vectors.
3. Pack once into a directory outside the checkout:

```sh
pnpm pack --pack-destination /absolute/path/to/release-artifacts
pnpm test:package /absolute/path/to/release-artifacts/refmint-1.0.0.tgz
```

The second command does **not** rebuild or repack. It installs that archive
offline, checks metadata/channel, inventory, licenses, documentation, runtime
hashes against the reviewed checkout evidence, types and the
alpha.3/beta.2/candidate matrix, then prints SHA-256 and
npm SHA-512 integrity. It checks the archive did not change during validation.
Temporary consumers/stores are removed on success or failure. Keep the exact
qualified archive for publication; if its bytes or source change, qualify again.
4. Record commit, CI URLs, commands/results, platform versions, package inventory,
SHA-256 and SHA-512 integrity in the release record. The file hash identifies
the candidate; a record containing its own archive hash must live outside it.
5. Authenticate to `https://registry.npmjs.org` using npm's web login/2FA flow.
Enter secrets only there. Trusted publishing requires a separately configured
and reviewed workflow; a repository URL does not grant publish permission.
6. Preview the **same archive** with the explicit channel:

```sh
npm publish /absolute/path/to/release-artifacts/refmint-1.0.0.tgz --dry-run --ignore-scripts --tag latest --access public --registry=https://registry.npmjs.org
```

Check name, version, inventory and integrity against step 4. For previews use
their exact filename and `--tag alpha` or `--tag beta` from the table. A dry run
does not prove authentication, registry acceptance or successful publication.

## Publication and rollback

After explicit release approval, publish the qualified archive with the same
command, removing only `--dry-run`. Read registry metadata back, verify the chosen
tag/version and unchanged other tags, download the public tarball and compare its
integrity and bytes. Install that registry archive in a fresh consumer and run
`pnpm test:package /absolute/path/to/downloaded.tgz` from the same checkout.
Attach the qualified archive, hashes and evidence to the matching GitHub release.
Do not claim publication until registry readback succeeds.

For a bad release, stop rollout and communicate the affected versions. Publish a
new version for a fix; never overwrite an existing one. Deprecation or moving
`latest` back requires an explicit owner decision and preserved evidence. A tag
rollback does not change existing lockfiles or already-installed applications.
Application owners decide when to revert their exact pin and deploy the old build.
Retain the v1 reader/configuration so newly issued codes still work after rollback;
see the [migration guide](migration-alpha3-to-1.md). Stable release approval does
not approve Billetsys deployment, permissions, or enabling its feature flag.
6 changes: 4 additions & 2 deletions docs/stability.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# Beta scope and stability criteria
# Stability criteria

The [published beta](https://www.npmjs.com/package/refmint/v/0.1.0-beta.1) defines
a [compatibility contract](beta-contract.md). Pin the exact version for a trial
Expand All @@ -17,7 +17,9 @@ The [1.0 API contract](stable-contract.md) fixes the surface being prepared.
`pnpm test:package` now compares its exact archive with integrity-pinned alpha.3
and beta.2 in both directions, including TypeScript consumers and historical
Billetsys codes. See [upgrade and rollback checks](migration-alpha3-to-1.md).
This work does not publish 1.0 or complete the remaining gates below.
The 1.0.0 candidate also defines [support](support.md) and [release channels](releasing.md),
including qualification of an existing final archive. It is not yet published;
final acceptance and consumer rollout remain separate.

## Criteria before a stable release

Expand Down
8 changes: 4 additions & 4 deletions docs/stable-contract.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# Public API contract for 1.0 preparation

This contract fixes the public surface being prepared for RefMint 1.0. The
repository still builds an unpublished candidate with the current beta version;
repository builds an unpublished 1.0.0 candidate;
this document does not publish 1.0, move npm tags, or authorize a consumer upgrade.
Changes under preparation must preserve this contract and the historical-release
checks. Release and support readiness remain separate [gates](stability.md).
Expand Down Expand Up @@ -125,8 +125,8 @@ A necessary security correction needs a documented impact analysis, regression
and migration or repair path; never conceal a compatibility failure by replacing
old fixtures. Follow [SECURITY.md](../SECURITY.md) for disclosure. This contract
does not promise an independent audit, calendar support period or response-time
SLA. Those release/maintenance decisions remain explicit gates before stable
publication. Neither a stable API nor its checksum proves authorization, record
SLA. The [support policy](support.md) and [release procedure](releasing.md)
apply before stable publication. Neither a stable API nor its checksum proves authorization, record
existence, or a practical manual-entry advantage.

## Executable checks
Expand All @@ -153,7 +153,7 @@ pnpm test:compatibility /absolute/path/to/refmint-candidate.tgz
```

The candidate's version must match the checkout; it is identified by its archive
hash even while its manifest still says beta.2. Historical digests and vectors
hash and its candidate manifest version. Historical digests and vectors
must not be regenerated to accommodate changes. The matrix supplements, rather
than replaces, independent Bech32m, boundary, browser, PDF and application tests.
See the [alpha.3 migration guide](migration-alpha3-to-1.md).
52 changes: 52 additions & 0 deletions docs/support.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
# Maintenance and support policy

This policy is prepared for the first stable 1.x release. The 1.0.0 candidate is
not yet published. RefMint is maintained by PerchAnton on a best-effort basis;
there is no paid support, response-time SLA, promised release date or independent
security audit. Stable describes a compatibility commitment, not a security or
human-performance guarantee.

## Supported lines

- After 1.0 is published, fixes target the latest stable 1.x release. Older 1.x
minors/patches are not separate maintained branches; update to the latest
compatible patch/minor after application testing.
- Alpha/beta/RC versions are previews, not long-term support lines. Historical
alpha.3/beta.2 archives and vectors remain compatibility baselines. Keeping
previously issued codes readable does not promise backports to old packages.
- A future major must announce its migration/support plan before publication.
Ending 1.x maintenance requires an explicit notice with the supported successor
and migration path. No end date is assigned here, and no indefinite staffing
or vulnerability-response guarantee is implied.

## Compatibility commitments

Keep the [public API contract](stable-contract.md) and [wire v1](format-v1.md).
Incompatible changes to public types, errors, accepted values, defaults or minimum
platform requirements require a major and migration notes. Additive changes must
also preserve exhaustive TypeScript consumers; an added union case is not
necessarily compatible. Deprecation must be documented with an alternative and
cannot remove working 1.x behavior in a minor or patch.

Old v1 and legacy random references must keep their identity and supported
normalization. Applications retain namespace/kind/version and random payload
length, and keep necessary readers for the lifetime of their issued references.
Do not replace fixtures to hide a failure. A security correction that affects
compatibility needs a regression, explicit impact analysis and a coordinated
repair/migration path, never silent reinterpretation as another record.

## Environments and reports

The supported baseline is Node 22+, native BigInt/ES2022 and ESM; secure Web Crypto
is required for random generation only. CI tests Node 22/24/26 on Linux, Node 24
on Windows/macOS, and the pinned Chromium/Firefox/WebKit engines. TypeScript is
checked with 5.9.3 in strict NodeNext. This is not every OS/runtime/browser version.
Removing a promised minimum environment is a breaking change. New combinations
need reproducible evidence before being advertised as tested.

For ordinary bugs, open an issue with exact package version, environment,
synthetic input, expected/actual results and a minimal reproduction. Keep private
records, credentials and account data out of reports. Report security concerns
through [SECURITY.md](../SECURITY.md). Consumer maintainers own authorization,
lookup/rate limits, uniqueness, rollout and rollback. Library tests cannot certify
those controls in a deployed application. See the [adoption guide](adoption.md).
4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "refmint",
"version": "0.1.0-beta.2",
"version": "1.0.0",
"description": "Generate public references or encode existing IDs with strict input diagnostics and a Bech32m checksum.",
"type": "module",
"license": "MIT OR Apache-2.0",
Expand All @@ -24,7 +24,7 @@
"sideEffects": false,
"publishConfig": {
"access": "public",
"tag": "beta"
"tag": "latest"
},
"exports": {
".": {
Expand Down
Loading
Loading