apache/iceberg · warning
Deleted only {} of {} files using bulk deletes
Error message
Deleted only {} of {} files using bulk deletes What it means
DeleteOrphanFilesSparkAction uses the FileIO's bulk delete API when supported. If the object store reports that some objects in the bulk request failed (BulkDeletionFailureException carries the failed count), the action logs this warning with how many of the total paths were actually deleted rather than throwing.
Source
Thrown at spark/v3.5/spark/src/main/java/org/apache/iceberg/spark/actions/DeleteOrphanFilesSparkAction.java:325
}
private void collectPathsForOutput(
List<String> paths, List<String> orphanFileList, int maxSampleSize) {
if (streamResults()) {
int lengthToAdd = Math.min(maxSampleSize - orphanFileList.size(), paths.size());
orphanFileList.addAll(paths.subList(0, lengthToAdd));
} else {
orphanFileList.addAll(paths);
}
}
private void deleteBulk(SupportsBulkOperations io, List<String> paths) {
try {
io.deleteFiles(paths);
LOG.info("Deleted {} files using bulk deletes", paths.size());
} catch (BulkDeletionFailureException e) {
int deletedFilesCount = paths.size() - e.numberFailedObjects();
LOG.warn(
"Deleted only {} of {} files using bulk deletes", deletedFilesCount, paths.size(), e);
}
}
private void deleteNonBulk(List<String> paths) {
Tasks.Builder<String> deleteTasks =
Tasks.foreach(paths)
.noRetry()
.executeWith(deleteExecutorService)
.suppressFailureWhenFinished()
.onFailure((file, exc) -> LOG.warn("Failed to delete file: {}", file, exc));
if (deleteFunc == null) {
LOG.info(
"Table IO {} does not support bulk operations. Using non-bulk deletes.",
table.io().getClass().getName());
deleteTasks.run(table.io()::deleteFile);
} else {View on GitHub (pinned to 86d9c8fc54)
Solutions
- Re-run the DeleteOrphanFiles action — remaining older-than-threshold files will be retried.
- Lower the batch size / concurrency of the S3FileIO if throttling causes partial failures.
- Check bucket retention/Object Lock and versioning settings for objects that permanently refuse deletion.
- If guaranteed cleanup is required, force the non-bulk path by using a FileIO without bulk support or by deleting the reported paths individually.
Defensive patterns
Strategy: retry
Validate before calling
if (table.io() instanceof SupportsBulkOperations) { /* bulk path: expect partial failures */ } Type guard
if (table.io() instanceof SupportsBulkOperations bulkIo) { bulkIo.deleteFiles(paths); } Prevention
- Re-run DeleteOrphanFiles periodically to retry partially deleted batches.
- Check S3 Object Lock/retention policies that block deletion.
- Reduce bulk batch sizes if the object store throttles large requests.
When it happens
Trigger: Calling DeleteOrphanFiles (RemoveOrphanFiles) against a FileIO implementing SupportsBulkOperations (e.g. S3FileIO) where io.deleteFiles(paths) partially fails, raising BulkDeletionFailureException with numberFailedObjects > 0.
Common situations: S3 multi-object delete partial failures; objects locked by retention policies (Object Lock) that cannot be removed; transient object-store errors during large bulk batches.
Understand the failure class
Background: "failed to write file", "Could not save figure", "Error saving remote file" — file write failed: causes and fixes across languages and libraries — this error's family across 38 libraries.
Related errors
- Unable to determine whether certain files are orphan. Metada
- Unable to determine whether certain files are orphan. Metada
- Failed to bulk delete {} {} files
- Delete failed for {}: {}
- Failed to delete file: {}
AI-assisted analysis of apache/iceberg@86d9c8fc54 (2026-09-12).
Data as JSON: /api/errors/53bdfb004a03b6bf.
Report an issue: GitHub.