semantics
This commit is contained in:
@@ -1,8 +1,8 @@
|
||||
# [DEF:TestDatasetsApi:Module]
|
||||
# @RELATION: DEPENDS_ON -> [DatasetsApi]
|
||||
# #region TestDatasetsApi [C:2] [TYPE Module]
|
||||
# @RELATION DEPENDS_ON -> [DatasetsApi]
|
||||
# @SEMANTICS: tests, datasets, api, metrics, inline-edit
|
||||
# @PURPOSE: Contract tests for dataset endpoints (list+stats, detail+metrics, inline-edit descriptions).
|
||||
# @LAYER: Domain (Tests)
|
||||
# @LAYER Tests
|
||||
from unittest.mock import AsyncMock, MagicMock, patch
|
||||
|
||||
import pytest
|
||||
@@ -19,7 +19,7 @@ from src.dependencies import (
|
||||
|
||||
client = TestClient(app)
|
||||
|
||||
# [DEF:mock_user:Function]
|
||||
# #region mock_user [C:2] [TYPE Function]
|
||||
# @PURPOSE: Create a mock user with Admin role and all permissions for testing.
|
||||
def _make_mock_user():
|
||||
admin_role = MagicMock()
|
||||
@@ -32,7 +32,7 @@ def _make_mock_user():
|
||||
return mock_user
|
||||
|
||||
|
||||
# [DEF:mock_deps:Function]
|
||||
# #region mock_deps [C:2] [TYPE Function]
|
||||
# @PURPOSE: Provide dependency override fixture for dataset route tests.
|
||||
# @TEST_FIXTURE: dataset_route_overrides -> INLINE_JSON
|
||||
@pytest.fixture
|
||||
@@ -97,7 +97,7 @@ def mock_deps():
|
||||
app.dependency_overrides.clear()
|
||||
|
||||
|
||||
# [DEF:test_get_datasets_returns_stats:Function]
|
||||
# #region test_get_datasets_returns_stats [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify GET /api/datasets returns stats object with correct counts.
|
||||
# @TEST_CONTRACT: datasets_list -> datasets with stats payload
|
||||
# @TEST_SCENARIO: datasets_with_stats -> HTTP 200 returns datasets, stats, and pagination.
|
||||
@@ -119,7 +119,7 @@ def test_get_datasets_returns_stats(mock_deps):
|
||||
assert len(data["datasets"]) == 3
|
||||
|
||||
|
||||
# [DEF:test_get_datasets_filter_unmapped:Function]
|
||||
# #region test_get_datasets_filter_unmapped [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify server-side filtering by unmapped datasets.
|
||||
# @TEST_SCENARIO: filter_unmapped -> Only returns datasets with mapped=0.
|
||||
def test_get_datasets_filter_unmapped(mock_deps):
|
||||
@@ -136,7 +136,7 @@ def test_get_datasets_filter_unmapped(mock_deps):
|
||||
assert data["datasets"][0]["table_name"] == "orders"
|
||||
|
||||
|
||||
# [DEF:test_get_datasets_filter_mapped:Function]
|
||||
# #region test_get_datasets_filter_mapped [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify server-side filtering by mapped datasets.
|
||||
def test_get_datasets_filter_mapped(mock_deps):
|
||||
response = client.get(
|
||||
@@ -149,7 +149,7 @@ def test_get_datasets_filter_mapped(mock_deps):
|
||||
assert data["datasets"][0]["table_name"] == "users"
|
||||
|
||||
|
||||
# [DEF:test_get_datasets_filter_linked:Function]
|
||||
# #region test_get_datasets_filter_linked [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify server-side filtering by datasets linked to dashboards.
|
||||
def test_get_datasets_filter_linked(mock_deps):
|
||||
response = client.get(
|
||||
@@ -162,7 +162,7 @@ def test_get_datasets_filter_linked(mock_deps):
|
||||
assert data["datasets"][0]["table_name"] == "users"
|
||||
|
||||
|
||||
# [DEF:test_get_datasets_filter_all:Function]
|
||||
# #region test_get_datasets_filter_all [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify filter=all returns all datasets (same as no filter).
|
||||
def test_get_datasets_filter_all(mock_deps):
|
||||
response = client.get(
|
||||
@@ -173,7 +173,7 @@ def test_get_datasets_filter_all(mock_deps):
|
||||
assert data["total"] == 3
|
||||
|
||||
|
||||
# [DEF:test_get_dataset_detail_returns_metrics:Function]
|
||||
# #region test_get_dataset_detail_returns_metrics [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify GET /api/datasets/{id} returns metrics and metric_count.
|
||||
# @TEST_SCENARIO: detail_with_metrics -> Response includes metrics list and metric_count.
|
||||
def test_get_dataset_detail_returns_metrics(mock_deps):
|
||||
@@ -217,7 +217,7 @@ def test_get_dataset_detail_returns_metrics(mock_deps):
|
||||
assert data["metrics"][0]["expression"] == "COUNT(*)"
|
||||
|
||||
|
||||
# [DEF:test_update_column_description:Function]
|
||||
# #region test_update_column_description [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify PUT /api/datasets/{id}/columns/{col_id}/description saves description.
|
||||
# @TEST_SCENARIO: save_column_desc -> Saves and returns updated description.
|
||||
def test_update_column_description(mock_deps):
|
||||
@@ -254,7 +254,7 @@ def test_update_column_description(mock_deps):
|
||||
assert update_call[1]["override_columns"] is False
|
||||
|
||||
|
||||
# [DEF:test_update_metric_description:Function]
|
||||
# #region test_update_metric_description [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify PUT /api/datasets/{id}/metrics/{metric_id}/description saves correctly.
|
||||
# @TEST_SCENARIO: save_metric_desc -> Saves and returns updated description.
|
||||
def test_update_metric_description(mock_deps):
|
||||
@@ -284,7 +284,7 @@ def test_update_metric_description(mock_deps):
|
||||
assert data["description"] == "Total row count"
|
||||
|
||||
|
||||
# [DEF:test_update_column_description_not_found:Function]
|
||||
# #region test_update_column_description_not_found [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify 404 when column not found.
|
||||
def test_update_column_description_not_found(mock_deps):
|
||||
with patch("src.api.routes.datasets.SupersetClient") as MockClient:
|
||||
@@ -307,7 +307,7 @@ def test_update_column_description_not_found(mock_deps):
|
||||
assert response.status_code == 404
|
||||
|
||||
|
||||
# [DEF:test_update_column_description_validation:Function]
|
||||
# #region test_update_column_description_validation [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify 400 when description exceeds max length.
|
||||
def test_update_column_description_validation(mock_deps):
|
||||
response = client.put(
|
||||
@@ -317,7 +317,7 @@ def test_update_column_description_validation(mock_deps):
|
||||
assert response.status_code == 400
|
||||
|
||||
|
||||
# [DEF:test_get_datasets_superset_503:Function]
|
||||
# #region test_get_datasets_superset_503 [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify GET /api/datasets returns 503 when Superset/ResourceService throws.
|
||||
# @TEST_SCENARIO: upstream_superset_failure -> 503 with error detail.
|
||||
# @TEST_INVARIANT: upstream_failure_503 -> VERIFIED_BY: [superset_failure]
|
||||
@@ -342,7 +342,7 @@ def test_get_datasets_superset_503(mock_deps):
|
||||
app.dependency_overrides[get_resource_service] = None
|
||||
|
||||
|
||||
# [DEF:test_update_column_description_superset_502:Function]
|
||||
# #region test_update_column_description_superset_502 [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify PUT column description returns 502 when SupersetClient.update_dataset throws.
|
||||
# @TEST_SCENARIO: superset_put_failure -> 502 with error detail.
|
||||
def test_update_column_description_superset_502(mock_deps):
|
||||
@@ -371,7 +371,7 @@ def test_update_column_description_superset_502(mock_deps):
|
||||
assert "Superset" in data.get("detail", "")
|
||||
|
||||
|
||||
# [DEF:test_update_column_description_strips_html:Function]
|
||||
# #region test_update_column_description_strips_html [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify HTML tags are stripped from description before saving.
|
||||
# @TEST_SCENARIO: html_in_description -> HTML tags stripped, clean text saved.
|
||||
def test_update_column_description_strips_html(mock_deps):
|
||||
@@ -406,7 +406,7 @@ def test_update_column_description_strips_html(mock_deps):
|
||||
assert updated_columns[0]["description"] == "Hello World with alert('xss')"
|
||||
|
||||
|
||||
# [DEF:test_dataset_item_has_metric_count:Function]
|
||||
# #region test_dataset_item_has_metric_count [C:2] [TYPE Function]
|
||||
# @PURPOSE: Verify DatasetItem in list response includes metric_count field.
|
||||
def test_dataset_item_has_metric_count(mock_deps):
|
||||
response = client.get(
|
||||
|
||||
Reference in New Issue
Block a user