{"record":{"id":"1ec696aaecb3712a","repo":"apache/iceberg","slug":"interrupted-during-commit-1ec696","errorCode":null,"errorMessage":"Interrupted during commit","messagePattern":"Interrupted during commit","errorType":"exception","errorClass":"RuntimeException","httpStatus":null,"severity":"error","filePath":"hive-metastore/src/main/java/org/apache/iceberg/hive/HiveTableOperations.java","lineNumber":420,"sourceCode":"          commitStatus = checkCommitStatus(newMetadataLocation, tableMetadata);\n        }\n\n        switch (commitStatus) {\n          case SUCCESS:\n            break;\n          case FAILURE:\n            throw e;\n          case UNKNOWN:\n            throw new CommitStateUnknownException(e);\n        }\n      }\n    } catch (TException e) {\n      throw new RuntimeException(\n          String.format(\"Metastore operation failed for %s.%s\", database, tableName), e);\n\n    } catch (InterruptedException e) {\n      Thread.currentThread().interrupt();\n      throw new RuntimeException(\"Interrupted during commit\", e);\n\n    } catch (LockException e) {\n      throw new CommitFailedException(e);\n\n    } finally {\n      HiveOperationsBase.cleanupMetadataAndUnlock(io(), commitStatus, newMetadataLocation, lock);\n    }\n\n    LOG.info(\n        \"Committed to table {} with the new metadata location {}\", fullName, newMetadataLocation);\n  }\n\n  @Override\n  public long maxHiveTablePropertySize() {\n    return maxHiveTablePropertySize;\n  }\n\n  @Override","sourceCodeStart":402,"sourceCodeEnd":438,"githubUrl":"https://github.com/apache/iceberg/blob/86d9c8fc543e7c56c9f624eb725f76c9baff9570/hive-metastore/src/main/java/org/apache/iceberg/hive/HiveTableOperations.java#L402-L438","documentation":"If the commit thread is interrupted while waiting or communicating with HMS, doCommit re-interrupts the thread and throws a RuntimeException 'Interrupted during commit'. The commit outcome may be unknown, so callers must check the table state before retrying.","triggerScenarios":"doCommit interrupted via Thread.interrupt() — e.g. task cancellation in Spark/Flink, executor shutdown, or query timeout killing the writing task while it is inside the HMS commit path.","commonSituations":"Spark stage cancellation/kill; Flink job cancel; application shutdown hooks; speculative-execution cleanup interrupting a slow commit.","solutions":["Allow the commit to complete before cancelling the job; avoid killing tasks mid-commit","After interruption, verify the table's metadata_location to see if the commit landed before retrying","Increase timeouts so commits aren't interrupted by supervising frameworks","Re-run the operation on a fresh (refreshed) table snapshot if the commit did not land"],"exampleFix":"// before\nfuture.cancel(true); // interrupts an in-flight commit\n// after\nfuture.get(10, TimeUnit.MINUTES); // wait for commit completion before teardown","handlingStrategy":"try-catch","validationCode":"// avoid committing inside interruptible cancellation scopes; check Thread.interrupted() before starting a long commit","typeGuard":null,"tryCatchPattern":"try {\n  table.newAppend().appendFile(f).commit();\n} catch (RuntimeException e) {\n  if (e.getMessage() != null && e.getMessage().contains(\"Interrupted during commit\")) {\n    verifyCommitLanded(catalog.loadTable(ident)); // check metadata_location before retry\n  } else throw e;\n}","preventionTips":["Don't cancel/kill tasks mid-commit; use graceful completion","Give commits enough time budget in Spark/Flink","Restore interrupt status and verify table state before any retry","Use idempotent commit verification after interruptions"],"tags":["hive-metastore","interruption","commit","cancellation"],"backgroundTag":"request-timeout","analyzedSha":"86d9c8fc543e7c56c9f624eb725f76c9baff9570","analyzedAt":"2026-09-12T00:46:39.097Z","contentChangedAt":"2026-09-12T00:46:39.097Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}