Files
KeelrLeek a667b4b28e Baseline: full tree snapshot after git repository loss
The previous .git directory was found gutted (only info/ remained), so
history is unrecoverable locally. This commit restores version control
with the tree exactly as it stands: the working app, the preview-tracks
launcher on the artist hero, the scrollable-track-previews design bundle
(docs + approved mockups), and the Phase 0 validation artifacts.
2026-07-22 17:57:00 -05:00

125 lines
3.4 KiB
Rust

//! Broad discography audit over the PRODUCTION artist pipeline.
//!
//! Runs `catalog_artist` (Deezer + Apple supplement, dedup, edition folding)
//! plus the deferred `catalog_artist_identity` MusicBrainz pass for each
//! requested artist, and prints one JSON object per artist (JSONL) with the
//! final album rows and MB type hints — exactly the data the artist page
//! files into tabs. An external analyzer replicates the frontend's category
//! rules over this dump to flag duplicates and misfiled releases.
//!
//! Usage:
//! cargo run -p metadata --example discography_audit -- "Artist" ...
//! cargo run -p metadata --example discography_audit -- --broad
use metadata::MetadataClient;
use std::sync::Arc;
const BROAD_ARTISTS: [&str; 44] = [
"Weezer",
"Radiohead",
"Queen",
"The Beatles",
"Taylor Swift",
"Beyoncé",
"Coldplay",
"Nirvana",
"Fleetwood Mac",
"Elton John",
"David Bowie",
"Pink Floyd",
"Led Zeppelin",
"Bob Dylan",
"Miles Davis",
"Daft Punk",
"deadmau5",
"Fatboy Slim",
"Bonobo",
"Four Tet",
"Calvin Harris",
"Aphex Twin",
"The Chemical Brothers",
"Crazy P",
"Moby",
"Björk",
"Depeche Mode",
"Kanye West",
"Kendrick Lamar",
"Eminem",
"Drake",
"Travis Scott",
"Hans Zimmer",
"John Williams",
"Danny Elfman",
"Ludwig Göransson",
"Nine Inch Nails",
"MGMT",
"Panda Bear",
"Tame Impala",
"Mac DeMarco",
"Gorillaz",
"Metallica",
"ABBA",
];
#[tokio::main]
async fn main() {
let mut requested: Vec<String> = std::env::args().skip(1).collect();
if requested.iter().any(|a| a == "--broad") {
requested = BROAD_ARTISTS.iter().map(|s| s.to_string()).collect();
}
if requested.is_empty() {
eprintln!("pass artist names or --broad");
std::process::exit(2);
}
let client = Arc::new(MetadataClient::new());
for name in requested {
let search = client.catalog_search(&name).await;
let want = normalize(&name);
let artist = search
.artists
.iter()
.filter(|a| normalize(&a.name) == want)
.max_by_key(|a| a.fans)
.or_else(|| search.artists.first());
let Some(artist) = artist else {
println!(
"{}",
serde_json::json!({ "requested": name, "error": "not_found" })
);
continue;
};
let id = artist.id;
let display = artist.name.clone();
let fans = artist.fans;
let page = client.catalog_artist(id).await;
let Some(page) = page else {
println!(
"{}",
serde_json::json!({ "requested": name, "artist_id": id, "error": "page_failed" })
);
continue;
};
let identity = client.catalog_artist_identity(id, &display).await;
println!(
"{}",
serde_json::json!({
"requested": name,
"artist_id": id,
"artist": display,
"fans": fans,
"albums": page.albums,
"type_hints": identity.type_hints,
"identity_albums": identity.albums,
})
);
}
}
fn normalize(s: &str) -> String {
s.to_lowercase()
.chars()
.filter(|c| c.is_alphanumeric())
.collect()
}