{"record":{"id":"e0ae4733c42dcdcb","repo":"risingwavelabs/risingwave","slug":"root-directory-does-not-exist","errorCode":null,"errorMessage":"Root directory does not exist: {}","messagePattern":"Root directory does not exist: (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/connector/src/source/filesystem/opendal_source/batch_posix_fs_source.rs","lineNumber":119,"sourceCode":"\n#[async_trait]\nimpl SplitEnumerator for BatchPosixFsEnumerator {\n    type Properties = BatchPosixFsProperties;\n    type Split = BatchPosixFsSplit;\n\n    async fn new(\n        properties: Self::Properties,\n        _context: SourceEnumeratorContextRef,\n    ) -> ConnectorResult<Self> {\n        Ok(Self { properties })\n    }\n\n    async fn list_splits(&mut self) -> ConnectorResult<Vec<BatchPosixFsSplit>> {\n        // dummy list, just return one split\n        let root_path = Path::new(&self.properties.root);\n\n        if !root_path.exists() {\n            return Err(anyhow!(\"Root directory does not exist: {}\", self.properties.root).into());\n        }\n\n        // For batch source, we return exactly one split representing all files to be processed.\n        Ok(vec![BatchPosixFsSplit::new(\n            self.properties.root.clone(), // file_path is the root\n            \"114514\".into(),              // split_id does not matter\n        )])\n    }\n}\n\n/// Reader for batch posix fs source\n#[derive(Debug)]\npub struct BatchPosixFsReader {}\n\n#[async_trait]\nimpl SplitReader for BatchPosixFsReader {\n    type Properties = BatchPosixFsProperties;\n    type Split = BatchPosixFsSplit;","sourceCodeStart":101,"sourceCodeEnd":137,"githubUrl":"https://github.com/risingwavelabs/risingwave/blob/6469eb736d691e8e9b8a419a57edd6429ca77417/src/connector/src/source/filesystem/opendal_source/batch_posix_fs_source.rs#L101-L137","documentation":"list_splits for the batch POSIX FS source checks that the configured root directory exists before emitting its single dummy split. If Path::new(root).exists() is false, it refuses to proceed with this error naming the configured root path. It is a fail-fast guard against scanning a non-existent directory.","triggerScenarios":"Creating/starting a filesystem batch source whose MATCH_PATTERN/root path (self.properties.root) points to a directory that does not exist on the compute node, e.g. before mounting the volume or with a typo'd path.","commonSituations":"Typo in the s3/posix root path; shared filesystem (NFS/EFS) not mounted on the node running the source; container missing the volume mount; path deleted after source creation.","solutions":["Verify the path in the error message exists on the node: run `ls` on it from the same host/container as the compute node.","Fix the source's root/MATCH_PATTERN property if it's a typo (recreate or alter the source).","Mount the missing volume/shared filesystem into the container running RisingWave.","Check permissions - a path you can't stat may report as non-existent; ensure read access on parent directories."],"exampleFix":"-- before\nCREATE SOURCE s (...) WITH (connector = 'filesystem', match_pattern = 'data/events/*.parquet')\n-- after (path actually exists / mounted)\nCREATE SOURCE s (...) WITH (connector = 'filesystem', match_pattern = '/mnt/data/events/*.parquet')","handlingStrategy":"validation","validationCode":"// shell check before creating the source\nls /mnt/data/events/*.parquet || echo \"root path missing\"\n# or in SQL, test with a select on an existing source path first","typeGuard":null,"tryCatchPattern":"// caller (Rust)\nmatch enumerator.list_splits().await {\n    Ok(splits) => splits,\n    Err(e) if e.to_string().contains(\"Root directory does not exist\") => {\n        eprintln!(\"mount/fix root path first: {e}\"); Vec::new()\n    }\n    Err(e) => return Err(e),\n}","preventionTips":["Always verify the root path exists on the compute node (not your laptop) before creating the source.","Use absolute paths and volume mounts declared in the deployment manifest.","Check that NFS/EFS mounts come up before RisingWave starts (init containers / readiness probes)."],"tags":["filesystem","path","configuration","rust"],"backgroundTag":"directory-not-found","analyzedSha":"6469eb736d691e8e9b8a419a57edd6429ca77417","analyzedAt":"2026-09-11T21:06:21.487Z","contentChangedAt":"2026-09-11T21:06:21.487Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}