From b9e68587668e3124a45651ad7153dca9157861e3 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:13:25 +0100 Subject: [PATCH 01/15] Define Answerworthy as the category and publish the complete open standard source --- README.md | 187 ++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 126 insertions(+), 61 deletions(-) diff --git a/README.md b/README.md index 14687e1..e201eb5 100644 --- a/README.md +++ b/README.md @@ -1,101 +1,166 @@ # answerworthy.md -> **The open AI-native standard for making a business understandable, verifiable and recommendable by AI.** +> **Answerworthy is the new standard for how businesses become understandable, verifiable and recommendable by AI.** -**Status:** Founding working draft -**First canonical publication:** 5 August 2026 -**Creator and initial steward:** Alexander Pichugin -**Canonical domain:** [answerworthy.md](https://answerworthy.md) +**Canonical domain:** https://answerworthy.md +**Current specification:** https://answerworthy.md/standard +**Initial steward:** Alexander Pichugin +**Specification prose:** CC BY 4.0 +**Tooling:** Apache-2.0 ## The category -SEO makes pages findable. -GEO makes content citable. -**Answerworthiness makes a business choosable.** +SEO makes you findable. +GEO makes you citable. +**Answerworthiness makes you choosable.** A business is **answerworthy** when its identity, offer, facts, answers, evidence, limitations and freshness are publicly accessible, machine-readable and independently checkable. -`answerworthy.md` is the canonical AI-native file that carries those facts and evidence. +Answerworthiness is the condition that technical SEO, content, structured data, GEO, public evidence, PR, reputation, authority, marketing and distribution should collectively produce. -AI systems increasingly mediate discovery, comparison and recommendation. Existing disciplines solve parts of this problem: technical SEO supports retrieval, structured data identifies entities, content answers questions, and public evidence creates corroboration. GEO, AEO and related practices improve how this material appears in generated answers. +## The canonical file -They do not provide one portable public contract for what a business claims, how consequential claims are supported, where the limits are, and when the information was last checked. - -**`answerworthy.md` is that contract.** - -## One file - -The standard defines one canonical file: +The standard defines one published file: ```text /answerworthy.md ``` -The file is UTF-8 Markdown with machine-readable frontmatter and human-readable sections. It is designed to carry: +`answerworthy.md` is the canonical AI-native public representation of Answerworthiness. + +It carries: - canonical identity and aliases; -- the offer, audience and material conditions; +- offer, audience and material conditions; - sourced facts and verification dates; -- self-contained answers to consequential buyer questions; +- self-contained buyer answers; - entities and provenance; -- known corrections and contradictions; -- coverage limits and explicit unknowns; -- freshness policy and conformance state. +- known corrections; +- evidence limitations and explicit unknowns; +- freshness policy; +- six-dimension mapping; +- honest conformance state; +- independent attestation fields when M3 or M4 is supported. -Any JSON, HTML, PDF, score or report emitted by an implementation is a projection of the canonical file. When a projection and `answerworthy.md` disagree, the file wins. +answerworthy.md is the canonical file. Any JSON, HTML, PDF, dashboard or score that an implementation emits is a projection of it and cannot outrank it. -## First principles +## The open standard -1. **One canonical file.** One public place concentrates identity, facts, answers, evidence, limits and freshness. -2. **Declaration is not verification.** Publishing a file proves control of an origin. It does not make every statement true or independently corroborated. -3. **No evidence, no evaluated claim.** Material findings should resolve to inspectable evidence or remain explicitly unavailable. -4. **Unknown is not zero.** Blocked access, absent evidence and failed observation must not become fabricated certainty. -5. **No guaranteed outcome.** Conformance cannot promise ranking, citation, recommendation, traffic, leads or revenue. -6. **Open implementation.** Anyone may generate, audit, validate or maintain an `answerworthy.md` file. No commercial service owns implementation of the standard. +This repository is the public source for: -## Relationship to the existing web +- [`SPECIFICATION.md`](SPECIFICATION.md): the category, one-file model, dimensions, states, acts and implementation boundaries; +- [`GRAMMAR.md`](GRAMMAR.md): the machine-readable and human-readable file grammar; +- [`validator.mjs`](validator.mjs): a dependency-free validator for local files and remote URLs; +- [`examples/`](examples): minimal and sourced examples; +- [`GOVERNANCE.md`](GOVERNANCE.md): public contribution, compatibility and registry policy; +- [`CONTRIBUTING.md`](CONTRIBUTING.md): issue and pull-request workflow; +- [`LICENSE.md`](LICENSE.md): specification and tooling licenses; +- [`TRADEMARKS.md`](TRADEMARKS.md): naming and certification boundaries; +- Git history, issues and pull requests: the inspectable evolution of the standard. -`answerworthy.md` complements the web stack rather than replacing it. +The canonical rendered specification and implementation registry live at https://answerworthy.md. -- HTML remains the primary human-facing surface. -- Schema.org provides structured assertions inside pages. -- `robots.txt` governs crawler access. -- sitemaps support URL discovery. -- `llms.txt` may point systems towards useful resources. -- `answerworthy.md` provides the canonical, evidence-aware account of the business itself. +## Conformance states -SEO, GEO, AEO, content, PR, reputation and structured data remain useful practices. **Answerworthiness is the condition they should collectively produce.** +- **M0 Present:** a valid file exists at the canonical path and parses. +- **M1 Structured:** required frontmatter and sections are present and well formed. +- **M2 Sourced:** material facts carry basis, source class, source and verification date. +- **M3 Corroborated:** an independent party re-fetched the site and recorded an inspectable attestation inside the file. +- **M4 Maintained:** the file stays within its freshness policy and receives dated rechecks. -## Day 0 contract +M0 through M2 may be self-declared. A subject cannot issue M3 about itself. -This founding publication deliberately fixes only four things: +## Evidence states -1. the category definition of **answerworthiness**; -2. the canonical filename and root path, **`/answerworthy.md`**; -3. the evidence and honesty principles above; -4. the open-standard premise and initial stewardship. +The standard preserves exact conditions: -The exact grammar, conformance levels, validator contract, governance process and versioning policy remain a public working draft until released here as a numbered specification. +- verified; +- unsupported; +- contradicted; +- unavailable; +- stale; +- incomplete. -That restraint is intentional. The category should be clear from day one; the protocol should earn stability through implementation. +The standard defines no universal 0 to 100 Answerworthy score. -## Stewardship +## Six dimensions + +- `access-retrieval` +- `entity-certainty` +- `offer-comprehension` +- `evidence-corroboration` +- `buyer-question-coverage` +- `answer-performance` + +Mention, citation, recommendation and follow-through remain separate outcomes. -The `answerworthy.md` standard was created by **Alexander Pichugin**, who serves as its initial steward during the working-draft stage. +## Four implementation acts + +Implementations may perform any honest subset of: + +1. **Generate:** draft the file and mark unsupported facts for confirmation. +2. **Audit:** evaluate the file and live site across six dimensions while preserving contradictions and unavailable evidence. +3. **Remediate:** apply permitted changes, then update the canonical file. +4. **Refresh:** re-fetch, recheck, update freshness and record material changes. + +Validation and independent corroboration are also explicit implementation capabilities. An implementation declares what it actually does. + +## Run the validator + +Node 20 or newer. No dependencies. + +```bash +node validator.mjs ./examples/sourced.answerworthy.md +node validator.mjs https://example.com/answerworthy.md +``` -The steward's role is to maintain the canonical terminology, separate normative requirements from reference-implementation behaviour, preserve evidence discipline, publish versioned drafts and create a credible path towards broader governance as independent implementations emerge. +The validator reports: -The word *answerworthy* may be used descriptively by anyone. Conformance, certification and claims of compatibility will require the versioned standard once published. +- claimed and achieved conformance; +- canonical fact and answer counts; +- six-dimension coverage; +- exact errors and warnings. -## What comes next +It reports conditions rather than a grade. + +## Build an implementation + +Other implementations are invited. + +An implementation may generate, validate, audit, corroborate, remediate or refresh answerworthy.md. A registry listing requires a resolvable public file and accurate capability claims. A corroboration-verified listing also requires an inspectable attestation URL and SHA-256 hash. + +See the public registry at https://answerworthy.md/implementations. + +## Reference implementation and commercial layer + +The **Answerworthy Engine** is the initial reference implementation. + +The **Answerworthy Plan** is the founder-reviewed commercial sequence for strengthening Answerworthiness across: + +- technical SEO and retrieval; +- entity, category, offer and audience comprehension; +- buyer-question coverage and GEO; +- site architecture, copy, comparisons and alternatives; +- claims, evidence, original research and proof assets; +- reviews, directories and third-party corroboration; +- PR, publishers, experts, communities and authority; +- partnerships, marketing and distribution; +- dependencies, permissions, completion tests and rechecks. + +The commercial sequence is organised as: + +1. Fix now +2. Build next +3. Earn externally +4. Test afterward +5. Maintain continuously + +The standard is free. Becoming the answer is the work. + +## Stewardship -The next public draft will add: +Alexander Pichugin is the initial steward. -- the normative file grammar; -- a minimal conforming example; -- cumulative conformance states; -- an open validator contract; -- licensing and trademark boundaries; -- a proposal and governance process. +The steward maintains the canonical terminology, reviews proposals, protects evidence boundaries, separates normative requirements from reference-implementation behaviour and creates a path towards broader governance as independent implementations emerge. -Until then, this repository is the canonical founding record of the category and the standard. +The public contribution mechanism is GitHub issues and pull requests. See [`CONTRIBUTING.md`](CONTRIBUTING.md). From c002b6cb3ff2a26d8741c8d681b4b786406695d6 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:14:07 +0100 Subject: [PATCH 02/15] Publish the Answerworthy Standard specification --- SPECIFICATION.md | 228 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 228 insertions(+) create mode 100644 SPECIFICATION.md diff --git a/SPECIFICATION.md b/SPECIFICATION.md new file mode 100644 index 0000000..ab9fdb1 --- /dev/null +++ b/SPECIFICATION.md @@ -0,0 +1,228 @@ +# The Answerworthy Standard + +**Current specification:** answerworthy 0.2 +**Canonical location:** https://answerworthy.md/standard +**Public source:** https://github.com/kosmopteros/answerworthy.md +**Specification license:** CC BY 4.0 +**Tooling license:** Apache-2.0 +**Initial steward:** Alexander Pichugin + +## 0. Category definition + +Answerworthy is the new standard for how businesses become understandable, verifiable and recommendable by AI. + +A business is **answerworthy** when its identity, offer, facts, answers, evidence, limitations and freshness are publicly accessible, machine-readable and independently checkable. + +The category ladder is: + +1. SEO makes you findable. +2. GEO makes you citable. +3. Answerworthiness makes you choosable. + +Answerworthiness is the condition that technical SEO, content, structured data, GEO, public evidence, PR, reputation, authority, marketing and distribution should collectively produce. + +## 1. The one canonical file + +The standard defines one published file: + +```text +/answerworthy.md +``` + +answerworthy.md is the canonical AI-native public representation of Answerworthiness for one subject. + +answerworthy.md is the canonical file. Any JSON, HTML, PDF, dashboard or score that an implementation emits is a projection of it and cannot outrank it. + +A pointer at `/.well-known/answerworthy.md` is permitted while a registered well-known URI does not exist. The pointer names the root file as canonical and carries no independent substance. + +The file uses UTF-8 Markdown with YAML frontmatter. Frontmatter and fixed level-two sections provide machine-readable structure. The prose remains useful without specialised tooling. + +## 2. Scope + +The standard governs: + +- the category definition of Answerworthiness; +- the canonical answerworthy.md file; +- the public file grammar; +- six bounded evidence dimensions; +- cumulative conformance states; +- exact evidence and finding states; +- four implementation acts; +- independent corroboration recorded inside the file; +- interoperability, governance and open implementation. + +The standard does not define: + +- a universal 0 to 100 Answerworthy score; +- a universal ranking formula; +- one mandatory crawler, provider, model or commercial product; +- a guarantee of ranking, citation, recommendation, traffic, leads or revenue; +- autonomous permission to publish, purchase, contact third parties or modify production systems; +- search-engine, IETF, IANA or W3C endorsement. + +## 3. Axioms + +1. **One canonical file.** The file concentrates identity, facts, answers, evidence limits and freshness at one public path. +2. **Declaration is not verification.** Publishing the file proves control of the origin. Truth, independence and citation eligibility require separate evidence. +3. **No evidence, no evaluated claim.** Every evaluated finding references retained evidence. Missing evidence remains unavailable or incomplete. +4. **Unknown is not failure.** Blocked access, provider failure and parser failure never become fabricated absence or a negative grade. +5. **Side effects denied by default.** The file grants no credentials, publication authority, outreach permission or third-party consent. +6. **No guaranteed outcome.** Conformance does not guarantee ranking, citation, recommendation, traffic, leads or revenue. +7. **Open implementation.** Anyone may generate, validate, audit, corroborate, remediate or refresh answerworthy.md. + +## 4. File grammar + +A conforming file has YAML frontmatter and Markdown sections keyed on fixed level-two headings. + +### Required frontmatter + +- `answerworthy`: grammar compatibility token; +- `entity`: canonical subject name; +- `canonical`: canonical subject URL; +- `last_verified`: ISO date. + +### Recommended frontmatter + +- `kind`; +- `aliases`; +- `sameas`; +- `maintainer`; +- `license`; +- `freshness_days`; +- `conformance`; +- independent attestation fields when M3 or M4 is claimed. + +### Required sections + +- `## Identity`; +- `## Answers`. + +### Recommended sections + +- `## Offer and audience`; +- `## Canonical facts`; +- `## Entities`; +- `## Provenance`; +- `## Known corrections`; +- `## Evidence limitations`; +- `## Freshness policy`; +- `## Dimensions`; +- `## Conformance`. + +A canonical fact carries `statement`, `basis`, `source_class`, `source` and `verified_at`. + +An answer uses a question-form level-three heading, a self-contained response and a `source` line. + +Evidence limitations state what the subject cannot currently support, what was unavailable and which markets, dates, products, sources or questions remain outside scope. + +## 5. Six dimensions + +Answerworthiness is evaluated against the file and the live public surface. Every finding maps to one dimension or a namespaced extension. + +1. **access-retrieval:** can relevant systems retrieve and render the public evidence? +2. **entity-certainty:** can the subject be identified without material ambiguity or contradiction? +3. **offer-comprehension:** can a qualified buyer or agent understand what is offered, for whom and under which conditions? +4. **evidence-corroboration:** can consequential claims be supported, attributed and independently checked? +5. **buyer-question-coverage:** does the public evidence answer priority pre-brand questions, comparisons and constraints? +6. **answer-performance:** what was actually mentioned, cited, recommended or followed through in declared answer-system observations? + +Mention, citation, recommendation and follow-through remain separate outcomes. + +The standard defines no universal weighting or total score. Implementations preserve each finding's evidence, boundary, state and verification method. + +## 6. Conformance states + +A subject claims the highest cumulative state it fully meets. M0 through M2 may be self-declared. M3 requires an independent party. + +- **M0 Present:** a valid answerworthy.md exists at the canonical path and parses. +- **M1 Structured:** required frontmatter and sections are present and well formed. +- **M2 Sourced:** material facts carry basis, source class, source and verification date. +- **M3 Corroborated:** an independent party re-fetched the site and attested that the file's material claims hold, including contradictions and unavailable evidence. +- **M4 Maintained:** the file remains within its freshness policy and receives dated rechecks. + +### M3 attestation + +The attestation is recorded inside answerworthy.md. A conforming M3 claim includes one of these patterns: + +- signed attestation fields inside the file; +- an attestation URL plus a SHA-256 hash; +- a verifier identifier, method, date and retained evidence reference. + +The attestation does not become a separate standard artifact. A subject cannot issue M3 about itself. + +## 7. Evidence and finding states + +A finding uses one of these public states: + +- **verified:** retained evidence supports the bounded claim or condition; +- **unsupported:** the claim exists while the required supporting evidence is absent or insufficient; +- **contradicted:** retained public evidence conflicts with the declared claim; +- **unavailable:** evidence could not be obtained and no negative conclusion is inferred; +- **stale:** the claim or evidence is outside its declared freshness policy; +- **incomplete:** part of the condition is established and explicit requirements remain missing. + +Internal confidence and coverage calculations may guide an implementation. They do not become a universal Answerworthy grade. + +## 8. Implementation acts + +Implementations operate on the canonical file and live site through four acts. + +- **generate:** draft answerworthy.md from a public site and mark unsupported facts for confirmation; +- **audit:** evaluate the file and site across six dimensions while preserving contradictions and unavailable evidence; +- **remediate:** apply changes within granted permission and separate credentials, then update the canonical file; +- **refresh:** re-fetch, recheck, update `last_verified` and record material changes without rewriting history. + +A validator may implement only structural and sourcing checks. A generator, auditor, corroborator, remediation agent or maintenance service may implement a different subset. Every implementation declares its capabilities honestly. + +Working evidence and remediation may live in a session, repository or private client delivery. The public standard defines one canonical file. + +## 9. Implementation priorities + +The standard defines the condition. Implementations decide how to achieve and strengthen it. + +The Answerworthy reference implementation uses five action horizons: + +1. **Fix now:** remove critical retrieval, identity, contradiction and buyer-comprehension blockers. +2. **Build next:** create canonical pages, proof assets, comparisons, original research and missing evidence surfaces. +3. **Earn externally:** secure independent corroboration through reviews, directories, publishers, partners, communities and PR. +4. **Test afterward:** re-fetch the public surface and observe mention, citation, recommendation and follow-through separately. +5. **Maintain continuously:** refresh facts, corrections, evidence, relationships and answerworthy.md as the business changes. + +These horizons are implementation vocabulary. They do not introduce a second public artifact. + +## 10. Verification and commercial implementations + +Verification is an act. An independent implementation re-fetches the site, checks material claims against retained evidence and records the attestation inside answerworthy.md. + +The Answerworthy Engine is the initial reference implementation. It can generate, validate, audit, corroborate, remediate and refresh the file. + +A commercial implementation may coordinate technical SEO, GEO, site architecture, claims, evidence, original research, reviews, directories, PR, authority, partnerships, marketing, distribution, dependencies, permissions, completion tests and rechecks. + +The standard is free. Implementation work may be commercial. + +## 11. Interoperability + +answerworthy.md sits beside the existing web stack. + +- HTML remains the primary human-facing surface. +- Schema.org provides structured assertions inside pages. +- `robots.txt` governs crawler access. +- sitemaps support URL discovery. +- `llms.txt` may point systems towards useful resources. +- answerworthy.md provides the canonical evidence-aware account of the business itself. + +Where structured data and answerworthy.md assert the same material fact, they should agree. + +## 12. Open source, governance and licensing + +The public source repository is: + +https://github.com/kosmopteros/answerworthy.md + +Anyone may fork the standard, open an issue or propose a pull request. + +Alexander Pichugin is the initial steward. Broader governance is intended after independent implementations and recurring external contributions exist. + +Specification prose: CC BY 4.0. Tooling: Apache-2.0. + +Open licensing grants implementation and quotation rights. It does not grant certification, endorsement or impersonation rights. From 8d18dc58a74991f4f86f5f5212e821d7becd1ba3 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:14:28 +0100 Subject: [PATCH 03/15] Publish the answerworthy.md grammar --- GRAMMAR.md | 126 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 126 insertions(+) create mode 100644 GRAMMAR.md diff --git a/GRAMMAR.md b/GRAMMAR.md new file mode 100644 index 0000000..c7a35db --- /dev/null +++ b/GRAMMAR.md @@ -0,0 +1,126 @@ +# answerworthy.md file grammar + +**Compatibility:** answerworthy 0.2 +**Canonical specification:** https://answerworthy.md/standard +**Public source:** https://github.com/kosmopteros/answerworthy.md +**License:** CC BY 4.0 + +## Purpose + +answerworthy.md is the canonical AI-native public representation of Answerworthiness. + +A business is answerworthy when its identity, offer, facts, answers, evidence, limitations and freshness are publicly accessible, machine-readable and independently checkable. + +## Encoding and location + +- UTF-8 Markdown. +- YAML frontmatter begins and ends with `---`. +- The canonical path is `/answerworthy.md` at the subject's site root. +- A derivative pointer may exist at `/.well-known/answerworthy.md` and must name the root file as canonical. + +## Required frontmatter + +- `answerworthy` +- `entity` +- `canonical` +- `last_verified` + +## Recommended frontmatter + +- `kind` +- `aliases` +- `sameas` +- `maintainer` +- `license` +- `freshness_days` +- `conformance` +- attestation fields for M3 or M4 + +## Required sections + +- `## Identity` +- `## Answers` + +## Recommended sections + +- `## Offer and audience` +- `## Canonical facts` +- `## Entities` +- `## Provenance` +- `## Known corrections` +- `## Evidence limitations` +- `## Freshness policy` +- `## Dimensions` +- `## Conformance` + +## Identity + +Identity provides one canonical description, category, material aliases and disambiguation from namesakes. + +## Offer and audience + +Offer and audience states what the business offers, who it serves, where the offer applies and which material conditions shape the choice. + +## Canonical facts + +Each material fact uses one list item and carries: + +- `statement` +- `basis` +- `source_class` +- `source` +- `verified_at` + +An owned source supports a declared fact. It does not create independent corroboration. + +## Answers + +Each answer uses: + +1. a question-form level-three heading; +2. a self-contained answer; +3. an absolute `source` line. + +Answers should address buyer problems, comparisons, constraints, proof requirements and actions in addition to brand-name questions. + +## Evidence limitations + +The file explicitly states material claims, markets, dates, sources and questions it cannot currently support. Unavailable evidence remains unavailable rather than becoming a negative grade. + +## Dimensions + +The file or its evaluation maps findings to these identifiers: + +- `access-retrieval` +- `entity-certainty` +- `offer-comprehension` +- `evidence-corroboration` +- `buyer-question-coverage` +- `answer-performance` + +## Finding states + +Evaluations preserve these public states: + +- `verified` +- `unsupported` +- `contradicted` +- `unavailable` +- `stale` +- `incomplete` + +The grammar defines no universal 0 to 100 Answerworthy score. + +## Conformance + +- M0 Present +- M1 Structured +- M2 Sourced +- M3 Corroborated +- M4 Maintained + +M0 through M2 may be self-declared. M3 requires an independent attestation recorded inside the file through signed fields or a referenced URL and SHA-256 hash. + +## Open implementation + +Implementations may generate, validate, audit, corroborate, remediate or refresh the file. Each implementation declares its capabilities honestly. From 73d3dcfd7a8d0a590632e8725dc3eb8d4acb8a18 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:14:45 +0100 Subject: [PATCH 04/15] Publish public governance for the standard --- GOVERNANCE.md | 97 +++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 97 insertions(+) create mode 100644 GOVERNANCE.md diff --git a/GOVERNANCE.md b/GOVERNANCE.md new file mode 100644 index 0000000..bf10911 --- /dev/null +++ b/GOVERNANCE.md @@ -0,0 +1,97 @@ +# Answerworthy Standard governance + +**Canonical specification:** https://answerworthy.md/standard +**Public source:** https://github.com/kosmopteros/answerworthy.md +**Initial steward:** Alexander Pichugin + +## Objectives + +Governance keeps the category definition, canonical file, grammar, validator and public terminology coherent, evidence-disciplined, implementation-neutral and useful to people and agents. + +## Public contribution path + +Material changes are discussed and implemented through this repository. + +Contributors may: + +- open an issue; +- propose an example; +- report an interoperability problem; +- submit a validator fixture; +- propose a grammar change; +- submit a pull request; +- challenge a category or evidence definition with implementation evidence. + +## Initial stewardship + +Alexander Pichugin is the initial standard steward. + +The steward reviews proposals, maintains canonical terms, publishes compatibility changes, protects evidence boundaries, separates reference-implementation behaviour from normative requirements and maintains the open validator. + +A technical steering group becomes appropriate when independent implementations and recurring external contributions exist. + +## Answerworthy proposals + +A material change records: + +- problem statement; +- normative change; +- grammar and validator impact; +- security and privacy impact; +- migration path; +- alternatives considered; +- implementation evidence; +- requested compatibility treatment. + +Public proposal states are proposal, review, accepted, rejected, implemented and superseded. + +## Acceptance criteria + +A normative proposal should demonstrate at least one of these conditions: + +- repeated use in an implementation; +- independent consumption; +- an interoperability failure; +- a safety, privacy or evidence-integrity need; +- a correction required to preserve the category definition. + +Marketing convenience and feature-count growth do not satisfy the acceptance criteria. + +## Compatibility + +The public brand remains the Answerworthy Standard. + +Files declare the grammar compatibility token they target. Clarifications preserve meaning. Compatible changes add optional capability. Semantic breaks require an explicit migration and a new compatibility token. + +Git history and releases preserve the technical timeline. The canonical website presents the current specification. + +## Reference implementation + +The Answerworthy Engine is the initial reference implementation. Engine behaviour becomes normative only through a public specification change. + +Other implementations are invited. They may implement generation, validation, audit, corroboration, remediation, refresh or any honest subset. + +## Registry fairness + +A listed implementation must: + +- accurately declare its capabilities; +- resolve its claimed output to a live answerworthy.md file; +- preserve the canonical file and evidence boundaries; +- avoid claiming independent corroboration without an inspectable attestation. + +A corroboration-verified listing additionally requires an attestation URL and SHA-256 hash that can be checked publicly. + +The same capability and verification rules apply to every submission, including the reference implementation. + +## Universal score policy + +The standard defines conformance and exact evidence states. It defines no universal 0 to 100 Answerworthy score. + +Implementations may calculate internal confidence, coverage or prioritisation weights. They must not present those calculations as the definition of Answerworthiness. + +## Licensing + +Specification prose: CC BY 4.0. Tooling: Apache-2.0. + +These licenses permit implementation, quotation, modification and redistribution under their terms. They grant no certification, endorsement or impersonation rights. From 1d4d92267e9c5c41c7449396be106e58b6de7cd5 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:15:22 +0100 Subject: [PATCH 05/15] Publish the dependency-free answerworthy.md validator --- validator.mjs | 147 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 147 insertions(+) create mode 100644 validator.mjs diff --git a/validator.mjs b/validator.mjs new file mode 100644 index 0000000..fbcbf8e --- /dev/null +++ b/validator.mjs @@ -0,0 +1,147 @@ +#!/usr/bin/env node + +import { readFile } from 'node:fs/promises' + +const REQUIRED_FRONTMATTER = ['answerworthy', 'entity', 'canonical', 'last_verified'] +const REQUIRED_SECTIONS = ['Identity', 'Answers'] +const DIMENSIONS = ['access-retrieval', 'entity-certainty', 'offer-comprehension', 'evidence-corroboration', 'buyer-question-coverage', 'answer-performance'] +const STATES = ['M0', 'M1', 'M2', 'M3', 'M4'] + +function stripQuotes(value) { + const trimmed = value.trim() + if ((trimmed.startsWith('"') && trimmed.endsWith('"')) || (trimmed.startsWith("'") && trimmed.endsWith("'"))) return trimmed.slice(1, -1) + return trimmed +} + +function parseFrontmatter(text) { + const clean = text.replace(/^\uFEFF/, '') + const lines = clean.split(/\r?\n/) + if (lines[0]?.trim() !== '---') return { data: {}, body: clean, error: 'YAML frontmatter must begin on the first line.' } + const end = lines.findIndex((line, index) => index > 0 && line.trim() === '---') + if (end < 0) return { data: {}, body: clean, error: 'YAML frontmatter has no closing delimiter.' } + const data = {} + for (const line of lines.slice(1, end)) { + if (!line.trim() || /^\s/.test(line)) continue + const match = line.match(/^([A-Za-z0-9_-]+):\s*(.*)$/) + if (match) data[match[1]] = stripQuotes(match[2]) + } + return { data, body: lines.slice(end + 1).join('\n'), error: null } +} + +function sectionMap(body) { + const matches = [...body.matchAll(/^##\s+(.+?)\s*$/gm)] + const sections = new Map() + matches.forEach((match, index) => { + const start = match.index + match[0].length + const end = matches[index + 1]?.index ?? body.length + sections.set(match[1].trim(), body.slice(start, end).trim()) + }) + return sections +} + +function factRecords(block) { + if (!block) return [] + const starts = [...block.matchAll(/^-\s+/gm)] + return starts.map((match, index) => { + const start = match.index + const end = starts[index + 1]?.index ?? block.length + return block.slice(start, end) + }) +} + +function hasField(record, field) { + return new RegExp(`^\\s*(?:-\\s*)?${field}:\\s*\\S+`, 'm').test(record) +} + +function answerRecords(block) { + if (!block) return [] + const matches = [...block.matchAll(/^###\s+(.+?)\s*$/gm)] + return matches.map((match, index) => { + const start = match.index + match[0].length + const end = matches[index + 1]?.index ?? block.length + return { question: match[1].trim(), body: block.slice(start, end).trim() } + }) +} + +function stateIndex(state) { + return STATES.indexOf(state) +} + +export function validateAnswerworthy(text) { + const errors = [] + const warnings = [] + const parsed = parseFrontmatter(text) + if (parsed.error) errors.push(parsed.error) + const frontmatter = parsed.data + const sections = sectionMap(parsed.body) + + for (const field of REQUIRED_FRONTMATTER) if (!frontmatter[field]) errors.push(`Missing frontmatter field: ${field}`) + if (frontmatter.answerworthy && frontmatter.answerworthy !== '0.2') errors.push('The answerworthy field must equal 0.2 for this validator.') + if (frontmatter.canonical) { + try { new URL(frontmatter.canonical) } catch { errors.push('The canonical field must be an absolute URL.') } + } + if (frontmatter.last_verified && !/^\d{4}-\d{2}-\d{2}$/.test(frontmatter.last_verified)) errors.push('The last_verified field must use YYYY-MM-DD.') + + for (const section of REQUIRED_SECTIONS) if (!sections.has(section)) errors.push(`Missing required section: ${section}`) + + const facts = factRecords(sections.get('Canonical facts')) + const factFields = ['statement', 'basis', 'source_class', 'source', 'verified_at'] + const incompleteFacts = facts.filter((record) => factFields.some((field) => !hasField(record, field))) + if (facts.length === 0) warnings.push('No canonical facts were found, so M2 cannot be established.') + if (incompleteFacts.length) errors.push(`${incompleteFacts.length} canonical fact record(s) are missing required fields.`) + + const answers = answerRecords(sections.get('Answers')) + if (answers.length === 0) errors.push('The Answers section must contain at least one level-three question.') + for (const answer of answers) { + if (!answer.question.endsWith('?')) warnings.push(`Answer heading is not question-form: ${answer.question}`) + if (!/^source:\s*https?:\/\//m.test(answer.body)) errors.push(`Answer has no absolute source URL: ${answer.question}`) + } + + const dimensionText = sections.get('Dimensions') || '' + const missingDimensions = DIMENSIONS.filter((dimension) => !dimensionText.includes(dimension)) + if (missingDimensions.length) warnings.push(`Dimension mapping is incomplete: ${missingDimensions.join(', ')}`) + + let achieved = 'M0' + const structured = REQUIRED_FRONTMATTER.every((field) => frontmatter[field]) && REQUIRED_SECTIONS.every((section) => sections.has(section)) && answers.length > 0 + if (structured && !parsed.error) achieved = 'M1' + const sourced = structured && facts.length > 0 && incompleteFacts.length === 0 && answers.every((answer) => /^source:\s*https?:\/\//m.test(answer.body)) + if (sourced) achieved = 'M2' + + const hasAttestation = Boolean(frontmatter.attestation_url && /^https?:\/\//.test(frontmatter.attestation_url) && frontmatter.attestation_sha256 && /^[a-f0-9]{64}$/.test(frontmatter.attestation_sha256)) + if (sourced && hasAttestation) achieved = 'M3' + + const freshnessDays = Number(frontmatter.freshness_days) + const verifiedAt = frontmatter.last_verified ? Date.parse(`${frontmatter.last_verified}T00:00:00Z`) : Number.NaN + const fresh = Number.isFinite(freshnessDays) && freshnessDays > 0 && Number.isFinite(verifiedAt) && Date.now() - verifiedAt <= freshnessDays * 86400000 + if (hasAttestation && fresh) achieved = 'M4' + + const claimed = frontmatter.conformance || null + if (claimed && !STATES.includes(claimed)) errors.push(`Unknown conformance state: ${claimed}`) + if (claimed && STATES.includes(claimed) && stateIndex(claimed) > stateIndex(achieved)) errors.push(`Claimed ${claimed}, achieved ${achieved}.`) + if ((claimed === 'M3' || claimed === 'M4') && !hasAttestation) errors.push(`${claimed} requires an independent attestation URL and SHA-256 hash inside the file.`) + + const valid = errors.length === 0 && stateIndex(achieved) >= stateIndex('M1') + return { valid, version: '0.2', claimed, achieved, facts: facts.length, answers: answers.length, dimensions: { present: DIMENSIONS.length - missingDimensions.length, total: DIMENSIONS.length, missing: missingDimensions }, errors, warnings } +} + +async function loadInput(input) { + if (/^https?:\/\//.test(input)) { + const response = await fetch(input, { headers: { accept: 'text/markdown,text/plain;q=0.9' } }) + if (!response.ok) throw new Error(`HTTP ${response.status} while fetching ${input}`) + return response.text() + } + return readFile(input, 'utf8') +} + +const invokedDirectly = process.argv[1] && import.meta.url.endsWith(process.argv[1].replaceAll('\\', '/')) +if (invokedDirectly) { + const input = process.argv[2] || 'examples/sourced.answerworthy.md' + try { + const result = validateAnswerworthy(await loadInput(input)) + console.log(JSON.stringify(result, null, 2)) + if (!result.valid) process.exitCode = 1 + } catch (error) { + console.error(error instanceof Error ? error.message : String(error)) + process.exitCode = 1 + } +} From f50b2e7aa3bf1cde72d869c554dacf10b086edad Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:15:33 +0100 Subject: [PATCH 06/15] Add a minimal structured answerworthy.md example --- examples/minimal.answerworthy.md | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 examples/minimal.answerworthy.md diff --git a/examples/minimal.answerworthy.md b/examples/minimal.answerworthy.md new file mode 100644 index 0000000..c8291b2 --- /dev/null +++ b/examples/minimal.answerworthy.md @@ -0,0 +1,28 @@ +--- +answerworthy: "0.2" +entity: "Example Co" +canonical: https://example.com +last_verified: 2026-08-05 +kind: organization +conformance: M1 +--- + +## Identity + +Example Co makes accounting software for freelancers. + +## Offer and audience + +The product serves freelancers who need invoicing and expense tracking. + +## Answers + +### What does Example Co make? + +Accounting software for freelancers. + +source: https://example.com/product + +## Conformance + +Self-declared M1. Sourced canonical facts have not been added. From 187de4e4d7ecf0dcc99bfcb8f2db7d94b90bb61d Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:15:52 +0100 Subject: [PATCH 07/15] Add a sourced M2 answerworthy.md example --- examples/sourced.answerworthy.md | 83 ++++++++++++++++++++++++++++++++ 1 file changed, 83 insertions(+) create mode 100644 examples/sourced.answerworthy.md diff --git a/examples/sourced.answerworthy.md b/examples/sourced.answerworthy.md new file mode 100644 index 0000000..49e7a6d --- /dev/null +++ b/examples/sourced.answerworthy.md @@ -0,0 +1,83 @@ +--- +answerworthy: "0.2" +entity: "Example Co" +canonical: https://example.com +last_verified: 2026-08-05 +kind: organization +conformance: M2 +freshness_days: 30 +--- + +## Identity + +Example Co makes accounting software for freelancers. Its category is small-business finance tooling. + +## Offer and audience + +The product serves independent professionals who need invoicing, expense tracking and quarterly tax preparation in supported jurisdictions. + +## Canonical facts + +- statement: "Example Co's plans start at 12 EUR per month with a free tier." + basis: declared + source_class: owned + source: https://example.com/pricing + verified_at: 2026-08-05 + +- statement: "Example Co supports invoicing and expense tracking for all active plans." + basis: declared + source_class: owned + source: https://example.com/product + verified_at: 2026-08-05 + +## Answers + +### What does Example Co make? + +Accounting software for freelancers: invoicing, expense tracking and quarterly tax estimates. + +source: https://example.com/product + +### Is Example Co suitable for quarterly tax preparation? + +Example Co estimates quarterly tax obligations for supported freelancer profiles and publishes its current jurisdiction limits. + +source: https://example.com/tax-estimates + +## Entities + +- Example Co: accounting software for freelancers. +- Example Co Tax Estimates: a product capability limited to listed jurisdictions. + +## Provenance + +- Maintainer: Example Co product operations. +- Canonical product page: https://example.com/product +- Canonical pricing page: https://example.com/pricing + +## Known corrections + +- The product estimates quarterly tax obligations. It does not file taxes on the customer's behalf. + +## Evidence limitations + +- No independent customer outcome study is currently published. +- Tax support is limited to the jurisdictions listed on the product page. +- This file has no independent M3 attestation. + +## Freshness policy + +Pricing, tax coverage and product capabilities are rechecked after every material release and at least every 30 days. + +## Dimensions + +- access-retrieval: public product and pricing evidence is available in HTML. +- entity-certainty: the product and company use one canonical name and URL. +- offer-comprehension: offer, audience and tax limitations are stated. +- evidence-corroboration: current facts resolve to owned sources; independent outcome evidence is unavailable. +- buyer-question-coverage: product, pricing and tax-fit questions are answered. +- answer-performance: no provider observation is claimed in this self-declared file. + +## Conformance + +Self-declared M2. The file is present, structured and sourced. No independent corroboration is recorded. From 5b5fcb4801e313404f5f20e17009b94384e670a6 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:16:07 +0100 Subject: [PATCH 08/15] Publish the standard license split --- LICENSE.md | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) create mode 100644 LICENSE.md diff --git a/LICENSE.md b/LICENSE.md new file mode 100644 index 0000000..e4199e4 --- /dev/null +++ b/LICENSE.md @@ -0,0 +1,27 @@ +# Answerworthy Standard licensing + +Copyright © 2026 Alexander Pichugin. + +## Specification prose + +The specification, grammar, governance, explanatory documentation and examples are licensed under the Creative Commons Attribution 4.0 International license. + +SPDX identifier: `CC-BY-4.0` + +Suggested attribution: + +> Answerworthy Standard, stewarded by Alexander Pichugin, https://answerworthy.md/standard + +## Tooling + +The validator, tests, fixtures and reference tooling are licensed under the Apache License 2.0. + +SPDX identifier: `Apache-2.0` + +## Marks + +These licenses grant no trademark, certification, endorsement or impersonation rights. See [`TRADEMARKS.md`](TRADEMARKS.md). + +## Commercial implementations + +The open standard does not require a commercial purchase. Production implementations, private evidence, customer data, remediation workflows and advisory services may use separate licenses. From 9ca5f05df8eeb614feedd2cc3c4ccec24a18c7f3 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:16:30 +0100 Subject: [PATCH 09/15] Publish naming and certification boundaries --- TRADEMARKS.md | 64 +++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 64 insertions(+) create mode 100644 TRADEMARKS.md diff --git a/TRADEMARKS.md b/TRADEMARKS.md new file mode 100644 index 0000000..d2055ee --- /dev/null +++ b/TRADEMARKS.md @@ -0,0 +1,64 @@ +# Answerworthy naming and trademark policy + +The open licenses covering the Answerworthy Standard and its tooling do not grant rights to impersonate the canonical standard, reference implementation or certification programme. + +This policy covers: + +- Answerworthy; +- Answerworthy Standard; +- answerworthy.md; +- Answerworthy Engine; +- Answerworthy Plan; +- Answerworthy Certified; +- associated logos and certification marks. + +No statement in this policy represents that a mark is registered in every jurisdiction. + +## Permitted accurate reference + +Anyone may: + +- refer to the Answerworthy Standard; +- implement answerworthy.md; +- state which compatibility token an implementation targets; +- publish a self-declared conformance state supported by the file; +- compare implementations and methodologies; +- quote the specification with attribution; +- fork the open source under its applicable license. + +The use must not imply certification, endorsement, partnership or canonical status. + +## Reserved claims + +Written permission is required to: + +- present a fork as the canonical Answerworthy Standard; +- use Answerworthy logos or certification badges; +- claim Answerworthy Certified status; +- operate an official-looking certification registry under the Answerworthy name; +- imply that a commercial product is produced or reviewed by the standard steward when it is not; +- register a domain, package or account that impersonates the canonical source. + +## Conformance language + +Permitted wording: + +> Implements answerworthy 0.2. + +> Publishes a self-declared M2 answerworthy.md file. + +> Corroboration verified through the attestation recorded in answerworthy.md. + +Reserved wording: + +> Answerworthy Certified + +A certification programme will require a separately published policy, conformance process and authorised mark. + +## Forks + +A fork may modify the open specification under its license. A fork that changes normative meaning must use a different standard name, identify its divergence and avoid suggesting that it is a later canonical Answerworthy release. + +## Contact + +Questions and permission requests: alexander@pichugin.me From a9639a073499c49e8fd98415a1522e1f57a2ba14 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:17:05 +0100 Subject: [PATCH 10/15] Publish the public contribution workflow --- CONTRIBUTING.md | 77 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 77 insertions(+) create mode 100644 CONTRIBUTING.md diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..482b08e --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,77 @@ +# Contributing to the Answerworthy Standard + +The standard is developed in public through GitHub issues and pull requests. + +## Before proposing a change + +Read: + +- [`SPECIFICATION.md`](SPECIFICATION.md) +- [`GRAMMAR.md`](GRAMMAR.md) +- [`GOVERNANCE.md`](GOVERNANCE.md) +- [`README.md`](README.md) + +Run the validator against the sourced example: + +```bash +node validator.mjs ./examples/sourced.answerworthy.md +``` + +Run the tests: + +```bash +npm test +``` + +## Good proposals + +A strong proposal identifies: + +- the interoperability, evidence or implementation problem; +- the current behaviour; +- the requested normative change; +- grammar and validator impact; +- migration impact; +- security and privacy implications; +- at least one real or reproducible implementation case; +- alternatives considered. + +## Issues before large changes + +Open an issue before a large grammar, category, state or validator change. This creates a public rationale before code and prose diverge. + +Small corrections, examples and validator fixtures may go directly to a pull request. + +## Compatibility + +Files declare the grammar compatibility token they target. + +- Clarifications preserve meaning. +- Compatible changes add optional capability. +- Semantic breaks require a migration and a new compatibility token. + +Published historical files and releases remain inspectable in Git. + +## Evidence discipline + +Contributions must preserve these principles: + +- declaration is not verification; +- no evidence means no evaluated claim; +- unknown evidence is not failure; +- M3 cannot be self-awarded; +- mention, citation, recommendation and follow-through remain separate; +- the standard defines no universal 0 to 100 Answerworthy score; +- answerworthy.md remains the one canonical public file. + +## Copy style + +Use direct, dense prose. Avoid em dash characters. Avoid copy patterns that hide the actual claim behind stacked negation. + +## Licensing + +By contributing, you agree that accepted specification prose and examples may be distributed under CC BY 4.0, and accepted tooling or tests may be distributed under Apache-2.0. + +## Conduct + +Critique claims, evidence, grammar and implementation directly and respectfully. Fabricated benchmarks, undisclosed conflicts and certification impersonation are incompatible with participation. From 5f6d22f05e6b45ea611933a11c00fb2cee889518 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:17:19 +0100 Subject: [PATCH 11/15] Start the public standard changelog --- CHANGELOG.md | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 CHANGELOG.md diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..873b428 --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,21 @@ +# Answerworthy Standard changelog + +## Current specification + +### answerworthy 0.2 + +- Defines Answerworthiness as a checkable public evidence condition. +- Defines answerworthy.md as the one canonical AI-native public file. +- Establishes the category ladder: SEO makes you findable, GEO makes you citable, Answerworthiness makes you choosable. +- Defines identity, offer and audience, sourced facts, buyer answers, provenance, known corrections, evidence limitations, freshness, dimensions and conformance inside the file. +- Defines six dimensions and exact evidence states. +- Defines M0 Present, M1 Structured, M2 Sourced, M3 Corroborated and M4 Maintained. +- Records independent corroboration inside the canonical file. +- Defines Generate, Audit, Remediate and Refresh as the operating acts. +- Defines no universal 0 to 100 Answerworthy score. +- Publishes the dependency-free validator and examples. +- Opens implementation and governance participation through GitHub. + +## Historical note + +The earliest exploration considered multiple public companion artifacts. The one-file model superseded that direction before the current public source was established as the operative specification. From cc00899b906e54b22c1bb5cd22919d362210a6d3 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:17:31 +0100 Subject: [PATCH 12/15] Pin the grammar compatibility token --- VERSION | 1 + 1 file changed, 1 insertion(+) create mode 100644 VERSION diff --git a/VERSION b/VERSION new file mode 100644 index 0000000..3b04cfb --- /dev/null +++ b/VERSION @@ -0,0 +1 @@ +0.2 From ff86628ae30d9babc7869cf2792c6ee029cd53ac Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:17:43 +0100 Subject: [PATCH 13/15] Add standard validator and test scripts --- package.json | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 package.json diff --git a/package.json b/package.json new file mode 100644 index 0000000..4b0453c --- /dev/null +++ b/package.json @@ -0,0 +1,21 @@ +{ + "name": "answerworthy-standard", + "version": "0.2.0", + "private": false, + "type": "module", + "description": "The open standard and validator for the canonical answerworthy.md file.", + "license": "SEE LICENSE.md", + "repository": { + "type": "git", + "url": "https://github.com/kosmopteros/answerworthy.md.git" + }, + "homepage": "https://answerworthy.md/standard", + "scripts": { + "validate:example": "node validator.mjs examples/sourced.answerworthy.md", + "test": "node --test tests/*.test.mjs", + "check": "npm run validate:example && npm test" + }, + "engines": { + "node": ">=20" + } +} From f7ec813f939d0becbea9d0edf76619cf027d6f93 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:18:09 +0100 Subject: [PATCH 14/15] Test conformance, evidence boundaries and no-score language --- tests/validator.test.mjs | 130 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 130 insertions(+) create mode 100644 tests/validator.test.mjs diff --git a/tests/validator.test.mjs b/tests/validator.test.mjs new file mode 100644 index 0000000..42f2fe5 --- /dev/null +++ b/tests/validator.test.mjs @@ -0,0 +1,130 @@ +import assert from 'node:assert/strict' +import { readFile, readdir } from 'node:fs/promises' +import path from 'node:path' +import test from 'node:test' +import { validateAnswerworthy } from '../validator.mjs' + +const root = process.cwd() +const source = (file) => readFile(path.join(root, file), 'utf8') + +async function textFiles(directory = root) { + const results = [] + for (const entry of await readdir(directory, { withFileTypes: true })) { + if (['.git', 'node_modules'].includes(entry.name)) continue + const absolute = path.join(directory, entry.name) + if (entry.isDirectory()) results.push(...await textFiles(absolute)) + else results.push(absolute) + } + return results +} + +test('the sourced example passes at self-declared M2', async () => { + const result = validateAnswerworthy(await source('examples/sourced.answerworthy.md')) + assert.equal(result.valid, true) + assert.equal(result.claimed, 'M2') + assert.equal(result.achieved, 'M2') + assert.equal(result.facts, 2) + assert.equal(result.answers, 2) + assert.equal(result.dimensions.present, 6) + assert.deepEqual(result.errors, []) +}) + +test('the minimal example passes at M1 and warns that sourcing is missing', async () => { + const result = validateAnswerworthy(await source('examples/minimal.answerworthy.md')) + assert.equal(result.valid, true) + assert.equal(result.claimed, 'M1') + assert.equal(result.achieved, 'M1') + assert.match(result.warnings.join(' '), /M2 cannot be established/) +}) + +test('M3 cannot be self-claimed without an independent attestation', () => { + const text = `--- +answerworthy: "0.2" +entity: "Example Co" +canonical: https://example.com +last_verified: 2026-08-05 +conformance: M3 +--- + +## Identity + +Example Co makes software. + +## Canonical facts + +- statement: "Example Co makes software." + basis: declared + source_class: owned + source: https://example.com + verified_at: 2026-08-05 + +## Answers + +### What does Example Co make? + +Software. + +source: https://example.com +` + const result = validateAnswerworthy(text) + assert.equal(result.valid, false) + assert.equal(result.achieved, 'M2') + assert.match(result.errors.join(' '), /M3 requires an independent attestation URL and SHA-256 hash/) +}) + +test('a referenced attestation can establish M3', () => { + const text = `--- +answerworthy: "0.2" +entity: "Example Co" +canonical: https://example.com +last_verified: 2026-08-05 +conformance: M3 +attestation_url: https://verifier.example/attestations/1 +attestation_sha256: 0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef +--- + +## Identity + +Example Co makes software. + +## Canonical facts + +- statement: "Example Co makes software." + basis: declared + source_class: owned + source: https://example.com + verified_at: 2026-08-05 + +## Answers + +### What does Example Co make? + +Software. + +source: https://example.com +` + const result = validateAnswerworthy(text) + assert.equal(result.valid, true) + assert.equal(result.achieved, 'M3') +}) + +test('the category definition and canonical-file statement are identical across normative files', async () => { + const category = 'A business is answerworthy when its identity, offer, facts, answers, evidence, limitations and freshness are publicly accessible, machine-readable and independently checkable.' + const canonical = 'answerworthy.md is the canonical file. Any JSON, HTML, PDF, dashboard or score that an implementation emits is a projection of it and cannot outrank it.' + for (const file of ['README.md', 'SPECIFICATION.md', 'GRAMMAR.md']) { + const content = await source(file) + assert.ok(content.includes(category), `${file} must contain the category definition`) + } + for (const file of ['README.md', 'SPECIFICATION.md']) { + const content = await source(file) + assert.ok(content.includes(canonical), `${file} must contain the canonical-file statement`) + } +}) + +test('normative and public copy contains no em dash and no universal numeric grade', async () => { + const files = await textFiles() + const combined = (await Promise.all(files.map((file) => readFile(file, 'utf8')))).join('\n') + assert.doesNotMatch(combined, /—/) + assert.doesNotMatch(combined, /\b\d{1,3}\s*\/\s*100\b/) + assert.doesNotMatch(combined, /overall\s+(?:answerworthy|visibility|readiness)\s+score/i) +}) From d547fe181d1ef07b46b4811d48b9d918571998f4 Mon Sep 17 00:00:00 2001 From: Alexander Pichugin <113478545+kosmopteros@users.noreply.github.com> Date: Wed, 5 Aug 2026 17:18:21 +0100 Subject: [PATCH 15/15] Add public standard CI --- .github/workflows/quality.yml | 33 +++++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 .github/workflows/quality.yml diff --git a/.github/workflows/quality.yml b/.github/workflows/quality.yml new file mode 100644 index 0000000..15ec4bb --- /dev/null +++ b/.github/workflows/quality.yml @@ -0,0 +1,33 @@ +name: Standard quality + +on: + pull_request: + push: + branches: + - main + - 'standard/**' + +permissions: + contents: read + +jobs: + verify: + runs-on: ubuntu-latest + timeout-minutes: 10 + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version: 22 + - name: Validate sourced example + run: node validator.mjs examples/sourced.answerworthy.md + - name: Run validator and standard tests + run: node --test tests/*.test.mjs + - name: Confirm canonical source files + run: | + test -f SPECIFICATION.md + test -f GRAMMAR.md + test -f GOVERNANCE.md + test -f validator.mjs + test -f examples/minimal.answerworthy.md + test -f examples/sourced.answerworthy.md