{"record":{"id":"dd1373597c9d0d3d","repo":"apache/seatunnel","slug":"mapping-vertex-uses-automatic-ids-under-at-le","errorCode":null,"errorMessage":"Mapping[VERTEX/{}] uses AUTOMATIC ids: under at-least-once delivery a replayed row creates a duplicate vertex, and DELETE is not supported. Use PRIMARY_KEY or CUSTOMIZE_* ids for idempotent writes.","messagePattern":"Mapping\\[VERTEX/(.+?)\\] uses AUTOMATIC ids: under at-least-once delivery a replayed row creates a duplicate vertex, and DELETE is not supported\\. Use PRIMARY_KEY or CUSTOMIZE_\\* ids for idempotent writes\\.","errorType":"console","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"seatunnel-connectors-v2/connector-hugegraph/src/main/java/org/apache/seatunnel/connectors/seatunnel/hugegraph/sink/HugeGraphSinkWriter.java","lineNumber":217,"sourceCode":"                LOG.info(\n                        \"Mapping[{}/{}] source_table '{}' does not match writer table '{}'; \"\n                                + \"skipping in this writer.\",\n                        mapping.getType(),\n                        mapping.getLabel(),\n                        mapping.getSourceTable(),\n                        tablePath);\n                continue;\n            }\n            Map<String, Integer> fieldsIndex = resolveFieldsIndex(mapping, availableFieldsIndex);\n            GraphDataMapper mapper;\n            if (mapping.getType() == LabelType.VERTEX) {\n                if (mapping.getIdStrategy()\n                        == org.apache.hugegraph.structure.constant.IdStrategy.AUTOMATIC) {\n                    // AUTOMATIC ids are server-assigned and not derivable from the row, so there is\n                    // no key to deduplicate on: under at-least-once, a replayed row inserts a NEW\n                    // vertex each time (duplicates). Warn so the trade-off is visible; use\n                    // PRIMARY_KEY / CUSTOMIZE_* for idempotent upserts.\n                    LOG.warn(\n                            \"Mapping[VERTEX/{}] uses AUTOMATIC ids: under at-least-once delivery a \"\n                                    + \"replayed row creates a duplicate vertex, and DELETE is not \"\n                                    + \"supported. Use PRIMARY_KEY or CUSTOMIZE_* ids for idempotent \"\n                                    + \"writes.\",\n                            mapping.getLabel());\n                }\n                mapper = new VertexMapper(mapping, fieldsIndex, client);\n            } else {\n                mapper = new EdgeMapper(mapping, fieldsIndex, client);\n            }\n            entries.add(new MappingEntry(mapping, mapper));\n        }\n\n        if (entries.isEmpty()) {\n            // Multi-table mode: at least one mapping has source_table, but none matched this\n            // writer's tablePath. This is a configuration error — the user intended multi-table\n            // but the table path strings don't align. Fail fast with a diagnostic that shows\n            // both sides so the user can reconcile them.","sourceCodeStart":199,"sourceCodeEnd":235,"githubUrl":"https://github.com/apache/seatunnel/blob/cf67b549a7a6c35fa0beb12d83c62892427ea919/seatunnel-connectors-v2/connector-hugegraph/src/main/java/org/apache/seatunnel/connectors/seatunnel/hugegraph/sink/HugeGraphSinkWriter.java#L199-L235","documentation":"This warning is emitted by HugeGraphSinkWriter.buildMappingEntries() when a vertex mapping uses the AUTOMATIC id strategy. With AUTOMATIC ids the HugeGraph server assigns ids, so the writer cannot derive a dedup key from the row. Under SeaTunnel's at-least-once delivery, a replayed row after a retry creates a duplicate vertex, and DELETE events cannot be supported. The warning surfaces the trade-off so users can choose an idempotent id strategy.","triggerScenarios":"A VERTEX mapping has id_strategy resolving to IdStrategy.AUTOMATIC; buildMappingEntries() (called from the HugeGraphSinkWriter constructor) detects it during writer initialization.","commonSituations":"Configs that let vertices auto-id because no natural key exists; users unaware SeaTunnel guarantees at-least-once, so retries/replays after task restarts or checkpoint recovery duplicate vertices; downstream DELETE/sync scenarios that silently do not work.","solutions":["Change id_strategy to PRIMARY_KEY and designate the row field(s) that form the primary key, so replayed rows upsert instead of duplicating.","Or use CUSTOMIZE_NUMBER / CUSTOMIZE_STRING ids and map a row field that deterministically identifies the vertex.","If AUTOMATIC ids are truly required (pure append-only load), accept duplicates on replay or make the source idempotent; also avoid DELETE changelog modes."],"exampleFix":"// before\nmappings = [\n  {type = \"VERTEX\", label = \"person\", id_strategy = \"AUTOMATIC\", properties = {name = \"name\"}}\n]\n// after\nmappings = [\n  {type = \"VERTEX\", label = \"person\", id_strategy = \"PRIMARY_KEY\", primary_keys = [\"id\"], properties = {id = \"id\", name = \"name\"}}\n]","handlingStrategy":"validation","validationCode":"mappings.each { m ->\n    if (m.type == \"VERTEX\" && m.id_strategy == \"AUTOMATIC\") {\n        println \"WARNING: mapping ${m.label} uses AUTOMATIC ids; replayed rows will duplicate vertices\"\n    }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Prefer PRIMARY_KEY or CUSTOMIZE_* id strategies for idempotent upserts","Design vertex schemas with a natural key derivable from the row","Remember SeaTunnel delivery is at-least-once; avoid non-idempotent sink configs for retryable jobs","Avoid AUTOMATIC ids when the pipeline may emit DELETE events"],"tags":["hugegraph","idempotency","at-least-once","duplicate-data"],"backgroundTag":"non-idempotent-write","analyzedSha":"cf67b549a7a6c35fa0beb12d83c62892427ea919","analyzedAt":"2026-09-10T21:44:55.265Z","contentChangedAt":"2026-09-10T21:44:55.265Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}