# Xiaohongshu Keyword Search Scraper (`opspilot.cc/xiaohongshu-keyword-search-scraper`) Actor

Search Xiaohongshu（小红书） notes by keyword. Filter by sort order, note type, and publishing time with automatic pagination.

- **URL**: https://apify.com/opspilot.cc/xiaohongshu-keyword-search-scraper.md
- **Developed by:** [wang wei](https://apify.com/opspilot.cc) (community)
- **Categories:** Social media
- **Stats:** 9 total users, 6 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

$0.10 / actor start

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## Xiaohongshu Keyword Search Scraper

Search public Xiaohongshu (Little Red Book / REDnote / 小红书) notes by **one keyword per run** and export structured results to an Apify Dataset. Built for marketers, content teams, e-commerce operators, and researchers who need reliable Xiaohongshu data without scraping infrastructure.

### Use it together with the other Xiaohongshu Actors

This Actor is one piece of a 4-piece Xiaohongshu toolkit. Run them in sequence to go from a topic, to a single note detail, to its comment thread.

| Where in the pipeline | Actor | Console | Use it to |
|---:|---|---|---|
| before / step ① | [Xiaohongshu Image Note Detail Scraper](https://console.apify.com/actors/kP7I5XcMAaLxaYj0R) | [kP7I5XcMAaLxaYj0R](https://console.apify.com/actors/kP7I5XcMAaLxaYj0R) | step ② — feed it any `noteId` from your search output to get the full image-note payload |
| sister Actor / step ② | [Xiaohongshu Video Note Detail Scraper](https://console.apify.com/actors/nIGSWsYF5htLotphk) | [nIGSWsYF5htLotphk](https://console.apify.com/actors/nIGSWsYF5htLotphk) | step ② — same, but for video notes (returns playback URLs + duration) |
| after / step ③ | [Xiaohongshu Note Comments Scraper](https://console.apify.com/actors/LNXEA0uuHX70vchNW) | [LNXEA0uuHX70vchNW](https://console.apify.com/actors/LNXEA0uuHX70vchNW) | step ③ — once you have a note, pull the comment thread (paginated) |

**You are here:** **Xiaohongshu Keyword Search Scraper** (step ① (start here)) — run this on its own for `find notes by keyword`. The other 3 Actors live in their own Apify listings — click their Console links to open them in a new tab.

### What this Xiaohongshu scraper does

- 🔎 **Search Xiaohongshu by keyword** — one search query, up to 20 unique notes returned.
- 📊 **Structured Xiaohongshu data** — note ID, title, description, note type, engagement metrics, author profile, cover image, and a shareable `noteUrl`.
- 🧹 **Deduplicated output** — duplicate note IDs are removed automatically.
- 📦 **Raw payload preserved** — every record keeps the original upstream response under `rawData` for downstream pipelines.
- 📈 **Run-level summary** — `SUMMARY` includes quota usage, source request count.
- 💸 **Free tier friendly** — 5 runs per day for free Apify users; no setup or API key required.

### Xiaohongshu Keyword Search Scraper — Input

```json
{
  "keyword": "美食推荐",
  "page": 1,
  "sortType": "general",
  "noteType": "不限",
  "timeFilter": "不限"
}
```

#### Input fields

| Field | Required | Default | Description |
|---|---:|---:|---|
| `keyword` | Yes | `美食推荐` | One Xiaohongshu search keyword, max 100 characters (e.g. `美食推荐`, `护肤`, `东京旅游`) |
| `page` | No | `1` | Page number, between 1 and 10. Each page triggers one upstream request (`page=3` = 3 requests). See *Pagination* below. |
| `searchId` | When `page >= 2` | `""` | Pagination token from a previous run. Copy from the previous SUMMARY field `nextSearchId` (or from the first Dataset item's `rawData.search_id`). Leave blank for page 1. |
| `searchSessionId` | When `page >= 2` | `""` | Pagination token from a previous run. Copy from the previous SUMMARY field `nextSearchSessionId` (or from the first Dataset item's `rawData.search_session_id`). Leave blank for page 1. |
| `sortType` | No | `general` | Sort order: `general` (Xiaohongshu default), `time_descending` (latest), `popularity_descending` (most liked), `comment_descending` (most commented), `collect_descending` (most collected), `english_preferred` (English-first) |
| `noteType` | No | `不限` | Note type filter: `不限` (all), `视频笔记` (video only), `普通笔记` (image only), `直播笔记` (live only) |
| `timeFilter` | No | `不限` | Publish-time filter: `不限` (all time), `一天内` (within 24 hours), `一周内` (within 7 days), `半年内` (within 6 months) |

The Actor is locked to **one keyword per run** (use multiple runs for different keywords). The `page` field controls how many pages — and therefore how many upstream requests (a request) — one run performs. The three filter fields map 1:1 to upstream query parameters; leaving them at their defaults is identical to Xiaohongshu's default search page.

### Pagination

The Actor follows Xiaohongshu's pagination protocol: every page after the first needs the **opaque `search_id` / `search_session_id` tokens** that the upstream returned on the previous page.

#### How to paginate (two-step pattern)

**Step 1 — First page (always works without tokens):**

```json
{
  "keyword": "美食推荐",
  "page": 1,
  "sortType": "popularity_descending"
}
```

After this run, read the Apify Key-Value Store entry `SUMMARY` — it contains:

```json
{
  "ok": true,
  "pagesFetched": 1,
  "requests": 1,
  "nextSearchId": "PASTE_THIS_INTO_searchId",
  "nextSearchSessionId": "PASTE_THIS_INTO_searchSessionId",
  "hasMoreInSource": true
}
```

If `hasMoreInSource` is `true`, more pages exist.

**Step 2 — Subsequent pages (must include both tokens):**

```json
{
  "keyword": "美食推荐",
  "page": 2,
  "searchId": "<paste nextSearchId from Step 1>",
  "searchSessionId": "<paste nextSearchSessionId from Step 1>"
}
```

Each call to `page=N` walks `N` pages forward. If `page=5` is requested but `hasMore` becomes `false` after page 3, the Actor stops and the SUMMARY's `pagesFetched` will be `3`, not `5`.

#### Cost & quota

- **Cost**: each page costs the same as a single request — see the Apify Actor pricing model.
- **Free Apify users**: 5 runs per day, regardless of pages per run. A `page=5` run consumes 1 quota slot.
- **Paid Apify users**: unlimited runs and unlimited pages.
- Maximum pages per run is **10** (input cap, validator rejects `page > 10`).

#### Why pagination tokens are opaque

Xiaohongshu's app API generates a fresh pagination token pair for every search session; the Actor must forward these exact tokens to fetch the next page. There is no way to derive them from the keyword alone. Treat them like a session cookie: copy from the previous run's SUMMARY and pass back unchanged.

### What you get in the Apify Dataset

Each Dataset item is one Xiaohongshu note with the following fields:

- **Query lineage** — `keyword`, `page`, `rank`, `collectedAt`
- **Xiaohongshu note identifiers** — `noteId`, `xsecToken`, `noteUrl`
- **Content** — `title`, `description`, `noteType`, `coverUrl`
- **Engagement** — `likedCount`, `collectedCount`, `commentCount`, `sharedCount`
- **Author** — `userId`, `nickname`, `avatar`
- **Raw upstream response** — full `rawData` object for any custom downstream processing

### Free tier and pricing

| Tier | Daily runs | Per run | Notes |
|---|---:|---|---|
| Free Apify users | 5 runs / day | Up to 20 unique notes | Quota enforced via Actor KV store |
| Paid Apify users (`APIFY_USER_IS_PAYING=1`) | Unlimited | Up to 20 unique notes | No quota gate inside the Actor |

Quota is per calendar day (UTC). Runs 1-5 succeed; run 6+ on the free tier fails fast with `Free tier limit reached` and writes a `SUMMARY.ok=false` record so you can detect the rejection programmatically.

### How to use the Xiaohongshu scraper

1. Open the Actor page on Apify.
2. Type one Xiaohongshu keyword (Chinese, English, or any language) into the **keyword** field.
3. Optionally pick a **sortType**, **noteType**, or **timeFilter** — see *Common filter recipes* below for ready-made combos. All three default to Xiaohongshu's standard search page.
4. Set `page` to the number of pages you want (default 1, max 10). Each page = one upstream request.
5. If `page >= 2`, paste `searchId` and `searchSessionId` from the previous run's SUMMARY (see *Pagination* above).
6. Click **Start**. The Actor searches Xiaohongshu and writes results to the run's Dataset in seconds.
7. Download the Dataset as JSON, CSV, or Excel, or pipe it into another Apify Actor.

### Common filter recipes

| Goal | Input combination |
|---|---|
| Trending video posts from the last week | `keyword: "美食推荐"`, `noteType: "视频笔记"`, `timeFilter: "一周内"`, `sortType: "popularity_descending"` |
| Latest image notes only | `keyword: "护肤"`, `noteType: "普通笔记"`, `sortType: "time_descending"` |
| 24-hour hot list, any type | `keyword: "东京旅游"`, `timeFilter: "一天内"`, `sortType: "popularity_descending"` |
| Most-discussed videos this half-year | `keyword: "健身"`, `noteType: "视频笔记"`, `timeFilter: "半年内"`, `sortType: "comment_descending"` |
| English-first discovery | `keyword: "Tokyo travel"`, `sortType: "english_preferred"` |

Leaving every filter at its default reproduces Xiaohongshu's standard search page — the most common usage. Combine any recipe with `page=2..10` plus the previous run's pagination tokens for deeper coverage.

### Use cases

- **Xiaohongshu keyword research** for content marketing and SEO.
- **Trend monitoring** on Xiaohongshu by recurring keyword searches.
- **Competitor note collection** for benchmark studies.
- **Influencer and KOL discovery** through author metadata.
- **E-commerce sourcing** for trending product mentions on Xiaohongshu.
- **Academic and market research** on Chinese social media content.

### Limitations

- Exactly one keyword and one upstream request per run. Multi-keyword batch runs and pagination are intentionally disabled to keep the free tier predictable.
- Field availability depends on the data returned by Xiaohongshu for the given search.
- Search rankings and available notes may change between runs.
- Use the data responsibly and comply with applicable laws and Xiaohongshu's terms of service.

### FAQ

**Is this an official Xiaohongshu API?** No. This Actor is a third-party Xiaohongshu scraper built on top of an independent data source. It is not affiliated with, endorsed by, or connected to Xiaohongshu.

**Do I need to bring my own API key or pay for Xiaohongshu data?** No. The Actor is fully managed. You only need an Apify account.

**Can I scrape multiple keywords in one run?** Not in this Actor. Run the Actor once per keyword. To automate batches, chain it with another Apify Actor such as the Apify Scheduler or a workflow tool.

**Why are the results limited to 20 notes per run?** Each run performs exactly one upstream request, and the upstream returns roughly 20 notes per page. The cap matches real upstream capacity and keeps the Actor affordable for casual users. Paid users can still get more coverage by running the Actor multiple times with different keywords.

**How do I paginate to get more than one page of results?** Run the Actor with `page=1` first. After it finishes, open the Apify Key-Value Store entry `SUMMARY` and copy the `nextSearchId` / `nextSearchSessionId` values. Then run again with `page=2` and paste those two values into `searchId` and `searchSessionId`. Repeat for `page=3`, etc. See the *Pagination* section above for the full pattern.

**How many pages can I fetch in one run?** Up to 10 pages (the `page` field caps at 10). The Actor stops early if upstream returns `hasMore=false` or an empty page — the SUMMARY's `pagesFetched` field reports the actual count.

**How is the free-tier quota counted?** Each Actor run — successful or not — consumes one quota slot. Quota resets every day at 00:00 UTC.

### Related searches

If you are looking for a way to scrape Xiaohongshu, search Xiaohongshu notes by keyword, run a Xiaohongshu search scraper, or pull a Xiaohongshu dataset for analysis, this Actor is the simplest starting point. The output JSON is schema-stable, so you can build downstream pipelines (Python, Node.js, Sheets, Airtable, Notion) without parsing the raw Xiaohongshu HTML.

# Actor input Schema

## `keyword` (type: `string`):

One Xiaohongshu search keyword, for example: 美食推荐. The Actor is locked to one keyword per run; use multiple runs to search different keywords.

## `page` (type: `integer`):

Page number, start from 1. The Actor calls the upstream once per page, so `page=3` makes 3 upstream requests. The default of 1 keeps every run cheap.

## `searchId` (type: `string`):

Required when page >= 2. Copy from the previous run SUMMARY field `nextSearchId` (or from the first item's `rawData.search_id`). Leave blank for page = 1.

## `searchSessionId` (type: `string`):

Required when page >= 2. Copy from the previous run SUMMARY field `nextSearchSessionId` (or from the first item's `rawData.search_session_id`). Leave blank for page = 1.

## `sortType` (type: `string`):

How Xiaohongshu ranks the returned notes. Defaults to `general` (Xiaohongshu general sort).

## `noteType` (type: `string`):

Filter by note type. Defaults to `不限` (all types).

## `timeFilter` (type: `string`):

Filter by publish time. Defaults to `不限` (all time).

## Actor input object example

```json
{
  "keyword": "美食推荐",
  "page": 1,
  "searchId": "",
  "searchSessionId": "",
  "sortType": "general",
  "noteType": "不限",
  "timeFilter": "不限"
}
```

# Actor output Schema

## `dataset` (type: `string`):

One normalized dataset item per unique Xiaohongshu note, with the original source record preserved in rawData.

## `summary` (type: `string`):

Keyword, filters, pages fetched, unique notes, duplicates, request count, and error details.

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {};

// Run the Actor and wait for it to finish
const run = await client.actor("opspilot.cc/xiaohongshu-keyword-search-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {}

# Run the Actor and wait for it to finish
run = client.actor("opspilot.cc/xiaohongshu-keyword-search-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{}' |
apify call opspilot.cc/xiaohongshu-keyword-search-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,opspilot.cc/xiaohongshu-keyword-search-scraper"
        }
    }
}

```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/JECW4SdwsOOgtuobc/builds/v9r9OQ0Id4JN9cJCt/openapi.json
