How to Export IPTV Playlists to Different Formats: JSON, M3U, and API Data
The iptv-org/iptv repository provides three npm commands—playlist:export for JSON, playlist:format for normalized M3U, and playlist:generate for categorized index files—that convert raw stream data into machine-readable formats.
The iptv-org/iptv project maintains a massive collection of publicly available IPTV streams and offers a TypeScript-based CLI toolkit to export these playlists into structured formats. Whether you need a JSON catalogue for API consumption or deduplicated M3U files organized by country, the automation scripts in scripts/commands/playlist/ handle the entire transformation pipeline.
Export IPTV Playlists to JSON for API Consumption
The JSON export produces .api/streams.json, a machine-readable catalogue containing normalized stream metadata. This format is ideal for downstream applications that need to query channel data programmatically rather than parsing raw M3U files.
Using the CLI Export Command
Run the built-in export command to generate the JSON API file:
npm run playlist:export
This command executes scripts/commands/playlist/export.ts, which performs the following operations:
- Loads reference data (countries, categories, channels) via
loadData()fromscripts/api.ts. - Discovers all
*.m3ufiles in the streams directory using theStorageclass. - Parses each file into a
Collection<Stream>usingPlaylistParserfromscripts/core/playlistParser.ts. - Serializes the collection to JSON using the
Stream.toObject()method defined inscripts/models/stream.ts.
You can override default paths using environment variables for CI pipelines or custom workflows:
DATA_DIR=tmp/data STREAMS_DIR=tmp/streams API_DIR=tmp/.api npm run playlist:export
Programmatic Export with TypeScript
For custom integrations, import the core classes directly to export IPTV playlists programmatically:
import { Storage } from '@freearhey/storage-js'
import { PlaylistParser } from './scripts/core'
import { loadData } from './scripts/api'
import { Stream } from './scripts/models'
async function exportJson() {
await loadData()
const storage = new Storage('streams')
const parser = new PlaylistParser({ storage })
const files = await storage.list('**/*.m3u')
const collection = await parser.parse(files)
const json = collection
.sortBy((s: Stream) => s.getId())
.map((s: Stream) => s.toObject())
.toJSON()
console.log(json)
}
exportJson()
The toObject() method in scripts/models/stream.ts handles the transformation of stream instances into plain objects suitable for JSON serialization.
Normalize and Reformat M3U Playlists
The playlist:format command cleans raw M3U files by normalizing URLs, deduplicating entries, and repairing metadata. This ensures consistent group-title, tvg-logo, and tvg-id attributes across all playlists.
Run the formatter via npm:
npm run playlist:format
Or target specific files:
npm run playlist:format mycountry.m3u other.m3u
The script scripts/commands/playlist/format.ts executes an eight-step pipeline:
- Loads API reference data via
loadData(). - Parses M3U files into a typed collection using
PlaylistParser. - Normalizes URLs using
Stream.normalizeURL()fromscripts/utils.ts. - Removes duplicate streams by comparing normalized URLs.
- Repairs missing identifiers including
tvg-id,channel, andfeedattributes. - Infers missing feed IDs where possible based on channel metadata.
- Sorts streams by title, resolution, label, and URL for deterministic output.
- Writes cleaned files back to the streams directory using
Storage.save().
To change the output location, modify STREAMS_DIR in scripts/constants.ts or set the STREAMS_DIR environment variable.
Generate Canonical Index Playlists by Category
The playlist:generate command creates a comprehensive set of index playlists that group streams by geography, language, and category. This is the primary method for exporting IPTV playlists into consumable, filtered M3U files.
Execute the generator:
npm run playlist:generate
This runs scripts/commands/playlist/generate.ts, which orchestrates generator classes located in scripts/generators/*. The command produces several index files:
index.m3u— Alphabetical list of all available streams.index.country.m3u— Individual files per country (e.g.,us.m3u,fr.m3u).index.language.m3u— Playlists grouped by broadcast language.index.category.m3u— Streams organized by content category.
The generation process removes duplicate IDs, sorts streams by quality and name, and logs progress to logs/generators.log.
Core Architecture and Key Files
Understanding the following source files helps when customizing export behavior or debugging the pipeline:
scripts/constants.ts— Centralizes path definitions (STREAMS_DIR,API_DIR) and configuration constants.scripts/api.ts— ImplementsloadData(), which fetches reference datasets (countries, categories, channels) required for normalization.scripts/core/playlistParser.ts— Contains thePlaylistParserclass that transforms raw M3U text intoCollection<Stream>objects.scripts/models/stream.ts— Defines theStreamdomain model with conversion methodstoObject()andtoString().scripts/utils.ts— Provides utility functions including URL normalization logic used during the export process.
End-to-End Workflow Example
Complete the following sequence to refresh, clean, export, and categorize your IPTV data:
# 1. Clean and normalize all raw M3U files
npm run playlist:format
# 2. Export the full catalogue as JSON for API consumers
npm run playlist:export
# 3. Generate ready-to-use country and language index files
npm run playlist:generate
After execution, the repository contains:
streams/*.m3u— Deduplicated, normalized playlist files..api/streams.json— Machine-readable JSON catalogue.logs/generators.log— Detailed generation logs for auditing.
Summary
npm run playlist:exportgenerates.api/streams.jsonviascripts/commands/playlist/export.ts, usingStream.toObject()for serialization.npm run playlist:formatcleans M3U files viascripts/commands/playlist/format.ts, normalizing URLs withStream.normalizeURL()and deduplicating entries.npm run playlist:generatebuilds categorized index files viascripts/commands/playlist/generate.ts, creating country-specific and language-specific M3U outputs.- Environment variables (
DATA_DIR,STREAMS_DIR,API_DIR) allow custom directory configurations without modifying source code. - Programmatic access is available by importing
PlaylistParser,Storage, andloadData()from the scripts directory.
Frequently Asked Questions
What is the difference between playlist:format and playlist:generate?
playlist:format cleans existing M3U files by normalizing URLs, removing duplicates, and repairing metadata, writing the results back to the same streams/ directory. playlist:generate creates new index files (like index.country.m3u) that aggregate streams into categorized playlists for end-user consumption. Use format to clean data, then generate to create distribution-ready files.
How do I export IPTV playlists to JSON for custom applications?
Import PlaylistParser from scripts/core, instantiate it with a Storage object pointing to your streams directory, call parser.parse(files) to get a Collection<Stream>, then use .map(s => s.toObject()).toJSON() to produce the JSON string. The export.ts command implements this exact workflow for the CLI.
Can I specify custom directories for the exported files?
Yes. Set the DATA_DIR, STREAMS_DIR, and API_DIR environment variables before running any command, or modify the constants in scripts/constants.ts. For example: STREAMS_DIR=custom/streams npm run playlist:format processes files from custom/streams instead of the default location.
Which script handles URL normalization during the export process?
URL normalization occurs in Stream.normalizeURL() within scripts/utils.ts, which is invoked by scripts/commands/playlist/format.ts during the formatting phase. This ensures consistent stream addresses before deduplication and JSON serialization, preventing the same channel from appearing multiple times with slightly different URLs.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →