A high-performance Golang service designed to parse iOS IPA files directly from remote URLs using HTTP Range requests. It extracts critical metadata, generates Apple OTA Manifests (.plist), and handles app icons with advanced optimization.
- ⚡ Blazing Fast Remote Parsing: Uses HTTP Range requests to read only the necessary ZIP headers and
Info.plist. No need to download the entire IPA file. - 🛡️ Hardened Security & Resilience:
- SSRF Protection: Prevents access to internal networks (IPv4 and IPv6 private/link-local ranges).
- DNS Rebinding Protection: Re-validates target IPs on every redirect.
- HTTP Range Retries: Automatically retries failed range requests (up to 3 times with backoff) to handle unstable remote servers.
- URL Normalization: Automatically decodes and re-encodes URLs to ensure standard format (e.g., handling spaces as
%20). - Rate Limiting: Configurable RPS and burst limits via environment variables.
- 📦 Optimized Performance:
- Gzip Compression: API responses are compressed to minimize bandwidth.
- Streaming Extraction: Icons are processed using streams to maintain a low memory footprint.
- SHA256 Hashing: Uses robust SHA256 for deterministic asset mapping.
- 📊 Production Ready:
- Graceful Shutdown: Handles OS signals to finish pending tasks and close connections cleanly.
- Detailed Error Reporting: Returns specific causes for parsing failures (e.g., server errors) for better debugging.
- Structured Logging: Production-ready JSON logs via Go's
slog.
- 🔄 Asynchronous Asset Extraction:
- Manifests: Automatically generated and cached in the background.
- Icons: Extracted and "de-crushed" (CgBI to standard PNG) in the background.
- 🧹 Auto-Maintenance: Built-in worker automatically cleans up stale assets.
- Go 1.21 or higher
./build.sh
# or
go build -o ipa-parser .# Using environment variables
PORT=7004 RATE_LIMIT_RPS=10 RATE_LIMIT_BURST=20 ./ipa-parserPOST /parse
Request Body:
{
"url": "https://example.com/app.ipa"
}Success Response (200 OK):
{
"success": true,
"ipa": {
"name": "My App",
"version": "1.0.0",
"build": "101",
"bundle_id": "com.example.app",
"icon": { "url": "https://api.example.com/icon/a1b2c3d4..." },
"plist": { "url": "https://api.example.com/assets/plists/e5f6g7h8...plist" }
},
"metrics": {
"duration": "0.345",
"cached": false
}
}GET /icon/:hash
Serves the extracted app icon. If the file is missing from disk but the URL is still in cache, it will perform an on-the-fly extraction.
GET /
Returns status, version, and server time.
| Variable | Description | Default |
|---|---|---|
PORT |
Server listening port | 7004 |
ICONS_DIR |
Directory for extracted icons | ./assets/icons |
PLISTS_DIR |
Directory for generated manifests | ./assets/plists |
ICON_RETENTION |
How long to keep assets (e.g., 24h, 48h) |
24h |
GIN_MODE |
Gin framework mode (release / debug) |
release |
RATE_LIMIT_RPS |
Allowed requests per second | 5 |
RATE_LIMIT_BURST |
Maximum burst size for requests | 10 |
The project includes unit tests for core logic (SSRF protection, URL parsing, etc.).
go test -v ./...- Request Validation: URL is decoded and checked for SSRF (internal IPs are blocked).
- Cache Lookup: If the URL exists in memory cache, the result is returned instantly.
- Remote Read: If not cached, the server fetches the ZIP directory and
Info.plistusing HTTP Range. - Metadata Extraction: Parse name, version, and best icon path.
- Fast Response: Return metadata and manifest URL to the user immediately.
- Background Processing:
- Save
.plistmanifest to disk. - Extract icon using the known file size to minimize network requests.
- Revert Apple's optimized PNG format (CgBI) to standard PNG for browser compatibility.
- Save
MIT