{
  "openapi": "3.0.1",
  "info": {
    "title": "Torrent / BitTorrent DHT corpus search & crawl statistics",
    "description": "Search a live BitTorrent DHT metadata corpus and see how fast it is growing. Two endpoints: /search with category filters and relevance ranking, and /stats with a per-minute capture rate you can verify. No endpoint or key needed — the corpus is crawled and hosted by this Actor's operator.",
    "version": "1.1",
    "x-build-id": "1opd8r0gKYaj9Up8z"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/apricot_inference~fast-tracker/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-apricot_inference-fast-tracker",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    },
    "/acts/apricot_inference~fast-tracker/runs": {
      "post": {
        "operationId": "runs-sync-apricot_inference-fast-tracker",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor and returns information about the initiated run in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/runsResponseSchema"
                }
              }
            }
          }
        }
      }
    },
    "/acts/apricot_inference~fast-tracker/run-sync": {
      "post": {
        "operationId": "run-sync-apricot_inference-fast-tracker",
        "x-openai-isConsequential": false,
        "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
        "tags": [
          "Run Actor"
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/inputSchema"
              }
            }
          }
        },
        "parameters": [
          {
            "name": "token",
            "in": "query",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Enter your Apify token here"
          }
        ],
        "responses": {
          "200": {
            "description": "OK"
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "inputSchema": {
        "type": "object",
        "properties": {
          "query": {
            "title": "Query",
            "type": "string",
            "description": "Free text, up to 200 characters. Separators are normalised, so \"ubuntu 24 04\" matches \"ubuntu-24.04-desktop-amd64.iso\". Leave empty to browse with filters only. This is a DHT crawl rather than a curated catalogue, so a specific title may genuinely not be present — run the Crawl statistics action to see what the corpus does contain."
          },
          "category": {
            "title": "Category",
            "enum": [
              "",
              "video",
              "audio",
              "software",
              "archive",
              "document",
              "image"
            ],
            "type": "string",
            "description": "Restrict to one category. These describe file content, not intent: a Linux or game ISO is \"archive\", while \"software\" means installers and packages (.exe, .msi, .deb, .rpm, .apk). Leave unset unless you are sure which one you want — the filter is exact, so the wrong guess returns nothing rather than less.",
            "default": ""
          },
          "sort": {
            "title": "Sort order",
            "enum": [
              "seeders",
              "newest",
              "relevance",
              "size"
            ],
            "type": "string",
            "description": "Seeders, Newest and Size are the corpus server's own orderings, forwarded untouched. Relevance has no server-side equivalent — that API sorts by seeders, size or capture time only — so it is computed by this Actor over a candidate window drawn in seeder order. That makes it a re-ranking of candidates rather than of the whole corpus, and it needs a query.",
            "default": "seeders"
          },
          "minSeeders": {
            "title": "Minimum seeders",
            "minimum": 0,
            "type": "integer",
            "description": "Drop records below this seeder count. Falls back to the DHT peer count for records the tracker scrape has not reached yet.",
            "default": 0
          },
          "year": {
            "title": "Year",
            "type": "string",
            "description": "Release year parsed from the name, for example 2024. Only matches records the parse job has processed."
          },
          "resolution": {
            "title": "Resolution",
            "type": "string",
            "description": "Resolution parsed from the name, for example 1080p."
          },
          "maxItems": {
            "title": "Maximum records",
            "minimum": 1,
            "maximum": 100200,
            "type": "integer",
            "description": "Stop after this many records. Paging is capped at offset 100000, so roughly 100200 records are reachable for any single query — narrow the query rather than paging deeper.",
            "default": 1000
          },
          "pageSize": {
            "title": "Records per request",
            "minimum": 1,
            "maximum": 200,
            "type": "integer",
            "description": "The API caps this at 200. Lower it only to be gentler on the corpus host.",
            "default": 200
          },
          "action": {
            "title": "Action",
            "enum": [
              "search",
              "stats"
            ],
            "type": "string",
            "description": "Search returns records to the dataset. Crawl statistics measures how fast the corpus is growing and publishes the evidence.",
            "default": "search"
          },
          "statsWindowMinutes": {
            "title": "Measurement window",
            "minimum": 1,
            "maximum": 1440,
            "type": "integer",
            "description": "How far back to count captures. At roughly 150 records per minute, 60 minutes costs about 45 requests against the corpus host.",
            "default": 60
          },
          "statsMaxPages": {
            "title": "Page budget",
            "minimum": 1,
            "maximum": 2000,
            "type": "integer",
            "description": "Hard ceiling on requests for the measurement. If the budget runs out before the window is covered, the result reports the shorter window it actually measured rather than extrapolating.",
            "default": 200
          },
          "crossCheckSeconds": {
            "title": "Cross-check dwell",
            "minimum": 0,
            "maximum": 900,
            "type": "integer",
            "description": "The row count is read before and after the measurement; the delta is an independent estimate of the same rate. Set a dwell to widen that interval — below 10 seconds the batch writer's commit boundaries dominate and the figure is noise. 0 uses however long the measurement took.",
            "default": 0
          },
          "relevancePoolMultiplier": {
            "title": "Candidate pool multiplier",
            "minimum": 1,
            "maximum": 50,
            "type": "integer",
            "description": "Candidates to collect per requested record. 5 means a 200-record page is chosen from 1000 candidates.",
            "default": 5
          },
          "relevanceMaxCandidates": {
            "title": "Maximum candidates",
            "minimum": 200,
            "maximum": 20000,
            "type": "integer",
            "description": "Hard ceiling on the candidate window, whatever the multiplier works out to. Every 200 candidates is one request against a deployment that is also crawling.",
            "default": 2000
          },
          "standbyStatsCacheSecs": {
            "title": "Statistics cache",
            "minimum": 0,
            "maximum": 3600,
            "type": "integer",
            "description": "How long a computed /stats report is reused. 0 recomputes on every request.",
            "default": 60
          },
          "standbyStatsMaxPages": {
            "title": "Statistics page budget",
            "minimum": 1,
            "maximum": 500,
            "type": "integer",
            "description": "Request ceiling for one /stats measurement. Lower than the batch budget because an HTTP caller is waiting for the response.",
            "default": 60
          },
          "includeStats": {
            "title": "Attach corpus statistics to every run",
            "type": "boolean",
            "description": "Store a corpus snapshot under CRAWL_STATS in the key-value store, so a dataset can be dated against the corpus it came from. Costs one request.",
            "default": true
          },
          "requestTimeoutSecs": {
            "title": "Request timeout",
            "minimum": 5,
            "maximum": 300,
            "type": "integer",
            "description": "Per-attempt timeout for a single API request.",
            "default": 60
          },
          "maxRequestRetries": {
            "title": "Retries per request",
            "minimum": 0,
            "maximum": 10,
            "type": "integer",
            "description": "Retries after the first attempt, for timeouts, 5xx and rate limiting. Backoff is exponential with jitter and honours Retry-After.",
            "default": 4
          }
        }
      },
      "runsResponseSchema": {
        "type": "object",
        "properties": {
          "data": {
            "type": "object",
            "properties": {
              "id": {
                "type": "string"
              },
              "actId": {
                "type": "string"
              },
              "userId": {
                "type": "string"
              },
              "startedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "finishedAt": {
                "type": "string",
                "format": "date-time",
                "example": "2025-01-08T00:00:00.000Z"
              },
              "status": {
                "type": "string",
                "example": "READY"
              },
              "meta": {
                "type": "object",
                "properties": {
                  "origin": {
                    "type": "string",
                    "example": "API"
                  },
                  "userAgent": {
                    "type": "string"
                  }
                }
              },
              "stats": {
                "type": "object",
                "properties": {
                  "inputBodyLen": {
                    "type": "integer",
                    "example": 2000
                  },
                  "rebootCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "restartCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "resurrectCount": {
                    "type": "integer",
                    "example": 0
                  },
                  "computeUnits": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "options": {
                "type": "object",
                "properties": {
                  "build": {
                    "type": "string",
                    "example": "latest"
                  },
                  "timeoutSecs": {
                    "type": "integer",
                    "example": 300
                  },
                  "memoryMbytes": {
                    "type": "integer",
                    "example": 1024
                  },
                  "diskMbytes": {
                    "type": "integer",
                    "example": 2048
                  }
                }
              },
              "buildId": {
                "type": "string"
              },
              "defaultKeyValueStoreId": {
                "type": "string"
              },
              "defaultDatasetId": {
                "type": "string"
              },
              "defaultRequestQueueId": {
                "type": "string"
              },
              "buildNumber": {
                "type": "string",
                "example": "1.0.0"
              },
              "containerUrl": {
                "type": "string"
              },
              "usage": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "integer",
                    "example": 1
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              },
              "usageTotalUsd": {
                "type": "number",
                "example": 0.00005
              },
              "usageUsd": {
                "type": "object",
                "properties": {
                  "ACTOR_COMPUTE_UNITS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATASET_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "KEY_VALUE_STORE_WRITES": {
                    "type": "number",
                    "example": 0.00005
                  },
                  "KEY_VALUE_STORE_LISTS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_READS": {
                    "type": "integer",
                    "example": 0
                  },
                  "REQUEST_QUEUE_WRITES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_INTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "DATA_TRANSFER_EXTERNAL_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                    "type": "integer",
                    "example": 0
                  },
                  "PROXY_SERPS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}