Skip to content

osm features: a city tile is served COMPLETE, and probe M4 says why the overland rule is still a placeholder - #110

Merged
AdaWorldAPI merged 1 commit into
mainfrom
claude/q2-osm-map-reencoding-56p5e2
Aug 11, 2026
Merged

osm features: a city tile is served COMPLETE, and probe M4 says why the overland rule is still a placeholder#110
AdaWorldAPI merged 1 commit into
mainfrom
claude/q2-osm-map-reencoding-56p5e2

Conversation

@AdaWorldAPI

@AdaWorldAPI AdaWorldAPI commented Aug 11, 2026

Copy link
Copy Markdown
Owner

What was wrong

The previous pass diagnosed the row cap as "spatially biased" and fixed how rows were dropped without asking whether they should be. They should not be.

MAX_FEATURES_PER_TILE was a flat 5_000 applied at every zoom. Against a real bake that is not a coarse-zoom backstop — it is the normal case. From the one measured tile (14/8802/5373, total = 15_016) and a slippy tile quartering in area per zoom step:

z rows/tile (Berlin-class) under the old flat 5k cap?
12 ~240,000 no — 98% dropped
13 ~60,000 no — 92% dropped
14 15,016 (measured) no — 67% dropped
15 ~3,800 yes

One mid-sized city, served two-thirds absent at the zoom where a person actually reads a city. Stride sampling only changes that from "wrong in one corner" to "wrong everywhere, evenly" — uniform loss looks better, which is worse.

The falsifier certified the defect

The test written for the first fix asserted the returned points cover ≥95% of the tile's extent. A uniform stride covers ~100% of a bounding box at any stride — measured on that exact fixture shape:

budget rows kept extent lon/lat verdict under ≥0.95
5,000 25.0% 0.9922 / 1.0000 PASSES
1,000 5.9% 1.0000 / 1.0000 PASSES
100 0.59% 0.9070 / 0.9922 fails

A test that passes at 94% data loss has no power over data loss. Counting rows discriminates; measuring their bounding box does not.

The fix

row_budget(z) — the budget is zoom-conditioned, because "how many features may I drop" is an LOD question and LOD is a function of what the tile is, not a constant.

  • CITY_ZOOM_FLOOR = 13 — at or above, a tile is a place you are looking at, served complete
  • OVERVIEW_ROW_BUDGET = 100_000 — decimation target below the floor
  • CITY_ROW_CEILING = 400_000 — transport backstop only

Probe M4, run — and it refutes part of the above

bf16-hhtl-terrain.md's process rule: an agent changing bucketing strategy runs the probe first, or labels the proposal CONJECTURE and defers commitment. row_budget is a bucketing-strategy change and it was written as settled fact. M4 has sat NOT RUN, and its harness (osm-soa-bake's tier_probe) was already written for it.

Ran on Berlin (city, 2.52M features) and Iceland (overland, 0.65M) — features per tile by cascade tier:

tier Berlin tiles / med / p95 / max / fit≤30 Iceland tiles / med / p95 / max / fit≤30
heel z8 2 / 1,564,647 / — / 1,564,647 / 0.0% 58 / 3,838 / 34,985 / 202,296 / 20.7%
hip z16 8,065 / 206 / 996 / 3,844 / 16.4% 178,962 / 1 / 8 / 1,067 / 95.2%
twig z24 2,435,641 / 1 / 1 / 20 / 99.7% 649,093 / 1 / 1 / 7 / 99.9%
leaf z32 2,513,559 / 1 / 1 / 11 / 99.8% 652,314 / 1 / 1 / 7 / 99.9%

Terminates at TWIG, not HEEL — M4's own FAIL direction. Three things follow, two of which cut against what I had just written:

  1. Exactly one useful bucketing level: the hip cell. Occupancy goes 1 (twig) → 206 (hip) → 1.56M (heel). So the principled overland rule is one representative per occupied hip cell — 8,065 cells for 2.52M features, a 312:1 cascade step. A uniform row stride is not that. OVERVIEW_ROW_BUDGET is now labelled CONJECTURE in its own doc comment.
  2. Density is a property of the extract, not the zoom. Berlin and Iceland differ ~200× at hip and converge by twig, so a zoom-keyed floor is a policy, not a measurement.
  3. What the probe does let me state as measured: CITY_ROW_CEILING is bounded, not chosen. A z13 tile is 8×8 = 64 hip tiles, and Berlin's densest hip tile holds 3,844, so a z13 tile is bounded above by 246,016 — 400,000 provably cannot fire for a Berlin-class bake.

M4's result is recorded upstream in lance-graph/.claude/knowledge/bf16-hhtl-terrain.md per that file's update protocol, scoped explicitly to the OSM point-feature form.

Falsifiers

Each verified red against the restored flat-5k defect (5000 of 10000 rows):

  • a_city_zoom_tile_is_served_complete — counts rows; fixture asserted > the old 5k cap so it cannot go vacuous
  • row_budget_is_zoom_conditioned_at_the_city_floor — can-fire and can-stay-silent on the same knob
  • a_decimated_overview_tile_samples_the_whole_curve_not_a_morton_prefix — the old coverage test, re-scoped to the selection rule at an injected budget and documented as no evidence of completeness. It stayed green through the disable-the-fix run, which is exactly why it must not be the gate.

Also in this PR

osint_gotham: three assertions still bounded the V3 tenant at FACET_CAPACITY + 1 after the 6×(8:8) completion widened it to FACET_STAKEHOLDER, failing on a byte production already writes. Widened, plus a positive assert_eq!(bv[FACET_TYPE], 10) — a widened zero-check alone would make the test pass by inspecting less.

Verification

⚠️ The green checks on this PR are skipped, not passing. test-suite.yml carries if: github.repository == 'quarto-dev/q2', so on this fork every CI job short-circuits. CI did not run. Do not read the absence of red as a pass.

What was actually run, locally:

  • cargo test --bin q2-cockpit83 passed, 0 failed (was 79 passing with 1 pre-existing failure)
  • Each new falsifier verified red against the restored defect, not merely green against the fix
  • rustfmt --check clean across every hunk in this diff; the file's remaining drift is pre-existing and deliberately not churned

Not run: cargo build --workspace / cargo nextest run --workspace / cargo xtask verify. The workspace's full dependency closure exceeds this environment's disk ceiling (recorded in the plan's Disk note). The change is confined to cockpit-server, a leaf binary crate; no shared crate is modified.

Not verified: CITY_ZOOM_FLOOR is set from Berlin-class density; a denser extract (Jakarta, Tokyo) has not been measured. If it is wrong it is wrong in the safe direction (more completeness, larger responses), and the completeness test fails loudly rather than silently thinning.

🤖 Generated with Claude Code

https://claude.ai/code/session_01NMeiLmtDKhomJNSo2ecbJw

Summary by CodeRabbit

  • New Features

    • Improved map tile data delivery with zoom-aware row limits.
    • City-level views can now display complete results for larger datasets.
    • Overview views use spatially distributed sampling for more representative coverage.
  • Bug Fixes

    • Corrected tenant facet validation to preserve type information and prevent unintended trailing data.

…rland rule is still a placeholder

The previous pass diagnosed the row cap as "spatially biased" and fixed HOW
rows were dropped without asking WHETHER they should be. They should not be.

MAX_FEATURES_PER_TILE was a flat 5,000 applied at every zoom. Against a real
bake that is not a coarse-zoom backstop, it is the normal case: from the one
measured tile (14/8802/5373, total 15,016) and a tile quartering per zoom
step, Berlin is decimated at z14 (67% dropped), z13 (92%) and z12 (98%). One
mid-sized city, served two-thirds absent at the zoom where a person reads a
city. Stride sampling only changes that from "wrong in one corner" to "wrong
everywhere, evenly" — uniform loss looks better, which is worse.

The falsifier written for the first fix certified the defect. It asserted the
returned points cover >=95% of the tile's EXTENT, and a uniform stride covers
~100% of a bounding box at ANY stride: measured on that exact fixture, the
assertion passes while keeping 25% of rows, and still passes at 5.9%. A test
that passes at 94% data loss has no power over data loss. Counting rows
discriminates; measuring their bounding box does not.

  row_budget(z) — the budget is zoom-conditioned, because "how many features
  may I drop" is an LOD question and LOD is a function of what the tile is.
    CITY_ZOOM_FLOOR   = 13       at or above, served complete
    OVERVIEW_ROW_BUDGET = 100k   decimation target below it
    CITY_ROW_CEILING  = 400k     transport backstop only

Then ran probe M4, which has been queued NOT RUN and whose process rule says
a bucketing-strategy change runs the probe first or is labelled CONJECTURE.
osm-soa-bake's tier_probe, on Berlin (city, 2.52M features) and Iceland
(overland, 0.65M) — features per tile by cascade tier:

  tier      Berlin med/p95/max        Iceland med/p95/max
  heel z8   1,564,647 (2 tiles)       3,838 / 34,985 / 202,296
  hip  z16  206 / 996 / 3,844         1 / 8 / 1,067
  twig z24  1 / 1 / 20   (99.7% fit)  1 / 1 / 7   (99.9% fit)
  leaf z32  1 / 1 / 11                1 / 1 / 7

It terminates at TWIG, not HEEL — M4's own FAIL direction. Two consequences:
there is exactly ONE useful bucketing level (the hip cell; occupancy goes
1 -> 206 -> 1.56M), so the principled overland rule is one representative per
occupied hip cell (312:1 on Berlin), not a row stride — OVERVIEW_ROW_BUDGET
is labelled CONJECTURE accordingly. And density is a property of the extract,
not the zoom (Berlin and Iceland differ ~200x at hip, converge by twig), so a
zoom-keyed floor is a policy, not a measurement.

What the probe does let me state as measured: CITY_ROW_CEILING is bounded,
not chosen. A z13 tile is 8x8 hip tiles and Berlin's densest hip tile holds
3,844, so a z13 tile is bounded above by 246,016 — 400,000 provably cannot
fire for a Berlin-class bake.

Falsifiers, each verified red against the restored flat-5k defect
("5000 of 10000 rows"):
  a_city_zoom_tile_is_served_complete            counts rows, not extent
  row_budget_is_zoom_conditioned_at_the_city_floor
  a_decimated_overview_tile_samples_..._prefix   re-scoped to the selection
    rule at an injected budget, documented as NO evidence of completeness —
    it stayed green through the disable-the-fix run, which is exactly why it
    must not be the gate.

Also in this commit, from the same pass:

osint_gotham: three assertions still bounded the V3 tenant at
FACET_CAPACITY + 1 after the 6x(8:8) completion widened it to
FACET_STAKEHOLDER, failing on a byte production already writes. Widened, plus
a positive assert_eq!(bv[FACET_TYPE], 10) — a widened zero-check alone would
make the test pass by inspecting less.

83 passed, 0 failed (was 79 passing with 1 pre-existing failure).

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

coderabbitai Bot commented Aug 11, 2026

Copy link
Copy Markdown

Review Change Stack

Caution

Review failed

The pull request is closed.

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 1ca5ebcb-5b16-4a06-af68-431a2f20b115

📥 Commits

Reviewing files that changed from the base of the PR and between d022a9e and 3f724dd.

📒 Files selected for processing (3)
  • claude-notes/plans/2026-08-08-osm-soa-cockpit-wiring.md
  • crates/cockpit-server/src/osint_gotham.rs
  • crates/cockpit-server/src/osm_features.rs

📝 Walkthrough

Walkthrough

The OSM tile endpoint now applies zoom-dependent row budgets and stride sampling. The plan records probe results and removes proposed projection authorization. Facet-tenant tests now cover the expanded V3 tenant layout and stakeholder type facet.

Changes

OSM tile serving

Layer / File(s) Summary
Tile policy and measurements
claude-notes/plans/2026-08-08-osm-soa-cockpit-wiring.md
The plan defines city completeness, overview budgeting, representative sampling checks, and Berlin and Iceland probe findings.
Zoom-aware tile sampling
crates/cockpit-server/src/osm_features.rs
The endpoint replaces the fixed cap with city and overview budgets. City responses remain complete within the ceiling. Overview rows use stride sampling, with tests for budgets and spatial coverage.
Public endpoint decision
claude-notes/plans/2026-08-08-osm-soa-cockpit-wiring.md
The plan removes the proposed projection authorization integration and documents the unauthenticated public-field behavior.

Facet-tenant test coverage

Layer / File(s) Summary
V3 tenant byte assertions
crates/cockpit-server/src/osint_gotham.rs
Tests verify the stakeholder type: Nation facet and require zero bytes after the complete V3 tenant layout.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Possibly related PRs

  • AdaWorldAPI/q2#108: Extends the same osm_features endpoint with zoom-dependent budgets and representative sampling.
  • AdaWorldAPI/q2#109: Addresses Morton-order truncation bias in the same OSM tile sampling path.
  • AdaWorldAPI/q2#68: Updates the related V3 facet-tenant byte layout and tests.

Suggested reviewers: claude

Poem

I’m a rabbit hopping through tiles,
Counting rows in widening files.
City streets stay whole and bright,
Overview paths spread samples right.
Tenant facets line up true—
A tidy burrow waits for you.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@cursor

cursor Bot commented Aug 11, 2026

Copy link
Copy Markdown

Bugbot couldn't run - usage limit reached

Bugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit.

A user or team admin can review and increase usage limits in the Cursor dashboard.

(requestId: serverGenReqId_6f82ba6e-da4f-4bf0-9c73-58083b633c53)

@AdaWorldAPI
AdaWorldAPI marked this pull request as ready for review August 11, 2026 01:24
@AdaWorldAPI
AdaWorldAPI merged commit 40a25f6 into main Aug 11, 2026
5 checks passed
@cursor

cursor Bot commented Aug 11, 2026

Copy link
Copy Markdown

Bugbot couldn't run - usage limit reached

Bugbot is counted against Cursor usage for this user or team, and this run hit a usage or spend limit.

A user or team admin can review and increase usage limits in the Cursor dashboard.

(requestId: serverGenReqId_ed39a2a8-60bb-4d68-91ae-12428343a9fe)

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