prestodb/presto · error

INVALID_TABLE_PROPERTY

INVALID_TABLE_PROPERTY

Error message

Locality groups string is malformed. See documentation for proper format.

What it means

Thrown by AccumuloTableProperties.getLocalityGroups when the locality_groups table property string cannot be parsed. The format must be pipe-separated groups, each 'groupName:col1,col2,...' with exactly one colon per group. Any group segment that does not split into exactly two colon-delimited parts throws INVALID_TABLE_PROPERTY.

Source

Thrown at presto-accumulo/src/main/java/com/facebook/presto/accumulo/conf/AccumuloTableProperties.java:194

     */
    public static Optional<Map<String, Set<String>>> getLocalityGroups(Map<String, Object> tableProperties)
    {
        requireNonNull(tableProperties);

        @SuppressWarnings("unchecked")
        String groupStr = (String) tableProperties.get(LOCALITY_GROUPS);
        if (groupStr == null) {
            return Optional.empty();
        }

        ImmutableMap.Builder<String, Set<String>> groups = ImmutableMap.builder();

        // Split all configured locality groups
        for (String group : PIPE_SPLITTER.split(groupStr)) {
            String[] locGroups = Iterables.toArray(COLON_SPLITTER.split(group), String.class);

            if (locGroups.length != 2) {
                throw new PrestoException(INVALID_TABLE_PROPERTY, "Locality groups string is malformed. See documentation for proper format.");
            }

            String grpName = locGroups[0];
            ImmutableSet.Builder<String> colSet = ImmutableSet.builder();

            for (String f : COMMA_SPLITTER.split(locGroups[1])) {
                colSet.add(f.toLowerCase(Locale.ENGLISH));
            }

            groups.put(grpName.toLowerCase(Locale.ENGLISH), colSet.build());
        }

        return Optional.of(groups.build());
    }

    public static Optional<String> getRowId(Map<String, Object> tableProperties)
    {
        requireNonNull(tableProperties);

View on GitHub (pinned to 55bb57d202)

Solutions

  1. Rewrite the locality_groups value so every pipe-separated segment has exactly one colon: 'group1:colA,colB|group2:colC'.
  2. Use pipes between groups and commas between column names within a group - never commas between groups.
  3. Remove empty segments (trailing or duplicate pipes) from the string.
  4. Quote the property string in SQL so colons and pipes survive parsing.
  5. Check the Accumulo connector documentation for the exact expected format before re-running the DDL.

Example fix

-- before
CREATE TABLE t (...) WITH (locality_groups='meta:foo:bar,stats:cnt');
-- after
CREATE TABLE t (...) WITH (locality_groups='meta:foo,bar|stats:cnt');
Defensive patterns

Strategy: validation

Validate before calling

boolean validLocalityGroups(String s) {
    if (s == null) return true;
    return java.util.Arrays.stream(s.split("\\|", -1))
        .allMatch(g -> g.split(":", -1).length == 2);
}
// call before CREATE TABLE: if (!validLocalityGroups(groupsStr)) throw new IllegalArgumentException("malformed locality_groups");

Type guard

boolean isWellFormedGroup(String group) {
    String[] parts = group.split(":", -1);
    return parts.length == 2 && !parts[0].isEmpty() && !parts[1].isEmpty();
}

Try / catch

try {
    createTableWithLocalityGroups(props);
} catch (PrestoException e) {
    if (e.getErrorCode().getName().equals("INVALID_TABLE_PROPERTY")) {
        // fix the locality_groups string: 'group1:colA,colB|group2:colC'
    } else {
        throw e;
    }
}

Prevention

When it happens

Trigger: CREATE TABLE ... WITH (locality_groups='...') where a group segment contains zero or multiple colons, e.g. 'grpA' (no colon), 'grpA:col1:col2' (two colons), an empty segment from a trailing pipe 'grpA:col1|', or groups separated by commas instead of pipes.

Common situations: Copy-pasting locality group config with the wrong separator; forgetting to quote the property string in SQL so a colon or pipe is misinterpreted; leaving a trailing/duplicate pipe producing an empty group; writing groups in the wrong order or with wrong delimiters.

Understand the failure class

Related errors


AI-assisted analysis of prestodb/presto@55bb57d202 (2026-09-04). Data as JSON: /api/errors/e500741f167eb76c. Report an issue: GitHub.