{"record":{"id":"81021ff3d72f6237","repo":"apache/seatunnel","slug":"source-and-sink-can-not-be-null","errorCode":null,"errorMessage":"Source And Sink can not be null","messagePattern":"Source And Sink can not be null","errorType":"validation","errorClass":"JobDefineCheckException","httpStatus":null,"severity":"error","filePath":"seatunnel-engine/seatunnel-engine-core/src/main/java/org/apache/seatunnel/engine/core/parse/ConfigParserUtil.java","lineNumber":70,"sourceCode":"            ReadonlyConfig readonlyConfig,\n            ClassLoader classLoader,\n            Class<T> factoryClass,\n            String factoryId) {\n        Set<URL> factoryUrls = new HashSet<>();\n        URL factoryUrl =\n                FactoryUtil.getFactoryUrl(\n                        FactoryUtil.discoverFactory(classLoader, factoryClass, factoryId));\n        factoryUrls.add(factoryUrl);\n        return factoryUrls;\n    }\n\n    public static void checkGraph(\n            List<? extends Config> sources,\n            List<? extends Config> transforms,\n            List<? extends Config> sinks) {\n        log.debug(\"Check whether this config file can generate DAG:\");\n        if (CollectionUtils.isEmpty(sources) || CollectionUtils.isEmpty(sinks)) {\n            throw new JobDefineCheckException(\"Source And Sink can not be null\");\n        }\n        if (isSimpleGraph(sources, transforms, sinks)) {\n            checkSimpleGraph(sources, transforms, sinks);\n            return;\n        }\n        checkComplexGraph(sources, transforms, sinks);\n    }\n\n    private static boolean isSimpleGraph(\n            List<? extends Config> sources,\n            List<? extends Config> transforms,\n            List<? extends Config> sinks) {\n        return sources.size() == 1\n                && sinks.size() == 1\n                && (CollectionUtils.isEmpty(transforms) || transforms.size() == 1);\n    }\n\n    private static void checkSimpleGraph(","sourceCodeStart":52,"sourceCodeEnd":88,"githubUrl":"https://github.com/apache/seatunnel/blob/cf67b549a7a6c35fa0beb12d83c62892427ea919/seatunnel-engine/seatunnel-engine-core/src/main/java/org/apache/seatunnel/engine/core/parse/ConfigParserUtil.java#L52-L88","documentation":"checkGraph validates that a job config has at least one source and one sink before building the DAG. If either the sources or sinks list is empty, a JobDefineCheckException with 'Source And Sink can not be null' is thrown. A SeaTunnel job is a data pipeline and must have both endpoints.","triggerScenarios":"Submitting a HOCON job config whose env block has source or sink plugin list empty/missing; passing empty lists programmatically to checkGraph; a config where all 'source'/'sink' blocks are commented out or malformed so the parser yields an empty list.","commonSituations":"Job config missing the 'source { }' or 'sink { }' block entirely; YAML/HOCON indentation error hiding plugin blocks; generating configs from templates that leave placeholder sections empty.","solutions":["Add a source block with at least one source plugin to the job config","Add a sink block with at least one sink plugin to the job config","Check HOCON/YAML indentation so source/sink blocks are actually parsed","Validate the config with a minimal working example (e.g. FakeSource + Console sink) to isolate the issue"],"exampleFix":"// before\nenv { parallelism = 1 }\ntransform { Sql { source_table_name = \"t\" } }\n// after\nenv { parallelism = 1 }\nsource {\n  FakeSource { result_table_name = \"t\" }\n}\nsink {\n  Console {}\n}","handlingStrategy":"validation","validationCode":"if (sources == null || sources.isEmpty() || sinks == null || sinks.isEmpty()) {\n    throw new IllegalArgumentException(\"Job config must define at least one source and one sink\");\n}","typeGuard":null,"tryCatchPattern":"try {\n    ConfigParserUtil.checkGraph(sources, transforms, sinks);\n} catch (JobDefineCheckException e) {\n    log.error(\"Invalid job definition: {}\", e.getMessage());\n    throw e;\n}","preventionTips":["Always include source and sink blocks in job configs","Lint configs before submission","Test with minimal FakeSource + Console pipeline","Check HOCON/YAML indentation carefully"],"tags":["java","job-config","dag","validation"],"backgroundTag":"missing-required-config-field","analyzedSha":"cf67b549a7a6c35fa0beb12d83c62892427ea919","analyzedAt":"2026-09-10T21:44:55.265Z","contentChangedAt":"2026-09-10T21:44:55.265Z","schemaVersion":2},"datasetVersion":"2026-09-14T21:17:11.552Z"}