{
  "openapi": "3.0.1",
  "info": {
    "title": "Substack Scraper — Posts, Comments & Newsletters",
    "description": "Scrape Substack publications: complete post archives with no silently skipped pages, full comment threads including nested replies, publication discovery by topic, and the recommendation graph. Respects paywalls by design.",
    "version": "1.0",
    "x-build-id": "m8yAbEwXq6tzdYxXu"
  },
  "servers": [
    {
      "url": "https://api.apify.com/v2"
    }
  ],
  "paths": {
    "/acts/pixflor~substack-scraper/run-sync-get-dataset-items": {
      "post": {
        "operationId": "run-sync-get-dataset-items-pixflor-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/pixflor~substack-scraper/runs": {
      "post": {
        "operationId": "runs-sync-pixflor-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/pixflor~substack-scraper/run-sync": {
      "post": {
        "operationId": "run-sync-pixflor-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": {
          "mode": {
            "title": "What to scrape",
            "enum": [
              "posts",
              "search",
              "discover",
              "recommendations",
              "comments"
            ],
            "type": "string",
            "description": "Pick one. 'posts' = a publication's archive. 'search' = posts matching a query inside a publication. 'discover' = find publications by topic when you don't know their URLs. 'recommendations' = the publications a newsletter recommends. 'comments' = full comment threads, replies included.",
            "default": "posts"
          },
          "publications": {
            "title": "Publications",
            "type": "array",
            "description": "One or more Substack publications. Accepts whatever you have to hand: a bare name (bigtechnology), a host (bigtechnology.substack.com), a full URL, or a custom domain (www.astralcodexten.com). Not needed for 'discover' mode.",
            "default": [
              "bigtechnology"
            ],
            "items": {
              "type": "string"
            }
          },
          "discoverQuery": {
            "title": "Discover: topic",
            "type": "string",
            "description": "Only used by 'discover' mode. The topic to find publications for, e.g. 'artificial intelligence', 'personal finance', 'climate'. This is how you find newsletters when you don't already know who writes about something."
          },
          "searchQuery": {
            "title": "Search text",
            "type": "string",
            "description": "In 'search' mode this is sent to Substack's own search inside the publication. In 'posts' mode it filters the returned rows on title, subtitle, teaser, tags and author."
          },
          "includeBody": {
            "title": "Include full post text",
            "type": "boolean",
            "description": "Fetch the full text of each post. Costs one extra request per post, so it is off by default. Only FREE posts return a body: paywalled posts return metadata and the public teaser, never the paid text. That is deliberate — see the Actor description.",
            "default": false
          },
          "sort": {
            "title": "Archive order",
            "enum": [
              "new",
              "top",
              "community"
            ],
            "type": "string",
            "description": "How Substack should order the archive before this Actor sweeps it. 'new' is newest-first, 'top' is by popularity.",
            "default": "new"
          },
          "sortBy": {
            "title": "Sort results by",
            "enum": [
              "default",
              "newest",
              "oldest",
              "reactions",
              "comments",
              "words"
            ],
            "type": "string",
            "description": "How to order the rows you get back. 'default' keeps the order Substack returned them in.",
            "default": "default"
          },
          "freeOnly": {
            "title": "Free posts only",
            "type": "boolean",
            "description": "Keep only posts anyone can read. These are the ones that can return a full body.",
            "default": false
          },
          "paidOnly": {
            "title": "Paywalled posts only",
            "type": "boolean",
            "description": "Keep only subscriber-only posts. Useful for studying what a publication puts behind its paywall — you get titles, teasers and engagement, not the paid text.",
            "default": false
          },
          "author": {
            "title": "Author",
            "type": "string",
            "description": "Keep only posts with this name among their bylines. Partial, case-insensitive."
          },
          "tag": {
            "title": "Tag",
            "type": "string",
            "description": "Keep only posts carrying this Substack tag. Partial, case-insensitive."
          },
          "postType": {
            "title": "Post type",
            "enum": [
              "",
              "newsletter",
              "podcast",
              "thread",
              "video"
            ],
            "type": "string",
            "description": "Keep only one kind of post: newsletter, podcast, thread or video.",
            "default": ""
          },
          "withAudioOnly": {
            "title": "Only posts with audio",
            "type": "boolean",
            "description": "Keep only posts with a podcast recording or a voiceover.",
            "default": false
          },
          "minReactions": {
            "title": "Minimum reactions",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only posts with at least this many likes.",
            "default": 0
          },
          "minComments": {
            "title": "Minimum comments",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only posts with at least this many comments.",
            "default": 0
          },
          "minWords": {
            "title": "Minimum word count",
            "minimum": 0,
            "type": "integer",
            "description": "Keep only posts of at least this length. Useful for separating real essays from short notes.",
            "default": 0
          },
          "publishedWithinDays": {
            "title": "Published within (days)",
            "minimum": 0,
            "type": "integer",
            "description": "Only posts from the last N days. 0 means the whole archive.",
            "default": 0
          },
          "maxItems": {
            "title": "Maximum rows",
            "minimum": 1,
            "maximum": 20000,
            "type": "integer",
            "description": "How many rows to return, and what you pay for. The archive sweep pages correctly, so large values really do return complete data rather than quietly skipping posts.",
            "default": 100
          }
        }
      },
      "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
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}