Vexaloom Labs

TikTok Anonymous For You Feed Snapshot Scraper

Capture a snapshot of posts currently surfacing on TikTok's anonymous For You feed, with engagement stats, author, music, and hashtag details for each video or slideshow.

Input schema

Input fields, types, required flags, descriptions, defaults, and prefills come from the published definition. Prefill examples are distinct from defaults.

FieldTypeRequiredDescription
maxItemsintegeroptionalMaximum number of For You posts to collect. Set to 0 to return no items.
regionstringoptionalMarket hint for the feed. AUTO follows the connection region. A selected market asks TikTok for that market and uses a matching datacenter exit when one is available; TikTok may still override the hint.
minPlayCountintegeroptionalDrop posts with fewer plays than this value. 0 disables the filter.
Show all input fields
FieldTypeRequiredDescription
maxItemsintegeroptionalMaximum number of For You posts to collect. Set to 0 to return no items.
regionstringoptionalMarket hint for the feed. AUTO follows the connection region. A selected market asks TikTok for that market and uses a matching datacenter exit when one is available; TikTok may still override the hint.
minPlayCountintegeroptionalDrop posts with fewer plays than this value. 0 disables the filter.
postedWithinDaysintegeroptionalOnly keep posts created in the last N days. 0 disables the filter.
excludeAdsbooleanoptionalDrop posts that TikTok marks as advertisements.

Download the published input schema

View complete JSON
{
  "description": "Capture an anonymous snapshot of TikTok's For You feed. No cookies, login, or proxy configuration required.",
  "properties": {
    "excludeAds": {
      "default": false,
      "description": "Drop posts that TikTok marks as advertisements.",
      "prefill": false,
      "title": "Exclude Ads",
      "type": "boolean"
    },
    "maxItems": {
      "default": 30,
      "description": "Maximum number of For You posts to collect. Set to 0 to return no items.",
      "maximum": 300,
      "minimum": 0,
      "prefill": 3,
      "title": "Maximum Posts",
      "type": "integer"
    },
    "minPlayCount": {
      "default": 0,
      "description": "Drop posts with fewer plays than this value. 0 disables the filter.",
      "maximum": 1000000000,
      "minimum": 0,
      "prefill": 0,
      "title": "Minimum Play Count",
      "type": "integer"
    },
    "postedWithinDays": {
      "default": 0,
      "description": "Only keep posts created in the last N days. 0 disables the filter.",
      "maximum": 365,
      "minimum": 0,
      "prefill": 0,
      "title": "Posted Within (Days)",
      "type": "integer"
    },
    "region": {
      "default": "AUTO",
      "description": "Market hint for the feed. AUTO follows the connection region. A selected market asks TikTok for that market and uses a matching datacenter exit when one is available; TikTok may still override the hint.",
      "editor": "select",
      "enum": [
        "AUTO",
        "US",
        "GB",
        "CA",
        "AU",
        "NZ",
        "IE",
        "DE",
        "FR",
        "ES",
        "IT",
        "NL",
        "SE",
        "NO",
        "DK",
        "FI",
        "PL",
        "PT",
        "BR",
        "MX",
        "AR",
        "CL",
        "CO",
        "IN",
        "PK",
        "BD",
        "ID",
        "MY",
        "PH",
        "SG",
        "TH",
        "VN",
        "JP",
        "KR",
        "TR",
        "SA",
        "AE",
        "ZA",
        "NG",
        "EG",
        "KE"
      ],
      "enumTitles": [
        "Automatic (connection region)",
        "United States",
        "United Kingdom",
        "Canada",
        "Australia",
        "New Zealand",
        "Ireland",
        "Germany",
        "France",
        "Spain",
        "Italy",
        "Netherlands",
        "Sweden",
        "Norway",
        "Denmark",
        "Finland",
        "Poland",
        "Portugal",
        "Brazil",
        "Mexico",
        "Argentina",
        "Chile",
        "Colombia",
        "India",
        "Pakistan",
        "Bangladesh",
        "Indonesia",
        "Malaysia",
        "Philippines",
        "Singapore",
        "Thailand",
        "Vietnam",
        "Japan",
        "South Korea",
        "Turkey",
        "Saudi Arabia",
        "United Arab Emirates",
        "South Africa",
        "Nigeria",
        "Egypt",
        "Kenya"
      ],
      "prefill": "AUTO",
      "title": "Region",
      "type": "string"
    }
  },
  "required": [],
  "schemaVersion": 1,
  "title": "TikTok For You Feed Scraper Input",
  "type": "object"
}

Output schema

Published result links and storage locations. This schema is not an exhaustive contract for every field in a dataset record.

FieldTypeRequiredDescription
datastringoptionalDataset containing TikTok For You feed post records. Each row includes rank, postId, postUrl, caption, feedType, observedRegion, isPersonalized, engagement counts and rate, collectedAt, author, music, video, subtitles, POI, hashtags, and category labels.

Download the published output schema

View complete JSON
{
  "actorOutputSchemaVersion": 1,
  "description": "Posts captured from the anonymous TikTok For You feed, with rank, engagement metrics, author, music, video, subtitles, POI, and category details.",
  "properties": {
    "data": {
      "description": "Dataset containing TikTok For You feed post records. Each row includes rank, postId, postUrl, caption, feedType, observedRegion, isPersonalized, engagement counts and rate, collectedAt, author, music, video, subtitles, POI, hashtags, and category labels.",
      "template": "{{links.apiDefaultDatasetUrl}}/items",
      "title": "For You Feed Posts",
      "type": "string"
    }
  },
  "title": "TikTok Anonymous For You Feed Snapshot Scraper Output"
}

Dataset schema

Published dataset views and any declared field definitions. A view can select only a subset of the returned record fields.

Download the published dataset schema

View complete JSON
{
  "actorSpecification": 1,
  "fields": {
    "adAuthorization": {
      "description": "Ad authorization flag reported by TikTok for some promoted posts",
      "title": "Ad Authorization",
      "type": "boolean"
    },
    "aigcLabelType": {
      "description": "TikTok's AI-generated-content label type when present",
      "title": "AIGC Label Type",
      "type": "integer"
    },
    "author": {
      "description": "Post author/creator information",
      "properties": {
        "avatarUrl": {
          "type": "string"
        },
        "bio": {
          "type": "string"
        },
        "displayName": {
          "type": "string"
        },
        "followerCount": {
          "type": "integer"
        },
        "followingCount": {
          "type": "integer"
        },
        "heartCount": {
          "type": "integer"
        },
        "id": {
          "type": "string"
        },
        "privateAccount": {
          "type": "boolean"
        },
        "roomId": {
          "type": "string"
        },
        "secUid": {
          "type": "string"
        },
        "username": {
          "type": "string"
        },
        "verified": {
          "type": "boolean"
        },
        "videoCount": {
          "type": "integer"
        }
      },
      "title": "Author",
      "type": "object"
    },
    "caption": {
      "description": "Post caption text including hashtags and mentions",
      "title": "Caption",
      "type": "string"
    },
    "categoryType": {
      "description": "TikTok's numeric content category for the post",
      "title": "Category Type",
      "type": "integer"
    },
    "collectCount": {
      "description": "Number of bookmarks/collects (from statsV2)",
      "title": "Collect Count",
      "type": "integer"
    },
    "collectedAt": {
      "description": "ISO 8601 UTC datetime when the snapshot was collected",
      "title": "Collected At",
      "type": "string"
    },
    "commentCount": {
      "description": "Number of comments (from statsV2)",
      "title": "Comment Count",
      "type": "integer"
    },
    "createTime": {
      "description": "Unix timestamp when the post was created",
      "title": "Create Time (Unix)",
      "type": "integer"
    },
    "createdAt": {
      "description": "ISO 8601 UTC datetime when the post was created",
      "title": "Created At",
      "type": "string"
    },
    "diversificationId": {
      "description": "Feed diversification identifier when the source provides it",
      "title": "Diversification ID",
      "type": [
        "integer",
        "string"
      ]
    },
    "diversificationLabels": {
      "description": "Content diversification labels from the SSR payload",
      "items": {
        "type": "string"
      },
      "title": "Diversification Labels",
      "type": "array"
    },
    "duetEnabled": {
      "description": "Whether duets are allowed",
      "title": "Duet Enabled",
      "type": "boolean"
    },
    "engagementRate": {
      "description": "Likes plus comments plus shares divided by plays, rounded to 4 decimals",
      "title": "Engagement Rate",
      "type": "number"
    },
    "feedType": {
      "description": "Always 'foryou' for this actor",
      "title": "Feed Type",
      "type": "string"
    },
    "hashtags": {
      "description": "Hashtags used in the post",
      "items": {
        "properties": {
          "id": {
            "type": "string"
          },
          "isCommerce": {
            "type": "boolean"
          },
          "name": {
            "type": "string"
          }
        },
        "type": "object"
      },
      "title": "Hashtags",
      "type": "array"
    },
    "images": {
      "description": "Slideshow images for photo posts (postType='slideshow')",
      "title": "Images",
      "type": "array"
    },
    "isAd": {
      "description": "Whether this post is a paid advertisement",
      "title": "Is Ad",
      "type": "boolean"
    },
    "isAigc": {
      "description": "Present and true when TikTok labels the content as AI-generated",
      "title": "Is AIGC",
      "type": "boolean"
    },
    "isPersonalized": {
      "description": "Always false — the feed is anonymous (no login required)",
      "title": "Is Personalized",
      "type": "boolean"
    },
    "itemControl": {
      "description": "Per-post interaction permissions reported by TikTok",
      "properties": {
        "canComment": {
          "type": "boolean"
        },
        "canCreatorRedirect": {
          "type": "boolean"
        },
        "canMusicRedirect": {
          "type": "boolean"
        },
        "canRepost": {
          "type": "boolean"
        },
        "canShare": {
          "type": "boolean"
        }
      },
      "title": "Item Control",
      "type": "object"
    },
    "likeCount": {
      "description": "Number of likes (from statsV2)",
      "title": "Like Count",
      "type": "integer"
    },
    "locationCreated": {
      "description": "Country code where the post was created, when the source provides it",
      "title": "Location Created",
      "type": "string"
    },
    "mediaUrlExpiresAt": {
      "description": "ISO 8601 UTC timestamp when the signed media URLs (playUrl, cover, etc.) expire",
      "title": "Media URL Expires At",
      "type": "string"
    },
    "mentions": {
      "description": "@mentions in the post caption",
      "items": {
        "properties": {
          "awemeId": {
            "type": "string"
          },
          "end": {
            "type": "integer"
          },
          "start": {
            "type": "integer"
          },
          "username": {
            "type": "string"
          }
        },
        "type": "object"
      },
      "title": "Mentions",
      "type": "array"
    },
    "music": {
      "description": "Sound/music used in the post",
      "properties": {
        "album": {
          "type": "string"
        },
        "authorName": {
          "type": "string"
        },
        "coverUrl": {
          "type": "string"
        },
        "duration": {
          "type": "integer"
        },
        "id": {
          "type": "string"
        },
        "original": {
          "type": "boolean"
        },
        "playUrl": {
          "type": "string"
        },
        "title": {
          "type": "string"
        }
      },
      "title": "Music",
      "type": "object"
    },
    "observedRegion": {
      "description": "Requested market label (or AUTO when following the connection region)",
      "title": "Observed Region",
      "type": "string"
    },
    "playCount": {
      "description": "Number of video plays (from statsV2)",
      "title": "Play Count",
      "type": "integer"
    },
    "poi": {
      "description": "Place tagged on the post when present",
      "properties": {
        "address": {
          "type": "string"
        },
        "category": {
          "type": "string"
        },
        "city": {
          "type": "string"
        },
        "cityCode": {
          "type": "string"
        },
        "countryCode": {
          "type": "string"
        },
        "id": {
          "type": "string"
        },
        "latitude": {
          "type": "number"
        },
        "longitude": {
          "type": "number"
        },
        "name": {
          "type": "string"
        },
        "province": {
          "type": "string"
        }
      },
      "title": "Point of Interest",
      "type": "object"
    },
    "postId": {
      "description": "TikTok's unique post ID (64-bit int as string)",
      "title": "Post ID",
      "type": "string"
    },
    "postType": {
      "description": "Either 'video' or 'slideshow'",
      "title": "Post Type",
      "type": "string"
    },
    "postUrl": {
      "description": "Direct URL to the TikTok post",
      "title": "Post URL",
      "type": "string"
    },
    "rank": {
      "description": "1-based position in this snapshot after filters",
      "title": "Rank",
      "type": "integer"
    },
    "repostCount": {
      "description": "Number of reposts (from statsV2)",
      "title": "Repost Count",
      "type": "integer"
    },
    "shareCount": {
      "description": "Number of shares (from statsV2)",
      "title": "Share Count",
      "type": "integer"
    },
    "shareEnabled": {
      "description": "Whether sharing is enabled",
      "title": "Share Enabled",
      "type": "boolean"
    },
    "stitchEnabled": {
      "description": "Whether stitching is allowed",
      "title": "Stitch Enabled",
      "type": "boolean"
    },
    "textLanguage": {
      "description": "Language code of the caption text",
      "title": "Text Language",
      "type": "string"
    },
    "textTranslatable": {
      "description": "Whether TikTok offers a translation for the caption",
      "title": "Text Translatable",
      "type": "boolean"
    },
    "video": {
      "description": "Video technical metadata and media URLs",
      "properties": {
        "codecType": {
          "type": "string"
        },
        "cover": {
          "type": "string"
        },
        "definition": {
          "type": "string"
        },
        "duration": {
          "type": "integer"
        },
        "dynamicCover": {
          "type": "string"
        },
        "format": {
          "type": "string"
        },
        "height": {
          "type": "integer"
        },
        "originCover": {
          "type": "string"
        },
        "playUrl": {
          "type": "string"
        },
        "quality": {
          "type": "string"
        },
        "ratio": {
          "type": "string"
        },
        "size": {
          "type": "integer"
        },
        "subtitles": {
          "items": {
            "properties": {
              "expiresAt": {
                "type": "string"
              },
              "format": {
                "type": "string"
              },
              "languageCode": {
                "type": "string"
              },
              "languageName": {
                "type": "string"
              },
              "url": {
                "type": "string"
              }
            },
            "type": "object"
          },
          "type": "array"
        },
        "width": {
          "type": "integer"
        }
      },
      "title": "Video",
      "type": "object"
    }
  },
  "title": "TikTok For You Feed Posts",
  "views": {
    "overview": {
      "description": "TikTok For You page posts with engagement metrics and snapshot position.",
      "display": {
        "component": "table",
        "properties": {
          "caption": {
            "format": "text",
            "label": "Caption"
          },
          "commentCount": {
            "format": "number",
            "label": "Comments"
          },
          "createdAt": {
            "format": "text",
            "label": "Created At"
          },
          "engagementRate": {
            "format": "number",
            "label": "Engagement Rate"
          },
          "likeCount": {
            "format": "number",
            "label": "Likes"
          },
          "observedRegion": {
            "format": "text",
            "label": "Region"
          },
          "playCount": {
            "format": "number",
            "label": "Plays"
          },
          "postId": {
            "format": "text",
            "label": "Post ID"
          },
          "postUrl": {
            "format": "link",
            "label": "Post URL"
          },
          "rank": {
            "format": "number",
            "label": "Rank"
          }
        }
      },
      "title": "Feed Overview",
      "transformation": {
        "fields": [
          "rank",
          "postId",
          "postUrl",
          "caption",
          "observedRegion",
          "playCount",
          "likeCount",
          "commentCount",
          "engagementRate",
          "createdAt"
        ]
      }
    }
  }
}

Key-value schema

Published key-value store definitions, when provided by this build.

This definition is not present in the default published build. See the published README for available documentation.

Published README

Read the full published documentation

TikTok Anonymous For You Feed Snapshot Scraper

TikTok's For You feed is a moving recommendation stream. This actor captures an anonymous snapshot of the posts surfacing on it — no account, cookies, or login — and returns the ranking, engagement counts, creator details, music, video metadata, subtitles, tagged places, and category labels for each post.

What this actor does

  • Collects posts from TikTok's anonymous For You feed, starting with the warm page payload and extending the snapshot across fresh anonymous sessions.
  • Deduplicates by post ID and stops when the requested count is reached or the rotating feed stops producing new posts.
  • Labels each post with its snapshot rank, collectedAt, and a derived engagementRate.
  • Supports a best-effort region market hint, plus client-side filters for minimum plays, recency, and ads.
  • Omits fields a post does not carry instead of writing nulls or placeholders.
  • Falls back to a headless browser only when the lightweight collection path returns nothing.

Input

Field Type Default Description
maxItems integer 30 Maximum posts to collect (0–300). 0 returns no rows.
region select AUTO AUTO follows the connection region. A market code (40 supported markets) asks TikTok for that market and uses a matching exit when available; TikTok may still override the hint.
minPlayCount integer 0 Drop posts below this play count. 0 disables the filter.
postedWithinDays integer 0 Keep only posts created in the last N days (0–365). 0 disables the filter.
excludeAds boolean false Remove posts TikTok marks as advertisements.

Example: quick US snapshot

{
  "maxItems": 20,
  "region": "US"
}

Example: recent high-reach posts, no ads

{
  "maxItems": 50,
  "region": "GB",
  "minPlayCount": 100000,
  "postedWithinDays": 7,
  "excludeAds": true
}

Example: daily trend check

{
  "maxItems": 40,
  "region": "AUTO",
  "postedWithinDays": 1
}

Saved tasks that still send the old regionObservation key keep working: when region is absent, a supported regionObservation value is used as the market hint. Other values are kept only as the informational observedRegion label.

Output per post

Field Description
rank 1-based position in this snapshot after filters.
postId TikTok's unique post ID.
postUrl Direct URL to the post.
postType "video" or "slideshow".
caption Caption text, including hashtags and mentions as typed.
feedType Always "foryou" for this actor.
observedRegion Requested market label, or AUTO when following the connection region.
isPersonalized Always false — the feed is anonymous.
createTime Unix timestamp when the post was created.
createdAt Creation time as an ISO 8601 UTC string.
collectedAt Collection time as an ISO 8601 UTC string.
locationCreated Country code where the post was created, when the source provides it.
playCount / likeCount / commentCount / shareCount / collectCount / repostCount Engagement counters, preferring TikTok's exact string counters.
engagementRate (likes + comments + shares) / plays, rounded to four decimals.
textLanguage Language code detected for the caption.
textTranslatable Whether TikTok offers a caption translation.
stitchEnabled / duetEnabled / shareEnabled Whether each interaction type is enabled.
isAd / adAuthorization Ad-related flags.
isAigc / aigcLabelType AI-generated-content labels when TikTok provides them.
categoryType TikTok's numeric content category.
diversificationId / diversificationLabels Feed diversification metadata when present.
author Object: id, secUid, username, displayName, bio, verified, privateAccount, roomId, avatarUrl, followerCount, followingCount, heartCount, videoCount.
music Object: id, title, authorName, original, duration, album, playUrl, coverUrl.
video Object: width, height, duration, ratio, definition, codecType, format, size, quality, playUrl, cover, originCover, dynamicCover, subtitles[] (languageCode, languageName, format, url, expiresAt).
poi Tagged place when present: id, name, address, category, city, cityCode, countryCode, province, latitude, longitude.
itemControl Interaction permissions: canComment, canRepost, canShare, canMusicRedirect, canCreatorRedirect.
hashtags Array of {id, name, isCommerce} objects.
mentions Array of {username, start, end, awemeId} objects.
images Slideshow image URLs for photo posts.
mediaUrlExpiresAt ISO 8601 UTC time when signed media URLs expire.

Use cases

  • Trend researchers tracking which formats, sounds, and creators the recommendation engine is surfacing.
  • Brand and sponsorship teams spotting promoted posts and ad labels in an organic feed.
  • Competitive intelligence comparing creator reach and engagement across markets.
  • Academic researchers building anonymous feed snapshots for content-distribution studies.
  • Media and dashboard teams feeding live trend monitoring with ranked post data.

FAQ

Q: Do I need a TikTok account or cookies?
A: No. The actor works as an anonymous visitor. It accepts no credentials, session IDs, API keys, or proxy configuration.

Q: Can I choose a specific country's feed?
A: region is a best-effort hint. TikTok decides the feed from the connection location, so a selected market may be partially or fully overridden. The actor reports the requested label in observedRegion and never fabricates a detected country.

Q: How many posts can I get in one run?
A: You can request up to 300. The anonymous feed rotates and has no resumable cursor; one fresh session usually yields around 20–25 unique posts, so deeper requests rotate sessions. If the source exhausts first, the run reports the honest delivered count.

Q: Why did I get fewer posts than maxItems?
A: Either TikTok stopped serving new posts, the run reached its bounded session search cap, or the active filters removed them. The status message states which case applies and how many posts were filtered out.

Q: Will two runs return the same posts?
A: Not necessarily. Each run negotiates fresh anonymous sessions, so the snapshot changes over time.

Q: Are media links permanent?
A: No. Video, cover, and subtitle URLs are signed and expire, usually within about two days. mediaUrlExpiresAt records the expiry where it can be parsed; use postUrl as the stable reference.

Q: Why are some fields missing on some posts?
A: TikTok only includes fields such as poi, locationCreated, subtitles, or music album for some posts. Empty values are omitted rather than written as null.

Q: Does this return personalized recommendations?
A: No. The feed is an anonymous, non-personalized observation and every row carries isPersonalized: false.

Notes and limits

  • The snapshot is a point-in-time observation, not a replayable list. Posts may repeat across sessions and are deduplicated by ID.
  • A deep request is bounded by a session search cap. If the cap is reached first, the status message says so instead of claiming the source is exhausted.
  • locationCreated is supplied mainly by the initial page payload and is absent for most API-served posts.
  • Region selection can consume Apify Proxy traffic when a matching datacenter exit is available; AUTO uses the connection directly.
  • Signed media URLs should be refreshed by re-running the actor when they expire.

Python quickstart

Use a schema-derived input and the Python standard library to start a run. An Apify account and token are required for execution.

Open the step-by-step Python guide →

Source build IewtZ1qwYr8qhwUl2. Documentation is regenerated from the default published build; private drafts are not included.