{"record":{"id":"98a40aa34b8adf6d","repo":"crewAIInc/crewAI","slug":"tool-crewai-definition-must-resolve-inside-the-p","errorCode":null,"errorMessage":"[tool.crewai] definition must resolve inside the project root; got {definition!r}.","messagePattern":"\\[tool\\.crewai\\] definition must resolve inside the project root; got (.+?)\\.","errorType":"exception","errorClass":"ProjectDefinitionError","httpStatus":null,"severity":"error","filePath":"lib/crewai-core/src/crewai_core/project.py","lineNumber":132,"sourceCode":"        )\n\n    try:\n        root = root_path.resolve(strict=True)\n    except OSError as exc:\n        raise ProjectDefinitionError(\n            f\"Invalid project root for [tool.crewai] definition: {exc}\"\n        ) from exc\n\n    candidate = root / definition_path\n    try:\n        resolved_candidate = candidate.resolve(strict=False)\n    except OSError as exc:\n        raise ProjectDefinitionError(\n            f\"Invalid [tool.crewai] definition path {definition!r}: {exc}\"\n        ) from exc\n\n    if not resolved_candidate.is_relative_to(root):\n        raise ProjectDefinitionError(\n            \"[tool.crewai] definition must resolve inside the project root; \"\n            f\"got {definition!r}.\"\n        )\n\n    if not resolved_candidate.exists():\n        raise ProjectDefinitionError(\n            \"[tool.crewai] definition must point to an existing file; \"\n            f\"got {definition!r}.\"\n        )\n\n    if not resolved_candidate.is_file():\n        raise ProjectDefinitionError(\n            \"[tool.crewai] definition must point to a regular file; \"\n            f\"got {definition!r}.\"\n        )\n\n    return resolved_candidate\n","sourceCodeStart":114,"sourceCodeEnd":150,"githubUrl":"https://github.com/crewAIInc/crewAI/blob/754d7323beb2fd042e33444a115ea2d5a47193f0/lib/crewai-core/src/crewai_core/project.py#L114-L150","documentation":"Raised when the resolved candidate path is not inside the resolved project root (is_relative_to fails), i.e. the definition escapes the project via '..' segments or through a symlink that resolves outside the root. This is a path-containment security guard: the crew definition must live within the project. Reported as ProjectDefinitionError with the offending definition value.","triggerScenarios":"definition = \"../../other-project/main.py\", or definition = \"link/main.py\" where link is a symlink to a directory outside the project root; any value whose resolved absolute path is not a prefix-descendant of root.","commonSituations":"Monorepos where the crew code lives in a sibling package and users try '../../' hops; accidentally committing a symlink to /etc or another checkout; shared crew code referenced across repositories.","solutions":["Move or copy the definition file inside the project root and reference it with a plain relative path.","If you need shared code, install it as a package dependency instead of path-hopping out of the project.","Replace symlinks that point outside the root with real files or a proper package reference."],"exampleFix":"# before\n[tool.crewai]\ndefinition = \"../../shared/crew/main.py\"\n\n# after\n# move the file into this project, then:\n[tool.crewai]\ndefinition = \"src/crew/main.py\"","handlingStrategy":"validation","validationCode":"from pathlib import Path\n\ndef stays_inside(definition: str, root: Path) -> bool:\n    r = root.resolve(strict=True)\n    c = (r / definition).resolve(strict=False)\n    return c.is_relative_to(r)","typeGuard":null,"tryCatchPattern":"except ProjectDefinitionError as e:\n    if \"inside the project root\" in str(e):\n        raise SecurityError(str(e)) from e","preventionTips":["Never allow '..' segments or out-of-tree symlinks in definition values.","In monorepos, package shared crew code instead of path-hopping."],"tags":["security","path-traversal","configuration","symlink"],"backgroundTag":null,"analyzedSha":"754d7323beb2fd042e33444a115ea2d5a47193f0","analyzedAt":"2026-08-15T04:06:56.746Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}