Review: Discogs mirror site (#34) - #109
jackjin1997 wants to merge 14 commits into
Conversation
Adds the 16th WebHarbor mirror at https://discogs.com — the world's largest music release database and marketplace. Real catalogue of 7,042 releases / 5,031 artists / 3,938 labels / 6,825 master records pulled from the Discogs public API + MusicBrainz, plus 323 real album covers from Wikipedia. Backed by a benchmark community of 29 users with seeded ratings, reviews, collections, wantlists, lists, marketplace listings, and forum threads. Registered as the 16th site at port 40015. Image bumps to 16 mirrors total; EXPOSE 40000-40015. ## Site features - Release / master / artist / label / genre / style / format pages - Token-overlap scored search across releases, artists, labels with genre / style / format / year / country facets - Marketplace with media-condition + genre filters, per-listing comments, grades, currencies, sellers - User collection (5 folders: Uncategorized / All / Vinyl / CD / Wishlist Bought) with media + sleeve grades per item - Wantlist with min-grade preferences - User-curated public lists (CRUD) - Forums (10 topical boards) with threaded replies - Rating (1-5) + Review submission with helpful counts - Auth (Flask-Login + bcrypt + CSRF), register / settings / logout - 20 WebVoyager-format tasks in sites/discogs/tasks.jsonl ## Data scale - releases: 7,042 (3,522 from Discogs API + 3,520 from MusicBrainz) - artists: 5,031, labels: 3,938, masters: 6,825 - ratings: 86,714, reviews: 3,253 - collection_items: 4,207, wantlist_items: 1,374 - lists: 40, listings: 2,640, threads: 43, posts: 333 - benchmark users: alice_crate, bob_vinyl, carol_jazz, dave_techno (passwords: alice12345 / bob123456 / carol12345 / dave12345) - + 25 collector-style users with realistic locations & seller status ## Determinism work - MIRROR_REFERENCE_DATE = datetime(2026,5,26) pins all date fields so re-seeding from scraped_data/ is bit-for-bit reproducible - random.Random(42) seed for the community generator - Idempotent gates on every seed_*() function (count() > 0 → early return); byte-identical reset verified ## Verification - Docker build green; all 16 sites return 200 - POST /reset/discogs keeps DB byte-identical to seed - All 20 tasks pass when walked via Playwright (Chromium) ## Paired Hugging Face assets - Heavy assets shipped via the ChilleD/WebHarbor HF dataset: - sites/discogs/instance_seed/discogs.db (13 MB) - sites/discogs/static/images/release/*.jpg (323 covers, 32 MB) - .assets-revision is left at `revision: main` so the HF merge will roll in automatically (same approach as TED / Phys.org PRs).
The Owner compared the mirror with discogs.com side by side and rejected the homepage: the top menu was completely different, the release rows used a scrollbar instead of the live prev/next arrows, the footer differed substantially, and the pages behind the benchmark tasks did not follow the original site closely enough. Measured the live site as a guest at 1440px (full-page captures, shadow-DOM markup for the header and footer components, computed styles for ~90 elements) and rebuilt against those measurements: - Header: the live two-row structure, the search component with its category panel, the cart and Sign Up / Log In controls, and the five dropdown menus with all 33 destinations. Menus are native <details>, so they work with or without JavaScript; narrow widths collapse to the live drawer. - Homepage: hero, three release carousels and the app promo in the live order. Carousels page with prev/next buttons and bullets instead of a scrollbar, and the cards carry the live field set. The homepage community block, which the live site does not have, is gone. - Footer: the live three-column plus social layout, labels, social icons, newsletter form, app badges, language selector, legal links and the keyboard shortcuts dialog. - Task-path pages: search results with entity tabs and in-result facet counts, release detail with the live two-column layout and right rail, marketplace with the You Selected chips and seven facet groups, List Explorer, list detail, forum index, board, thread, login and register. - Twelve routes added so every menu and footer destination resolves locally, plus marketplace format/ships-from/year/price filters and label, catalog number and barcode filters behind an advanced search form. Ranking carousels are computed from the benchmark's own marketplace and collection state and labelled as such; no source ranking is fabricated. Route paths and query parameter names used by verifiers are unchanged, the seed database is untouched and reset stays byte-identical. 48/48 application tests and 23/23 verifier-contract tests pass.
The footer newsletter input carried name="email", which collided with the register form's own email field on /register, so a form-filling agent saw two elements named "email" on that page. The live Discogs footer input has no name attribute; match it. Found while re-walking the 15 task paths on the repaired UI. 48/48 application tests pass.
Matching the live search card meant showing the full format description, which put "Album, Dolby System" and "Album, Repress" on the results page. Task 3 asked for exactly that descriptor plus each release ID, so two of its three facts became readable without opening either detail page, while the verifier still demanded both detail visits. That is a task-versus-verifier contradiction: a completion the question allows was rejected by a navigation condition the question never stated. Re-anchor the task on identifier facts that only the detail pages carry. One of the two Spanish 1978 cassettes lists an extra "Impuesto de lujo" entry (Num. 6649) that the other does not, and both share a "Deposito Legal" value; neither appears on a search card. The question now asks for both release IDs, which edition carries the extra entry and its value, and the shared value. Replace the generic nearest-token association for this task with an explicit attribution check: the nearest release ID preceding the fact decides the binding, so a swapped answer fails even though every requested token is present. Proximity alone did not do this, because sentence order could place the correct ID closer than the wrong one. Tests: swapped-binding and results-page-only answers now fail, a second natural paraphrase passes, and the full verifier suite plus 48 application tests pass.
The verifiers accepted a step URL only when its port was exactly 40024. That pinned grading to one operator choice while implementing no control: the adversarial test that justified it rewrites the origin to https://attacker.invalid, which differs in scheme and host, so the port never took part in rejecting it. It also made the workflow AGENTS.md prescribes ungradeable, since that guide runs the image on 41000+ when the default range is busy. Replace it with checks on what actually matters, asserted explicitly on every task rather than used as a silent filter: no_foreign_origins any non-loopback step fails single_origin a trajectory spanning two origins fails origin_matches_expected optional exact pin via WHR_EXPECTED_ORIGIN single_origin rejects a trajectory stitched together from two local services, which the port pin could not detect at all. Tests: all 15 tasks grade identically when re-hosted on 127.0.0.1:41024; the foreign-origin spoof still fails all 15; a mixed-origin trajectory fails all 15 with reason single_origin; the optional pin accepts its origin and rejects another. Suite 24/24. Also make the fixture's subprocess cap WHR_VERIFIER_TIMEOUT (default 180s). A verifier takes ~19s on a host running many environments at once, and the old 30s cap failed runs for lack of CPU rather than for verifier behaviour.
Review report — Discogs mirror site (PR #34)Reviewer takeover of #34 by @hqhq1025. Draft PR: #109, head Asset: Verification summary
Read-only tasks leave the database byte-identical to seed. Each state task persists exactly Reproducing it./scripts/fetch_assets.sh
./scripts/build.sh webharbor:dev
docker run -d --rm --name wh-test -p 8201:8101 -p 41000-41024:40000-40024 webharbor:dev
python3 -m unittest discover -s sites/discogs/tests
python3 -m unittest discover -s sites/discogs/verify -p 'test_*.py'Discogs is site index 24. Registration is in sync across Grading does not depend on which host port you publish. The verifiers require every recorded What the review changed
Task set15 tasks, each with a deterministic verifier and a non-answer-leaking Limitations, stated plainly
|
|
Correction to the reproduce section above, found in a final standards audit against
This is the ordering CONTRIBUTING.md prescribes rather than an oversight: the pin is bumped Until then, build with the documented override, which is what every verification run in the ASSETS_REVISION=a990a311de354dc1dab85c31a498e6e287e99342 ./scripts/fetch_assets.sh
./scripts/build.sh webharbor:dev
docker run -d --rm --name wh-test -p 8201:8101 -p 41000-41024:40000-40024 webharbor:devAfter #76 merges, Two smaller items from the same audit, for completeness. The Discogs seed carries 32 |
|
The seed row counts in my previous comment are wrong. I wrote them from memory instead of
Where the wrong numbers came from, so you can judge how far the error spreads: 145 is the This affects only that comment. No verification result changes: the test suites, the build Apologies for the noise on your PR. |
main added two sites since this branch's base, so the three registration
places conflicted and discogs no longer fits at index 24 -- FedEx holds that
index, and therefore port 40024, on main. Appending discogs after webmd_doctor
puts it at index 26, port 40026, with 27 sites in the image.
Resolved by appending discogs last in websyn_start.sh, control_server.py and
the Dockerfile EXPOSE range, then following the consequences:
tasks.jsonl web -> http://localhost:40026/ in all 15 rows
test_environment_quality.py asserts that value; would have failed
test_verifiers.py fixture origins moved off 40024 (now FedEx), which
changes nothing about what is tested
docs port range and site count in README, CONTRIBUTING,
AGENTS, CLAUDE, agent_demo/README and the skills;
README's site list now names Discogs
The site itself is untouched by the merge: app.py, templates, seed database and
verifier logic are identical, so the questions, answers and acceptable paths do
not change. Grading is origin-agnostic -- it requires only that every recorded
step share one loopback origin -- so the frozen task executions remain valid
across this port move.
Verified on the merged tree: discogs application suite 48/48, verifier and
environment-quality suites 27/27. The 27-site integration build is not re-run
here; assets for twelve sites are absent locally and the host lacks the space.
|
Rebased onto current
Discogs moved from index 24 to index 26. FedEx holds index 24 on The port numbers in my two comments above are stale. Corrected: ASSETS_REVISION=a990a311de354dc1dab85c31a498e6e287e99342 ./scripts/fetch_assets.sh
./scripts/build.sh webharbor:dev
docker run -d --rm --name wh-test -p 8201:8101 -p 41000-41026:40000-40026 webharbor:devThat revision carries Re-verified on the merged tree, both in-container: Discogs application suite 48/48, One check is not re-run and I would rather say so than imply otherwise: the full 27-site |
…se relative times Two defects found while walking the authenticated task paths against the live site. "All" is the unfiltered view, not a folder, but it sat in COLLECTION_FOLDERS. So it was offered in the folder select, accepted by the write path, and then unreachable: the collection list treats folder == "All" as "do not filter", so a row stored with that folder could never be viewed as a folder again. Confirmed by posting one and finding it in the database. The template also rendered the tab row as ["All"] + COLLECTION_FOLDERS, which duplicated the tab. The sentinel now has its own name, UNFILTERED_FOLDER, and the template takes it from the route instead of hard-coding the literal a second time -- that duplication is what allowed the two meanings to drift apart. Relative timestamps had no singular form, so the forum showed "1 years ago", and the minute unit was abbreviated. Live Discogs writes "1 day ago" and "12 minutes ago", per the captured reference pages. Tests: three regressions covering the enum, a rejected folder writing no row, the tab row listing "All" exactly once, and eight relative-time cases. Application suite 51/51, verifier and environment-quality suites 27/27.
|
Head moved to
The sentinel now has its own name, Relative timestamps had no singular form, so the forum read "1 years ago", and minutes Three regression tests pin both: the enum, a rejected folder writing no row, the tab row Timestamps render on nearly every page, so all fifteen task runs were re-executed rather than
Read-only tasks still leave the database byte-identical to seed; each state task persists Unchanged from earlier comments: the 27-site image has still not been built and booted on |
…ex 28
main added two more sites since the last merge, and Healthline took index 26 --
the slot discogs held. Appending discogs after Kaggle puts it at index 28, port
40028, giving 29 sites in the image.
Conflicts were the same three registration places plus the port range and site
count in the docs, all resolved by taking main's text and then adding the 29th
site on top of it. Nothing in sites/discogs/ conflicted.
Followed through, as before:
tasks.jsonl web -> http://localhost:40028/ in all 15 rows
test_environment_quality.py asserts that value
test_verifiers.py fixture origins moved off 40026 (now Healthline)
docs range and count in README, CONTRIBUTING, AGENTS,
CLAUDE, agent_demo/README and the skills; README's
site list now names Discogs
The site is untouched by the merge: app.py, templates, seed and verifier logic
are identical, so the questions, answers and acceptable paths do not change.
Grading requires only that every recorded step share one loopback origin, so the
frozen executions remain valid across this second port move.
Application suite 51/51 on the merged tree.
|
Rebased onto current
Every port number in my earlier comments is stale. Discogs has been re-slotted twice during ASSETS_REVISION=a990a311de354dc1dab85c31a498e6e287e99342 ./scripts/fetch_assets.sh
./scripts/build.sh webharbor:dev
docker run -d --rm --name wh-test -p 8201:8101 -p 41000-41028:40000-40028 webharbor:devThe frozen task runs survived both re-slots, because grading requires only that every recorded
Two limitations stand, unchanged and stated plainly. The 15 executions were driven by me, with the answers already known. They show the tasks are The full multi-site image has not been built and booted on my machine. All 29 build steps
|
Merge upstream main at 7ace1c7, preserve NVIDIA at index 28, and append Discogs at index 29 (port 40029). Update registry declarations, task URLs, verifier fixtures, and active documentation to the 30-site range.
|
Merged the current NVIDIA remains at index 28 / port 40028. Discogs is appended at index 29 / Verification on the merged tree:
The Discogs application, templates, seed, and verifier logic are unchanged by |
Reviewer takeover of #34 by @hqhq1025. The original contributor commit is
preserved at the base of this branch; later commits are review work.
What this branch adds
The Discogs mirror, now registered as site index 29 / port 40029 in the current
30-site tree, plus 15 accepted tasks, one deterministic verifier per task, and a
non-answer-leaking
judge_rubricin every task row.Registration is in sync across
websyn_start.sh,control_server.py, theDockerfile
EXPOSErange, active documentation, and all Discogs task URLs.What was repaired during review
from the live site. Menus remain usable with JavaScript disabled.
placeholder identities and preserving source-native missing images.
without visiting both detail pages.
across origins, so alternate host ports remain gradeable.
sorting, external login redirects, malformed pagination, duplicate registration
fields, collection-folder sentinels, and relative-time pluralisation.
Verification at
b92d74dRead-only tasks leave the database byte-identical to seed. Each state task persists
exactly its requested change.
The current merge only integrates upstream NVIDIA and moves Discogs from index 28
to 29. The Discogs application, templates, seed, questions, and verifier logic are
byte-identical across the merge, so the frozen task runs and blind-review results
remain applicable.
Assets
The Discogs asset is fixed at immutable Hugging Face revision
a990a311de354dc1dab85c31a498e6e287e99342, proposed as dataset PR#76. The archive
was downloaded back from that revision and verified byte-for-byte before the
Discogs environment checks.
HF #76 is still open. The branch's default
.assets-revisionfollows currentupstream main and does not yet carry
discogs.tar.gz; conversely, the frozenDiscogs PR revision predates NVIDIA and does not carry
nvidia.tar.gz. There istherefore no single HF revision that prepares all 30 sites from a clean checkout
until maintainers merge #76 and bump
.assets-revisionto the resulting mainlineasset commit.
Disclosed limitations
known. They prove the tasks are completable and that the verifiers grade real
trajectories; they do not show how often an unaided agent discovers the paths.
source-fidelity and verifier audits.
authenticated chrome is aligned by inference.
merge's registry and port assignment are verified mechanically, and Discogs was
run in an isolated current-worktree preview. Full-image integration remains a
maintainer check, as previously disclosed.
This PR is ready for maintainer review and currently mergeable. HF #76 must be
merged and the final asset pin updated before a clean-clone release build.
Closes nothing on its own; #34 remains the original contribution of record.