Skip to content

Commit db6fecc

Browse files
committed
added clean orphan metadata when status failed
1 parent 8759f49 commit db6fecc

2 files changed

Lines changed: 54 additions & 1 deletion

File tree

pyiceberg/catalog/bigquery_metastore.py

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
from __future__ import annotations
1818

1919
import json
20+
import logging
2021
from enum import Enum
2122
from typing import TYPE_CHECKING, Any
2223

@@ -67,6 +68,8 @@
6768
HIVE_FILE_INPUT_FORMAT = "org.apache.iceberg.mr.hive.HiveIcebergInputFormat"
6869
HIVE_FILE_OUTPUT_FORMAT = "org.apache.iceberg.mr.hive.HiveIcebergOutputFormat"
6970

71+
logger = logging.getLogger(__name__)
72+
7073

7174
class BigqueryCommitStatus(str, Enum):
7275
SUCCESS = "SUCCESS"
@@ -317,6 +320,17 @@ def commit_table(
317320
raise CommitStateUnknownException(
318321
f"Commit state unknown for table {dataset_name}.{table_name}"
319322
) from commit_error
323+
elif commit_status == BigqueryCommitStatus.FAILURE:
324+
logger.warning("Failed to commit updates to table %s", table_name)
325+
try:
326+
updated_staged_table.io.delete(updated_staged_table.metadata_location)
327+
except Exception:
328+
logger.error(
329+
"Failed to cleanup metadata file at %s for table %s",
330+
updated_staged_table.metadata_location,
331+
table_name,
332+
exc_info=logger.isEnabledFor(logging.DEBUG),
333+
)
320334

321335
if commit_error:
322336
raise commit_error

tests/catalog/test_bigquery_metastore.py

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,12 @@
2323
from google.cloud.bigquery.external_config import ExternalCatalogDatasetOptions, ExternalCatalogTableOptions
2424
from pytest_mock import MockFixture
2525

26-
from pyiceberg.catalog.bigquery_metastore import ICEBERG_TABLE_TYPE_VALUE, TABLE_TYPE_PROP, BigQueryMetastoreCatalog
26+
from pyiceberg.catalog.bigquery_metastore import (
27+
ICEBERG_TABLE_TYPE_VALUE,
28+
TABLE_TYPE_PROP,
29+
BigqueryCommitStatus,
30+
BigQueryMetastoreCatalog,
31+
)
2732
from pyiceberg.exceptions import CommitStateUnknownException, NoSuchTableError
2833
from pyiceberg.schema import Schema
2934

@@ -309,3 +314,37 @@ def test_check_bigquery_commit_status_returns_success_when_metadata_in_history(m
309314
)
310315

311316
assert status == "SUCCESS"
317+
318+
319+
def test_commit_table_deletes_written_metadata_when_commit_status_is_failure(mocker: MockFixture) -> None:
320+
client_mock = MagicMock()
321+
current_bq_table = MagicMock()
322+
client_mock.get_table.return_value = current_bq_table
323+
client_mock.update_table.side_effect = RuntimeError("boom")
324+
mocker.patch("pyiceberg.catalog.bigquery_metastore.Client", return_value=client_mock)
325+
mocker.patch.dict(os.environ, values={"PYICEBERG_LEGACY_CURRENT_SNAPSHOT_ID": "True"})
326+
327+
catalog = BigQueryMetastoreCatalog("test_catalog", **{"gcp.bigquery.project-id": "my-project"})
328+
table = MagicMock()
329+
table.name.return_value = ("my-dataset", "my-table")
330+
331+
current_table = MagicMock()
332+
current_table.metadata = MagicMock()
333+
current_table.metadata_location = "gs://bucket/db/table/metadata/00000.metadata.json"
334+
mocker.patch.object(catalog, "_convert_bigquery_table_to_iceberg_table", return_value=current_table)
335+
336+
staged = MagicMock()
337+
staged.metadata = MagicMock()
338+
staged.metadata.location = "gs://bucket/db/table"
339+
staged.metadata_location = "gs://bucket/db/table/metadata/00001.metadata.json"
340+
staged.io = MagicMock()
341+
mocker.patch.object(catalog, "_update_and_stage_table", return_value=staged)
342+
mocker.patch.object(catalog, "_write_metadata")
343+
mocker.patch.object(catalog, "_create_table_parameters", return_value={"metadata_location": staged.metadata_location})
344+
mocker.patch.object(catalog, "_create_external_catalog_table_options", return_value=MagicMock())
345+
mocker.patch.object(catalog, "_check_bigquery_commit_status", return_value=BigqueryCommitStatus.FAILURE)
346+
347+
with pytest.raises(RuntimeError, match="boom"):
348+
catalog.commit_table(table, requirements=(), updates=())
349+
350+
staged.io.delete.assert_called_once_with(staged.metadata_location)

0 commit comments

Comments
 (0)