Skip to content

GitLab 10-K corpus: seven-year income statement and operating metrics - #7202

Merged
briansrls merged 12 commits into
mainfrom
claude/gitlab-10k-scm-costs-baz90x
Jul 25, 2026
Merged

briansrls merged 12 commits into
mainfrom
claude/gitlab-10k-scm-costs-baz90x

Conversation

@briansrls

Copy link
Copy Markdown
Contributor

Summary

Models GitLab's complete post-IPO financial history (FY2020–FY2026) from SEC filings, grounding the company's income statement and operating metrics in XBRL facts. Establishes the foundation for SCM economics analysis by capturing revenue, cost of revenue, operating expenses (broken into three components), operating income/loss, net income/loss, and key operating metrics (ARR-threshold customer counts, dollar-based net retention, registered users, purchase commitments).

Key changes

  • extdeps/sec/issuer/gitlab_facts.dag — Added seven years of income statement facts (FY2020–FY2026) with proper citations to each filing's accession number and period. Introduced FiledSignedMonetaryFact for credit-balance elements (operating income/loss, net income/loss). Added operating metrics facts (ARR customer counts, DBNRR, registered users, hosting commitments). Updated provenance notes with detailed filing authority and cross-footing guarantees.

  • extdeps/sec/facts.dag — Refactored FiledFactCitation to use a closed FiledPeriod sum type (FiledDuration for flows, FiledInstant for balance/commitment amounts) instead of optional start/end fields. Added FiledSignedMonetaryFact type and signed_usd_negative() constructor for negative filed values. Added filed_signed_value() accessor.

  • extdeps/sec/operating_metrics.dag (new) — Defined shapes for issuer-disclosed KPIs: DollarBasedNetRetentionRow, ArrThresholdCustomerCountRow, RegisteredUserCountRow. Captures GitLab's SaaS metrics with proper rate semantics (floor vs. exact).

  • extdeps/pricing/gitlab_subscription.dag (new) — Modeled GitLab's three-tier subscription pricing (Free, Premium, Ultimate) with per-seat-month billing and Duo Credits bundling. Cites the live pricing page as authority.

  • gunbc/econ/free_tier_serving.dag (new) — Bottom-up free-tier serving cost floor: derives infrastructure box count from per-user storage/egress envelope against Hetzner dedicated server pricing. Includes top-down average serving cost per registered user (filed cost of revenue ÷ registered user floor).

  • test/claim/gitlab_10k_income_series_witness_test.dag (new) — Comprehensive witness suite verifying all seven years cross-foot exactly (GrossProfit = Revenue − CostOfRevenue; OperatingExpenses = three components; OperatingIncomeLoss = GrossProfit − OperatingExpenses). Witnesses revenue growth, S&M share decline, gross margin band stability, and operating loss convergence.

  • test/claim/free_tier_serving_witness_test.dag (new) — Witnesses for free-tier serving floor derivation and average serving cost bounds.

  • docs/plans/dag-scm-design.md (new) — Design seed for node-grain source control: thesis that merges/conflicts happen at node identity (not text grain), architecture sketch (content-addressed store, keyed diff, visibility grants, publication ladder, CI-as-realization), and roadmap integration.

  • gunbc/roadmap_authority.dag — Added SCM roadmap section (operator-directed 2026-07-25).

  • extdeps/sec/us_gaap.dag — Added GAAP element definitions for operating expense components and purchase commitments.

  • Existing facts files (chemed_facts.dag, rollins_facts.dag) — Updated to use new FiledPeriod closed sum type.

Notable implementation details

  • Period modeling as closed sum — FiledPeriod is a discriminated union, not optional fields, so a half-specified period is unwritable (correctness by construction per CLAUDE.md §1).

  • Signed values for losses — FiledSignedMonetaryFact

https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG

claude added 3 commits July 25, 2026 03:05
… comparatives) from live EDGAR pulls, with pricing + operating metrics

Seed for the .dag-native SCM lane (node-grain merges vs file/textual conflicts): what running an SCM business costs and how one is priced, from primary sources.

- extdeps.sec.facts: FiledPeriod = FiledDuration | FiledInstant (half-specified citation periods unwritable); SignedUsdWholeDollars sign-as-sum carrier (GroupCompletion shape, dissolve-on Int = GroupCompletion<Nat>) so filed losses are representable; opex/operating-income cross-foot fns
- extdeps.sec.us_gaap: OperatingExpenses, NetIncomeLoss, PurchaseObligation(+due-next-12mo), LongTermPurchaseCommitmentAmount element rows
- extdeps.sec.operating_metrics (new): MD&A KPI shapes - DBNRR as typed lower-bound-vs-exact sum, ARR-threshold customer counts
- extdeps.sec.issuer.gitlab_facts: seven fiscal years x full face income statement (cross-foots exactly every year), purchase-obligation/hosting-commitment instant facts, DBNRR >175%..118% and 100k-ARR customer series, per-year own-10-K citations; disaggregation gap + FY2024 net-vs-operating divergence typed as notes
- extdeps.pricing.gitlab_subscription (new): live-fetched tier rows (Premium 29 USD/seat-month billed annually, Ultimate CustomNegotiatedPricing, FreeOfCharge), Duo credit bundles, compute-minute meter, 2023 Premium 19->29 price-change row cited to GitLab's announcement
- rollins/chemed citations migrated to FiledDuration
- witness: gitlab_10k_income_series_witness (24 claim families incl. 5 RED controls) PASS; sec_edgar, econ_wedge, rollins_chemed witnesses re-run PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
…10k-user launch question)

- extdeps.sec.operating_metrics: RegisteredUserCountRow (Item 1 'more than N million registered users' is a FLOOR, same lower-bound honesty as DBNRR)
- extdeps.sec.issuer.gitlab_facts: registered-user floors FY2023/24 (30M) and FY2025/26 (50M), quoted + cited per filing
- gunbc.econ.free_tier_serving (new, knowable-wedge shape): bottom-up floor pricing a declared per-user envelope against cited Hetzner rows (storage x replicas + declared egress allowance -> box count; refuse-on-unknown, six typed refusal causes); top-down glean upper-bounding average serving cost per registered user from filed cost of revenue over the user floor
- witness free_tier_serving_witness PASS: 10k users floor = 2x AX41-1-LTD = 114.60 EUR/mo, 100k users = 19 boxes = 1088.70 EUR/mo, FY2026 glean = 2.414860 USD/user-yr (< 2.50), FY2023 glean = 1.722667 USD/user-yr, + 7 RED refusal controls; gitlab_10k/sec_edgar/econ_wedge witnesses re-run PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
…-scm design seed

- roadmap_authority: new section-2 group with 5 nodes — 2-scm-visibility-stage0 (NOW: Publish/Reference grant model implemented properly, realized over git public/private roots per the visibility design P-A/P-B, with Accept + RED), 2-scm-publication-ladder (locked/ciphertext rung, key-wraps, churn blinding, crypto-shred — design-only until Stage 0), 2-scm-node-merge (node-identity merges on the keyed-diff spine; git as one storage realization), 2-scm-remote-realization (withheld nodes execute server-side, metered — the SCM's CI), 2-scm-infra-econ (store/serving riding module-identity + belt B, grounded in the cited econ carriers); dependency edges visibility-first
- docs/plans/dag-scm-design.md (new): thesis, architecture-as-composed-lanes, publication ladder + locked realizations + hole residues + realization placements + churn blinding, sequencing, dissolution trigger
- node-subtree-visibility-grants.md section 11: extension pointer + the 2026-07-25 sequencing decision (visibility first over git roots, same interface carried by the native SCM)
- design_document.dag: re-home the SCM-economics open thread into the DESIGN.md authority (the two prior hand edits to generated DESIGN.md broke the drift fixed point — this restores it) + roadmap/design pointers
- DESIGN.md + ROADMAP.md regenerated via main_wet; generated_artifact_drift_witnesses PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG

Copy link
Copy Markdown
Contributor Author

Management review at e5279eb + the entity-modeling ruling the operator asked to flesh out.

What verifies well: FiledPeriod as a closed sum is the right §5 construction (a half-specified period is unwritable, not validated); FiledSignedMonetaryFact + signed_usd_negative model losses as typed negatives instead of sign-in-prose; the seven-year cross-footing witnesses assert the accounting identities exactly (GrossProfit = Revenue − CoR; OpEx = three components; OperatingIncomeLoss = GP − OpEx) plus honest trend witnesses; the free-tier serving floor grounds on the cited Hetzner price rows + RegisteredUserCountRow + std.measure, not hand numbers; chemed/rollins migrated to the new sum in the same PR (no dual representation left behind).

One finding: FiledFactCitation? — the optional citation means an uncited filed fact is representable. For SEC facts the citation IS the grounding; an Absent arm is a fail-open invitation. Make it required, or if migration needs the gap, a typed UncitedLegacy{reason} arm that's counted — never a bare ?.

The entity question (operator nit, adjudicated): the pieces already exist — extdeps/vendor/gitlab.dag (Vendor { legal_name: "GitLab Inc." }) and extdeps/sec/issuer/gitlab.dag binding that entity to its typed Cik. What's missing is the edges: gitlab_facts.dag carries its CIK only inside a URL string and imports neither row; the new pricing/gitlab_subscription.dag doesn't reference the entity at all. Today the only thing correlating the two fact families is the filename prefix — exactly the operator's discomfort.

The rule to land with this PR: folder = which upstream authority produced the facts; typed edge = which entity the facts are about. Subject and source are orthogonal axes, and filenames encode neither. Concretely: (a) gitlab_subscription.dag gains a subject edge to extdeps.vendor.gitlab.gitlab (its ExternalAuthority stays the pricing page — source unchanged, subject now typed); (b) the facts file threads the issuer row (or FiledFactCitation gains an issuer field) so the CIK-in-URL prose stops being the identity carrier.

Flag, not for this PR: GitLab is the tree's first two-domain entity, and it exposes that Vendor<Securities> puts the domain parameter on the wrong node — one GitLab Inc. can't be Vendor<Securities> and Vendor<Saas> without forking the entity. The parameter belongs on the relationship rows (each fact family declares its domain), with the entity row un-parameterized. That's a ~14-file migration touching all vendor consumers — file it on the grounding-inventory lane with this PR as its discriminating receipt, don't absorb it here.

The SCM design seed + roadmap section are operator-directed and read as a seed (no code claims); no adjudication needed. CI green + the two edge additions + the citation-required fix and this is merge-shaped.


Generated by Claude Code

claude added 2 commits July 25, 2026 05:58
…dened to Microsoft + Atlassian

Review (PR #7202) fixes:
- citation is REQUIRED on FiledMonetaryFact / FiledSignedMonetaryFact / the three operating-metric rows — for a filed fact the citation IS the grounding, so the optional arm was a fail-open invitation. Zero uncited rows existed in the corpus, so it lands as plainly required with no UncitedLegacy arm; all 97 sites migrated (Present{value: X} -> X)
- subject/source ruling landed: folder = which upstream authority produced the facts, typed edge = which entity they are about. Every issuer facts module gains an IssuerCatalogRow subject edge (gitlab, chemed, rollins — no dual standard); pricing/gitlab_subscription gains a Vendor subject edge so filed financials and list prices correlate through the graph, not a filename prefix. The CIK-in-URL is now a locator, not the identity carrier
- Vendor<Domain> parameter-on-the-wrong-node filed (NOT fixed here) on the grounding-inventory lane with this PR as the discriminating receipt; the pricing subject row carries the known-mismatch note + dissolve-on

Corpus widened (operator request — flesh out the modeling, set the example):
- extdeps.vendor.{microsoft,atlassian} + extdeps.sec.issuer.{microsoft,atlassian} entity/issuer rows
- microsoft_facts (FY2022-FY2025) and atlassian_facts (FY2022-FY2025), live EDGAR pulls, all cross-footing exactly; comparable set is now three SIC-7372 issuers: GitLab pure-play, Atlassian nearest comparable, Microsoft as GitHub's owner / scale contrast
- exercises arms GitLab's seven loss years could not: NonNegativeUsd (MSFT profitable throughout, TEAM profitable FY2022 then three loss years) and Unfiled (MSFT FY2022 OperatingExpenses untagged in its own 10-K — refused, never back-computed)
- proves the per-row element grain: Atlassian switched cost elements mid-series (CostOfRevenue FY2023/24 -> CostOfGoodsAndServicesSold FY2025), each row carrying its own filing's tag
- GitHub-level economics typed as a gap: not filed anywhere (three segments, no GitHub line, dimensional facts stripped) — no estimate stored
- witness scm_issuer_corpus_witness (15 families incl. entity edges + 4 RED controls) PASS; all five prior SEC/econ witnesses re-run PASS; DESIGN.md regenerated, drift fixed point PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
…ill calculator

Answers "where are the vendor cost tables, and how do we calculate compute/quota/network usage".

- std.measure: three storage billing-unit markers on the existing MoneyRate<P> axis (PerStoredUnitMonth, PerTransferredUnit, PerMillionRequests). Byte basis deliberately NOT baked into the unit type — vendors quote incompatible bases for the same word
- extdeps.pricing.object_storage (new): AWS S3 storage tiers + egress tiers + request tiers from the machine-readable Price List API (same authority aws_ec2 cites), GCS standard + separately-priced inter-region replication, Cloudflare R2 storage/ops/zero-egress. Backblaze B2 and Hetzner Object Storage land as RateUnavailable{cause} — client-rendered rates this fetch cannot read, refused rather than filled from memory
- durability as a CITED attribute: Durability=99.999999999% sits on the S3 price-list row itself (11 nines, erasure-coded). Names the trap it implies: multiplying an object-storage rate by a replica count double-charges redundancy the vendor already sells; replica multiplication belongs on self-managed block storage (free_tier_serving), and the two carriers cross-reference
- byte-basis honesty: S3 quotes GB-Mo, GCS quotes gibibyte-hour, no surface states 10^9 vs 2^30 (7.4% — wider than several vendor gaps). Every row carries its quoted label verbatim + a typed ByteBasis; comparison requires a declared assumption or refuses
- gunbc.econ.scm_serving_model (new): workload profile -> capacity/network/operations bill, refuse-on-unknown throughout. Compute deliberately delegated to knowable_wedge/free_tier_serving rather than modeled twice. Construction wall: rows from different vendors refuse (VendorMismatchAcrossRows), so "S3 storage with R2 free egress" is unwritable
- witness scm_serving_model_witness (11 families, 6 RED controls) PASS: same 10k-user profile prices at ~474.80 USD/mo on S3 (egress 94.8% of the bill) vs ~16.62 USD/mo on R2 — a ~28x spread on identical usage, derived not asserted
- DESIGN.md regenerated; drift + free_tier_serving witnesses PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG

Copy link
Copy Markdown
Contributor Author

The regen red, explained + the fix that dissolves it without a regen run.

Why regen failed while heal passed: they verify disjoint generator outputs. regen proves the emitted-Rust seed fixed point — fresh emit of the seed closure vs the committed src/v1 .rs, byte-identical. heal_generated_artifacts covers the generated-artifact registry (ci.yml, ROADMAP.md, …), all of which this branch already carries regenerated. This PR edited seed-emitted dag/std/measure.dag (three new phantom markers PerStoredUnitMonth/PerTransferredUnit/PerMillionRequests + aliases + accessors) without regenerating the seed — the job log's diff shows exactly those symbols present in fresh emit and absent from the committed seed. Both jobs told the truth about different artifact sets.

Don't fix it by regenerating — fix it by relocating. This morning's management ruling (census lane) named the MoneyRate<P> phantom family the specimen defect (structureless phantoms, hand accessor pairs, no derivable conversions), with the directive to this PR: consume the current shape as-is; don't fork ahead. Adding three new phantom arms in std grows the family the Rate-framework item is queued to dissolve — every new arm is another consumer to migrate later. And MoneyRate<P> is generic: the markers don't need to live in std at all. Declare the three markers + aliases + accessors in the pricing layer (extdeps.pricing.object_storage or a sibling pricing-units module). That single move: (a) leaves dag/std/measure.dag untouched, so the regen divergence vanishes with no seed regeneration; (b) stops the anemic family growing in the framework layer; (c) parks the new units where the Rate-framework consumer sweep will collect them with the rest.

Keep the byte-basis insight exactly as written — the storage_billing_unit_note's refusal to bake a byte basis into the unit (AWS "GB-Mo" vs GCS "gibibyte hour", the 7.4% trap) is genuinely good modeling and survives unchanged as the per-row declared basis in object_storage. It's the phantom location, not the reasoning, that moves.

Also still open from the earlier review: the FiledFactCitation? optional-citation arm, the two entity edges (pricing → extdeps.vendor.gitlab, facts → the issuer row), and the body describing the Atlassian additions now in the diff.


Generated by Claude Code

claude added 5 commits July 25, 2026 06:48
…ility requirement

- extdeps.pricing.object_storage widened to 8 vendors: AWS S3, Azure Blob (LRS/ZRS/GZRS/RA-GZRS ladders x 3 tiers + egress tiers + operation rates, all from the unauthenticated retail price API), Google Cloud Storage (basis CORRECTED to BinaryGibibyte — GCS states "per 1 gibibyte", so it must not be reinterpreted under a decimal assumption; egress row added), Cloudflare R2, Wasabi (flat rate, no egress/API fees), Storj (distributed, metered egress), plus B2/Hetzner still RateUnavailable
- RedundancyScope + ReliabilityRequirement + three-valued verdict: Meets | Fails{axis} | RequirementUnknown{unstated_axis}. Unknown is neither pass nor fail — a vendor silent on geo-redundancy has not satisfied a geo-redundancy requirement. Scope is admitted only where the vendor's own surface names it (Azure in the SKU, Storj in its distribution claim); all others RedundancyUnstated
- progressive_cost: tier fold applying each band to its own slice (tax-bracket semantics) — required because at 1M users the profile crosses AWS's 50TB storage step and all three egress steps. saturating_sub keeps the clamp typed as Nat rather than an Int-typed literal branch
- ProviderQuote bundle + RequestsIncludedAtNoCharge arm (vendor-stated free is a different fact from rate zero and from unknown)
- witness scm_provider_matrix_witness (13 families) PASS: matrix at 10k/100k/1M users, tier-fold arithmetic, flat-rate-overstates RED, Azure redundancy ladder priced within one vendor, and four reliability-verdict controls. Regressions (scm_serving_model, free_tier_serving, econ_wedge) PASS; DESIGN regenerated, drift PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
… the provider ranking inverts

Operator: "LLM programming is more stressful than humans writing code" — the human profile loads the wrong axis.

- PackingPolicy = UnpackedNodeGrain | PackedObjects{nodes_per_object} + profile_with_packed_ops: workload stated in logical NODE operations, billing consequence derived. Per-request billing punishes fine granularity, so a node-grain store mapping one node to one object pays a fee per node — this is an architectural choice, not an implementation detail, so it is typed
- witness scm_agentic_stress_witness (11 families) PASS. Raising per-user access 4 orders of magnitude (200 reads/20 writes -> 2,000,000 node reads/200,000 node writes per user-month) while raising bytes only single-digit multiples:
  * operations go from 0.4% of a request-metered bill to 99.5% of it (both ends asserted)
  * at 10k users: R2 $16,275/mo · S3 $19,866 · Storj $175 · Wasabi $39.95 — no-request-fee vendors win by >400x
  * the ranking INVERTS: R2 < Storj on the human profile, R2 > Storj on the agentic one (both directions witnessed)
  * at 1M users unpacked: R2 $1,627,500/mo vs Wasabi $3,995
  * packing 1000 nodes/object collapses R2 from $16,275 to $91.20 (178x), byte axes provably untouched
- Two design rules follow: request pricing (not storage rate) is the selection criterion for an agentic SCM, and UnpackedNodeGrain is the expensive default a naive content-addressed store falls into
- DESIGN regenerated; drift + matrix regressions PASS

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
…en fixed point)

CI regen_verify_gate_passes red on this branch: adding PerStoredUnitMonth / PerTransferredUnit /
PerMillionRequests (plus their accessors and the storage_billing_unit_note) to dag/std/measure.dag
left the committed emitted seed std_measure.rs stale against a fresh self-compile.

regen_stage0 rerun; only std_measure.rs changed (99 generated files written, 1 differing).
`regen_stage0 --verify` now reports regen_divergence_count=0, and the regenerated seed builds.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
…nstruction, not by roster row

CI batch 3 red: non_fold_residue_no_unrostered_or_stale. The lens flags a match over a
closed-coproduct PARAM carrying a top-level wildcard arm; three such sites landed with the
serving model, all on the 3-variant ByteBasis:

  assumed_basis            match b        { ByteBasisUnstated => none  _ => ... }
  basis_compatible_with_row match assumed { DecimalGigabyte => true   _ => false }  (x2 inner)
  effective_basis          match quoted   { ByteBasisUnstated => ...   _ => ... }

Fixed by enumerating every variant rather than adding roster rows: the roster is for residue
with a real dissolution cost, and these are 3-variant matches whose totality is free. A new
ByteBasis variant now fails to compile at each site instead of silently taking a wildcard arm —
construction over declared debt (DESIGN sections 5/6).

Behaviour unchanged by execution: scm_serving_model, scm_provider_matrix, and scm_agentic_stress
witnesses all still PASS, non_fold_residue_no_unrostered_or_stale now PASSes, and the
synthetic-unrostered RED control still fires.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
…-costs-baz90x

# Conflicts:
#	docs/plans/extdeps-std-grounding-inventory.md

Copy link
Copy Markdown
Contributor Author

CI red on ci — failing on the base branch too, not from this PR

ci failed on 2e2b231 (run 30161916870) at batch 4:

✗ infer_semantics_witness_keystone_holds (src/v2/test/claim/infer_semantics_witness_test.dag)
  infer_semantics_witness.rs:628 assertion `left == right` failed
    left: 0   right: 1
  in invalid_slice_returns_compiler_error_type

The witness asserts that slicing a List<Int> yields exactly one "slice is only supported" diagnostic; it now yields zero.

Attribution, proven by execution rather than inferred. I built and ran the same witness from a clean worktree at origin/main (25873a3) with none of this branch's changes:

$ git worktree add <tmp> origin/main && cargo build --bin infer_semantics_witness && ./infer_semantics_witness
infer_semantics_witness: invalid_slice_returns_compiler_error_type panicked

Main is red on this witness on its own. Corroborating: this branch's only change under src/v1/stage0/src/ is the regenerated std_measure.rs (+36 lines of money-rate carriers); git diff origin/main HEAD -- src/v1/stage0/src/v1_compiler_infer_access.rs src/v1/stage0/src/bin/infer_semantics_witness.rs is empty — both the tested function and the test are byte-identical to main. The slice path was last touched on main by bb4347d (#7196, the Range-vs-usize seed-emitter trio).

Not fixing it here. Whether List slicing is now intentionally supported (update the witness) or the diagnostic was lost (restore it) is the #7196 lane's call, not something to guess at from an unrelated PR. Re-running once main recovers.

Separate observation from the same run, flagged as possibly partly mine: FLOOR-BATCH-OVER-BUDGET batch=4 wall_ms=551945 budget_ms=420000. This PR adds five witness entries to the discovery corpus, so some of that wall is mine; the budget row is a refusal-not-a-widen by design, so if it persists after main goes green I'll price my witnesses' contribution and either scope them or bring a receipt rather than ask for the budget to be raised.

This branch's own state is green by local execution at 2e2b231: regen_stage0 --verify → regen_divergence_count=0; generated_artifact_drift_witnesses, non_fold_residue_no_unrostered_or_stale, and all five SCM/econ witnesses PASS.


Generated by Claude Code

… accessors, ground registrant_name

Two review items (2026-07-25), both fixed by construction rather than annotation.

1. LAYER PLACEMENT — the std/measure.dag deviation, reverted:
   - new extdeps.pricing.billing_units carries PerStoredUnitMonth / PerTransferredUnit /
     PerMillionRequests, the three MoneyRate<P> aliases, and the storage_billing_unit_note.
     MoneyRate<P> itself stays in std (universal carrier); the P markers are VENDOR-BILLING
     vocabulary and belong beside their citations. Generics instantiate downstream, so the
     defense of the original note survives relocation verbatim.
   - dag/std/measure.dag and src/v1/stage0/src/std_measure.rs REVERTED to origin/main content:
     `git diff origin/main -- src/v1/ dag/std/` is now empty. The PR touches zero seed files,
     which also removes the regen coupling that redded this branch's own fixed-point gate.
   - money_per_stored_unit_month_micros / money_per_transferred_unit_micros /
     money_per_million_requests_micros DELETED as hollow aliases of money_rate_micros<P>
     (DESIGN section 3 nickname); both consumers now call money_rate_micros directly.

2. IssuerCatalogRow.legal_name — not a duplicate, a fidelity gap; renamed and grounded:
   measured against the EDGAR submissions API, the name of record differs from the company's
   own legal name for EVERY issuer in the corpus: 'Gitlab Inc.' vs 'GitLab Inc.',
   'MICROSOFT CORP' vs 'Microsoft Corporation', 'ROLLINS INC' vs 'Rollins, Inc.',
   'CHEMED CORP' vs 'Chemed Corporation', 'Atlassian Corp' vs 'Atlassian Corporation'.
   The field held the company form, so it WAS a duplicate of vendor.legal_name and not the
   cited fact it implied. Renamed to registrant_name, repopulated with EDGAR's actual string
   (live pull), and annotated: it is the lookup key EDGAR company search matches on, while the
   vendor edge carries the company's own legal name. Deriving either from the other would
   fabricate a string neither authority publishes.

Green by execution: all six SCM/econ keystones + econ_wedge + both sec_edgar witnesses PASS;
regen_stage0 --verify reports regen_divergence_count=0; artifact gate clean.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG

Copy link
Copy Markdown
Contributor Author

Review items addressed — dd13596

1. std/measure.dag relocation — done, seed now untouched

Accepted without reservation; the argument that decided it is the one I should have applied myself: these markers are what clouds bill on, not universal-framework vocabulary, and the generics-instantiate-downstream point means nothing was bought by putting them in std.

  • New extdeps/pricing/billing_units.dag carries PerStoredUnitMonth / PerTransferredUnit / PerMillionRequests, the three MoneyRate<P> aliases, and the storage_billing_unit_note. MoneyRate<P> itself stays in std.measure — the universal carrier is not the vendor's meter.
  • dag/std/measure.dag and src/v1/stage0/src/std_measure.rs reverted to origin/main content. Receipt: git diff origin/main -- src/v1/ dag/std/ is empty. The PR touches zero seed files.
  • The three money_per_*_micros wrappers deleted — byte-for-byte hollow aliases of money_rate_micros<P>. Both consumers now call it directly. The new module carries a note saying why no accessors are declared there, so the next author doesn't re-add them.

The seed-coupling argument was self-demonstrating: the +36 std_measure.rs lines were exactly what redded this branch's regen fixed-point gate earlier today.

2. IssuerCatalogRow.legal_name — not a duplicate, a fidelity gap

Investigating the nit turned it into a real finding. Measured against the EDGAR submissions API, the name of record differs from the company's own legal name for every issuer in the corpus:

issuer EDGAR name of record vendor legal name
GitLab Gitlab Inc. GitLab Inc.
Microsoft MICROSOFT CORP Microsoft Corporation
Atlassian Atlassian Corp Atlassian Corporation
Rollins ROLLINS INC Rollins, Inc.
Chemed CHEMED CORP Chemed Corporation

The field held the company form in all five rows — so it was a duplicate of vendor.legal_name and not the cited fact its position implied. Annotating it as "EDGAR's name of record" would have made the note a lie. Renamed to registrant_name, repopulated with EDGAR's actual strings from a live pull, and annotated: the registrant name is what EDGAR company/full-text search matches on (the lookup key for the filings), while the vendor edge carries the company's own legal name. Deriving either from the other would fabricate a string neither authority publishes.

3. Timing receipt (the criterion still owed)

Measured locally on this branch, one claim_batch invocation per entry:

keystone witness eval claim families resolve (cold, standalone)
gitlab_10k_income_series_witness 11 ms 24 19.8 s
scm_provider_matrix_witness 9 ms 13 18.9 s
scm_issuer_corpus_witness 8 ms 15 20.3 s
scm_agentic_stress_witness 5 ms 11 20.2 s
free_tier_serving_witness 2 ms 11 20.2 s
scm_serving_model_witness 2 ms 11 18.3 s

37 ms of witness eval across all six — three orders of magnitude under the 5 s fast-lane rule, so all six are per-PR fixture-grain by measurement, not by assertion. Nothing here wants the falsifier cadence.

Stated plainly because it is the honest reading of the same table: the standalone resolve is ~19 s per entry and dwarfs eval. That is a closure-assembly cost, not witness work, and it is shared in the floor (the failing run's own receipt reads floor resolves: 1 entry resolve(s), 2439ms) — but it is the axis my six entries actually load, so it is where any batch-4 contribution of mine lives. If the over-budget signal survives main going green, that is the number I will price and scope against, not the eval column.

Verification

All green by execution at dd13596: six SCM/econ keystones + econ_wedge + both sec_edgar witnesses PASS; regen_stage0 --verify → regen_divergence_count=0; generated-artifact gate clean.

CI remains blocked on the pre-existing main red (invalid_slice_returns_compiler_error_type, base-branch control in the previous comment) — unblocked the moment the #7196 fix lands on main.


Generated by Claude Code

…KU held fixed per provider

Answers the wage-intuition question by measurement: compute is NOT cheaper where wages are lower.

- extdeps.pricing.regional_compute (new): AWS m7i.large across 10 regions (Price List API) and
  Azure Standard_D2s_v5 across 12 (retail API), 2 vCPU / 8 GiB held fixed per provider so a price
  gap is a REGION fact rather than a hardware fact. Geography axis spans North/South America,
  Europe, Africa, Middle East, South/East/Southeast Asia.
- Every sampled region prices ABOVE its provider's US baseline: Mumbai +5.2%, Frankfurt +19.8%,
  UAE +22.6%, Singapore +25%, Tokyo +29.2%, Cape Town +32.3%, Hong Kong +37.5%, Sao Paulo +59.4%.
  The two providers agree to the basis point on Brazil (5937 bp each, independently derived).
- Two structural findings as rows, not prose: instance families are not uniformly available
  (Bahrain has no m7i, so its row carries m6i.large and states the comparison is not like-for-like),
  and local/regional providers essentially never publish machine-readable prices — E2E Networks,
  Magalu, Afrihost, Alibaba, Contabo all land HourlyUnavailable{cause} with the specific obstacle
  (404 / client-rendered / 403 bot-block) recorded per row.
- HourlyUnrepresentable is a distinct third arm from HourlyUnavailable: Sakura Internet (Japan) was
  read successfully but quotes JPY and std.currency admits only Eur/Usd. "Could not read it" and
  "read it but cannot represent it" are different states with different remedies; the dissolve-on
  names adding Jpy to std.currency (legitimate std vocabulary, unlike a vendor billing unit).
- gunbc.econ.regional_compute_premium (new): basis-point premium vs a baseline region, refusing
  across providers (ProviderMismatch) and vCPU counts so a vendor comparison cannot masquerade as
  a region comparison.
- witness regional_compute_witness (10 families, 4 RED controls) PASS: the headline is a TOTALITY
  claim (no sampled region is cheaper than its US baseline) so a future re-pull finding one breaks
  loudly, plus the cross-provider agreement, the geography coverage, and refusals for unreadable
  rates, unrepresentable currency, and cross-provider premiums.

Self-review catch: the first draft asserted a dedicated-vs-cloud ratio that silently compared
micro-USD against micro-EUR — the exact unit conflation this corpus refuses elsewhere. Replaced
with a same-currency per-vCPU-month claim; any cross-currency comparison needs a declared FX rate
the way gunbc.econ.knowable_wedge already declares eur_to_usd.

Seed untouched: `git diff origin/main -- src/v1/ dag/std/` remains empty. Drift gate PASS.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XddFQprkpseK3EsQDkUbRG
@briansrls
briansrls merged commit 768f750 into main Jul 25, 2026
5 checks passed
@briansrls
briansrls deleted the claude/gitlab-10k-scm-costs-baz90x branch July 25, 2026 17:51
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants