{
  "openapi": "3.0.1",
  "info": {
    "title": "Substack Scraper - Newsletters, Posts, Comments & Leaderboards",
    "description": "Scrape Substack newsletters, posts and comments: subscriber counts, paid plan prices, author socials and contact emails, leaderboard ranks, full text of free posts, likes, restacks. Search by keyword or category. $0.45 per 1,000 newsletters, $0.27 per 1,000 posts, $0.18 per 1,000 comments.",
    "version": "0.1",
    "x-build-id": "BnQkV5MFdQ0JBL2m2"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/topapi~substack-scraper/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-topapi-substack-scraper",
        "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/topapi~substack-scraper/runs": {
      "post": {
        "operationId": "runs-sync-topapi-substack-scraper",
        "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/topapi~substack-scraper/run-sync": {
      "post": {
        "operationId": "run-sync-topapi-substack-scraper",
        "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": {
          "startUrls": {
            "title": "🔗 Substack links or names",
            "type": "array",
            "description": "A newsletter (\"https://www.lennysnewsletter.com\", \"lenny.substack.com\" or \"lenny\"; custom domains work), a post (\".../p/<slug>\"), a profile (\"substack.com/@lenny\"), a leaderboard (\"substack.com/leaderboard/technology/paid\") or a search link (\"substack.com/search/ai\").",
            "items": {
              "type": "string"
            }
          },
          "searchQueries": {
            "title": "🔎 Search terms",
            "type": "array",
            "description": "Words to search Substack for, e.g. \"artificial intelligence\", \"personal finance\". Search type below picks newsletters or posts.",
            "items": {
              "type": "string"
            }
          },
          "searchType": {
            "title": "Search type",
            "enum": [
              "newsletters",
              "posts"
            ],
            "type": "string",
            "description": "What the search terms find: newsletters (one full newsletter row each) or posts.",
            "default": "newsletters"
          },
          "maxResultsPerSearch": {
            "title": "Max results per search term",
            "minimum": 1,
            "maximum": 1000,
            "type": "integer",
            "description": "Newsletters (or posts) per search term.",
            "default": 20
          },
          "leaderboardCategories": {
            "title": "🏆 Leaderboard categories",
            "type": "array",
            "description": "Substack categories to read rankings from. \"All categories\" has a Rising list only.",
            "items": {
              "type": "string",
              "enum": [
                "bestseller",
                "culture",
                "technology",
                "business",
                "us-politics",
                "finance",
                "food",
                "sports",
                "art",
                "world-politics",
                "health-politics",
                "news",
                "fashionandbeauty",
                "music",
                "faith",
                "climate",
                "science",
                "literature",
                "fiction",
                "health",
                "design",
                "travel",
                "parenting",
                "philosophy",
                "comics",
                "international",
                "crypto",
                "history",
                "humor",
                "education",
                "film-and-tv",
                "home-garden",
                "games"
              ],
              "enumTitles": [
                "All categories (Rising)",
                "Culture",
                "Technology",
                "Business",
                "U.S. Politics",
                "Finance",
                "Food & Drink",
                "Sports",
                "Art & Illustration",
                "World Politics",
                "Health Politics",
                "News",
                "Fashion & Beauty",
                "Music",
                "Faith & Spirituality",
                "Climate & Environment",
                "Science",
                "Literature",
                "Fiction",
                "Health & Wellness",
                "Design",
                "Travel",
                "Parenting",
                "Philosophy",
                "Comics",
                "International",
                "Crypto",
                "History",
                "Humor",
                "Education",
                "Film & TV",
                "Home & Garden",
                "Games"
              ]
            }
          },
          "boardTypes": {
            "title": "Lists to read",
            "type": "array",
            "description": "Which ranking of each category: Substack's paid Bestsellers leaderboard (100), the Rising leaderboard (100), or the category's Top / Top paid / Top free lists (up to 525).",
            "items": {
              "type": "string",
              "enum": [
                "paid",
                "rising",
                "top",
                "topPaid",
                "topFree"
              ],
              "enumTitles": [
                "Bestsellers (paid leaderboard)",
                "Rising",
                "Top",
                "Top paid",
                "Top free"
              ]
            },
            "default": [
              "paid"
            ]
          },
          "maxResultsPerBoard": {
            "title": "Max newsletters per list",
            "minimum": 1,
            "maximum": 525,
            "type": "integer",
            "description": "Newsletters per category list, in rank order. Leaderboards hold 100; Top lists up to 525.",
            "default": 25
          },
          "includePublicationInfo": {
            "title": "Newsletter rows",
            "type": "boolean",
            "description": "Save a newsletter row for each newsletter link (newsletters found by search or a leaderboard always get one).",
            "default": true
          },
          "newsletterDetails": {
            "title": "Author profile, email and post count",
            "type": "boolean",
            "description": "Read the author's public profile (followers, Twitter/X, LinkedIn, Instagram, YouTube, TikTok, website), the About page (contact emails), the sitemap (post count) and the latest posts (last post date, posts per month). Off = faster big leaderboard sweeps with the list fields only.",
            "default": true
          },
          "includeRecommendations": {
            "title": "Recommended newsletters",
            "type": "boolean",
            "description": "Add the newsletters each newsletter recommends (name, link) to its row.",
            "default": false
          },
          "minSubscribers": {
            "title": "Min subscribers",
            "minimum": 0,
            "type": "integer",
            "description": "Skip newsletters with fewer subscribers (or no public count). Skipped newsletters are not charged and their posts are not read."
          },
          "onlyPaidNewsletters": {
            "title": "Only newsletters with a paid plan",
            "type": "boolean",
            "description": "Skip newsletters without a paid plan (not charged, posts not read).",
            "default": false
          },
          "onlyWithEmail": {
            "title": "Only newsletters with a contact email",
            "type": "boolean",
            "description": "Skip newsletters with no contact email on their About page (not charged, posts not read).",
            "default": false
          },
          "includePosts": {
            "title": "Posts of newsletter links",
            "type": "boolean",
            "description": "Read the posts of every newsletter link you gave.",
            "default": true
          },
          "scrapePostsOfFoundNewsletters": {
            "title": "Posts of newsletters found by search or leaderboards",
            "type": "boolean",
            "description": "Also read the posts of every newsletter a search term or leaderboard found.",
            "default": false
          },
          "maxPostsPerNewsletter": {
            "title": "Max posts per newsletter",
            "minimum": 0,
            "type": "integer",
            "description": "Posts per newsletter after your filters. 0 = newsletter rows only.",
            "default": 20
          },
          "postSort": {
            "title": "Post order",
            "enum": [
              "new",
              "top"
            ],
            "type": "string",
            "description": "Read each archive newest first or most-liked first.",
            "default": "new"
          },
          "searchInNewsletter": {
            "title": "Search inside each newsletter",
            "type": "string",
            "description": "Only posts of each newsletter that match these words (Substack's archive search)."
          },
          "includeContent": {
            "title": "Full text of free posts",
            "type": "boolean",
            "description": "Read the full body of every free post. Paid posts keep their metadata and Substack's public teaser line.",
            "default": true
          },
          "contentFormat": {
            "title": "Body format",
            "enum": [
              "textAndHtml",
              "text",
              "html",
              "markdown",
              "all"
            ],
            "type": "string",
            "description": "How the full text of free posts is saved: plain text, HTML, Markdown, or several at once.",
            "default": "textAndHtml"
          },
          "audience": {
            "title": "Free or paid posts",
            "enum": [
              "all",
              "free",
              "paid"
            ],
            "type": "string",
            "description": "Keep only free posts or only paid posts. Paid posts carry metadata and the public teaser line, never the paid body.",
            "default": "all"
          },
          "postType": {
            "title": "Post type",
            "enum": [
              "all",
              "newsletter",
              "podcast",
              "thread",
              "video"
            ],
            "type": "string",
            "description": "Keep only one kind of post.",
            "default": "all"
          },
          "dateFrom": {
            "title": "Published on or after",
            "type": "string",
            "description": "YYYY-MM-DD."
          },
          "dateTo": {
            "title": "Published on or before",
            "type": "string",
            "description": "YYYY-MM-DD."
          },
          "withinDays": {
            "title": "Published in the last N days",
            "minimum": 1,
            "type": "integer",
            "description": "Keep only posts from the last N days."
          },
          "minReactions": {
            "title": "Min likes",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only posts with at least this many likes."
          },
          "minComments": {
            "title": "Min comments",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only posts with at least this many comments."
          },
          "minWordCount": {
            "title": "Min word count",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only posts with at least this many words."
          },
          "titleContains": {
            "title": "Title contains",
            "type": "string",
            "description": "Only posts whose title or subtitle contains these words."
          },
          "includeComments": {
            "title": "Comments",
            "type": "boolean",
            "description": "Save the comment threads of every post (replies flattened, with parent id and depth).",
            "default": false
          },
          "maxCommentsPerPost": {
            "title": "Max comments per post",
            "minimum": 1,
            "type": "integer",
            "description": "Comments and replies per post, in Substack's order (best first).",
            "default": 50
          },
          "maxItems": {
            "title": "Max rows",
            "minimum": 0,
            "type": "integer",
            "description": "Most rows to save in this run (newsletters, posts and comments together). 0 = no cap.",
            "default": 500
          },
          "monitorMode": {
            "title": "Only new since the last run",
            "type": "boolean",
            "description": "Scheduled runs save only posts and comments not saved before, and newsletters that are new or changed (subscribers, prices, post count, rank). State is kept in the named store below.",
            "default": false
          },
          "monitorStoreName": {
            "title": "Monitor store name",
            "type": "string",
            "description": "Named key-value store that remembers what earlier runs saved. Use one name per watch list.",
            "default": "substack-monitor"
          },
          "proxyConfiguration": {
            "title": "Proxy",
            "type": "object",
            "description": "Optional. Substack answers without a proxy; a proxy you set is tried first.",
            "default": {
              "useApifyProxy": false
            }
          },
          "maxConcurrency": {
            "title": "Parallel requests",
            "minimum": 1,
            "maximum": 20,
            "type": "integer",
            "description": "Requests to Substack at the same time.",
            "default": 8
          }
        }
      },
      "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
                  },
                  "PROXY_UNBLOCKER_UNITS": {
                    "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
                  },
                  "PROXY_UNBLOCKER_UNITS": {
                    "type": "integer",
                    "example": 0
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}