diff --git a/docs/projects/modpackchecker-status-2026-04-06.md b/docs/projects/modpackchecker-status-2026-04-06.md new file mode 100644 index 0000000..c04ea06 --- /dev/null +++ b/docs/projects/modpackchecker-status-2026-04-06.md @@ -0,0 +1,277 @@ +# ModpackChecker Development Status Report + +**Date:** April 6, 2026 +**Task:** #26 - Modpack Version Checker (Blueprint Extension) +**Status:** Development Paused — Awaiting Hybrid Detection Implementation +**Chronicler:** #63 + +--- + +## Executive Summary + +ModpackChecker is functionally complete but **not commercially viable** in its current state. The extension requires manual egg variable configuration per server, which is unacceptable for: +- Michael's 21 production servers +- BuiltByBit customers expecting plug-and-play + +**Next milestone:** Implement hybrid auto-discovery system before BuiltByBit launch. + +--- + +## What Works ✅ + +### Core Functionality +- **Dashboard Badge:** Colored dot next to server names (orange=update, cyan=current) +- **Console Widget:** StatBlock-style card in right column with click-to-check +- **Admin Panel:** CurseForge API key config, dark theme callouts, PRO tier badges +- **API Routes:** Clean URLs, no double-prefixing +- **4-Platform Support:** CurseForge, Modrinth, FTB, Technic +- **Rate Limiting:** 2 requests/minute per server, 429 handling in UI +- **Caching:** 60-second TTL on dashboard, 12-hour Technic build cache + +### Code Quality +- Centralized `ModpackApiService` for all API calls +- Short error codes in UI ("Not configured", "Wait 60s", "API error") +- Gemini-reviewed architecture (4 batch review complete) +- Proper authorship (Firefrost Gaming / Frostystyle) + +--- + +## What's Broken ❌ + +### Blueprint Packaging Issues + +**Problem:** Blueprint production install behaves differently than dev mode. + +| Issue | Dev Mode | Production Install | +|-------|----------|-------------------| +| `build.sh` execution | ✅ Runs | ❌ Does NOT run | +| App files (Controllers, Services, Commands) | Auto-copied via conf.yml | ❌ Stays in `.blueprint/extensions/` subfolder | +| Frontend injection | Via build.sh sed commands | ❌ Must use conf.yml wrapper fields | +| File locations | `.blueprint/dev/` | `.blueprint/extensions/modpackchecker/` (reorganized) | + +**Root Cause:** Our `conf.yml` uses `requests.app: "app"` which tells Blueprint where source files are, but we relied on `build.sh` to inject React components. Blueprint doesn't run build.sh on `blueprint -install`. + +**Solution Required:** Rewrite `conf.yml` to use Blueprint's native wrapper injection fields OR find the correct production deployment method. + +### Manual Deployment Steps Required (Live Panel) + +When installing on a fresh panel, these manual steps were required: + +```bash +# 1. Copy PHP files to correct locations +cp .blueprint/extensions/modpackchecker/app/Http/Controllers/ModpackAPIController.php /var/www/pterodactyl/app/Http/Controllers/ +cp .blueprint/extensions/modpackchecker/app/Services/ModpackApiService.php /var/www/pterodactyl/app/Services/ +cp .blueprint/extensions/modpackchecker/app/Console/Commands/CheckModpackUpdates.php /var/www/pterodactyl/app/Console/Commands/ + +# 2. Copy React components +cp .blueprint/extensions/modpackchecker/views/server/wrapper.tsx /var/www/pterodactyl/resources/scripts/components/server/ModpackVersionCard.tsx +cp .blueprint/extensions/modpackchecker/views/dashboard/UpdateBadge.tsx /var/www/pterodactyl/resources/scripts/components/dashboard/UpdateBadge.tsx + +# 3. Inject into AfterInformation.tsx +cat > /var/www/pterodactyl/resources/scripts/blueprint/components/Server/Terminal/AfterInformation.tsx << 'EOF' +import React from 'react'; +import ModpackVersionCard from "@/components/server/ModpackVersionCard"; +/* blueprint/import */ +export default () => { + return ( + <> + {/* blueprint/react */} + + + ); +}; +EOF + +# 4. Inject UpdateBadge into ServerRow.tsx +sed -i '1i import UpdateBadge from "@/components/dashboard/UpdateBadge";' /var/www/pterodactyl/resources/scripts/components/dashboard/ServerRow.tsx +sed -i 's|{server.name}

|{server.name}

|' /var/www/pterodactyl/resources/scripts/components/dashboard/ServerRow.tsx + +# 5. Rebuild +composer dump-autoload +php artisan optimize:clear +export NODE_OPTIONS=--openssl-legacy-provider && yarn build:production +``` + +### UX Blocker — Egg Variable Dependency + +**The showstopper:** ModpackChecker requires these egg variables per server: +- `MODPACK_PLATFORM` (curseforge, modrinth, ftb, technic) +- `MODPACK_ID` (platform-specific ID) +- `MODPACK_CURRENT_VERSION` (optional, for update detection) + +**Problem:** Standard Forge/NeoForge/Fabric eggs don't have these variables. Adding them requires: +- Modifying every egg +- Configuring every server +- Teaching customers how to find modpack IDs + +This is unacceptable for commercial release. + +--- + +## Gemini's Recommended Solution + +### Hybrid Auto-Discovery + Self-Service Model + +**Phase 1: Auto-Discovery (Cron Job)** +``` +1. Check egg variables (fastest) +2. If missing → Read manifest.json via DaemonFileRepository (CurseForge) +3. If missing → Read modrinth.index.json (Modrinth) +4. Save to DB with detection_method = 'egg' | 'file' | 'manual' +``` + +**Phase 2: Self-Service Fallback (Console Widget)** +- If unconfigured: Show "Configure Manually" button +- Modal lets server owner select platform + paste modpack ID +- Saves to DB with `detection_method = 'manual'` +- `is_user_overridden = true` prevents cron from overwriting + +### Implementation Details + +**DaemonFileRepository Usage:** +```php +use Pterodactyl\Repositories\Wings\DaemonFileRepository; + +private function detectCurseForge(Server $server): ?string +{ + try { + $this->fileRepository->setServer($server); + $content = $this->fileRepository->getContent('manifest.json'); + $manifest = json_decode($content, true); + return $manifest['projectID'] ?? null; + } catch (\Exception $e) { + return null; + } +} +``` + +**Database Schema Additions:** +```php +$table->string('detection_method')->default('unknown'); // egg, file, manual +$table->boolean('is_user_overridden')->default(false); // prevents auto-overwrite +``` + +**Critical Warning from Gemini:** +- File detection via Wings API is a network call +- **NEVER do this on page load** — only in cron job +- CurseForge fingerprinting is **rejected** — too resource intensive + +--- + +## File Locations + +### Repository +``` +firefrost-services/services/modpack-version-checker/ +├── blueprint-extension/ # Source code +│ ├── conf.yml +│ ├── build.sh +│ ├── README.md +│ ├── CHANGELOG.md +│ ├── icon.png +│ ├── app/ +│ │ ├── Console/Commands/CheckModpackUpdates.php +│ │ ├── Http/Controllers/ModpackAPIController.php +│ │ └── Services/ModpackApiService.php +│ ├── admin/ +│ │ ├── controller.php +│ │ └── view.blade.php +│ ├── database/migrations/ +│ ├── routes/client.php +│ └── views/ +│ ├── server/wrapper.tsx +│ └── dashboard/UpdateBadge.tsx +└── releases/ + └── modpackchecker-1.0.0.blueprint # Packaged (has issues) +``` + +### Dev Panel (64.50.188.128) +- Extension dev folder: `/var/www/pterodactyl/.blueprint/dev/` +- Works correctly in dev mode + +### Live Panel (45.94.168.138) +- Extension folder: `/var/www/pterodactyl/.blueprint/extensions/modpackchecker/` +- Required manual file copying (see above) +- Panel version: 1.12.1 (dev is 1.12.2) + +--- + +## API Endpoints + +``` +POST /api/client/extensions/modpackchecker/servers/{server}/check + → Manual version check, rate limited 2/min + +GET /api/client/extensions/modpackchecker/status + → Returns cached status for all user's servers +``` + +--- + +## Testing Notes + +### CurseForge Test Data +- **FTB StoneBlock 4:** Project ID `1373378` +- Latest version as of April 2026: `1.9.6` + +### Modrinth Test Data (no API key needed) +- **Adrenaserver:** Slug `adrenaserver` + +--- + +## Next Steps (Task #95) + +### Priority 1: Hybrid Detection System +1. Add `detection_method` and `is_user_overridden` columns to migration +2. Inject `DaemonFileRepository` into `CheckModpackUpdates` command +3. Implement `detectCurseForge()` and `detectModrinth()` methods +4. Update cron logic: egg vars → file detection → skip if manual override +5. Test on live panel with real modpack servers + +### Priority 2: Self-Service UI +1. Update `wrapper.tsx` with "Configure Manually" button +2. Create configuration modal (Platform dropdown + ID input) +3. Add new API endpoint: `POST /servers/{server}/configure` +4. Store manual config with `is_user_overridden = true` + +### Priority 3: Fix Blueprint Packaging +1. Research Blueprint's native wrapper injection (`conf.yml` fields) +2. Eliminate dependency on `build.sh` for production installs +3. Re-test full install cycle on clean panel +4. Update `modpackchecker-1.0.0.blueprint` package + +### Priority 4: Documentation +1. Update README with hybrid detection explanation +2. Document supported manifest file formats +3. Add troubleshooting section +4. Screenshot gallery for BuiltByBit listing + +--- + +## Commits Today + +| Hash | Message | +|------|---------| +| 35315c2 | Batch 1 fixes - routes, migration, build.sh | +| 8e37120 | Batch 2 fixes - ModpackApiService, rate limiting | +| 5a607c8 | Batch 3+4 fixes - frontend, admin, docs | +| d735e3d | Wizard review fixes - UI polish | +| c160647 | Move card to right column, StatBlock style | +| 05d2164 | Console card redesign - short error codes | +| 6e15a62 | Update website link to Discord | +| 1a3e884 | Release v1.0.0 packaged blueprint file | +| e59ee04 | Fix check_interval validation (nullable) | + +--- + +## Gemini Consultations + +All saved in `docs/consultations/`: +- `gemini-blueprint-confyml-2026-04-06.md` +- `gemini-technic-api-fix-2026-04-06.md` +- `gemini-batch1-review.md` through `gemini-batch4-review.md` +- `gemini-modpack-detection-consultation.md` (today's UX pivot) + +--- + +*Fire + Frost + Foundation = Where Love Builds Legacy* 💙🔥❄️