Torrent Search MCP Server
This server lets you search and browse torrents from multiple sources, retrieve magnet links, and manage Telegram-based webapp authorization.
search_torrents: Perform advanced searches across providers, returning ranked top 3-5 recommendations with reasons and source details.
popular_torrents: Get the most popular torrents per site (e.g., thepiratebay.org, 1337x.to, nyaa.si), pre-ranked by swarm health.
get_torrent: Resolve the magnet link for a specific torrent by its ID.
available_sources: List the configured torrent source domains.
authorize_webapp: Approve a one-time Telegram pairing code to grant browser access to the web UI.
torrent_webapp: Present the web UI URL and explain how the user can authorize via Telegram.
Provides a containerized deployment option with preconfigured DNS settings (using quad9) to bypass common connection issues when accessing torrent sites
Supports configuration through .env files for storing sensitive information like YggTorrent passkeys
Includes a FastAPI server as an alternative interface with interactive API documentation (Swagger UI and ReDoc) for direct HTTP access
Available as a PyPI package for easy installation and integration into other Python applications
Provides a Python API wrapper for programmatic access to torrent search functionality
Uses Shields.io for generating status badges in the README
Offers Swagger UI documentation for the FastAPI interface, enabling easy API exploration and testing
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@Torrent Search MCP Serversearch for the latest Ubuntu ISO torrent"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
Torrent Search MCP/API/WebUI
This repository provides a Python API/WebUI and an MCP (Model Context Protocol) server to find torrents programmatically on ThePirateBay, 1337x, Nyaa, YTS, EZTV, FitGirl, SubsPlease and UIndex. It allows for easy integration into other applications or services.
Quickstart
uvx torrent-search-mcp --mode cli "sample show"
# MCP server over stdio (default)
uvx torrent-search-mcp --mode stdio
# MCP server over streamable HTTP (port 8000, endpoint /mcp)
uvx torrent-search-mcp --mode http
# MCP server over SSE (port 8000, endpoint /sse, legacy)
uvx torrent-search-mcp --mode sse
# Standalone API server (port 8000)
uvx torrent-search-mcp --mode apiRelated MCP server: rqbit Torrent Client MCP
Table of Contents
Features
API wrapper for ThePirateBay, 1337x, Nyaa, YTS, EZTV, FitGirl, SubsPlease and UIndex.
MCP server interface (FastMCP 4) serving the
2026-07-28protocol revision overstdioor streamable HTTP (http), with automatic negotiation of older handshake revisions and legacy transport aliases (streamable-http,sse).API server interface for alternative HTTP access (e.g., for direct API calls or testing).
CLI mode for quick one-off searches directly from the terminal.
popular_torrentscached for 2 minutes for Web UI delivery; searches are never cached (only identical concurrent requests are coalesced) so new results appear immediately.In-memory 1-hour, 5000-entry torrent cache used only to resolve magnet links via
get_torrentwithout re-scraping.Magnet links are always stored internally; MCP hides them unless
INCLUDE_LINKS=true.Configurable source filtering via environment variables.
Telegram-gated web UI: one-time QR/deep-link pairing, forward-to-Telegram popup and (optional) server-side forwarding.
Tools:
Search for torrents across all available sources.
Get the most popular torrents per source (apibay, uindex, 1337x, YTS, nyaa, EZTV).
Get the magnet link for a specific torrent by id.
List available sources.
Present the web UI and its Telegram pairing access, approve pairing codes, and forward torrents to Telegram chats.
Supported Sources
Source | Scraping domain | Fetch method |
ThePirateBay |
| JSON API |
1337x |
| HTML search/top pages |
Nyaa |
| RSS + HTML top page |
YTS |
| JSON API |
EZTV |
| JSON API |
FitGirl |
| RSS |
SubsPlease |
| JSON API |
UIndex |
| HTML top list |
The API exposes public display domains where applicable: apibay.org is shown as thepiratebay.org, and yts.mx as yts.vg. Results may include a validated HTTP(S) page_url linking back to their source page.
Note on UIndex: the site exposes no programmatic search endpoint (its search path is protected by a browser challenge), so queries are matched client-side against its live top list - which conveniently carries magnet links inline.
Sources can be excluded individually via the EXCLUDE_SOURCES env var.
Setup
Prerequisites
Python 3.10+ (required for PyPI install). CI and Docker images use Python 3.14.
uv(for local development).Docker and Docker Compose (for Docker setup).
Configuration (Optional)
The application reads configuration from environment variables. The recommended way to set them is by creating a .env file in your project's root directory. The application will load it automatically. See .env.example for all available options.
Variable | Default | Description |
|
| When |
| (none) | Comma-separated list of sources to exclude from results (e.g. |
| (none) | MCP only: base URL of a running Torrent Search REST API - tools proxy it instead of scraping locally. Unset = standalone. |
| (none) | Telegram bot handle used by the Web UI torrent action. Unset = the web UI runs without the pairing gate and Telegram features stay hidden. |
| (none) | Secret required to approve Web UI pairing codes (register endpoint + |
| (none) | Bot token enabling server-side sending via |
| (none) | Agent relay mode (with |
| (none) | Agent relay mode: shared secret sent as the |
| (none) | Agent relay mode: |
| (none) | Agent relay mode: |
|
| When |
|
| Persistence file for authorized session tokens (SHA-256 hashes only); shared between API and MCP processes via mtime-based reload. |
| (none) | MCP only: public URL of the web UI; enables the |
Installation
Choose one of the following installation methods.
Install from PyPI (Recommended)
This method is best for using the package as a library or running the server without modifying the code.
Install the package from PyPI:
pip install torrent-search-mcpCreate a
.envfile in the directory where you'll run the application (optional).Run the MCP server (default: stdio):
python -m torrent_searchFor Local Development
This method is for contributors who want to modify the source code.
Using uv:
Clone the repository:
git clone https://github.com/philogicae/torrent-search-mcp.git
cd torrent-search-mcpInstall dependencies using
uv:
uv sync --frozenCreate your configuration file by copying the example:
cp .env.example .envRun the MCP server (default: stdio):
uv run -m torrent_searchThe repo also ships a dev.sh helper that locks/syncs deps, formats, lints, type-checks (ty) and runs the test suite with coverage:
./dev.shFor Docker
This method uses Docker Compose to run two containers: the REST API + web UI, and an MCP server that proxies the API (no local scraping).
compose.yaml is configured to bypass DNS issues (using quad9 DNS).
Container | Mode | Host port | Endpoints |
|
|
|
|
|
|
|
|
Clone the repository (if you haven't already):
git clone https://github.com/philogicae/torrent-search-mcp.git
cd torrent-search-mcpCreate your configuration file by copying the example:
cp .env.example .envBuild and run the containers using Docker Compose:
docker compose up --build -dAccess container logs:
docker logs torrent-search-api -f
docker logs torrent-search-mcp -fUsage
The package exposes a single entry point, torrent-search-mcp (installed by pip/uvx), equivalent to python -m torrent_search. It supports the following --mode values:
Mode | Endpoint | Description |
| - | Run a single search query and print results to stdout. |
| - | MCP server over stdio (default). |
|
| MCP server using streamable HTTP. Serves MCP protocol revision |
|
| Alias of |
|
| MCP server using Server-Sent Events. Legacy HTTP transport (deprecated by the MCP spec in favor of |
|
| Standalone API HTTP server (see As API Server). |
The server is built on FastMCP 4 (MCP SDK v2). Clients supporting the 2026-07-28 revision negotiate it automatically (stateless requests, server/discover, no session IDs); older clients fall back to the previous handshake era against the same deployment.
MCP modes (stdio, http, streamable-http, sse) run standalone by default (tools scrape locally). Set TORRENT_SEARCH_API_URL to switch to API mode: the tools proxy a running Torrent Search REST API instead.
Common flags (for http, streamable-http, sse and api modes): --host (default 0.0.0.0), --port (default 8000), --reload, --workers (API only).
As CLI
Run a one-off search directly from the terminal. Prints each result as id (seeders|leechers|downloads) - filename, then fetches the magnet/torrent for the top hit.
# Using the installed entry point
torrent-search-mcp --mode cli "sample show"
# Or via uvx without installing
uvx torrent-search-mcp --mode cli "sample show"
# Or from source
uv run -m torrent_search --mode cli "sample show"As Python Wrapper
from torrent_search import torrent_search_api
results = await torrent_search_api.search_torrents("sample show")
for torrent in results:
print(
f"{torrent.filename} | {torrent.size} | {torrent.seeders} SE | {torrent.leechers} LE | {torrent.date} | {torrent.source}"
)search_torrents is async and accepts an optional max_items (default 20). popular_torrents(per_source=20) returns the current most popular torrents from sources with a top listing - up to per_source results per source (pass per_source=None for everything), merged and ranked by seeders + leechers. Each Torrent exposes id, filename, category, size, seeders, leechers, downloads, date, source, uploader, and, when available, magnet_link and a validated HTTP(S) page_url. Pass a torrent's id to get_torrent() to retrieve its magnet link.
As MCP Server
from torrent_search import torrent_search_mcp
torrent_search_mcp.run(transport="http")As API Server
This project also includes a API server as an alternative way to interact with the library via a standard HTTP API. This can be useful for direct API calls, integration with other web services, or for testing purposes.
Running the API Server:
# With Python
python -m torrent_search --mode api
# With uv
uv run -m torrent_search --mode api--host <host>: Default:0.0.0.0.--port <port>: Default:8000.--reload: Enables auto-reloading when code changes (useful for development).--workers <workers>: Default:1. Caching and request coalescing are in-process, so each worker keeps its own cache; use the default single worker unless per-worker caches are acceptable (a shared backend such as Redis would be needed to scale out).
The API server will then be accessible at http://<host>:<port>.
Available Endpoints: The API server exposes similar functionalities to the MCP server. Key endpoints include:
GET /: Built-in web UI (dark/light) - search, per-site popular tiles, sortable results, source-page links and magnet actions. Telegram sending requires one-time QR pairing when configured.POST /torrent/search: Search for torrents. Query params:query(required),max_items(optional, default20; uncapped whenper_sourceis set) andper_source(optional, keep up to N results per source, ranked by swarm health).GET /sources: List the available torrent source domains.GET /torrent/popular: Get the most popular torrents. Query param:per_source(optional, default20).GET /torrent/{torrent_id}: Get the magnet link for a specific torrent by id. Returns the magnet URI as a JSON string.GET /telegram/session: Web UI auth state (enabled,authenticated, public bothandle,prune_magnet_links). Send the session token asAuthorization: Bearer.POST /telegram/auth/challenge: Create a one-time 16-character alphanumeric pairing code (rate-limited). Codes expire after ~5 minutes and are shown as a QR + deep link in the pairing popup.GET /telegram/auth/poll?code=: Poll a pairing code; on approval returns the one-time session token for the browser to store.DELETE /telegram/auth/challenge/{code}: Cancel a pending pairing code.POST /telegram/auth/register: Approve a pairing code bound to a Telegramchat_id. RequiresAuthorization: Bearer $TORRENT_SEARCH_API_KEY.POST /telegram/auth/logout: Revoke the presented session token.POST /forward_telegram: Send torrent info to the Telegram chat bound to the presented session token; server-to-server callers may instead useAuthorization: Bearer $TORRENT_SEARCH_API_KEYwith the targetchat_idquery param. JSON body:filename(required),magnet_link(required), optionalsize,seeders. WhenPRUNE_MAGNET_LINKS=truethe forwarded magnet is pruned; requiresTELEGRAM_BOT_TOKEN, otherwise 503./docs: Interactive API documentation (Swagger UI)./redoc: Alternative API documentation (ReDoc).
Environment variables are configured the same way as for the MCP server (via an .env file in the project root).
Via MCP Clients
Usable with any MCP-compatible client. Available tools:
search_torrents(user_intent, query): Search for torrents across all available sources.user_intent: A short description reflecting the user's overall intention (e.g."latest episode of Sample Show").query: Optimized, lowercase, space-separated keywords (e.g."sample show s01e05"). Generic/filler/technical terms should be stripped per the tool's docstring.By default magnet links are stripped from the response to save tokens; set
INCLUDE_LINKS=trueto include them.Magnet round trips: with
INCLUDE_LINKSunset, results keep theiridbut no magnet. After picking the 2-5 torrents worth recommending, callget_torrent(id)once per pick: the server resolves it from its 1-hour torrent cache, or re-runs the search if the entry expired. Do not fetch magnets for every result.
popular_torrents(per_source=20): Get the most popular torrents right now from sources with an official top listing (apibay, uindex, 1337x, YTS, nyaa, EZTV) - up toper_sourceresults each, grouped per source and pre-ranked by seeders + leechers.By default magnet links are stripped from the response to save tokens; set
INCLUDE_LINKS=trueto include them.
available_sources(): Get the list of available torrent sources.get_torrent(torrent_id): Get the magnet link for a specific torrent by id (theidreturned bysearch_torrentsorpopular_torrents).authorize_webapp(code, chat_id): Approve a Web UI pairing code bound to your Telegram chat id (the code shown in the browser pairing gate). RequiresTORRENT_SEARCH_API_KEYandTORRENT_SEARCH_API_URL.forward_torrent(filename, magnet_link, chat_id, size=None, seeders=None): Forward a torrent (filename + magnet) to your Telegram chat through the REST API (magnet pruned whenPRUNE_MAGNET_LINKS=true). RequiresTORRENT_SEARCH_API_KEYandTORRENT_SEARCH_API_URL; rate-limited per chat (20/min).torrent_webapp(): Present the web UI URL (WEBUI_URL) and its pairing-based access system.
Example with Devin
Configuration:
{
"mcpServers": {
...
# with stdio (only requires uv)
"torrent-search-mcp": {
"command": "uvx",
"args": [ "torrent-search-mcp" ]
},
# with streamable-http transport (Docker compose: MCP on port 8001; standalone server: 8000)
"torrent-search-mcp": {
"serverUrl": "http://127.0.0.1:8001/mcp"
},
# with sse transport (legacy; requires running server)
"torrent-search-mcp": {
"serverUrl": "http://127.0.0.1:8001/sse"
},
...
}
}Changelog
See CHANGELOG.md for a history of changes to this project.
Contributing
Contributions are welcome! Please open an issue or submit a pull request.
License
This project is licensed under the MIT License - see the LICENSE file for details.
Available Tools
7 toolsauthorize_webappAuthorize WebappA
Authorize a browser on the Torrent Search webapp via its pairing code.
The code comes from an user interaction on the webapp: they click "Open in Telegram", scan the QR code, or copy the prompt message, which sends "Authorize for Torrent Search" to you. Take the code from that message and call this tool with it and the user's Telegram chat id. Codes are single-use and expire after 5 minutes. After approval the user MUST go back to the webapp: the browser polls and completes the authentication there (it shows "Access granted" and unlocks the app permanently).
| Name | Required | Description | Default |
|---|---|---|---|
| code | Yes | Pairing code shown in the webapp 'Telegram Access' gate. | |
| chat_id | Yes | The owner's Telegram chat id the webapp access is bound to. |
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
No annotations exist, so the description carries the full behavioral burden. It discloses important non-obvious traits: codes are single-use, expire after 5 minutes, and authentication is only completed in the browser once the user returns to the webapp. This is strong transparency for an authorization tool.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The single-sentence purpose statement is front-loaded, followed by a compact workflow explanation. No filler or redundant content; every sentence adds relevant operational detail, though the length is slightly more than minimal.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a two-parameter tool with a full schema and output schema, the description covers the complete invocation flow: source of the code, required inputs, single-use/expiry constraint, and the required post-call user action. Minor details like error handling for invalid/expired codes are absent but acceptable given the tool's simplicity.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so baseline is 3. The description adds meaningful context beyond the schema by explaining where the code comes from, its exact message format, and that it must be paired with the user's Telegram chat id. This helps an agent correctly extract and pass parameters.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description opens with a precise verb and resource: 'Authorize a browser on the Torrent Search webapp via its pairing code.' This clearly identifies the tool's action and distinguishes it from sibling tools like search, get, and forward, which have different purposes.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It thoroughly explains when to use the tool: when a user sends an 'Authorize <CODE> for Torrent Search' message, with the code and chat id as inputs. It doesn't explicitly list alternative tools to use instead, but no siblings fulfill this same role, so exclusion is not necessary.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
available_sourcesAvailable SourcesB
Get the list of available torrent sources.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations provided, the description carries the full burden of behavioral disclosure. It only says 'Get the list', implying a read operation, but gives no detail on side effects, permissions, caching, or failure modes. There is no contradiction, but the disclosure is too thin.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is a single, front-loaded sentence with no wasted words. It is concise, though it is also very sparse – perhaps too sparse to fully convey the tool's role.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given the simple zero-parameter interface and the presence of an output schema, the description is mostly adequate. However, it omits any context about what a 'torrent source' is, why a user would call this, or how it fits into the workflow (e.g., before searching).
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool has zero parameters, so no parameter semantics are needed. Schema description coverage is trivially 100% and the baseline for a no-parameter tool is 4, which applies here.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb and resource: 'Get the list of available torrent sources'. It clearly indicates a retrieval operation unlike the sibling search, popular, or forward tools, though it doesn't explicitly contrast itself with them.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
There is no guidance on when to use this tool versus its siblings. It doesn't mention that it could be a prerequisite for search_torrents or that it only lists supported sources. No alternatives or exclusions are provided.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
forward_torrentForward TorrentA
Send a torrent (filename + magnet) to the user's Telegram chat.
The forward goes through the Torrent Search REST API, which owns the Telegram bot token; when PRUNE_MAGNET_LINKS is enabled the magnet is pruned to 'magnet:?xt=urn:btih:HASH&dn=' before sending. Requires TORRENT_SEARCH_API_KEY (same value as the API server) and TORRENT_SEARCH_API_URL. Forwards are rate-limited per chat (20/min).
| Name | Required | Description | Default |
|---|---|---|---|
| size | No | ||
| chat_id | Yes | The owner's Telegram chat id the torrent is sent to. | |
| seeders | No | ||
| filename | Yes | Exact torrent filename shown in the search results. | |
| magnet_link | Yes | Magnet link of the torrent (from get_torrent, or from a search run with INCLUDE_LINKS=true). |
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations provided, the description carries the burden of behavioral disclosure. It does well by explaining the API routing, the API key/URL requirements, the conditional PRUNE_MAGNET_LINKS behavior, and the per-chat rate limit. It does not describe error behavior or side effects beyond sending, but the core behavioral traits are well covered.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The main purpose is front-loaded in the first sentence, and each subsequent sentence adds necessary operational detail: API routing, environment-dependent pruning, required configuration, and rate limiting. The text is dense but not redundant, though the technical details could be slightly better organized.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
The description covers the essential calling context: prerequisites, rate limits, configuration variables, and conditional magnet transformation. Since an output schema is present, return-value details are not needed. Minor gaps remain around explicit integration with sibling tools, but the description is strong enough for an agent to invoke the tool correctly.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The input schema already describes each parameter, so the description only adds moderate value. It clarifies the filename+magnet relationship and the magnet pruning format, but it does not enrich the meaning of chat_id, size, or seeders beyond what the schema already states. With schema coverage around 60%, the description partially compensates but is not exceptional.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description opens with a specific action verb and resource: 'Send a torrent (filename + magnet) to the user's Telegram chat.' This clearly distinguishes the tool from sibling search/retrieval tools such as search_torrents and get_torrent, which do not send messages to Telegram.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The context of use is clear: this tool is for delivering a torrent to a Telegram chat, and the description provides prerequisites and rate limits. However, it does not explicitly state when to use this tool versus alternatives like get_torrent or search_torrents, nor does it provide any when-not-to-use guidance.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_torrentGet TorrentA
Get the magnet link for a specific torrent by id.
| Name | Required | Description | Default |
|---|---|---|---|
| torrent_id | Yes | Torrent ID returned by a previous search_torrents or popular_torrents call. |
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations provided, the description carries the behavioral burden. It clearly indicates a read-only retrieval operation returning a magnet link, and the existence of an output schema covers the return structure. It does not mention error behavior or prerequisites beyond the ID, but for a simple getter this is sufficient.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single, front-loaded sentence states the verb, output, and selection key with no filler. Every element earns its place.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
The tool is simple, has one required parameter, has an output schema, and the description plus parameter description fully specify how to call it and where the ID comes from. Nothing needed for correct invocation is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the parameter description already explains that torrent_id is returned by previous search or popular calls. The tool description adds little beyond restating 'by id', so the schema carries the semantic weight and the description meets the baseline.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a clear verb ('get') and resource ('magnet link for a specific torrent by id'), which fully distinguishes this from sibling tools like search_torrents and popular_torrents that find torrents rather than resolve a single known torrent to its magnet link.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description implies the tool is used after obtaining a torrent_id, and the parameter description explicitly says the ID comes from a previous search_torrents or popular_torrents call. It does not explicitly name alternatives or state when not to use it, but the usage context is clear.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
popular_torrentsPopular TorrentsA
Get the most popular torrents right now across providers with an official top listing.
Output is grouped per source (thepiratebay.org, uindex.org, 1337x.to, eztvx.to,
yts.vg, nyaa.si), keeping up to per_source results per site, each site's
entries pre-ranked by swarm health.
Response Requirements:
Recommend the top 5-10 results maximum, focused on latest releases.
For each recommendation, include: Filename, Size, Seeds/Leechs, Date, Source, and a 1-sentence "Why this?" reason.
| Name | Required | Description | Default |
|---|---|---|---|
| per_source | No | How many top results to keep per source (default 20). |
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations provided, the description carries the full burden of behavioral disclosure. It clearly explains that output is grouped per source, limited to per_source results per site, and pre-ranked by swarm health. It also details the expected response format via the 'Response Requirements' section. It does not disclose rate limits, authentication needs, or failure modes, but for a read-only list tool, the disclosed behavior is fairly comprehensive.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is concise and well-structured: a clear purpose sentence, a grouping/ranking explanation, and a bulleted list of response requirements. It is front-loaded with the core purpose. The response requirements are useful instructions but add length; still, every sentence serves a purpose. No fluff.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given one parameter with full schema coverage and an output schema (indicated), the description covers the tool's purpose, output grouping, ranking, and response format. It lists the exact sources and the per_source limit. It does not mention potential edge cases like empty results or error handling, but for a list tool with an output schema, this is adequate.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The schema already describes the only parameter `per_source` with full coverage. The description adds value by explaining that per_source controls 'how many top results to keep per source' and ties it to the grouping behavior. This reinforces the parameter's effect on output, going beyond the schema's simple description.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description opens with a specific verb and resource: 'Get the most popular torrents right now across providers with an official top listing.' It clearly differentiates this from search_torrents and get_torrent by emphasizing 'most popular' and 'official top listing.' The mention of specific sources (thepiratebay.org, uindex.org, etc.) further concretizes the scope.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description implies usage (for fetching popular torrent lists) but does not explicitly state when to prefer it over search_torrents or get_torrent. It mentions 'across providers with an official top listing' as a distinguishing factor, but no explicit 'when-not-to-use' or alternative names are provided. The response requirements give guidance on output formatting but not on tool selection.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
search_torrentsSearch TorrentsA
Perform an advanced torrent search across multiple providers.
Result Analysis & Ranking:
Quality: Prefer 1080p or 4k, over 720p.
Efficiency: Prefer h265/HEVC for better quality/size ratio.
Health: Maximize seeders + leechers.
Size: Prefer smaller files within the same quality bracket.
Language: Ultimately, if multiple equivalent options are available, choose the one with more languages.
Response Requirements:
Recommend the top 3-5 results maximum.
For each recommendation, include: Filename, Size, Seeds/Leechs, Date, Source, and a 1-sentence "Why this?" reason.
If results are poor, irrelevant or too diverse, suggest specific keywords to improve the search.
| Name | Required | Description | Default |
|---|---|---|---|
| query | Yes | Optimized search keywords, lowercase and space-separated. Strip generic terms (movie, torrent, download), filler words (the, a, of) and technical tags (1080p, h265, bluray) unless explicitly requested. TV shows: 'name sXXeYY' for episodes, 'name sXX' for seasons. Add 'multi' only if a multi-language version is requested. | |
| user_intent | Yes | User's overall intention (e.g. 'latest episode of Sample Show'). |
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With no annotations provided, the description carries the full burden of behavioral disclosure. It transparently explains the ranking criteria (quality, efficiency, health, size, language) and the response format (top 3-5 results with specific fields and 'Why this?' reasons), plus the fallback of suggesting keywords. This is substantial and goes beyond basic operation.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is structured with headers and bullet points, making it scannable, but it's fairly long with detailed ranking and response requirements. While each section is informative, it could be more concise; the ranking criteria and response format are somewhat verbose, though they do add context. It's not overly redundant but is longer than strictly necessary.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given the complexity of the tool (multi-provider search, ranking, response formatting) and the presence of an output schema, the description covers the essential behavior, query construction, ranking logic, and response requirements, including a fallback for poor results. It doesn't mention auth or limitations, but for a search tool with an output schema, it's sufficiently complete for correct invocation.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The schema already describes both parameters with 100% coverage, so the baseline is 3. The description adds significant value by detailing how to construct the query (strip generic terms, TV show format, 'multi' flag), which is not in the schema. This enriches the meaning of the query parameter beyond its type/description.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly states the tool performs an advanced torrent search across multiple providers, which is a specific action and resource. However, it doesn't explicitly differentiate itself from siblings like popular_torrents or get_torrent beyond calling itself 'advanced' and mentioning 'multiple providers', so it's clear but not fully distinguishing.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description provides no explicit guidance on when to use this tool versus alternatives. It gives detailed ranking and response instructions, but doesn't say when to prefer this over popular_torrents or other siblings, nor does it mention exclusions or conditions. Usage is only implied by the search nature.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
torrent_webappTorrent WebappA
Present the Torrent Search webapp and its Telegram pairing access system.
Returns the webapp URL and how to get authorized by you. Tell the user to open the URL: on first visit the site shows a pairing dialog with a QR code and buttons ("Open in Telegram", "t.me" fallback, "Copy Prompt"). Ask the user to scan the QR code, click "Open in Telegram", or copy the prompt message and send it to you in the Telegram chat. That message ("Authorize for Torrent Search") carries the code; when it arrives, extract it and call authorize_webapp with it and the user's Telegram chat id. Codes expire after 5 minutes.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
Output Schema
| Name | Required | Description |
|---|---|---|
| result | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
No annotations are provided, so the description carries the full burden of behavioral disclosure. It transparently explains the pairing dialog, the buttons, the code expiration (5 minutes), and instructs the agent to call authorize_webapp with the extracted code and chat id. This covers all relevant behaviors and side effects (the tool returns a URL and guides a user interaction). The only minor gap is not explicitly stating that no data is modified, but it's implied by the presentation nature.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is moderately long but every sentence contributes to the user interaction flow—it explains the URL, the pairing dialog, the actions, the code extraction, and the expiry. It is well-structured, starting with the purpose and then detailing steps. It could be slightly more compact by merging some sentences, but the detail is necessary for this interactive tool.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given the tool's complexity (an interactive pairing process with user involvement), the description is complete. It covers the output (webapp URL), the steps the agent must take, the exact message format, the expiry, and the call to authorize_webapp. An output schema exists (though not shown), so return-value details are presumably covered there. Nothing essential is missing for an agent to correctly invoke and follow through.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool has zero parameters, so schema coverage is trivially 100%. The description correctly does not need to explain parameters, and it adds no parameter-related details. Baseline for zero parameters is 4, and the description's focus on behavior is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly states the tool's purpose: to present the Torrent Search webapp and its Telegram pairing system, returning the webapp URL and the authorization procedure. It distinguishes itself from sibling tools like search_torrents or authorize_webapp by focusing on the initial presentation and pairing flow, not on searching or authorizing directly.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description provides explicit step-by-step usage instructions: tell the user to open the URL, guide them through the QR code/Telegram options, extract the code from their message, and call authorize_webapp. It clearly defines when to use this tool (to initiate pairing) and the follow-up action, though it doesn't explicitly contrast with alternatives like 'use search_torrents when searching'—but the flow is self-contained and unambiguous.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
Tool Schema Changelog
Recent tool additions, removals, and schema changes observed during successful MCP inspections.
2 tool updates
v4.5.0- Added
forward_torrent - Changed
search_torrents1 field changed- changed
Input schema / properties / user_intent / descriptionPrevious value: -"User's overall intention (e.g. 'latest episode of Breaking Bad')."New value: +"User's overall intention (e.g. 'latest episode of Sample Show')."
6 tool updates
v4.3.3- Added
authorize_webapp - Added
available_sources - Changed
get_torrent1 field changed- added
Input schema / properties / torrent_id / descriptionAdded value: +"Torrent ID returned by a previous search_torrents or popular_torrents call."
- Added
popular_torrents - Changed
search_torrents2 fields changed- added
Input schema / properties / query / descriptionAdded value: +"Optimized search keywords, lowercase and space-separated. Strip generic terms (movie, torrent, download), filler words (the, a, of) and technical tags (1080p, h265, bluray) unless explicitly requested. TV shows: 'name sXXeYY' for episodes, 'name sXX' for seasons. Add 'multi' only if a multi-language version is requested." - added
Input schema / properties / user_intent / descriptionAdded value: +"User's overall intention (e.g. 'latest episode of Breaking Bad')."
- Added
torrent_webapp
4 tool updates
v2.4.0- Added
get_torrent - Removed
get_ygg_magnet_link - Removed
get_ygg_torrent_details - Changed
search_torrents7 fields changed- added
Input schema / additionalPropertiesAdded value: +false - removed
Input schema / properties / max_itemsRemoved value: -{ - "default": 10, - "title": "Max Items", - "type": "integer" -} - removed
Input schema / properties / query / titleRemoved value: -"Query" - removed
Input schema / properties / sourcesRemoved value: -{ - "anyOf": [ - { - "items": { - "type": "string" - }, - "type": "array" - }, - { - "type": "null" - } - ], - "default": null, - "title": "Sources" -} - added
Input schema / properties / user_intentAdded value: +{ + "type": "string" +} - changed
Input schema / requiredPrevious value: -[ - "query" -]New value: +[ + "user_intent", + "query" +] - changed
Output schema / (root)Previous value: -nullNew value: +{ + "properties": { + "result": { + "type": "string" + } + }, + "required": [ + "result" + ], + "type": "object", + "x-fastmcp-wrap-result": true +}
3 tool updates
v1.0.0- First observed
get_ygg_magnet_link - First observed
get_ygg_torrent_details - First observed
search_torrents
TDQS
Scored across 7 tools
The search, popular, get-by-id, source-list, forwarding, and webapp auth tools each target distinct actions, and the descriptions clearly separate them. search_torrents and popular_torrents are the closest pair, but query-based search vs. official top listings is explicit. torrent_webapp and authorize_webapp are complementary steps rather than overlapping tools.
Most tools follow a verb_noun pattern (get_torrent, search_torrents, authorize_webapp, forward_torrent), but available_sources and popular_torrents use adjective_noun phrasing and torrent_webapp is a bare resource name. These deviations are readable but break the otherwise consistent command-style convention.
Seven tools is a well-scoped size for a torrent search server with an additional Telegram/webapp pairing flow. Each tool covers a distinct step without redundancy or unnecessary breadth.
The core workflow is covered: discover sources, search or list popular torrents, resolve a magnet by id, and forward it to Telegram, plus the webapp authorization flow. Minor gaps remain such as source-specific browsing or more detailed torrent metadata, but they do not create dead ends for the main use case.
Maintenance
Related MCP Connectors
A simple MCP server built with FastMCP and python
Primarily to be used as a template repository for developing MCP servers with FastMCP in Python, P…
Related MCP Servers
- AlicenseBqualityNot gradedmaintenanceA Python MCP server that allows programmatic interaction with YggTorrent, enabling torrent search, details retrieval, and magnet link generation without exposing your Ygg passkey.418MIT
- AlicenseBqualityCmaintenancePython wrapper & MCP server for the rqbit API83MIT
- AlicenseBqualityFmaintenanceA Python MCP server that allows programmatic interaction to find torrents programmatically on YggTorrent and La Cale.42MIT
- AlicenseAqualityDmaintenanceMCP server for searching, viewing details, and downloading torrents from kinozal.tv35 npm2MIT