Files
order-bak/tests/test_delete.py
2026-04-22 12:26:38 +08:00

146 lines
4.4 KiB
Python

from datetime import datetime, timezone
from unittest.mock import MagicMock, patch
import pytest
from click.testing import CliRunner
from order_bak.cli import main
from order_bak.csv_utils import write_csv
from order_bak.delete import delete_orders
def _make_entity(pk, rk):
return {
"PartitionKey": pk,
"RowKey": rk,
"OrderTime": datetime(2025, 1, 1, tzinfo=timezone.utc),
"ReceiveTime": None,
"revenue": 10.0,
"platformOrder": "p",
"prodCount": 1,
"pfId": pk,
"prodId": "prod",
"prodPrice": 10.0,
"state": 1,
"ver": 3,
"customData": None,
}
# --- delete_orders unit tests ---
def test_delete_groups_by_partition_and_batches(tmp_path):
entities = []
for i in range(3):
entities.append(_make_entity("user1", f"order{i}"))
for i in range(3, 5):
entities.append(_make_entity("user2", f"order{i}"))
csv_path = tmp_path / "2025-01-01.csv"
write_csv(csv_path, entities)
mock_table = MagicMock()
deleted_count = delete_orders(
table_client=mock_table,
csv_path=csv_path,
batch_size=2,
delay_ms=0,
)
assert deleted_count == 5
# user1: 3 entities, batch_size=2 -> 2 batches (2 + 1)
# user2: 2 entities, batch_size=2 -> 1 batch
assert mock_table.submit_transaction.call_count == 3
def test_delete_respects_batch_size(tmp_path):
entities = [_make_entity("user1", f"order{i}") for i in range(5)]
csv_path = tmp_path / "2025-01-01.csv"
write_csv(csv_path, entities)
mock_table = MagicMock()
deleted_count = delete_orders(
table_client=mock_table,
csv_path=csv_path,
batch_size=2,
delay_ms=0,
)
assert deleted_count == 5
assert mock_table.submit_transaction.call_count == 3 # 2+2+1
# --- delete CLI command tests ---
@pytest.fixture
def runner():
return CliRunner()
@pytest.fixture
def config_file(tmp_path):
cfg = tmp_path / "config.toml"
cfg.write_text('[azure]\nconnection_string = "UseDevelopmentStorage=true"\n')
return cfg
def test_delete_command_no_backups(runner, config_file, tmp_path, monkeypatch):
monkeypatch.chdir(tmp_path)
(tmp_path / "backups").mkdir()
result = runner.invoke(main, ["--config", str(config_file), "delete"])
assert result.exit_code == 1
assert "No backup files found" in result.output
def test_delete_command_aborts(runner, config_file, tmp_path, monkeypatch):
monkeypatch.chdir(tmp_path)
backup_dir = tmp_path / "backups"
backup_dir.mkdir()
write_csv(backup_dir / "2025-01-01.csv", [_make_entity("u1", "o1")])
mock_table = MagicMock()
with patch("azure.data.tables.TableClient.from_connection_string", return_value=mock_table):
result = runner.invoke(main, ["--config", str(config_file), "delete"], input="n\n")
assert "Aborted" in result.output
mock_table.submit_transaction.assert_not_called()
def test_delete_command_single_file(runner, config_file, tmp_path, monkeypatch):
monkeypatch.chdir(tmp_path)
backup_dir = tmp_path / "backups"
backup_dir.mkdir()
write_csv(backup_dir / "2025-01-01.csv", [_make_entity("u1", f"o{i}") for i in range(3)])
mock_table = MagicMock()
with patch("azure.data.tables.TableClient.from_connection_string", return_value=mock_table):
result = runner.invoke(main, ["--config", str(config_file), "delete"], input="y\n")
assert result.exit_code == 0
assert "3 orders" in result.output
assert "1 file" in result.output
assert mock_table.submit_transaction.called
def test_delete_command_multiple_files(runner, config_file, tmp_path, monkeypatch):
monkeypatch.chdir(tmp_path)
backup_dir = tmp_path / "backups"
backup_dir.mkdir()
write_csv(backup_dir / "2025-01-01.csv", [_make_entity("u1", f"o{i}") for i in range(2)])
write_csv(backup_dir / "2025-01-02.csv", [_make_entity("u2", f"o{i}") for i in range(3)])
mock_table = MagicMock()
with patch("azure.data.tables.TableClient.from_connection_string", return_value=mock_table):
result = runner.invoke(main, ["--config", str(config_file), "delete"], input="y\n")
assert result.exit_code == 0
assert "5 orders" in result.output
assert "2 file" in result.output
# u1 (2 entities, batch 100) → 1 call; u2 (3 entities, batch 100) → 1 call
assert mock_table.submit_transaction.call_count == 2