unclecode/crawl4ai · error · ValueError
link_preview_config must be LinkPreviewConfig object or dict
Error message
link_preview_config must be LinkPreviewConfig object or dict
What it means
CrawlerRunConfig accepts link_preview_config as None, a LinkPreviewConfig instance, or a plain dict (which it converts via LinkPreviewConfig.from_dict for backward compatibility). Any other type — string, tuple, list — raises this error.
Source
Thrown at crawl4ai/async_configs.py:1880
)
# Set default chunking strategy if None
if self.chunking_strategy is None:
self.chunking_strategy = RegexChunking()
# Deep Crawl Parameters
self.deep_crawl_strategy = deep_crawl_strategy
# Link Extraction Parameters
if link_preview_config is None:
self.link_preview_config = None
elif isinstance(link_preview_config, LinkPreviewConfig):
self.link_preview_config = link_preview_config
elif isinstance(link_preview_config, dict):
# Convert dict to config object for backward compatibility
self.link_preview_config = LinkPreviewConfig.from_dict(link_preview_config)
else:
raise ValueError("link_preview_config must be LinkPreviewConfig object or dict")
# Virtual Scroll Parameters
if virtual_scroll_config is None:
self.virtual_scroll_config = None
elif isinstance(virtual_scroll_config, VirtualScrollConfig):
self.virtual_scroll_config = virtual_scroll_config
elif isinstance(virtual_scroll_config, dict):
# Convert dict to config object for backward compatibility
self.virtual_scroll_config = VirtualScrollConfig.from_dict(virtual_scroll_config)
else:
raise ValueError("virtual_scroll_config must be VirtualScrollConfig object or dict")
# URL Matching Parameters
self.url_matcher = url_matcher
self.match_mode = match_mode
# Experimental Parameters
self.experimental = experimental or {}View on GitHub (pinned to 7e80152142)
Solutions
- Pass a dict of LinkPreviewConfig fields: link_preview_config={"include_external": True, "max_links": 10}
- Or construct the object: LinkPreviewConfig(include_external=True)
- If the value arrives as a JSON string, json.loads it first
Example fix
// before
cfg = CrawlerRunConfig(link_preview_config='{"max_links": 10}')
// after
import json
cfg = CrawlerRunConfig(link_preview_config=json.loads('{"max_links": 10}')) Defensive patterns
Strategy: type-guard
Validate before calling
from crawl4ai.async_configs import LinkPreviewConfig
if isinstance(link_preview_config, str):
import json
link_preview_config = json.loads(link_preview_config)
assert link_preview_config is None or isinstance(link_preview_config, (LinkPreviewConfig, dict)) Type guard
def is_link_preview_config(v) -> bool:
return v is None or isinstance(v, (LinkPreviewConfig, dict)) Prevention
- json.loads stringified config values before passing
- Keep nested config objects as dicts in JSON pipelines
When it happens
Trigger: Passing link_preview_config="enabled", a JSON string, a list of settings, or a config object from a different library/version.
Common situations: JSON config where the value parses as a string instead of an object; mixing crawl4ai versions where LinkPreviewConfig was imported from a relocated module.
Related errors
- concurrency must be positive
- timeout must be positive
- max_links must be positive
- score_threshold must be between 0.0 and 1.0
- At least one of include_internal or include_external must be
AI-assisted analysis of unclecode/crawl4ai@7e80152142 (2026-08-14).
Data as JSON: /api/errors/9f7aedd1948db962.
Report an issue: GitHub.