datawhalechina/hello-agents · warning · FileNotFoundError
学习计划不存在:{domain}
Error message
学习计划不存在:{domain} What it means
Standard FileNotFoundError raised by FileManager.read_plan when BASE_DIR/<domain>/plan.md does not exist on disk. It is a guard before any I/O: the file simply was never saved (or was saved under a different domain name), so there is nothing to read.
Source
Thrown at Co-creation-projects/Yixiang-Wu-LearningAgent/core/file_manager.py:114
return session_path
def read_plan(self, domain: str) -> str:
"""
读取学习计划
Args:
domain: 领域名称
Returns:
计划内容
Raises:
FileNotFoundError: 如果计划不存在
"""
plan_path = self.BASE_DIR / domain / "plan.md"
if not plan_path.exists():
raise FileNotFoundError(f"学习计划不存在:{domain}")
try:
return plan_path.read_text(encoding="utf-8")
except Exception as e:
raise FileReadError(f"无法读取学习计划:{e}")
def domain_exists(self, domain: str) -> bool:
"""
检查领域是否存在
Args:
domain: 领域名称
Returns:
是否存在
"""
return (self.BASE_DIR / domain).exists()
View on GitHub (pinned to 606a07d341)
Solutions
- Call save_plan (or an initializer that creates plan.md) before read_plan for a new domain
- Normalize the domain string (strip + casefold consistently) everywhere it is used as a key
- Check domain_exists(domain) before reading and surface a friendly 'create plan first' flow
- Pin BASE_DIR to an absolute path so the working directory cannot change resolution
Example fix
# before
plan_path = self.BASE_DIR / domain / "plan.md"
if not plan_path.exists():
raise FileNotFoundError(f"学习计划不存在:{domain}")
# after
plan_path = self.BASE_DIR / domain.strip().lower() / "plan.md"
if not plan_path.exists():
raise FileNotFoundError(
f"学习计划不存在:{domain}(已存在的领域: "
f"{[p.name for p in self.BASE_DIR.iterdir() if p.is_dir()]})"
) Defensive patterns
Strategy: validation
Validate before calling
if not fm.domain_exists(domain):
# no domain -> nothing was ever saved; create plan first
fm.save_plan(domain, default_plan(domain))
plan = fm.read_plan(domain) Try / catch
try:
plan = fm.read_plan(domain)
except FileNotFoundError:
plan = default_plan(domain) # or prompt user to create one
fm.save_plan(domain, plan) Prevention
- Canonicalize the domain key (strip().lower()) in one helper and use it for both save and read
- Check domain_exists() before read_plan and branch to a creation flow
- Keep BASE_DIR absolute so different working directories cannot split the state
When it happens
Trigger: Calling read_plan(domain) before save_plan was ever called for that domain; domain string mismatch (case differences, leading/trailing whitespace, different naming between save and read); the workspace/BASE_DIR was deleted or reset; running from a different working directory so BASE_DIR resolves elsewhere.
Common situations: Fresh clone with empty learning workspace; agent resumed a session with a slightly different domain label; tests that read without first writing; BASE_DIR relative path resolving differently between launch contexts.
Related errors
AI-assisted analysis of datawhalechina/hello-agents@606a07d341 (2026-08-14).
Data as JSON: /api/errors/b060ddfe10e5e0b9.
Report an issue: GitHub.