Skip to content

Commit 664e419

Browse files
committed
docs(agent): update skill with the latest changes
1 parent 88d0459 commit 664e419

4 files changed

Lines changed: 51 additions & 0 deletions

File tree

agent-skill/Scrapling-Skill.zip

1005 Bytes
Binary file not shown.

agent-skill/Scrapling-Skill/SKILL.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -302,6 +302,8 @@ QuotesSpider(crawldir="./crawl_data").start()
302302
```
303303
Press Ctrl+C to pause gracefully - progress is saved automatically. Later, when you start the spider again, pass the same `crawldir`, and it will resume from where it stopped.
304304

305+
While iterating on a spider's `parse()` logic, set `development_mode = True` on the spider class to cache responses to disk on the first run and replay them on subsequent runs - so you can re-run the spider as many times as you want without re-hitting the target servers. The cache lives in `.scrapling_cache/{spider.name}/` by default and can be overridden with `development_cache_dir`. Don't ship a spider with this enabled.
306+
305307
### Advanced Parsing & Navigation
306308
```python
307309
from scrapling.fetchers import Fetcher

agent-skill/Scrapling-Skill/references/spiders/advanced.md

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,49 @@ async def on_start(self, resuming: bool = False):
8585
self.logger.info("Starting fresh crawl")
8686
```
8787

88+
## Development Mode
89+
90+
When you're iterating on a spider's `parse()` logic, re-hitting the target servers on every run is slow and noisy. Development mode caches every response to disk on the first run and replays them from disk on subsequent runs, so you can tweak your selectors and re-run the spider as many times as you want without making a single network request.
91+
92+
Enable it by setting `development_mode = True` on your spider:
93+
94+
```python
95+
class MySpider(Spider):
96+
name = "my_spider"
97+
start_urls = ["https://example.com"]
98+
development_mode = True
99+
100+
async def parse(self, response: Response):
101+
yield {"title": response.css("title::text").get("")}
102+
```
103+
104+
The first run fetches normally and stores each response on disk. Every subsequent run serves the same requests from the cache, skipping the network entirely.
105+
106+
### Cache Location
107+
108+
By default, responses are cached in `.scrapling_cache/{spider.name}/` relative to the current working directory (where you ran the spider from, **not** where the spider script lives). You can override the location with `development_cache_dir`:
109+
110+
```python
111+
class MySpider(Spider):
112+
name = "my_spider"
113+
start_urls = ["https://example.com"]
114+
development_mode = True
115+
development_cache_dir = "/tmp/my_spider_cache"
116+
```
117+
118+
### How It Works
119+
120+
1. **Cache key**: Each response is keyed by the request's fingerprint, so any change to fingerprint-affecting attributes (`fp_include_kwargs`, `fp_include_headers`, `fp_keep_fragments`) will produce a fresh fetch.
121+
2. **Storage format**: One JSON file per response, named `{fingerprint_hex}.json`. The body is base64-encoded so binary content is preserved exactly. Writes are atomic (temp file + rename).
122+
3. **Replay**: On a cache hit, the engine skips the network entirely, including `download_delay`, rate limiting, and the `is_blocked()` retry path. The cached response goes straight to your callback.
123+
4. **Stats**: Cached requests still count toward `requests_count`, `response_bytes`, and the per-status counters, so your stat output looks the same as a normal crawl. Two extra counters, `cache_hits` and `cache_misses`, let you see how the cache performed.
124+
125+
### Clearing the Cache
126+
127+
There's no automatic expiration. To force a fresh crawl, delete the cache directory or call the manager's `clear()` method directly.
128+
129+
**Warning:** Development mode is meant for development, not production. Cached responses never expire, and replay bypasses rate limiting and blocked-request retries. Don't ship a spider with `development_mode = True`.
130+
88131
## Streaming
89132

90133
For long-running spiders or applications that need real-time access to scraped items, use the `stream()` method instead of `start()`:
@@ -220,6 +263,8 @@ print(f"Failed: {stats.failed_requests_count}")
220263
print(f"Blocked: {stats.blocked_requests_count}")
221264
print(f"Offsite filtered: {stats.offsite_requests_count}")
222265
print(f"Robots.txt disallowed: {stats.robots_disallowed_count}")
266+
print(f"Cache hits: {stats.cache_hits}")
267+
print(f"Cache misses: {stats.cache_misses}")
223268
print(f"Items scraped: {stats.items_scraped}")
224269
print(f"Items dropped: {stats.items_dropped}")
225270
print(f"Response bytes: {stats.response_bytes}")

agent-skill/Scrapling-Skill/references/spiders/architecture.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,10 @@ When a request comes in, the Session Manager routes it to the correct session ba
6060

6161
An optional system that, if enabled, saves the crawler's state (pending requests + seen URL fingerprints) to a pickle file on disk. Writes are atomic (temp file + rename) to prevent corruption. Checkpoints are saved periodically at a configurable interval and on graceful shutdown. Upon successful completion (not paused), checkpoint files are automatically cleaned up.
6262

63+
### Response Cache
64+
65+
An optional cache that, when development mode is enabled, stores every fetched response on disk and replays it on subsequent runs. Each response is keyed by request fingerprint and serialized as JSON (with the body base64-encoded so binary content survives). It's meant for iterating on `parse()` logic without re-hitting the target servers, not for production use.
66+
6367
### Output
6468

6569
Scraped items are collected in an `ItemList` (a list subclass with `to_json()` and `to_jsonl()` export methods). Crawl statistics are tracked in a `CrawlStats` dataclass which contains a lot of useful info.

0 commit comments

Comments
 (0)