{"record":{"id":"7cc11ba340d60552","repo":"risingwavelabs/risingwave","slug":"invalid-postgres-cdc-table-name-expected-sc","errorCode":null,"errorMessage":"Invalid Postgres CDC table name '{}'. Expected 'schema.table'.","messagePattern":"Invalid Postgres CDC table name '(.+?)'\\. Expected 'schema\\.table'\\.","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/frontend/src/handler/create_table.rs","lineNumber":1141,"sourceCode":"\n    while let Some(ch) = chars.next() {\n        if in_quote {\n            if ch == '\"' {\n                if chars.peek() == Some(&'\"') {\n                    current.push('\"');\n                    chars.next();\n                } else {\n                    in_quote = false;\n                    just_closed_quote = true;\n                }\n            } else {\n                current.push(ch);\n            }\n        } else {\n            match ch {\n                '.' => {\n                    if current.is_empty() {\n                        return Err(anyhow!(\n                            \"Invalid Postgres CDC table name '{}'. Expected 'schema.table'.\",\n                            external_table_name\n                        )\n                        .into());\n                    }\n                    parts.push(std::mem::take(&mut current));\n                    just_closed_quote = false;\n                }\n                '\"' if current.is_empty() => {\n                    in_quote = true;\n                }\n                '\"' => {\n                    return Err(anyhow!(\n                        \"Invalid Postgres CDC table name '{}'. Expected 'schema.table'.\",\n                        external_table_name\n                    )\n                    .into());\n                }","sourceCodeStart":1123,"sourceCodeEnd":1159,"githubUrl":"https://github.com/risingwavelabs/risingwave/blob/6469eb736d691e8e9b8a419a57edd6429ca77417/src/frontend/src/handler/create_table.rs#L1123-L1159","documentation":"The Postgres CDC table-name parser (`parse_postgres_cdc_external_table_name`) walks the string char-by-char supporting double-quoted identifiers; a '.' encountered while `current` is empty (e.g. a leading dot or 'schema..table') is invalid because it would produce an empty identifier segment.","triggerScenarios":"table_name = '.public.table' or 'public..table' or '\".t\"' patterns in a postgres-cdc CREATE TABLE option.","commonSituations":"Templated DDL inserting an empty variable ('{schema}.{table}' with empty schema); accidental extra dot when concatenating schema and table strings.","solutions":["Remove empty segments: use exactly one dot between two non-empty identifiers.","If an identifier part starts with a dot by accident (string concat), fix the concatenation.","For quoted identifiers, ensure quotes wrap whole segments: '\"my schema\".table'.","Verify the final string has the 'schema.table' shape before passing it to RisingWave."],"exampleFix":"// before\nlet name = format!(\"{}.{}\", schema_or_empty, table); // '.public.users'\n// after\nassert!(!schema.is_empty());\nlet name = format!(\"{}.{}\", schema, table); // 'public.users'","handlingStrategy":"validation","validationCode":"const segs = name.split('.');\nif (segs.some(s => s.length === 0)) throw new Error(`Postgres CDC table name has empty segment: ${name}`);","typeGuard":"const hasNoEmptySegments = (n) => n.split('.').every(s => s.length > 0);","tryCatchPattern":null,"preventionTips":["Guard template variables ({schema}, {table}) against empty values before concatenation.","Validate the joined name matches /^([^.\"]+|\"[^\"]+\")(\\.([^.\"]+|\"[^\"]+\"))?$/ before DDL.","Log the fully assembled option string in CI so empty segments are visible."],"tags":["cdc","postgres","table-name-format","frontend"],"backgroundTag":"invalid-argument-format","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"}