mirror of
https://github.com/Shineii86/MiruroAPI.git
synced 2026-10-22 10:15:10 +00:00
pipe.js now tries 3 methods in order with automatic fallback: 1. Direct — mirror rotation (.ru → .to → .bz → .tv) with browser headers 2. ScraperAPI — free proxy (1K req/mo, no CC required) 3. FlareSolverr — self-hosted browser proxy (solves Cloudflare Turnstile) When one method fails (403/timeout), the next is tried automatically. Zero-config: works without any env vars. Add SCRAPER_API_KEY or FLARESOLVERR_URL for Cloudflare bypass. New endpoint: /api/pipe-health — tests all configured methods, reports latency and working/failed status, recommends preferred method. Files changed: - src/helpers/pipe.js — methodDirect(), methodScraperAPI(), methodFlareSolverr(), pipeHealthCheck() - src/routes/apiRoutes.js — added /api/pipe-health endpoint - .env.example — documented SCRAPER_API_KEY, FLARESOLVERR_URL Version bumped to 2.3.0 across package.json, server.js, /api/health, /api/openapi, public/openapi.json. CHANGELOG updated.
17 KiB
17 KiB
Changelog
v2.3.0
Self-Healing Fallback System — Auto-Recovery from Cloudflare Blocks
New: Multi-Method Fallback System
Pipe requests now try 3 methods in order with automatic fallback:
- Direct — mirror rotation across
.ru→.to→.bz→.tvwith browser headers - ScraperAPI — proxy through
api.scraperapi.com(free 1,000 req/month, no CC) - FlareSolverr — self-hosted browser proxy that solves Cloudflare Turnstile
When one method fails (403/timeout), the next is tried automatically. No manual intervention needed.
New Endpoint: /api/pipe-health
Diagnostic endpoint that tests all configured methods and reports:
- Which methods are working/failed
- Latency for each method
- Recommendation on preferred method
GET /api/pipe-health
→ { methods: { direct: {status:"ok"}, scraperapi: {status:"skipped"} }, working: 1, ... }
Configuration (all optional, zero-config to start)
| Env Var | Purpose | Free? |
|---|---|---|
SCRAPER_API_KEY |
ScraperAPI proxy | Yes (1K req/mo) |
FLARESOLVERR_URL |
FlareSolverr browser | Yes (self-hosted) |
PIPE_OBF_KEY |
XOR decode key | N/A |
How it works
Client → /api/episodes/20
↓ pipeRequest()
├─ Try direct → 403 (Cloudflare block)
├─ Try ScraperAPI → 200 ✓ (returns data)
└─ Cache result, return to client
Files Changed
src/helpers/pipe.js— rewritten withmethodDirect(),methodScraperAPI(),methodFlareSolverr(),pipeHealthCheck()src/routes/apiRoutes.js— added/api/pipe-healthendpoint.env.example— documentedSCRAPER_API_KEY,FLARESOLVERR_URL
Notes
- Zero-config: works without any env vars (direct only)
- Add
SCRAPER_API_KEYfor free Cloudflare bypass (no server needed) - Add
FLARESOLVERR_URLfor self-hosted browser bypass (needs Docker/VPS) - All methods use the same pipe protocol (base64+gzip, x-obfuscated header)
v2.2.0
Critical Fix — Miruro Pipe Protocol Migration (Streaming Endpoints Restored)
Diagnostic Summary
- Full diagnostic sweep of all live
/api/*endpoints againstmirurotvapi.vercel.app - AniList-backed endpoints (
/search,/trending,/info,/popular,/top, …) — confirmed all 200/healthy - Streaming endpoints (
/episodes,/sources,/stream,/watch,/download) — all 500 - Deep-scanned the Miruro frontend (
miruro.to/.bz/.ru) bundles +env2.jsto reverse-engineer the new pipe contract
Root Cause (streaming failure)
- Dead data source —
pipe.jstargetedhttps://www.miruro.tv/api/secure/pipe, which is now hard-blocked by Cloudflare (returns 403 "Sorry, you have been blocked" page). - Stale decode protocol — the old
decode()always didbase64url → XOR(PIPE_OBF_KEY) → gunzip. Miruro's pipe now signals the scheme via a response header:x-obfuscatedabsent → plain JSONx-obfuscated: 1→base64url(gzip(json))(no XOR)x-obfuscated: 2→base64url(XOR(gzip(json)))withPIPE_OBF_KEY- The hard-coded always-XOR decode corrupted the new
:1payloads.
Fixes
src/helpers/pipe.js- New mirror rotation list:
miruro.ru→miruro.to→miruro.bz→miruro.tv, iterating one mirror per retry. - New header-driven
decodePipeResponse(text, obfHeader)supporting plain / scheme-1 / scheme-2. - Browser-accurate request headers (UA +
Accept,Accept-Language, fullsec-ch-ua/sec-fetch-*family) to pass Cloudflare bot fingerprinting rather than just UA+Referer. - Request payload reverted to plain base64url of the JSON (no XOR on the request) matching the current client.
- Subtitle-proxy referer updated to canonical
https://www.miruro.to/. - Default
maxRetriesbumped 3 → 4 so each mirror gets an attempt; 403/444 now rotate instead of failing.
- New mirror rotation list:
api/proxy.js— default CDN referer/Origin switched from the deadmiruro.tvto the canonicalmiruro.to.- Version bump to
2.2.0acrosspackage.json,server.jsbanner,/api/health,/api/openapi, andpublic/openapi.json.
Notes
- Streaming endpoints depend on Miruro's upstream pipe, which sits behind Cloudflare bot protection and may intermittently rate-limit datacenter egress IPs. The new rotation + browser headers + retry logic maximizes success; AniList endpoints are unaffected and remain fully healthy.
v2.1.4
Security Hardening, Bug Fixes, Code Quality Improvements
Security
- XOR keys moved to env vars —
PRU_PROXY_KEYandPIPE_OBF_KEYno longer hardcoded in source (proxy.js, pipe.js) - CORS restricted in production — returns 403 when
ALLOWED_ORIGINSis set and origin doesn't match - Input sanitization — new
sanitizeId()andsanitizeString()helpers applied to all route params (character, staff, studio, genre, year, status, format, season) - Security headers in vercel.json — added at CDN level for faster response
Bug Fixes
- multi-search — now actually combines query + filters (was ignoring
qwhen filters present) filterAnime— addedsearchparameter andSEARCH_MATCHsort optiongetTrendingWeekly— now returns 40 results (was identical to daily with 20)calendar— fetches 200 results instead of 50 (was missing late-month shows)getBestStream— improved quality matching (checks quality/label fields), supports HLS+DASH, better fallbackdeepTranslate— now returns deep clone instead of mutating in-place (prevents cache corruption)- Version strings — updated to 2.1.3 in server.js and test.js
Code Quality
- Deleted
server.py— dead Flask code, not used on Vercel - Rate limiter — aggressive cleanup on serverless (prunes empty entries every request)
stats/genre— usesPromise.allSettledfor parallel execution (faster, safer)
Config
- vercel.json — added security headers at CDN level
- .env.example — added
PRU_PROXY_KEY,PIPE_OBF_KEYdocumentation
v2.1.3
Diagnostic Sweep — Bug fixes, security, AniList query corrections
Full Diagnostic Sweep Results
- Tested all 44 endpoints across 10 sections
- Found and fixed 5 bugs
- Added missing security headers
Bug Fixes
- Tags endpoint:
data.TagCollection→data.MediaTagCollection(was returning empty array) - Random endpoint: Added
Cache-Control: no-storeheaders +Date.now() % 499for true randomness (CDN was caching rapid requests) - Character/Staff 404: Now returns HTTP 404 instead of 500 on not-found
- Character query: Removed
dateOfDeath(not in AniList schema),role→characterRole - Staff query: Removed
dateOfDeathand invalidrolefield - Studio query: Removed
type: ANIMEfromStudio.media(not supported by AniList) - Tags query:
TagCollection→MediaTagCollection, removedrankfield - Trending: Removed invalid
trending: 7/30args (not in AniList schema)
Security
- Added
X-XSS-Protection: 1; mode=blockheader
Pipe Resilience
- Added
pipeRequest()helper with retry logic and exponential backoff (3 attempts: 1s, 2s, 4s delays) - Cached episodes (5 min) and sources (10 min) responses
- Confirmed kiwi/bonk CDNs serve real content, bee/ally serve decoys
- Fixed
getWatchSourcesslug matching for both raw and slugged episode IDs
Performance
- Fastest:
/providers~0.8s (static data) - Average: Most endpoints ~1.0-2.0s
- Slowest:
/stats/genre~5.7s (10 AniList queries)
v2.1.2
Streaming Architecture — pru proxy + raw CDN URLs
Streaming Pipeline Discovery
- Decoded pru.ultracloud.cc URL format:
base64url(XOR(url, key))~base64url(XOR(referer, key))/pl.m3u8 - Key:
a54d389c18527d9fd3e7f0643e27edbe(16-byte XOR) - pru rewrites ALL M3U8 URLs (master, variant, segments) to proxy through itself
- CDN at mt.nekostream.site serves decoy PNG images to all server-side requests
Proxy Changes
/api/proxynow handles both pru-encoded URLs (decodes + re-encodes) and direct CDN URLs (for subtitles)- Stream URLs returned as raw CDN URLs (browser loads directly — CDN has CORS *)
- Subtitle URLs proxied through
/api/proxy(third-party CDNs may lack CORS) - Added
Origin: https://www.miruro.tvheader to pipe requests
Known Limitations
- Pipe sources endpoint returns 444 from Cloudflare for datacenter IPs
- Client-side pipe blocked by CORS (only allows miruro.tv origin)
- CDN segments serve PNG decoys to server IPs
- Video playback requires further investigation — likely needs miruro.tv domain or alternative streaming source
v2.1.1
Bug Fix — Pipe response XOR decoding
Fix
decodePipeResponsenow XOR-decodes with obfuscation key before gzip decompression — pipe was returning XOR+gzip, not plain gzip- Updated pipe version from
0.1.0to0.2.0to match miruro.tv getWatchSourcesnow properly returns streams (was always failing before this fix)
v2.1.0
Major Feature Update — Provider capabilities, enriched metadata, skip times
New Endpoints
- GET /api/providers — Provider capabilities and configuration (12 providers with full metadata)
Anime Info Enrichment
- Added
alternateName— multiple language titles from synonyms - Added
aggregateRating— rating with count, mean score - Added
sameAs— external links (AniList, MAL, official sites) - Added
externalLinks— structured external links with site/type - Added
productionCompany— non-animation studios - Added
animationStudio— animation studios - Added
trailer— anime trailer info - Added
nextAiringEpisode— next episode air time - Added
tags— simplified tag names array
Streaming Improvements
- Added
extractSkipTimes— extract OP/ED skip timestamps from sources - Added
skipTimesfield to /stream and /watch responses - Episode thumbnails already included in pipe response
Provider Capabilities (from miruro.tv SSR_CONFIG)
- kiwi: sub, download
- pewe: sub
- bonk: sub, ssub, download, skip_times
- bee: ssub
- ally: sub, download, thumbnails
- moo: sub, download
- hop: ssub, thumbnails
- nun: sub (embed of ally)
- bun: ssub (embed of bee)
- twin: sub, ssub (embed of bonk)
- cog: sub (embed of moo)
- telli: sub (embed of kiwi, hidden)
v2.0.1
Streaming Improvements — Better subtitle extraction, quality fallback
Streaming Enhancements
- Improved
extractSubtitles— now handles multiple provider formats (bonk: file/label/kind/language, others: url/name/lang) - Updated
getBestStream— falls back to first active HLS stream when quality metadata is missing - Updated
getDownloadUrl— now returns subtitles and bestStream in response - Added subtitle fields: url, label, language, kind, format, encoding, isDefault
Provider Improvements
- Bonk provider confirmed to return subtitles (English, VTT format, captions kind)
- Better handling of providers without quality metadata (bonk, ally, bee return undefined quality)
Verified
- Subtitle extraction working: bonk provider returns 1 English subtitle per episode
- Download URL working: bonk provider returns direct download link
- Batch sources: subtitles included in batch responses
v2.0.0
Major Release — 35 endpoints, streaming improvements, new features
Technical Foundation
- Added gzip compression middleware (30-70% response size reduction)
- Added request logging with method, path, status, duration, IP
- Added Cache-Control headers for API responses (varies by endpoint type)
- Improved CORS with preflight caching (24h max-age)
- Health endpoint now includes memory stats (heap, RSS), cache size, node version
New AniList Helpers (11 new functions)
- getAllGenres — complete genre list from AniList
- getAllTags — complete tag list with metadata
- getTopAnime — top-rated anime of all time (SCORE_DESC)
- getTrendingDaily — trending anime (last 7 days)
- getTrendingWeekly — trending anime (last 30 days)
- getSeasonalAnime — anime by year + season (e.g., 2025/Spring)
- getAnimeByStudio — anime produced by a specific studio
- getCharacterInfo — character detail with anime list
- getStaffInfo — staff detail with anime list
- searchCharacters — search characters by name
- searchStaff — search staff by name
New Streaming & Download Features
- extractSubtitles — extract subtitle URLs from sources
- getBestStream — automatic quality fallback (1080p → 720p → 360p)
- getDownloadUrl — dedicated download URL endpoint
- getBatchSources — fetch multiple episode sources in parallel
New API Endpoints (17 new)
- GET /api/trending/daily — daily trending anime
- GET /api/trending/weekly — weekly trending anime
- GET /api/top — top anime by score
- GET /api/random — random anime of the day
- GET /api/multi-search — combined query + filters
- GET /api/season/:year/:season — seasonal anime
- GET /api/studio/:name — anime by studio
- GET /api/genres — all genres list
- GET /api/tags — all tags list
- GET /api/genre/:name — anime by genre
- GET /api/year/:year — anime by year
- GET /api/status/:status — anime by status
- GET /api/format/:format — anime by format
- GET /api/character/:id — character detail
- GET /api/staff/:id — staff detail
- GET /api/characters — search characters
- GET /api/staff — search staff
- GET /api/episodes/:id/batch — batch episode sources
- GET /api/stream — streaming with quality fallback
- GET /api/download — download URL
- GET /api/compare/:id1/:id2 — compare two anime
- GET /api/stats/genre — genre statistics
- GET /api/calendar — monthly airing calendar
- GET /api/timeline/:id — anime release timeline
Streaming Improvements
- Subtitle URL extraction from pipe responses
- Quality fallback: tries 1080p → 720p → 480p → 360p automatically
- Batch episode fetching (up to 5 parallel requests)
- Dedicated download endpoint with provider metadata
- Cache headers: episodes/sources (2min), info (5min), genres/tags (24h)
Version synced to 2.0.0 across all files
v1.4.0
- Added creator attribution middleware — injects author info into every response
- Fixed Vercel deployment: replaced legacy
builds/routesconfig with modernfunctionsconfig - Added
api/index.jsserverless entry point - Security headers: removed deprecated
X-XSS-Protection, addedStrict-Transport-Security(HSTS) - Rate limiter: uses
x-forwarded-forheader for correct IP detection on Vercel - Rate limiter: added periodic IP entry pruning when >200 IPs tracked
- Cache: added periodic expired entry cleanup when cache reaches 80% capacity
- Version synced to 1.4.0
v1.3.0
- Full landing page upgrade to match AniKotoAPI style
- Added canvas particle effects with cyan-colored floating particles
- Added scroll-reveal animations (IntersectionObserver)
- Added animated stat counters that count up on scroll
- Added infinite scrolling marquee with 8 feature badges
- Added live interactive API console with 5 preset endpoint buttons
- Added sidebar endpoint explorer with 16 endpoints and multi-language code tabs
- Added 4 interactive playground cards (Search, Info, Episodes, Trending)
- Added custom scrollbar styling
- Added JetBrains Mono font for code blocks
- Added 4-column grid footer
- Added fixed header with scroll-aware blur/glass effect
- Added ambient orb gradient animations
- Added CTA section with gradient overlay
- Color scheme updated to match MiruroAPI brand (cyan #38bdf8 + indigo #818cf8)
- All branding updated: AniKotoAPI references → MiruroAPI
- OG/Twitter meta tags updated for mirurotvapi.vercel.app
- JSON-LD structured data updated
- Real Miruro SVG favicons used in header and footer
v1.2.0
- Fixed critical response format bug: all endpoints now return {success: true, results: data}
- Root cause: createApiRoutes() had (app, jsonResponse, jsonError) but was called with (jsonResponse, jsonError), shifting all params
- Every jsonResponse() call was actually calling jsonError(), returning {success: false, message: data}
- Health endpoint worked because it used res.json() directly, bypassing the wrapper
- All 18 endpoints verified working
v1.1.0
- Added Swagger UI interactive docs at /docs
- Added OpenAPI 3.0 spec at /openapi.json
- Added mappings field in episodes response
- Added Docker support (Dockerfile + .dockerignore)
- Improved landing page with premium design
- Added "Try it" buttons on all endpoints
- Health endpoint now includes version, providers list, and endpoint count
- Version bump to 1.1.0
v1.0.0
- Initial release
- AniList GraphQL integration for anime metadata
- Miruro pipe integration for streaming sources
- 16 API endpoints: search, suggestions, trending, popular, upcoming, recent, spotlight, schedule, filter, info, characters, relations, recommendations, episodes, sources, watch
- In-memory caching with TTL
- CORS support
- Health endpoint
- Deployed on Vercel