{"record":{"id":"47e0b8315f16f359","repo":"prestodb/presto","slug":"hive-unsupported-format-47e0b8","errorCode":"HIVE_UNSUPPORTED_FORMAT","errorMessage":"Table StorageDescriptor is null for table %s.%s (%s)","messagePattern":"Table StorageDescriptor is null for table (.+?)\\.(.+?) \\((.+?)\\)","errorType":"error_code","errorClass":"PrestoException","httpStatus":null,"severity":"error","filePath":"presto-hive-metastore/src/main/java/com/facebook/presto/hive/metastore/glue/converter/GlueToPrestoConverter.java","lineNumber":96,"sourceCode":"                .setTableName(glueTable.name())\n                .setOwner(nullToEmpty(glueTable.owner()))\n                // Athena treats missing table type as EXTERNAL_TABLE.\n                .setTableType(PrestoTableType.optionalValueOf(glueTable.tableType()).orElse(EXTERNAL_TABLE))\n                .setParameters(tableParameters)\n                .setViewOriginalText(Optional.ofNullable(glueTable.viewOriginalText()))\n                .setViewExpandedText(Optional.ofNullable(glueTable.viewExpandedText()));\n\n        StorageDescriptor sd = glueTable.storageDescriptor();\n        if (isIcebergTable(tableParameters) || (sd == null && isDeltaLakeTable(tableParameters))) {\n            // Iceberg and Delta Lake tables do not use the StorageDescriptor field, but we need to return a Table so the caller can check that\n            // the table is an Iceberg/Delta table and decide whether to redirect or fail.\n            tableBuilder.setDataColumns(ImmutableList.of(new Column(\"dummy\", HIVE_INT, Optional.empty(), Optional.empty())));\n            tableBuilder.getStorageBuilder().setStorageFormat(StorageFormat.fromHiveStorageFormat(HiveStorageFormat.PARQUET));\n            tableBuilder.getStorageBuilder().setLocation(sd == null ? \"\" : sd.location());\n        }\n        else {\n            if (sd == null) {\n                throw new PrestoException(HIVE_UNSUPPORTED_FORMAT, format(\"Table StorageDescriptor is null for table %s.%s (%s)\", dbName, glueTable.name(), glueTable));\n            }\n            tableBuilder.setDataColumns(convertColumns(sd.columns()));\n            if (glueTable.partitionKeys() != null) {\n                tableBuilder.setPartitionColumns(convertColumns(glueTable.partitionKeys()));\n            }\n            else {\n                tableBuilder.setPartitionColumns(ImmutableList.of());\n            }\n\n            new StorageConverter().setConvertedStorage(sd, tableBuilder.getStorageBuilder());\n        }\n\n        return tableBuilder.build();\n    }\n\n    private static Column convertColumn(software.amazon.awssdk.services.glue.model.Column glueColumn)\n    {\n        return new Column(glueColumn.name(), HiveType.valueOf(glueColumn.type().toLowerCase(Locale.ENGLISH)), Optional.ofNullable(glueColumn.comment()), Optional.empty());","sourceCodeStart":78,"sourceCodeEnd":114,"githubUrl":"https://github.com/prestodb/presto/blob/55bb57d202de3b926896fa966c2c4a44c779634e/presto-hive-metastore/src/main/java/com/facebook/presto/hive/metastore/glue/converter/GlueToPrestoConverter.java#L78-L114","documentation":"When converting a Glue Table to Presto's internal Table, a null StorageDescriptor is tolerated only for the dummy/empty path; otherwise convertTable throws HIVE_UNSUPPORTED_FORMAT because the table has no storage definition (columns, location, format).","triggerScenarios":"Reading (getTable) a Glue table whose StorageDescriptor field is null — e.g. a table entry created without storage metadata.","commonSituations":"Tables created by non-Hive Glue producers (Crawlers edge cases, manual API writes, cross-account copies that stripped StorageDescriptor).","solutions":["Fix the table in the Glue console by providing a StorageDescriptor (location, format, columns)","Recreate the table via CREATE TABLE in Presto/Hive","Check whatever process produced the table so it writes a complete StorageDescriptor"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"Table glueTable = glueClient.getTable(GetTableRequest.builder().databaseName(db).name(t).build());\nif (glueTable.storageDescriptor() == null) {\n    throw new IllegalStateException(\"Glue table \" + db + \".\" + t + \" has no StorageDescriptor; fix metadata before querying\");\n}","typeGuard":"boolean queryable = glueTable != null && glueTable.storageDescriptor() != null;","tryCatchPattern":"try {\n    table = metastore.getTable(db, table);\n} catch (PrestoException e) {\n    if (e.getErrorCode().getName().equals(\"HIVE_UNSUPPORTED_FORMAT\")) {\n        // report broken table metadata to user / skip table\n    } else throw e;\n}","preventionTips":["Ensure all table-creating pipelines write a full StorageDescriptor","Monitor Glue catalog for tables missing storage metadata","Validate tables created by crawlers/external tools"],"tags":["glue","metadata","storage-descriptor","unsupported-format"],"backgroundTag":"null-storage-descriptor","analyzedSha":"55bb57d202de3b926896fa966c2c4a44c779634e","analyzedAt":"2026-09-04T12:50:26.162Z","contentChangedAt":"2026-09-04T12:50:26.162Z","schemaVersion":2},"datasetVersion":"2026-09-11T21:17:09.523Z"}