diff --git a/README.md b/README.md index 0142558..47925e7 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,8 @@ # Campaign Creator TUI **Quick use:** -`deno task tui` or `deno task validate`, `deno task generate`, `deno task deploy -- --dry-run`. \ No newline at end of file +`deno task tui` or `deno task validate`, `deno task generate`, `deno task deploy -- --dry-run`. + +## Requirements + +* [Custom Campaigns](https://github.com/monkeymanboy/BeatSaberCustomCampaigns/releases) diff --git a/data/campaign.inventory.json b/data/campaign.inventory.json index 3a1fcd0..eb7f0c5 100644 --- a/data/campaign.inventory.json +++ b/data/campaign.inventory.json @@ -38,6 +38,87 @@ "requirements": [], "notes": "", "purpose": "" + }, + { + "index": 1, + "name": "Droobix's Breezer", + "songid": "43a47", + "hash": "4944e7285d06bd452c0e7089e1e94bdfd807626f", + "customDownloadURL": "", + "characteristic": "Standard", + "difficulty": 1, + "modifiers": { + "disappearingArrows": false, + "strictAngles": false, + "fastNotes": false, + "noBombs": false, + "failOnSaberClash": false, + "instaFail": false, + "noFail": false, + "batteryEnergy": false, + "ghostNotes": false, + "noArrows": false, + "speedMul": 1, + "energyType": 0, + "enabledObstacleType": 0 + }, + "requirements": [], + "notes": "", + "purpose": "test message" + }, + { + "index": 2, + "name": "Ramen Noodle's Be There For You", + "songid": "112aa", + "hash": "ad77a5fb3fa53792c341359c07da841d735c3c71", + "customDownloadURL": "", + "characteristic": "Standard", + "difficulty": 4, + "modifiers": { + "disappearingArrows": false, + "strictAngles": false, + "fastNotes": false, + "noBombs": false, + "failOnSaberClash": false, + "instaFail": false, + "noFail": false, + "batteryEnergy": false, + "ghostNotes": false, + "noArrows": false, + "speedMul": 1, + "energyType": 0, + "enabledObstacleType": 0 + }, + "requirements": [], + "notes": "", + "purpose": "" + }, + { + "index": 3, + "name": "TGF Gamesta's Rum N Bass", + "songid": "31fe8", + "hash": "abb471ab6ab77d2146d93d97f949ffec9c8d736a", + "customDownloadURL": "", + "characteristic": "Standard", + "difficulty": 4, + "modifiers": { + "disappearingArrows": false, + "strictAngles": false, + "fastNotes": false, + "noBombs": false, + "failOnSaberClash": false, + "instaFail": false, + "noFail": false, + "batteryEnergy": false, + "ghostNotes": false, + "noArrows": false, + "speedMul": 1, + "energyType": 0, + "enabledObstacleType": 0 + }, + "requirements": [], + "notes": "", + "purpose": "" } ] } diff --git a/deno.json b/deno.json index 62fdd5d..d9214ad 100644 --- a/deno.json +++ b/deno.json @@ -8,7 +8,7 @@ "generate": "deno run -A ./tools/cli.ts generate", "deploy": "deno run -A ./tools/cli.ts deploy", "check": "deno check ./tools/**/*.ts && deno lint ./tools", - "test": "deno test -A ./tools/lib/mission-markdown_test.ts" + "test": "deno test -A ./tools/lib/" }, "imports": { "@std/assert": "jsr:@std/assert@^1.0", diff --git a/tools/lib/beatsaver.ts b/tools/lib/beatsaver.ts index 761ee5b..9f77bc0 100644 --- a/tools/lib/beatsaver.ts +++ b/tools/lib/beatsaver.ts @@ -87,10 +87,15 @@ export async function fetchBeatSaverByHash( return mapBeatSaverResponseToMeta(data); } +/** Strip Twitch-style `!bsr` prefix when pasting a map key (e.g. `!bsr 43a47` → `43a47`). */ +export function normalizeBeatSaverLookupInput(input: string): string { + return input.trim().replace(/^!bsr\s*/i, "").trim(); +} + export async function resolveBeatSaverMeta( input: string, ): Promise { - const s = input.trim(); + const s = normalizeBeatSaverLookupInput(input); if (!s) return null; if (/^[a-f0-9]{40}$/i.test(s)) { return await fetchBeatSaverByHash(s); diff --git a/tools/lib/beatsaver_test.ts b/tools/lib/beatsaver_test.ts new file mode 100644 index 0000000..76e8e1b --- /dev/null +++ b/tools/lib/beatsaver_test.ts @@ -0,0 +1,19 @@ +import { assertEquals } from "@std/assert"; +import { normalizeBeatSaverLookupInput } from "./beatsaver.ts"; + +Deno.test("normalizeBeatSaverLookupInput strips !bsr prefix with space", () => { + assertEquals(normalizeBeatSaverLookupInput("!bsr 43a47"), "43a47"); +}); + +Deno.test("normalizeBeatSaverLookupInput strips !BSR and trims", () => { + assertEquals(normalizeBeatSaverLookupInput(" !BSR abc12 "), "abc12"); +}); + +Deno.test("normalizeBeatSaverLookupInput strips !bsr without space before key", () => { + assertEquals(normalizeBeatSaverLookupInput("!bsr43a47"), "43a47"); +}); + +Deno.test("normalizeBeatSaverLookupInput leaves hash unchanged", () => { + const h = "a".repeat(40); + assertEquals(normalizeBeatSaverLookupInput(h), h); +});