mvanhorn/last30days-skill · warning · DrillTargetError
No cluster matched {target!r}. Available clusters: {candidat
Error message
No cluster matched {target!r}. Available clusters: {candidates} What it means
DrillTargetError (a ValueError subclass) from resolve_drill_clusters when the target parses as a 1-based cluster index (e.g. '3', 'cluster 3', '#3') but the number is outside 1..len(report.clusters). The error carries the target and the report's clusters so its message can list available candidates.
Source
Thrown at skills/last30days/scripts/lib/planner.py:245
def _drill_cluster_text(report: schema.Report, cluster: schema.Cluster) -> str:
candidates = {candidate.candidate_id: candidate for candidate in report.ranked_candidates}
parts = [cluster.title]
for candidate_id in cluster.candidate_ids:
candidate = candidates.get(candidate_id)
if candidate:
parts.extend((candidate.title, candidate.snippet))
return " ".join(part for part in parts if part)
def resolve_drill_clusters(report: schema.Report, target: str) -> list[schema.Cluster]:
"""Resolve a 1-based cluster index or fuzzy title/entity description."""
cleaned = target.strip()
numeric = re.fullmatch(r"(?:cluster\s*)?#?(\d+)", cleaned, flags=re.IGNORECASE)
if numeric:
index = int(numeric.group(1))
if 1 <= index <= len(report.clusters):
return [report.clusters[index - 1]]
raise DrillTargetError(target, report.clusters)
target_entities = entity_extract.extract_text_entities(cleaned)
scored: list[tuple[float, schema.Cluster]] = []
for cluster in report.clusters:
cluster_text = _drill_cluster_text(report, cluster)
title_score = relevance.token_overlap_relevance(cleaned, cluster.title)
body_score = relevance.token_overlap_relevance(cleaned, cluster_text)
entity_score = entity_extract.entity_overlap(
target_entities,
entity_extract.extract_text_entities(cluster_text),
)
score = max(title_score, (0.75 * body_score) + (0.25 * entity_score))
scored.append((score, cluster))
scored.sort(key=lambda entry: entry[0], reverse=True)
if not scored or scored[0][0] < 0.35:
raise DrillTargetError(target, report.clusters)
return [scored[0][1]]View on GitHub (pinned to c7460f6114)
Solutions
- Use an index between 1 and len(report.clusters) — clusters are 1-based.
- Or pass the cluster title / entity description instead of a number; fuzzy matching will resolve it.
- Re-check the current report's cluster count before drilling.
Example fix
# before plan = build_drill_plan(report, target="7") # report has 4 clusters # after plan = build_drill_plan(report, target=str(len(report.clusters))) # or drill by title: plan = build_drill_plan(report, target="AI agent frameworks")
Defensive patterns
Strategy: validation
Validate before calling
import re
m = re.fullmatch(r"(?:cluster\s*)?#?(\d+)", target.strip(), re.IGNORECASE)
if m and not (1 <= int(m.group(1)) <= len(report.clusters)):
raise SystemExit(f"cluster index must be 1..{len(report.clusters)}") Try / catch
try:
plan = build_drill_plan(report, target=t)
except DrillTargetError as exc:
print(f"valid targets: 1..{len(report.clusters)} or cluster titles")
raise Prevention
- Clusters are 1-based — never use 0.
- Bounds-check numeric targets against len(report.clusters) before drilling.
- Prefer exact cluster titles; numbers go stale between report regenerations.
When it happens
Trigger: Calling build_drill_plan / resolve_drill_clusters with target='5' on a report whose clusters list has fewer than 5 entries; target='0' (index is 1-based, so 0 never matches); large indices after re-running with shallower depth produced fewer clusters.
Common situations: User asks to drill into cluster 7 from a previous report but the current report has 4 clusters; stale cluster numbers quoted from an earlier session; off-by-one from assuming 0-based indexing.
Related errors
- [Planner] Cannot read --plan file: {exc}\n
- [Planner] Invalid --plan JSON: {exc}\n
- Discovery supports listing sources only: reddit, hackernews,
- No listing sources are available for global trending
- No listing sources are available for {normalized_domain!r}
AI-assisted analysis of mvanhorn/last30days-skill@c7460f6114 (2026-08-15).
Data as JSON: /api/errors/f8701079f396a9e4.
Report an issue: GitHub.