How to Manage Geoblocked IPTV Channels Across Countries Using Free-TV/IPTV
The Free-TV/IPTV repository handles geoblocked channels by marking them with the Ⓖ flag in country-specific markdown files and injecting ISO-3166-1 alpha-2 country codes into the tvg-country M3U attribute during playlist generation.
Managing geoblocked IPTV channels across different countries requires a systematic approach to metadata and playlist generation. The Free-TV/IPTV project solves this through a transparent build process that converts markdown tables in lists/*.md into structured M3U playlists. By understanding how the make_playlist.py script processes country codes and the Ⓖ marker, you can effectively filter, add, or exclude region-locked streams.
Understanding the Geo-Blocking Mechanism
The repository implements a two-layered approach to geoblocking: human-readable markers in source files and machine-parseable attributes in generated playlists.
The Ⓖ Flag and Markdown Tables
Contributors indicate geo-restricted channels by appending the Ⓖ symbol to the channel name in the respective country markdown file. For example, in lists/usa.md line 7, a restricted channel appears as BBC One Ⓖ. This convention is documented in README.md lines 47-48, providing a visual cue for reviewers that the stream requires IP addresses from that specific country.
Country Code Mapping in make_playlist.py
The COUNTRY_CODES dictionary in make_playlist.py (lines 45-46) maps file stems to ISO-3166-1 alpha-2 codes. When the script processes usa.md, it identifies the country as US; for uk.md, it assigns GB. This mapping ensures every channel carries accurate origin metadata regardless of the filename format.
M3U Generation Logic
The Channel.to_m3u_line() method (lines 15-20) constructs the final #EXTINF entry. It conditionally adds tvg-country="XX" only when a country code exists, meaning geo-blocked streams are explicitly tagged while international channels omit the attribute. This stateless generation happens every time you run the build script, ensuring metadata stays synchronized with source changes.
How Geo-Blocked Channels Are Processed
The workflow from source to playlist follows three distinct stages:
-
Marking in Source Tables – Contributors add the
Ⓖsymbol to the Name column of the relevant markdown file (e.g.,France 2 Ⓖinlists/france.md). They ensure the stream URL is active and marked with[>]rather than[x]. -
Country Identification –
make_playlist.pyderives the country key from the filename (france.md→france) and performs a lookup inCOUNTRY_CODESto retrieve the alpha-2 code (FR). -
M3U Output – For each active line containing
[>], the script creates aChannelinstance with the derived country code. The resulting entry includestvg-country="FR", which IPTV players can use for client-side filtering.
A typical geo-blocked entry appears as:
#EXTINF:-1 tvg-name="BBC One" tvg-logo="https://…/BBC_One_logo.png" tvg-country="GB" group-title="UK",BBC One
https://vs-hls-pushb-uk-live.akamaized.net/x=4/i=urn:bbc:pips:service:bbc_one_yorks/iptv_hd_abr_v1.m3u8
Managing Geoblocked Channels in Practice
Exclude All Geo-Blocked Streams
Filter the generated playlist to remove lines containing country metadata. This produces a global-only playlist:
grep -v 'tvg-country' playlist.m3u8 > playlist_no_geo.m3u8
Isolate Specific Countries
Use the tvg-country attribute to extract region-specific content. To create a UK-only playlist without geo-blocked streams (for use outside the UK):
grep 'tvg-country="GB"' playlist.m3u8 > uk_geo_only.m3u8
Add New Geo-Blocked Channels
- Edit the appropriate
lists/<country>.mdfile. - Insert a new table row using the
[>]marker, include theⒼflag in the channel name, and verify the stream URL. - Submit a pull request. The
make_playlist.pyscript will automatically attach the correcttvg-countryattribute during the next build.
Remove or Disable Channels
To remove a channel from the generated playlist, replace the [>] marker with [x] in the markdown source. Alternatively, delete the line entirely. The next run of make_playlist.py will omit the entry from playlist.m3u8.
Automation Examples
Generate the full global playlist from source:
python3 make_playlist.py
Extract only geo-blocked entries for analysis:
grep -i 'tvg-country' playlist.m3u8 > geo_blocked.m3u8
Build a country-specific playlist excluding that country's geo-blocked content (useful for testing international availability):
python3 make_playlist.py
grep -v 'tvg-country="DE"' playlist.m3u8 > germany_international.m3u8
Summary
- The
Ⓖflag in markdown tables provides human-readable indication of geo-restrictions, while thetvg-countryattribute enables machine filtering. - Country codes are derived from filenames via the
COUNTRY_CODESmapping inmake_playlist.pyand injected at build time. - Active streams are marked with
[>]in source files; changing to[x]removes them from the output. - Playlist filtering using standard Unix tools like
grepallows you to include or exclude geo-blocked content without modifying source code.
Frequently Asked Questions
What does the Ⓖ symbol mean in Free-TV/IPTV channel lists?
The Ⓖ symbol indicates that a channel's stream URL is restricted to IP addresses from that specific country (geo-IP blocked) or requires a regional license to view. It appears in the Name column of the markdown tables within lists/*.md files and serves as a visual marker for contributors and users.
How do I filter out all geoblocked channels from my playlist?
Run a negative grep filter against the tvg-country attribute: grep -v 'tvg-country' playlist.m3u8 > clean_playlist.m3u8. This removes all lines containing country codes, leaving only internationally available streams.
Can I generate a playlist for only one specific country using Free-TV/IPTV?
Yes. First generate the full playlist with python3 make_playlist.py, then filter for your target country code: grep 'tvg-country="FR"' playlist.m3u8 > france_only.m3u8. The tvg-country attribute is standardized to ISO-3166-1 alpha-2 codes as defined in the COUNTRY_CODES mapping.
Where is the country code metadata added in the M3U file?
The tvg-country attribute is added to the #EXTINF line by the Channel.to_m3u_line() method in make_playlist.py (lines 15-20). It appears immediately after the tvg-logo attribute and before group-title, populated from the COUNTRY_CODES dictionary lookup based on the source markdown filename.
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 →