pinpoint-apm/pinpoint · error · InvalidHbaseSchemaException

Duplicate changeSet id :

Error message

Duplicate changeSet id : 

What it means

Thrown by HbaseSchemaMapper.mapChangeSets when two <changeSet> elements in the schema XML share the same id attribute. ChangeSet ids are the primary key for tracking which changes were applied (schema change log), so duplicates make execution order and idempotency ambiguous. The mapper fails fast while mapping the XML definition.

Source

Thrown at hbase/hbase-schema/src/main/java/com/navercorp/pinpoint/hbase/schema/reader/xml/mapper/HbaseSchemaMapper.java:75

        for (HbaseSchema.Include schemaInclude : schemaIncludes) {
            String includeFile = schemaInclude.getFile();
            if (includeFiles.contains(includeFile)) {
                throw new InvalidHbaseSchemaException("Duplicate include file : " + includeFile);
            }
            includeFiles.add(includeFile);
        }
        return includeFiles;
    }

    private Collection<ChangeSet> mapChangeSets(List<com.navercorp.pinpoint.hbase.schema.definition.xml.ChangeSet> schemaChangeSets) {
        if (CollectionUtils.isEmpty(schemaChangeSets)) {
            return Collections.emptySet();
        }
        Map<String, ChangeSet> changeSets = new LinkedHashMap<>();
        for (com.navercorp.pinpoint.hbase.schema.definition.xml.ChangeSet schemaChangeSet : schemaChangeSets) {
            String changeSetId = schemaChangeSet.getId();
            if (changeSets.containsKey(changeSetId)) {
                throw new InvalidHbaseSchemaException("Duplicate changeSet id : " + changeSetId);
            }
            ChangeSet changeSet = changeSetMapper.mapChangeSet(schemaChangeSet);
            changeSets.put(changeSetId, changeSet);
        }
        return changeSets.values();
    }
}

View on GitHub (pinned to 744c3d3075)

Solutions

  1. Give each <changeSet id="..."> a unique id (re-run and fix each duplicate reported).
  2. Never reuse an id for a modified change — add a new changeSet with a new id instead, since executed change sets are recorded by id.
  3. Add a unit test that loads all schema XML files through HbaseSchemaMapper to catch duplicates in CI.

Example fix

<!-- before -->
<changeSet id="create-agent-table" ...>...</changeSet>
<changeSet id="create-agent-table" ...>...</changeSet>
<!-- after -->
<changeSet id="create-agent-table" ...>...</changeSet>
<changeSet id="add-agent-columnfamily" ...>...</changeSet>
Defensive patterns

Strategy: validation

Validate before calling

Set<String> ids = new HashSet<>();
for (ChangeSet cs : schema.getChangeSets()) {
    if (!ids.add(cs.getId())) {
        throw new IllegalArgumentException("Duplicate changeSet id: " + cs.getId());
    }
}

Try / catch

try { mapper.mapChangeSets(xmlChangeSets); } catch (InvalidHbaseSchemaException e) { fail("Fix duplicate changeSet id: " + e.getMessage()); }

Prevention

When it happens

Trigger: Parsing a schema definition where changeSets() is called and schemaChangeSet.getId() returns a value already seen in the LinkedHashMap during the same file's mapping.

Common situations: Copy-pasting a changeSet block and forgetting to bump the id; cherry-picking/merging branches that both added a changeSet with the same id; id collisions after XML refactoring.

Understand the failure class

Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.

Related errors


AI-assisted analysis of pinpoint-apm/pinpoint@744c3d3075 (2026-09-07). Data as JSON: /api/errors/7e00d4137293baa4. Report an issue: GitHub.