From 1cd88442a35ce842a8907146c98d6002efcc6759 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Tue, 16 Jun 2026 11:47:48 -0700 Subject: [PATCH 01/12] initially generated tests Signed-off-by: Alina (Xi) Li --- .../commands/serverStatus/__init__.py | 0 .../test_serverStatus_argument_handling.py | 169 +++++++++ .../test_serverStatus_core_behavior.py | 269 ++++++++++++++ .../test_serverStatus_error_conditions.py | 51 +++ .../test_serverStatus_field_toggle.py | 232 ++++++++++++ .../test_serverStatus_response_structure.py | 339 ++++++++++++++++++ 6 files changed, 1060 insertions(+) create mode 100644 documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/__init__.py create mode 100644 documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py create mode 100644 documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py create mode 100644 documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py create mode 100644 documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py create mode 100644 documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/__init__.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py new file mode 100644 index 000000000..217ce33be --- /dev/null +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py @@ -0,0 +1,169 @@ +"""Tests for serverStatus command argument handling. + +Validates that serverStatus accepts any BSON type as its argument value. +The command field value is ignored by serverStatus. +""" + +from datetime import datetime, timezone + +import pytest +from bson import Binary, Code, Decimal128, Int64, MaxKey, MinKey, ObjectId, Regex, Timestamp + +from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( + DiagnosticTestCase, +) +from documentdb_tests.framework.assertions import assertProperties +from documentdb_tests.framework.executor import execute_admin_command +from documentdb_tests.framework.parametrize import pytest_params +from documentdb_tests.framework.property_checks import Eq + +pytestmark = pytest.mark.admin + + +ARGUMENT_TYPE_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + "int_1", + command={"serverStatus": 1}, + checks={"ok": Eq(1.0)}, + msg="Should accept int 1", + ), + DiagnosticTestCase( + "int_0", + command={"serverStatus": 0}, + checks={"ok": Eq(1.0)}, + msg="Should accept int 0", + ), + DiagnosticTestCase( + "int_neg1", + command={"serverStatus": -1}, + checks={"ok": Eq(1.0)}, + msg="Should accept int -1", + ), + DiagnosticTestCase( + "bool_true", + command={"serverStatus": True}, + checks={"ok": Eq(1.0)}, + msg="Should accept true", + ), + DiagnosticTestCase( + "bool_false", + command={"serverStatus": False}, + checks={"ok": Eq(1.0)}, + msg="Should accept false", + ), + DiagnosticTestCase( + "string", + command={"serverStatus": "hello"}, + checks={"ok": Eq(1.0)}, + msg="Should accept string", + ), + DiagnosticTestCase( + "empty_string", + command={"serverStatus": ""}, + checks={"ok": Eq(1.0)}, + msg="Should accept empty string", + ), + DiagnosticTestCase( + "null", + command={"serverStatus": None}, + checks={"ok": Eq(1.0)}, + msg="Should accept null", + ), + DiagnosticTestCase( + "empty_object", + command={"serverStatus": {}}, + checks={"ok": Eq(1.0)}, + msg="Should accept empty object", + ), + DiagnosticTestCase( + "empty_array", + command={"serverStatus": []}, + checks={"ok": Eq(1.0)}, + msg="Should accept empty array", + ), + DiagnosticTestCase( + "double", + command={"serverStatus": 1.5}, + checks={"ok": Eq(1.0)}, + msg="Should accept double", + ), + DiagnosticTestCase( + "int64", + command={"serverStatus": Int64(1)}, + checks={"ok": Eq(1.0)}, + msg="Should accept int64", + ), + DiagnosticTestCase( + "decimal128", + command={"serverStatus": Decimal128("1")}, + checks={"ok": Eq(1.0)}, + msg="Should accept decimal128", + ), + DiagnosticTestCase( + "decimal128_nan", + command={"serverStatus": Decimal128("NaN")}, + checks={"ok": Eq(1.0)}, + msg="Should accept decimal128 NaN", + ), + DiagnosticTestCase( + "infinity", + command={"serverStatus": float("inf")}, + checks={"ok": Eq(1.0)}, + msg="Should accept infinity", + ), + DiagnosticTestCase( + "date", + command={"serverStatus": datetime(2024, 1, 1, tzinfo=timezone.utc)}, + checks={"ok": Eq(1.0)}, + msg="Should accept date", + ), + DiagnosticTestCase( + "binData", + command={"serverStatus": Binary(b"")}, + checks={"ok": Eq(1.0)}, + msg="Should accept binData", + ), + DiagnosticTestCase( + "objectId", + command={"serverStatus": ObjectId()}, + checks={"ok": Eq(1.0)}, + msg="Should accept objectId", + ), + DiagnosticTestCase( + "regex", + command={"serverStatus": Regex("test")}, + checks={"ok": Eq(1.0)}, + msg="Should accept regex", + ), + DiagnosticTestCase( + "timestamp", + command={"serverStatus": Timestamp(0, 0)}, + checks={"ok": Eq(1.0)}, + msg="Should accept timestamp", + ), + DiagnosticTestCase( + "minKey", + command={"serverStatus": MinKey()}, + checks={"ok": Eq(1.0)}, + msg="Should accept minKey", + ), + DiagnosticTestCase( + "maxKey", + command={"serverStatus": MaxKey()}, + checks={"ok": Eq(1.0)}, + msg="Should accept maxKey", + ), + DiagnosticTestCase( + "code", + command={"serverStatus": Code("function(){}")}, + checks={"ok": Eq(1.0)}, + msg="Should accept JavaScript code", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(ARGUMENT_TYPE_TESTS)) +def test_serverStatus_argument_types(collection, test): + """Test that serverStatus accepts various BSON types as argument value.""" + result = execute_admin_command(collection, test.command) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py new file mode 100644 index 000000000..7b71aa19e --- /dev/null +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py @@ -0,0 +1,269 @@ +"""Tests for serverStatus command core behavior. + +Validates semantic correctness of response field values, non-negative +counters, and cross-field consistency. +""" + +import pytest + +from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( + DiagnosticTestCase, +) +from documentdb_tests.framework.assertions import assertProperties +from documentdb_tests.framework.executor import execute_admin_command, execute_command +from documentdb_tests.framework.parametrize import pytest_params +from documentdb_tests.framework.property_checks import Eq, Gt, Gte + +pytestmark = pytest.mark.admin + + +# --- Positive Value Checks --- + +POSITIVE_VALUE_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="uptime_gte_0", + checks={"uptime": Gte(0)}, + msg="'uptime' should be >= 0", + ), + DiagnosticTestCase( + id="uptimeMillis_gte_0", + checks={"uptimeMillis": Gte(0)}, + msg="'uptimeMillis' should be >= 0", + ), + DiagnosticTestCase( + id="uptimeEstimate_gte_0", + checks={"uptimeEstimate": Gte(0)}, + msg="'uptimeEstimate' should be >= 0", + ), + DiagnosticTestCase( + id="pid_gt_0", + checks={"pid": Gt(0)}, + msg="'pid' should be > 0", + ), + DiagnosticTestCase( + id="connections_current_gte_1", + checks={"connections.current": Gte(1)}, + msg="At least the test connection should exist", + ), + DiagnosticTestCase( + id="connections_available_gte_0", + checks={"connections.available": Gte(0)}, + msg="'connections.available' should be >= 0", + ), + DiagnosticTestCase( + id="connections_totalCreated_gte_1", + checks={"connections.totalCreated": Gte(1)}, + msg="At least one connection should have been created", + ), + DiagnosticTestCase( + id="mem_resident_gt_0", + checks={"mem.resident": Gt(0)}, + msg="Process should use some resident memory", + ), + DiagnosticTestCase( + id="mem_virtual_gt_0", + checks={"mem.virtual": Gt(0)}, + msg="Process should use some virtual memory", + ), + DiagnosticTestCase( + id="globalLock_totalTime_gte_0", + checks={"globalLock.totalTime": Gte(0)}, + msg="'globalLock.totalTime' should be >= 0", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(POSITIVE_VALUE_TESTS)) +def test_serverStatus_positive_values(collection, test): + """Verifies serverStatus fields have expected positive/non-negative values.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Non-Negative Counter Checks --- + +COUNTER_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="asserts_regular_gte_0", + checks={"asserts.regular": Gte(0)}, + msg="'asserts.regular' should be >= 0", + ), + DiagnosticTestCase( + id="asserts_warning_gte_0", + checks={"asserts.warning": Gte(0)}, + msg="'asserts.warning' should be >= 0", + ), + DiagnosticTestCase( + id="asserts_msg_gte_0", + checks={"asserts.msg": Gte(0)}, + msg="'asserts.msg' should be >= 0", + ), + DiagnosticTestCase( + id="asserts_user_gte_0", + checks={"asserts.user": Gte(0)}, + msg="'asserts.user' should be >= 0", + ), + DiagnosticTestCase( + id="asserts_rollovers_gte_0", + checks={"asserts.rollovers": Gte(0)}, + msg="'asserts.rollovers' should be >= 0", + ), + DiagnosticTestCase( + id="opcounters_insert_gte_0", + checks={"opcounters.insert": Gte(0)}, + msg="'opcounters.insert' should be >= 0", + ), + DiagnosticTestCase( + id="opcounters_query_gte_0", + checks={"opcounters.query": Gte(0)}, + msg="'opcounters.query' should be >= 0", + ), + DiagnosticTestCase( + id="opcounters_update_gte_0", + checks={"opcounters.update": Gte(0)}, + msg="'opcounters.update' should be >= 0", + ), + DiagnosticTestCase( + id="opcounters_delete_gte_0", + checks={"opcounters.delete": Gte(0)}, + msg="'opcounters.delete' should be >= 0", + ), + DiagnosticTestCase( + id="opcounters_getmore_gte_0", + checks={"opcounters.getmore": Gte(0)}, + msg="'opcounters.getmore' should be >= 0", + ), + DiagnosticTestCase( + id="opcounters_command_gte_0", + checks={"opcounters.command": Gte(0)}, + msg="'opcounters.command' should be >= 0", + ), + DiagnosticTestCase( + id="network_bytesIn_gte_0", + checks={"network.bytesIn": Gte(0)}, + msg="'network.bytesIn' should be >= 0", + ), + DiagnosticTestCase( + id="network_bytesOut_gte_0", + checks={"network.bytesOut": Gte(0)}, + msg="'network.bytesOut' should be >= 0", + ), + DiagnosticTestCase( + id="network_numRequests_gte_0", + checks={"network.numRequests": Gte(0)}, + msg="'network.numRequests' should be >= 0", + ), + DiagnosticTestCase( + id="catalogStats_collections_gte_0", + checks={"catalogStats.collections": Gte(0)}, + msg="'catalogStats.collections' should be >= 0", + ), + DiagnosticTestCase( + id="catalogStats_capped_gte_0", + checks={"catalogStats.capped": Gte(0)}, + msg="'catalogStats.capped' should be >= 0", + ), + DiagnosticTestCase( + id="catalogStats_views_gte_0", + checks={"catalogStats.views": Gte(0)}, + msg="'catalogStats.views' should be >= 0", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(COUNTER_TESTS)) +def test_serverStatus_counters(collection, test): + """Verifies serverStatus counter fields are non-negative.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Cross-Field Consistency (standalone tests) --- + + +def test_serverStatus_totalCreated_gte_current(collection): + """Verify connections.totalCreated >= connections.current.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + current = result["connections"]["current"] + assertProperties( + result, + {"connections.totalCreated": Gte(current)}, + raw_res=True, + msg="totalCreated should include current and closed connections", + ) + + +def test_serverStatus_uptimeMillis_consistent_with_uptime(collection): + """Verify uptime (seconds, rounded) is consistent with uptimeMillis.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + uptime_from_millis = result["uptimeMillis"] // 1000 + assertProperties( + result, + {"uptime": Gte(uptime_from_millis)}, + raw_res=True, + msg="uptime in seconds should be >= uptimeMillis / 1000", + ) + + +def test_serverStatus_pid_consistent_across_calls(collection): + """Verify pid is the same across multiple serverStatus calls.""" + result1 = execute_admin_command(collection, {"serverStatus": 1}) + result2 = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties( + result2, + {"pid": Eq(result1["pid"])}, + raw_res=True, + msg="pid should not change between calls", + ) + + +def test_serverStatus_host_consistent_across_calls(collection): + """Verify host is the same across multiple serverStatus calls.""" + result1 = execute_admin_command(collection, {"serverStatus": 1}) + result2 = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties( + result2, + {"host": Eq(result1["host"])}, + raw_res=True, + msg="host should not change between calls", + ) + + +def test_serverStatus_version_consistent_across_calls(collection): + """Verify version is the same across multiple serverStatus calls.""" + result1 = execute_admin_command(collection, {"serverStatus": 1}) + result2 = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties( + result2, + {"version": Eq(result1["version"])}, + raw_res=True, + msg="version should not change between calls", + ) + + +def test_serverStatus_cross_database_same_core_fields(collection): + """Verify core identity fields are same regardless of database.""" + admin_result = execute_admin_command(collection, {"serverStatus": 1}) + db_result = execute_command(collection, {"serverStatus": 1}) + assertProperties( + db_result, + { + "host": Eq(admin_result["host"]), + "version": Eq(admin_result["version"]), + "process": Eq(admin_result["process"]), + "pid": Eq(admin_result["pid"]), + }, + raw_res=True, + msg="Core identity fields should be same regardless of database", + ) + + +def test_serverStatus_process_is_mongod(collection): + """Verify process field value is 'mongod' on a mongod instance.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties( + result, + {"process": Eq("mongod")}, + raw_res=True, + msg="'process' should be 'mongod' on a mongod instance", + ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py new file mode 100644 index 000000000..e01b9783f --- /dev/null +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py @@ -0,0 +1,51 @@ +"""Tests for serverStatus command error conditions. + +Validates that invalid usages of serverStatus produce appropriate errors. +Note: serverStatus treats unrecognized top-level fields as section toggles, +so it may not reject unknown fields like most other commands do. +""" + +import pytest + +from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( + DiagnosticTestCase, +) +from documentdb_tests.framework.assertions import assertFailureCode, assertProperties +from documentdb_tests.framework.error_codes import COMMAND_NOT_FOUND_ERROR +from documentdb_tests.framework.executor import execute_admin_command +from documentdb_tests.framework.parametrize import pytest_params +from documentdb_tests.framework.property_checks import Eq + +pytestmark = pytest.mark.admin + + +ERROR_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="case_sensitive", + command={"ServerStatus": 1}, + error_code=COMMAND_NOT_FOUND_ERROR, + msg="Case-mismatched command name should fail", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(ERROR_TESTS)) +def test_serverStatus_error_conditions(collection, test): + """Verifies serverStatus rejects invalid usages with appropriate error codes.""" + result = execute_admin_command(collection, test.command) + assertFailureCode(result, test.error_code, msg=test.msg) + + +def test_serverStatus_unrecognized_field_accepted(collection): + """Verify serverStatus accepts unrecognized fields as section toggles. + + Unlike most commands, serverStatus treats unknown top-level fields as + section toggle names rather than rejecting them. + """ + result = execute_admin_command(collection, {"serverStatus": 1, "completelyFakeFieldName": 1}) + assertProperties( + result, + {"ok": Eq(1.0)}, + raw_res=True, + msg="Unrecognized fields should be accepted as section toggles", + ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py new file mode 100644 index 000000000..83a463a6c --- /dev/null +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -0,0 +1,232 @@ +"""Tests for serverStatus command field toggle behavior. + +Validates section inclusion/exclusion via field toggles, multiple +toggle combinations, and toggle value coercion. +""" + +import pytest + +from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( + DiagnosticTestCase, +) +from documentdb_tests.framework.assertions import assertProperties +from documentdb_tests.framework.executor import execute_admin_command +from documentdb_tests.framework.parametrize import pytest_params +from documentdb_tests.framework.property_checks import Exists, IsType, NotExists + +pytestmark = pytest.mark.admin + + +# --- Excluding Default Sections --- + +EXCLUDE_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="exclude_metrics", + command={"serverStatus": 1, "metrics": 0}, + checks={"metrics": NotExists()}, + msg="Setting metrics: 0 should exclude metrics section", + ), + DiagnosticTestCase( + id="exclude_locks", + command={"serverStatus": 1, "locks": 0}, + checks={"locks": NotExists()}, + msg="Setting locks: 0 should exclude locks section", + ), + DiagnosticTestCase( + id="exclude_connections", + command={"serverStatus": 1, "connections": 0}, + checks={"connections": NotExists()}, + msg="Setting connections: 0 should exclude connections section", + ), + DiagnosticTestCase( + id="exclude_opcounters", + command={"serverStatus": 1, "opcounters": 0}, + checks={"opcounters": NotExists()}, + msg="Setting opcounters: 0 should exclude opcounters section", + ), + DiagnosticTestCase( + id="exclude_asserts", + command={"serverStatus": 1, "asserts": 0}, + checks={"asserts": NotExists()}, + msg="Setting asserts: 0 should exclude asserts section", + ), + DiagnosticTestCase( + id="exclude_network", + command={"serverStatus": 1, "network": 0}, + checks={"network": NotExists()}, + msg="Setting network: 0 should exclude network section", + ), + DiagnosticTestCase( + id="exclude_globalLock", + command={"serverStatus": 1, "globalLock": 0}, + checks={"globalLock": NotExists()}, + msg="Setting globalLock: 0 should exclude globalLock section", + ), + DiagnosticTestCase( + id="exclude_extra_info", + command={"serverStatus": 1, "extra_info": 0}, + checks={"extra_info": NotExists()}, + msg="Setting extra_info: 0 should exclude extra_info section", + ), + DiagnosticTestCase( + id="exclude_wiredTiger", + command={"serverStatus": 1, "wiredTiger": 0}, + checks={"wiredTiger": NotExists()}, + msg="Setting wiredTiger: 0 should exclude wiredTiger section", + ), + DiagnosticTestCase( + id="exclude_transactions", + command={"serverStatus": 1, "transactions": 0}, + checks={"transactions": NotExists()}, + msg="Setting transactions: 0 should exclude transactions section", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(EXCLUDE_TESTS)) +def test_serverStatus_exclude_section(collection, test): + """Verifies that setting a section to 0 excludes it from the response.""" + result = execute_admin_command(collection, test.command) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Including Excluded-by-Default Sections --- + +INCLUDE_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="include_mirroredReads", + command={"serverStatus": 1, "mirroredReads": 1}, + checks={"mirroredReads": Exists()}, + msg="Setting mirroredReads: 1 should include mirroredReads section", + ), + DiagnosticTestCase( + id="include_metrics_explicit", + command={"serverStatus": 1, "metrics": 1}, + checks={"metrics": IsType("object")}, + msg="Explicit metrics: 1 should include metrics section", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(INCLUDE_TESTS)) +def test_serverStatus_include_section(collection, test): + """Verifies that setting a section to 1 includes it in the response.""" + result = execute_admin_command(collection, test.command) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Multiple Toggles --- + + +def test_serverStatus_exclude_multiple_sections(collection): + """Verify excluding multiple sections simultaneously works.""" + result = execute_admin_command( + collection, {"serverStatus": 1, "metrics": 0, "locks": 0, "asserts": 0} + ) + assertProperties( + result, + { + "metrics": NotExists(), + "locks": NotExists(), + "asserts": NotExists(), + "connections": IsType("object"), + "opcounters": IsType("object"), + }, + raw_res=True, + msg="Multiple exclusions should work together", + ) + + +def test_serverStatus_exclude_some_include_some(collection): + """Verify mixed include/exclude toggles work together.""" + result = execute_admin_command( + collection, {"serverStatus": 1, "metrics": 0, "mirroredReads": 1} + ) + assertProperties( + result, + { + "metrics": NotExists(), + "mirroredReads": Exists(), + }, + raw_res=True, + msg="Mixed include/exclude should work", + ) + + +# --- Toggle Value Coercion --- + +TOGGLE_COERCION_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="toggle_false_excludes", + command={"serverStatus": 1, "metrics": False}, + checks={"metrics": NotExists()}, + msg="Boolean false should exclude section", + ), + DiagnosticTestCase( + id="toggle_true_includes", + command={"serverStatus": 1, "metrics": True}, + checks={"metrics": IsType("object")}, + msg="Boolean true should include section", + ), + DiagnosticTestCase( + id="toggle_int_0_excludes", + command={"serverStatus": 1, "metrics": 0}, + checks={"metrics": NotExists()}, + msg="Int 0 should exclude section", + ), + DiagnosticTestCase( + id="toggle_int_1_includes", + command={"serverStatus": 1, "metrics": 1}, + checks={"metrics": IsType("object")}, + msg="Int 1 should include section", + ), + DiagnosticTestCase( + id="toggle_negative_includes", + command={"serverStatus": 1, "metrics": -1}, + checks={"metrics": IsType("object")}, + msg="Negative int should be truthy and include section", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(TOGGLE_COERCION_TESTS)) +def test_serverStatus_toggle_coercion(collection, test): + """Verifies that toggle values are coerced to truthy/falsy correctly.""" + result = execute_admin_command(collection, test.command) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Core Fields Unaffected by Toggles --- + + +def test_serverStatus_core_fields_present_with_exclusions(collection): + """Verify excluding optional sections does not affect core fields.""" + result = execute_admin_command(collection, {"serverStatus": 1, "metrics": 0, "locks": 0}) + assertProperties( + result, + { + "ok": Exists(), + "host": Exists(), + "version": Exists(), + "process": Exists(), + "pid": Exists(), + "uptime": Exists(), + "localTime": Exists(), + }, + raw_res=True, + msg="Excluding optional sections should not affect core fields", + ) + + +# --- Default Exclusions --- + + +def test_serverStatus_mirroredReads_excluded_by_default(collection): + """Verify mirroredReads is excluded from default response.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties( + result, + {"mirroredReads": NotExists()}, + raw_res=True, + msg="mirroredReads should be excluded by default", + ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py new file mode 100644 index 000000000..74146fe76 --- /dev/null +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py @@ -0,0 +1,339 @@ +"""Tests for serverStatus command response structure. + +Validates presence and types of core response fields, default sections, +and sub-document fields returned by serverStatus. +""" + +import pytest + +from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( + DiagnosticTestCase, +) +from documentdb_tests.framework.assertions import assertProperties +from documentdb_tests.framework.executor import execute_admin_command +from documentdb_tests.framework.parametrize import pytest_params +from documentdb_tests.framework.property_checks import Eq, Exists, IsType, NonEmptyStr + +pytestmark = pytest.mark.admin + + +# --- Top-Level Fields --- + +TOP_LEVEL_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="ok_is_1", + checks={"ok": Eq(1.0)}, + msg="'ok' should be 1.0", + ), + DiagnosticTestCase( + id="host_is_string", + checks={"host": IsType("string")}, + msg="'host' should be a string", + ), + DiagnosticTestCase( + id="version_is_string", + checks={"version": IsType("string")}, + msg="'version' should be a string", + ), + DiagnosticTestCase( + id="process_is_string", + checks={"process": IsType("string")}, + msg="'process' should be a string", + ), + DiagnosticTestCase( + id="pid_is_long", + checks={"pid": IsType("long")}, + msg="'pid' should be a long", + ), + DiagnosticTestCase( + id="uptime_exists", + checks={"uptime": Exists()}, + msg="'uptime' should exist", + ), + DiagnosticTestCase( + id="uptimeMillis_is_long", + checks={"uptimeMillis": IsType("long")}, + msg="'uptimeMillis' should be a long", + ), + DiagnosticTestCase( + id="uptimeEstimate_is_long", + checks={"uptimeEstimate": IsType("long")}, + msg="'uptimeEstimate' should be a long", + ), + DiagnosticTestCase( + id="localTime_is_date", + checks={"localTime": IsType("date")}, + msg="'localTime' should be a date", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(TOP_LEVEL_TESTS)) +def test_serverStatus_top_level_fields(collection, test): + """Verifies serverStatus top-level response fields have expected types.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Default Sections --- + +DEFAULT_SECTION_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="asserts_is_object", + checks={"asserts": IsType("object")}, + msg="'asserts' should be an object", + ), + DiagnosticTestCase( + id="connections_is_object", + checks={"connections": IsType("object")}, + msg="'connections' should be an object", + ), + DiagnosticTestCase( + id="extra_info_is_object", + checks={"extra_info": IsType("object")}, + msg="'extra_info' should be an object", + ), + DiagnosticTestCase( + id="globalLock_is_object", + checks={"globalLock": IsType("object")}, + msg="'globalLock' should be an object", + ), + DiagnosticTestCase( + id="locks_is_object", + checks={"locks": IsType("object")}, + msg="'locks' should be an object", + ), + DiagnosticTestCase( + id="logicalSessionRecordCache_is_object", + checks={"logicalSessionRecordCache": IsType("object")}, + msg="'logicalSessionRecordCache' should be an object", + ), + DiagnosticTestCase( + id="mem_is_object", + checks={"mem": IsType("object")}, + msg="'mem' should be an object", + ), + DiagnosticTestCase( + id="metrics_is_object", + checks={"metrics": IsType("object")}, + msg="'metrics' should be an object", + ), + DiagnosticTestCase( + id="network_is_object", + checks={"network": IsType("object")}, + msg="'network' should be an object", + ), + DiagnosticTestCase( + id="opcounters_is_object", + checks={"opcounters": IsType("object")}, + msg="'opcounters' should be an object", + ), + DiagnosticTestCase( + id="opcountersRepl_is_object", + checks={"opcountersRepl": IsType("object")}, + msg="'opcountersRepl' should be an object", + ), + DiagnosticTestCase( + id="storageEngine_is_object", + checks={"storageEngine": IsType("object")}, + msg="'storageEngine' should be an object", + ), + DiagnosticTestCase( + id="transactions_is_object", + checks={"transactions": IsType("object")}, + msg="'transactions' should be an object", + ), + DiagnosticTestCase( + id="wiredTiger_is_object", + checks={"wiredTiger": IsType("object")}, + msg="'wiredTiger' should be an object", + ), + DiagnosticTestCase( + id="catalogStats_is_object", + checks={"catalogStats": IsType("object")}, + msg="'catalogStats' should be an object", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(DEFAULT_SECTION_TESTS)) +def test_serverStatus_default_sections(collection, test): + """Verifies serverStatus default sections are present with expected types.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) + + +# --- Sub-Document Fields --- + +SUB_DOC_TESTS: list[DiagnosticTestCase] = [ + # asserts sub-fields + DiagnosticTestCase( + id="asserts_regular_exists", + checks={"asserts.regular": Exists()}, + msg="'asserts.regular' should exist", + ), + DiagnosticTestCase( + id="asserts_warning_exists", + checks={"asserts.warning": Exists()}, + msg="'asserts.warning' should exist", + ), + DiagnosticTestCase( + id="asserts_msg_exists", + checks={"asserts.msg": Exists()}, + msg="'asserts.msg' should exist", + ), + DiagnosticTestCase( + id="asserts_user_exists", + checks={"asserts.user": Exists()}, + msg="'asserts.user' should exist", + ), + DiagnosticTestCase( + id="asserts_rollovers_exists", + checks={"asserts.rollovers": Exists()}, + msg="'asserts.rollovers' should exist", + ), + # connections sub-fields + DiagnosticTestCase( + id="connections_current_exists", + checks={"connections.current": Exists()}, + msg="'connections.current' should exist", + ), + DiagnosticTestCase( + id="connections_available_exists", + checks={"connections.available": Exists()}, + msg="'connections.available' should exist", + ), + DiagnosticTestCase( + id="connections_totalCreated_exists", + checks={"connections.totalCreated": Exists()}, + msg="'connections.totalCreated' should exist", + ), + DiagnosticTestCase( + id="connections_active_exists", + checks={"connections.active": Exists()}, + msg="'connections.active' should exist", + ), + # opcounters sub-fields + DiagnosticTestCase( + id="opcounters_insert_exists", + checks={"opcounters.insert": Exists()}, + msg="'opcounters.insert' should exist", + ), + DiagnosticTestCase( + id="opcounters_query_exists", + checks={"opcounters.query": Exists()}, + msg="'opcounters.query' should exist", + ), + DiagnosticTestCase( + id="opcounters_update_exists", + checks={"opcounters.update": Exists()}, + msg="'opcounters.update' should exist", + ), + DiagnosticTestCase( + id="opcounters_delete_exists", + checks={"opcounters.delete": Exists()}, + msg="'opcounters.delete' should exist", + ), + DiagnosticTestCase( + id="opcounters_getmore_exists", + checks={"opcounters.getmore": Exists()}, + msg="'opcounters.getmore' should exist", + ), + DiagnosticTestCase( + id="opcounters_command_exists", + checks={"opcounters.command": Exists()}, + msg="'opcounters.command' should exist", + ), + # network sub-fields + DiagnosticTestCase( + id="network_bytesIn_exists", + checks={"network.bytesIn": Exists()}, + msg="'network.bytesIn' should exist", + ), + DiagnosticTestCase( + id="network_bytesOut_exists", + checks={"network.bytesOut": Exists()}, + msg="'network.bytesOut' should exist", + ), + DiagnosticTestCase( + id="network_numRequests_exists", + checks={"network.numRequests": Exists()}, + msg="'network.numRequests' should exist", + ), + # globalLock sub-fields + DiagnosticTestCase( + id="globalLock_totalTime_exists", + checks={"globalLock.totalTime": Exists()}, + msg="'globalLock.totalTime' should exist", + ), + DiagnosticTestCase( + id="globalLock_currentQueue_is_object", + checks={"globalLock.currentQueue": IsType("object")}, + msg="'globalLock.currentQueue' should be an object", + ), + DiagnosticTestCase( + id="globalLock_activeClients_is_object", + checks={"globalLock.activeClients": IsType("object")}, + msg="'globalLock.activeClients' should be an object", + ), + # storageEngine sub-fields + DiagnosticTestCase( + id="storageEngine_name_is_string", + checks={"storageEngine.name": IsType("string")}, + msg="'storageEngine.name' should be a string", + ), + DiagnosticTestCase( + id="storageEngine_name_is_nonempty", + checks={"storageEngine.name": NonEmptyStr()}, + msg="'storageEngine.name' should be non-empty", + ), + # mem sub-fields + DiagnosticTestCase( + id="mem_resident_exists", + checks={"mem.resident": Exists()}, + msg="'mem.resident' should exist", + ), + DiagnosticTestCase( + id="mem_virtual_exists", + checks={"mem.virtual": Exists()}, + msg="'mem.virtual' should exist", + ), + # catalogStats sub-fields + DiagnosticTestCase( + id="catalogStats_collections_exists", + checks={"catalogStats.collections": Exists()}, + msg="'catalogStats.collections' should exist", + ), + DiagnosticTestCase( + id="catalogStats_capped_exists", + checks={"catalogStats.capped": Exists()}, + msg="'catalogStats.capped' should exist", + ), + DiagnosticTestCase( + id="catalogStats_views_exists", + checks={"catalogStats.views": Exists()}, + msg="'catalogStats.views' should exist", + ), + DiagnosticTestCase( + id="catalogStats_timeseries_exists", + checks={"catalogStats.timeseries": Exists()}, + msg="'catalogStats.timeseries' should exist", + ), + DiagnosticTestCase( + id="catalogStats_internalCollections_exists", + checks={"catalogStats.internalCollections": Exists()}, + msg="'catalogStats.internalCollections' should exist", + ), + DiagnosticTestCase( + id="catalogStats_internalViews_exists", + checks={"catalogStats.internalViews": Exists()}, + msg="'catalogStats.internalViews' should exist", + ), +] + + +@pytest.mark.parametrize("test", pytest_params(SUB_DOC_TESTS)) +def test_serverStatus_sub_document_fields(collection, test): + """Verifies serverStatus sub-document fields exist with expected types.""" + result = execute_admin_command(collection, {"serverStatus": 1}) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) From 5c0bdc68e8e671f0cee684d8155ad6c6796c6ebf Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Tue, 16 Jun 2026 11:58:38 -0700 Subject: [PATCH 02/12] apply style guide Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_argument_handling.py | 49 +++---- .../test_serverStatus_core_behavior.py | 92 ++++++------- .../test_serverStatus_error_conditions.py | 20 +-- .../test_serverStatus_field_toggle.py | 67 +++++---- .../test_serverStatus_response_structure.py | 129 ++++++++---------- 5 files changed, 176 insertions(+), 181 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py index 217ce33be..43588c098 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py @@ -4,6 +4,8 @@ The command field value is ignored by serverStatus. """ +from __future__ import annotations + from datetime import datetime, timezone import pytest @@ -20,144 +22,145 @@ pytestmark = pytest.mark.admin +# Property [BSON Type Acceptance]: serverStatus accepts any BSON type as the command argument value. ARGUMENT_TYPE_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( "int_1", command={"serverStatus": 1}, checks={"ok": Eq(1.0)}, - msg="Should accept int 1", + msg="serverStatus should accept int 1 as argument value", ), DiagnosticTestCase( "int_0", command={"serverStatus": 0}, checks={"ok": Eq(1.0)}, - msg="Should accept int 0", + msg="serverStatus should accept int 0 as argument value", ), DiagnosticTestCase( "int_neg1", command={"serverStatus": -1}, checks={"ok": Eq(1.0)}, - msg="Should accept int -1", + msg="serverStatus should accept negative int as argument value", ), DiagnosticTestCase( "bool_true", command={"serverStatus": True}, checks={"ok": Eq(1.0)}, - msg="Should accept true", + msg="serverStatus should accept boolean true as argument value", ), DiagnosticTestCase( "bool_false", command={"serverStatus": False}, checks={"ok": Eq(1.0)}, - msg="Should accept false", + msg="serverStatus should accept boolean false as argument value", ), DiagnosticTestCase( "string", command={"serverStatus": "hello"}, checks={"ok": Eq(1.0)}, - msg="Should accept string", + msg="serverStatus should accept string as argument value", ), DiagnosticTestCase( "empty_string", command={"serverStatus": ""}, checks={"ok": Eq(1.0)}, - msg="Should accept empty string", + msg="serverStatus should accept empty string as argument value", ), DiagnosticTestCase( "null", command={"serverStatus": None}, checks={"ok": Eq(1.0)}, - msg="Should accept null", + msg="serverStatus should accept null as argument value", ), DiagnosticTestCase( "empty_object", command={"serverStatus": {}}, checks={"ok": Eq(1.0)}, - msg="Should accept empty object", + msg="serverStatus should accept empty object as argument value", ), DiagnosticTestCase( "empty_array", command={"serverStatus": []}, checks={"ok": Eq(1.0)}, - msg="Should accept empty array", + msg="serverStatus should accept empty array as argument value", ), DiagnosticTestCase( "double", command={"serverStatus": 1.5}, checks={"ok": Eq(1.0)}, - msg="Should accept double", + msg="serverStatus should accept double as argument value", ), DiagnosticTestCase( "int64", command={"serverStatus": Int64(1)}, checks={"ok": Eq(1.0)}, - msg="Should accept int64", + msg="serverStatus should accept int64 as argument value", ), DiagnosticTestCase( "decimal128", command={"serverStatus": Decimal128("1")}, checks={"ok": Eq(1.0)}, - msg="Should accept decimal128", + msg="serverStatus should accept Decimal128 as argument value", ), DiagnosticTestCase( "decimal128_nan", command={"serverStatus": Decimal128("NaN")}, checks={"ok": Eq(1.0)}, - msg="Should accept decimal128 NaN", + msg="serverStatus should accept Decimal128 NaN as argument value", ), DiagnosticTestCase( "infinity", command={"serverStatus": float("inf")}, checks={"ok": Eq(1.0)}, - msg="Should accept infinity", + msg="serverStatus should accept infinity as argument value", ), DiagnosticTestCase( "date", command={"serverStatus": datetime(2024, 1, 1, tzinfo=timezone.utc)}, checks={"ok": Eq(1.0)}, - msg="Should accept date", + msg="serverStatus should accept datetime as argument value", ), DiagnosticTestCase( "binData", command={"serverStatus": Binary(b"")}, checks={"ok": Eq(1.0)}, - msg="Should accept binData", + msg="serverStatus should accept Binary as argument value", ), DiagnosticTestCase( "objectId", command={"serverStatus": ObjectId()}, checks={"ok": Eq(1.0)}, - msg="Should accept objectId", + msg="serverStatus should accept ObjectId as argument value", ), DiagnosticTestCase( "regex", command={"serverStatus": Regex("test")}, checks={"ok": Eq(1.0)}, - msg="Should accept regex", + msg="serverStatus should accept Regex as argument value", ), DiagnosticTestCase( "timestamp", command={"serverStatus": Timestamp(0, 0)}, checks={"ok": Eq(1.0)}, - msg="Should accept timestamp", + msg="serverStatus should accept Timestamp as argument value", ), DiagnosticTestCase( "minKey", command={"serverStatus": MinKey()}, checks={"ok": Eq(1.0)}, - msg="Should accept minKey", + msg="serverStatus should accept MinKey as argument value", ), DiagnosticTestCase( "maxKey", command={"serverStatus": MaxKey()}, checks={"ok": Eq(1.0)}, - msg="Should accept maxKey", + msg="serverStatus should accept MaxKey as argument value", ), DiagnosticTestCase( "code", command={"serverStatus": Code("function(){}")}, checks={"ok": Eq(1.0)}, - msg="Should accept JavaScript code", + msg="serverStatus should accept JavaScript Code as argument value", ), ] diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py index 7b71aa19e..6f7136b8a 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py @@ -4,6 +4,8 @@ counters, and cross-field consistency. """ +from __future__ import annotations + import pytest from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( @@ -17,58 +19,57 @@ pytestmark = pytest.mark.admin -# --- Positive Value Checks --- - +# Property [Positive Values]: serverStatus fields have expected positive or non-negative bounds. POSITIVE_VALUE_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="uptime_gte_0", checks={"uptime": Gte(0)}, - msg="'uptime' should be >= 0", + msg="serverStatus should return uptime >= 0", ), DiagnosticTestCase( id="uptimeMillis_gte_0", checks={"uptimeMillis": Gte(0)}, - msg="'uptimeMillis' should be >= 0", + msg="serverStatus should return uptimeMillis >= 0", ), DiagnosticTestCase( id="uptimeEstimate_gte_0", checks={"uptimeEstimate": Gte(0)}, - msg="'uptimeEstimate' should be >= 0", + msg="serverStatus should return uptimeEstimate >= 0", ), DiagnosticTestCase( id="pid_gt_0", checks={"pid": Gt(0)}, - msg="'pid' should be > 0", + msg="serverStatus should return pid > 0", ), DiagnosticTestCase( id="connections_current_gte_1", checks={"connections.current": Gte(1)}, - msg="At least the test connection should exist", + msg="serverStatus should report at least one current connection", ), DiagnosticTestCase( id="connections_available_gte_0", checks={"connections.available": Gte(0)}, - msg="'connections.available' should be >= 0", + msg="serverStatus should return connections.available >= 0", ), DiagnosticTestCase( id="connections_totalCreated_gte_1", checks={"connections.totalCreated": Gte(1)}, - msg="At least one connection should have been created", + msg="serverStatus should report at least one created connection", ), DiagnosticTestCase( id="mem_resident_gt_0", checks={"mem.resident": Gt(0)}, - msg="Process should use some resident memory", + msg="serverStatus should report positive resident memory usage", ), DiagnosticTestCase( id="mem_virtual_gt_0", checks={"mem.virtual": Gt(0)}, - msg="Process should use some virtual memory", + msg="serverStatus should report positive virtual memory usage", ), DiagnosticTestCase( id="globalLock_totalTime_gte_0", checks={"globalLock.totalTime": Gte(0)}, - msg="'globalLock.totalTime' should be >= 0", + msg="serverStatus should return globalLock.totalTime >= 0", ), ] @@ -80,93 +81,92 @@ def test_serverStatus_positive_values(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Non-Negative Counter Checks --- - +# Property [Non-Negative Counters]: serverStatus counter fields are non-negative integers. COUNTER_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="asserts_regular_gte_0", checks={"asserts.regular": Gte(0)}, - msg="'asserts.regular' should be >= 0", + msg="serverStatus should return asserts.regular >= 0", ), DiagnosticTestCase( id="asserts_warning_gte_0", checks={"asserts.warning": Gte(0)}, - msg="'asserts.warning' should be >= 0", + msg="serverStatus should return asserts.warning >= 0", ), DiagnosticTestCase( id="asserts_msg_gte_0", checks={"asserts.msg": Gte(0)}, - msg="'asserts.msg' should be >= 0", + msg="serverStatus should return asserts.msg >= 0", ), DiagnosticTestCase( id="asserts_user_gte_0", checks={"asserts.user": Gte(0)}, - msg="'asserts.user' should be >= 0", + msg="serverStatus should return asserts.user >= 0", ), DiagnosticTestCase( id="asserts_rollovers_gte_0", checks={"asserts.rollovers": Gte(0)}, - msg="'asserts.rollovers' should be >= 0", + msg="serverStatus should return asserts.rollovers >= 0", ), DiagnosticTestCase( id="opcounters_insert_gte_0", checks={"opcounters.insert": Gte(0)}, - msg="'opcounters.insert' should be >= 0", + msg="serverStatus should return opcounters.insert >= 0", ), DiagnosticTestCase( id="opcounters_query_gte_0", checks={"opcounters.query": Gte(0)}, - msg="'opcounters.query' should be >= 0", + msg="serverStatus should return opcounters.query >= 0", ), DiagnosticTestCase( id="opcounters_update_gte_0", checks={"opcounters.update": Gte(0)}, - msg="'opcounters.update' should be >= 0", + msg="serverStatus should return opcounters.update >= 0", ), DiagnosticTestCase( id="opcounters_delete_gte_0", checks={"opcounters.delete": Gte(0)}, - msg="'opcounters.delete' should be >= 0", + msg="serverStatus should return opcounters.delete >= 0", ), DiagnosticTestCase( id="opcounters_getmore_gte_0", checks={"opcounters.getmore": Gte(0)}, - msg="'opcounters.getmore' should be >= 0", + msg="serverStatus should return opcounters.getmore >= 0", ), DiagnosticTestCase( id="opcounters_command_gte_0", checks={"opcounters.command": Gte(0)}, - msg="'opcounters.command' should be >= 0", + msg="serverStatus should return opcounters.command >= 0", ), DiagnosticTestCase( id="network_bytesIn_gte_0", checks={"network.bytesIn": Gte(0)}, - msg="'network.bytesIn' should be >= 0", + msg="serverStatus should return network.bytesIn >= 0", ), DiagnosticTestCase( id="network_bytesOut_gte_0", checks={"network.bytesOut": Gte(0)}, - msg="'network.bytesOut' should be >= 0", + msg="serverStatus should return network.bytesOut >= 0", ), DiagnosticTestCase( id="network_numRequests_gte_0", checks={"network.numRequests": Gte(0)}, - msg="'network.numRequests' should be >= 0", + msg="serverStatus should return network.numRequests >= 0", ), DiagnosticTestCase( id="catalogStats_collections_gte_0", checks={"catalogStats.collections": Gte(0)}, - msg="'catalogStats.collections' should be >= 0", + msg="serverStatus should return catalogStats.collections >= 0", ), DiagnosticTestCase( id="catalogStats_capped_gte_0", checks={"catalogStats.capped": Gte(0)}, - msg="'catalogStats.capped' should be >= 0", + msg="serverStatus should return catalogStats.capped >= 0", ), DiagnosticTestCase( id="catalogStats_views_gte_0", checks={"catalogStats.views": Gte(0)}, - msg="'catalogStats.views' should be >= 0", + msg="serverStatus should return catalogStats.views >= 0", ), ] @@ -178,71 +178,71 @@ def test_serverStatus_counters(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Cross-Field Consistency (standalone tests) --- +# Property [Cross-Field Consistency]: serverStatus fields are consistent across calls. def test_serverStatus_totalCreated_gte_current(collection): - """Verify connections.totalCreated >= connections.current.""" + """Verify serverStatus connections.totalCreated >= connections.current.""" result = execute_admin_command(collection, {"serverStatus": 1}) current = result["connections"]["current"] assertProperties( result, {"connections.totalCreated": Gte(current)}, raw_res=True, - msg="totalCreated should include current and closed connections", + msg="serverStatus should report totalCreated >= current connections", ) def test_serverStatus_uptimeMillis_consistent_with_uptime(collection): - """Verify uptime (seconds, rounded) is consistent with uptimeMillis.""" + """Verify serverStatus uptime is consistent with uptimeMillis.""" result = execute_admin_command(collection, {"serverStatus": 1}) uptime_from_millis = result["uptimeMillis"] // 1000 assertProperties( result, {"uptime": Gte(uptime_from_millis)}, raw_res=True, - msg="uptime in seconds should be >= uptimeMillis / 1000", + msg="serverStatus should return uptime >= uptimeMillis / 1000", ) def test_serverStatus_pid_consistent_across_calls(collection): - """Verify pid is the same across multiple serverStatus calls.""" + """Verify serverStatus pid is stable across calls.""" result1 = execute_admin_command(collection, {"serverStatus": 1}) result2 = execute_admin_command(collection, {"serverStatus": 1}) assertProperties( result2, {"pid": Eq(result1["pid"])}, raw_res=True, - msg="pid should not change between calls", + msg="serverStatus should return the same pid across calls", ) def test_serverStatus_host_consistent_across_calls(collection): - """Verify host is the same across multiple serverStatus calls.""" + """Verify serverStatus host is stable across calls.""" result1 = execute_admin_command(collection, {"serverStatus": 1}) result2 = execute_admin_command(collection, {"serverStatus": 1}) assertProperties( result2, {"host": Eq(result1["host"])}, raw_res=True, - msg="host should not change between calls", + msg="serverStatus should return the same host across calls", ) def test_serverStatus_version_consistent_across_calls(collection): - """Verify version is the same across multiple serverStatus calls.""" + """Verify serverStatus version is stable across calls.""" result1 = execute_admin_command(collection, {"serverStatus": 1}) result2 = execute_admin_command(collection, {"serverStatus": 1}) assertProperties( result2, {"version": Eq(result1["version"])}, raw_res=True, - msg="version should not change between calls", + msg="serverStatus should return the same version across calls", ) def test_serverStatus_cross_database_same_core_fields(collection): - """Verify core identity fields are same regardless of database.""" + """Verify serverStatus core identity fields match across databases.""" admin_result = execute_admin_command(collection, {"serverStatus": 1}) db_result = execute_command(collection, {"serverStatus": 1}) assertProperties( @@ -254,16 +254,16 @@ def test_serverStatus_cross_database_same_core_fields(collection): "pid": Eq(admin_result["pid"]), }, raw_res=True, - msg="Core identity fields should be same regardless of database", + msg="serverStatus should return the same core fields regardless of database", ) def test_serverStatus_process_is_mongod(collection): - """Verify process field value is 'mongod' on a mongod instance.""" + """Verify serverStatus process field is mongod.""" result = execute_admin_command(collection, {"serverStatus": 1}) assertProperties( result, {"process": Eq("mongod")}, raw_res=True, - msg="'process' should be 'mongod' on a mongod instance", + msg="serverStatus should return process as mongod on a mongod instance", ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py index e01b9783f..ffd397b6d 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py @@ -2,9 +2,11 @@ Validates that invalid usages of serverStatus produce appropriate errors. Note: serverStatus treats unrecognized top-level fields as section toggles, -so it may not reject unknown fields like most other commands do. +so it does not reject unknown fields like most other commands do. """ +from __future__ import annotations + import pytest from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( @@ -19,33 +21,33 @@ pytestmark = pytest.mark.admin +# Property [Case Sensitivity]: serverStatus command name is case-sensitive. ERROR_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="case_sensitive", command={"ServerStatus": 1}, error_code=COMMAND_NOT_FOUND_ERROR, - msg="Case-mismatched command name should fail", + msg="serverStatus should reject case-mismatched command name", ), ] @pytest.mark.parametrize("test", pytest_params(ERROR_TESTS)) def test_serverStatus_error_conditions(collection, test): - """Verifies serverStatus rejects invalid usages with appropriate error codes.""" + """Verify serverStatus rejects invalid usages with appropriate error codes.""" result = execute_admin_command(collection, test.command) assertFailureCode(result, test.error_code, msg=test.msg) -def test_serverStatus_unrecognized_field_accepted(collection): - """Verify serverStatus accepts unrecognized fields as section toggles. +# Property [Unrecognized Fields]: serverStatus accepts unknown fields as section toggles. - Unlike most commands, serverStatus treats unknown top-level fields as - section toggle names rather than rejecting them. - """ + +def test_serverStatus_unrecognized_field_accepted(collection): + """Verify serverStatus accepts unrecognized fields as section toggles.""" result = execute_admin_command(collection, {"serverStatus": 1, "completelyFakeFieldName": 1}) assertProperties( result, {"ok": Eq(1.0)}, raw_res=True, - msg="Unrecognized fields should be accepted as section toggles", + msg="serverStatus should accept unrecognized fields as section toggles", ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 83a463a6c..61cbefa64 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -4,6 +4,8 @@ toggle combinations, and toggle value coercion. """ +from __future__ import annotations + import pytest from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( @@ -17,68 +19,67 @@ pytestmark = pytest.mark.admin -# --- Excluding Default Sections --- - +# Property [Section Exclusion]: serverStatus omits a section when its toggle is set to 0. EXCLUDE_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="exclude_metrics", command={"serverStatus": 1, "metrics": 0}, checks={"metrics": NotExists()}, - msg="Setting metrics: 0 should exclude metrics section", + msg="serverStatus should exclude metrics when set to 0", ), DiagnosticTestCase( id="exclude_locks", command={"serverStatus": 1, "locks": 0}, checks={"locks": NotExists()}, - msg="Setting locks: 0 should exclude locks section", + msg="serverStatus should exclude locks when set to 0", ), DiagnosticTestCase( id="exclude_connections", command={"serverStatus": 1, "connections": 0}, checks={"connections": NotExists()}, - msg="Setting connections: 0 should exclude connections section", + msg="serverStatus should exclude connections when set to 0", ), DiagnosticTestCase( id="exclude_opcounters", command={"serverStatus": 1, "opcounters": 0}, checks={"opcounters": NotExists()}, - msg="Setting opcounters: 0 should exclude opcounters section", + msg="serverStatus should exclude opcounters when set to 0", ), DiagnosticTestCase( id="exclude_asserts", command={"serverStatus": 1, "asserts": 0}, checks={"asserts": NotExists()}, - msg="Setting asserts: 0 should exclude asserts section", + msg="serverStatus should exclude asserts when set to 0", ), DiagnosticTestCase( id="exclude_network", command={"serverStatus": 1, "network": 0}, checks={"network": NotExists()}, - msg="Setting network: 0 should exclude network section", + msg="serverStatus should exclude network when set to 0", ), DiagnosticTestCase( id="exclude_globalLock", command={"serverStatus": 1, "globalLock": 0}, checks={"globalLock": NotExists()}, - msg="Setting globalLock: 0 should exclude globalLock section", + msg="serverStatus should exclude globalLock when set to 0", ), DiagnosticTestCase( id="exclude_extra_info", command={"serverStatus": 1, "extra_info": 0}, checks={"extra_info": NotExists()}, - msg="Setting extra_info: 0 should exclude extra_info section", + msg="serverStatus should exclude extra_info when set to 0", ), DiagnosticTestCase( id="exclude_wiredTiger", command={"serverStatus": 1, "wiredTiger": 0}, checks={"wiredTiger": NotExists()}, - msg="Setting wiredTiger: 0 should exclude wiredTiger section", + msg="serverStatus should exclude wiredTiger when set to 0", ), DiagnosticTestCase( id="exclude_transactions", command={"serverStatus": 1, "transactions": 0}, checks={"transactions": NotExists()}, - msg="Setting transactions: 0 should exclude transactions section", + msg="serverStatus should exclude transactions when set to 0", ), ] @@ -90,20 +91,19 @@ def test_serverStatus_exclude_section(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Including Excluded-by-Default Sections --- - +# Property [Section Inclusion]: serverStatus includes non-default sections when toggled to 1. INCLUDE_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="include_mirroredReads", command={"serverStatus": 1, "mirroredReads": 1}, checks={"mirroredReads": Exists()}, - msg="Setting mirroredReads: 1 should include mirroredReads section", + msg="serverStatus should include mirroredReads when set to 1", ), DiagnosticTestCase( id="include_metrics_explicit", command={"serverStatus": 1, "metrics": 1}, checks={"metrics": IsType("object")}, - msg="Explicit metrics: 1 should include metrics section", + msg="serverStatus should include metrics when explicitly set to 1", ), ] @@ -115,11 +115,11 @@ def test_serverStatus_include_section(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Multiple Toggles --- +# Property [Multiple Toggles]: serverStatus respects multiple section toggles simultaneously. def test_serverStatus_exclude_multiple_sections(collection): - """Verify excluding multiple sections simultaneously works.""" + """Verify serverStatus excludes multiple sections simultaneously.""" result = execute_admin_command( collection, {"serverStatus": 1, "metrics": 0, "locks": 0, "asserts": 0} ) @@ -133,12 +133,12 @@ def test_serverStatus_exclude_multiple_sections(collection): "opcounters": IsType("object"), }, raw_res=True, - msg="Multiple exclusions should work together", + msg="serverStatus should exclude multiple sections when each is set to 0", ) def test_serverStatus_exclude_some_include_some(collection): - """Verify mixed include/exclude toggles work together.""" + """Verify serverStatus handles mixed include and exclude toggles.""" result = execute_admin_command( collection, {"serverStatus": 1, "metrics": 0, "mirroredReads": 1} ) @@ -149,42 +149,41 @@ def test_serverStatus_exclude_some_include_some(collection): "mirroredReads": Exists(), }, raw_res=True, - msg="Mixed include/exclude should work", + msg="serverStatus should respect mixed include and exclude toggles", ) -# --- Toggle Value Coercion --- - +# Property [Toggle Value Coercion]: serverStatus coerces toggle values to truthy or falsy. TOGGLE_COERCION_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="toggle_false_excludes", command={"serverStatus": 1, "metrics": False}, checks={"metrics": NotExists()}, - msg="Boolean false should exclude section", + msg="serverStatus should exclude section when toggle is boolean false", ), DiagnosticTestCase( id="toggle_true_includes", command={"serverStatus": 1, "metrics": True}, checks={"metrics": IsType("object")}, - msg="Boolean true should include section", + msg="serverStatus should include section when toggle is boolean true", ), DiagnosticTestCase( id="toggle_int_0_excludes", command={"serverStatus": 1, "metrics": 0}, checks={"metrics": NotExists()}, - msg="Int 0 should exclude section", + msg="serverStatus should exclude section when toggle is int 0", ), DiagnosticTestCase( id="toggle_int_1_includes", command={"serverStatus": 1, "metrics": 1}, checks={"metrics": IsType("object")}, - msg="Int 1 should include section", + msg="serverStatus should include section when toggle is int 1", ), DiagnosticTestCase( id="toggle_negative_includes", command={"serverStatus": 1, "metrics": -1}, checks={"metrics": IsType("object")}, - msg="Negative int should be truthy and include section", + msg="serverStatus should include section when toggle is negative int (truthy)", ), ] @@ -196,11 +195,11 @@ def test_serverStatus_toggle_coercion(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Core Fields Unaffected by Toggles --- +# Property [Core Fields Preserved]: serverStatus core fields are unaffected by section toggles. def test_serverStatus_core_fields_present_with_exclusions(collection): - """Verify excluding optional sections does not affect core fields.""" + """Verify serverStatus core fields are present despite section exclusions.""" result = execute_admin_command(collection, {"serverStatus": 1, "metrics": 0, "locks": 0}) assertProperties( result, @@ -214,19 +213,19 @@ def test_serverStatus_core_fields_present_with_exclusions(collection): "localTime": Exists(), }, raw_res=True, - msg="Excluding optional sections should not affect core fields", + msg="serverStatus should include core fields even when optional sections are excluded", ) -# --- Default Exclusions --- +# Property [Default Exclusions]: serverStatus omits certain sections by default. def test_serverStatus_mirroredReads_excluded_by_default(collection): - """Verify mirroredReads is excluded from default response.""" + """Verify serverStatus excludes mirroredReads by default.""" result = execute_admin_command(collection, {"serverStatus": 1}) assertProperties( result, {"mirroredReads": NotExists()}, raw_res=True, - msg="mirroredReads should be excluded by default", + msg="serverStatus should exclude mirroredReads by default", ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py index 74146fe76..7c8d4f3cf 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py @@ -4,6 +4,8 @@ and sub-document fields returned by serverStatus. """ +from __future__ import annotations + import pytest from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( @@ -17,53 +19,52 @@ pytestmark = pytest.mark.admin -# --- Top-Level Fields --- - +# Property [Top-Level Fields]: serverStatus response contains core fields with expected types. TOP_LEVEL_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="ok_is_1", checks={"ok": Eq(1.0)}, - msg="'ok' should be 1.0", + msg="serverStatus should return ok: 1.0", ), DiagnosticTestCase( id="host_is_string", checks={"host": IsType("string")}, - msg="'host' should be a string", + msg="serverStatus should return host as a string", ), DiagnosticTestCase( id="version_is_string", checks={"version": IsType("string")}, - msg="'version' should be a string", + msg="serverStatus should return version as a string", ), DiagnosticTestCase( id="process_is_string", checks={"process": IsType("string")}, - msg="'process' should be a string", + msg="serverStatus should return process as a string", ), DiagnosticTestCase( id="pid_is_long", checks={"pid": IsType("long")}, - msg="'pid' should be a long", + msg="serverStatus should return pid as a long", ), DiagnosticTestCase( id="uptime_exists", checks={"uptime": Exists()}, - msg="'uptime' should exist", + msg="serverStatus should include uptime in response", ), DiagnosticTestCase( id="uptimeMillis_is_long", checks={"uptimeMillis": IsType("long")}, - msg="'uptimeMillis' should be a long", + msg="serverStatus should return uptimeMillis as a long", ), DiagnosticTestCase( id="uptimeEstimate_is_long", checks={"uptimeEstimate": IsType("long")}, - msg="'uptimeEstimate' should be a long", + msg="serverStatus should return uptimeEstimate as a long", ), DiagnosticTestCase( id="localTime_is_date", checks={"localTime": IsType("date")}, - msg="'localTime' should be a date", + msg="serverStatus should return localTime as a date", ), ] @@ -75,83 +76,82 @@ def test_serverStatus_top_level_fields(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Default Sections --- - +# Property [Default Sections]: serverStatus includes standard sections as objects by default. DEFAULT_SECTION_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( id="asserts_is_object", checks={"asserts": IsType("object")}, - msg="'asserts' should be an object", + msg="serverStatus should include asserts as an object", ), DiagnosticTestCase( id="connections_is_object", checks={"connections": IsType("object")}, - msg="'connections' should be an object", + msg="serverStatus should include connections as an object", ), DiagnosticTestCase( id="extra_info_is_object", checks={"extra_info": IsType("object")}, - msg="'extra_info' should be an object", + msg="serverStatus should include extra_info as an object", ), DiagnosticTestCase( id="globalLock_is_object", checks={"globalLock": IsType("object")}, - msg="'globalLock' should be an object", + msg="serverStatus should include globalLock as an object", ), DiagnosticTestCase( id="locks_is_object", checks={"locks": IsType("object")}, - msg="'locks' should be an object", + msg="serverStatus should include locks as an object", ), DiagnosticTestCase( id="logicalSessionRecordCache_is_object", checks={"logicalSessionRecordCache": IsType("object")}, - msg="'logicalSessionRecordCache' should be an object", + msg="serverStatus should include logicalSessionRecordCache as an object", ), DiagnosticTestCase( id="mem_is_object", checks={"mem": IsType("object")}, - msg="'mem' should be an object", + msg="serverStatus should include mem as an object", ), DiagnosticTestCase( id="metrics_is_object", checks={"metrics": IsType("object")}, - msg="'metrics' should be an object", + msg="serverStatus should include metrics as an object", ), DiagnosticTestCase( id="network_is_object", checks={"network": IsType("object")}, - msg="'network' should be an object", + msg="serverStatus should include network as an object", ), DiagnosticTestCase( id="opcounters_is_object", checks={"opcounters": IsType("object")}, - msg="'opcounters' should be an object", + msg="serverStatus should include opcounters as an object", ), DiagnosticTestCase( id="opcountersRepl_is_object", checks={"opcountersRepl": IsType("object")}, - msg="'opcountersRepl' should be an object", + msg="serverStatus should include opcountersRepl as an object", ), DiagnosticTestCase( id="storageEngine_is_object", checks={"storageEngine": IsType("object")}, - msg="'storageEngine' should be an object", + msg="serverStatus should include storageEngine as an object", ), DiagnosticTestCase( id="transactions_is_object", checks={"transactions": IsType("object")}, - msg="'transactions' should be an object", + msg="serverStatus should include transactions as an object", ), DiagnosticTestCase( id="wiredTiger_is_object", checks={"wiredTiger": IsType("object")}, - msg="'wiredTiger' should be an object", + msg="serverStatus should include wiredTiger as an object", ), DiagnosticTestCase( id="catalogStats_is_object", checks={"catalogStats": IsType("object")}, - msg="'catalogStats' should be an object", + msg="serverStatus should include catalogStats as an object", ), ] @@ -163,171 +163,162 @@ def test_serverStatus_default_sections(collection, test): assertProperties(result, test.checks, msg=test.msg, raw_res=True) -# --- Sub-Document Fields --- - +# Property [Sub-Document Fields]: serverStatus sections contain expected nested fields. SUB_DOC_TESTS: list[DiagnosticTestCase] = [ - # asserts sub-fields DiagnosticTestCase( id="asserts_regular_exists", checks={"asserts.regular": Exists()}, - msg="'asserts.regular' should exist", + msg="serverStatus should include asserts.regular", ), DiagnosticTestCase( id="asserts_warning_exists", checks={"asserts.warning": Exists()}, - msg="'asserts.warning' should exist", + msg="serverStatus should include asserts.warning", ), DiagnosticTestCase( id="asserts_msg_exists", checks={"asserts.msg": Exists()}, - msg="'asserts.msg' should exist", + msg="serverStatus should include asserts.msg", ), DiagnosticTestCase( id="asserts_user_exists", checks={"asserts.user": Exists()}, - msg="'asserts.user' should exist", + msg="serverStatus should include asserts.user", ), DiagnosticTestCase( id="asserts_rollovers_exists", checks={"asserts.rollovers": Exists()}, - msg="'asserts.rollovers' should exist", + msg="serverStatus should include asserts.rollovers", ), - # connections sub-fields DiagnosticTestCase( id="connections_current_exists", checks={"connections.current": Exists()}, - msg="'connections.current' should exist", + msg="serverStatus should include connections.current", ), DiagnosticTestCase( id="connections_available_exists", checks={"connections.available": Exists()}, - msg="'connections.available' should exist", + msg="serverStatus should include connections.available", ), DiagnosticTestCase( id="connections_totalCreated_exists", checks={"connections.totalCreated": Exists()}, - msg="'connections.totalCreated' should exist", + msg="serverStatus should include connections.totalCreated", ), DiagnosticTestCase( id="connections_active_exists", checks={"connections.active": Exists()}, - msg="'connections.active' should exist", + msg="serverStatus should include connections.active", ), - # opcounters sub-fields DiagnosticTestCase( id="opcounters_insert_exists", checks={"opcounters.insert": Exists()}, - msg="'opcounters.insert' should exist", + msg="serverStatus should include opcounters.insert", ), DiagnosticTestCase( id="opcounters_query_exists", checks={"opcounters.query": Exists()}, - msg="'opcounters.query' should exist", + msg="serverStatus should include opcounters.query", ), DiagnosticTestCase( id="opcounters_update_exists", checks={"opcounters.update": Exists()}, - msg="'opcounters.update' should exist", + msg="serverStatus should include opcounters.update", ), DiagnosticTestCase( id="opcounters_delete_exists", checks={"opcounters.delete": Exists()}, - msg="'opcounters.delete' should exist", + msg="serverStatus should include opcounters.delete", ), DiagnosticTestCase( id="opcounters_getmore_exists", checks={"opcounters.getmore": Exists()}, - msg="'opcounters.getmore' should exist", + msg="serverStatus should include opcounters.getmore", ), DiagnosticTestCase( id="opcounters_command_exists", checks={"opcounters.command": Exists()}, - msg="'opcounters.command' should exist", + msg="serverStatus should include opcounters.command", ), - # network sub-fields DiagnosticTestCase( id="network_bytesIn_exists", checks={"network.bytesIn": Exists()}, - msg="'network.bytesIn' should exist", + msg="serverStatus should include network.bytesIn", ), DiagnosticTestCase( id="network_bytesOut_exists", checks={"network.bytesOut": Exists()}, - msg="'network.bytesOut' should exist", + msg="serverStatus should include network.bytesOut", ), DiagnosticTestCase( id="network_numRequests_exists", checks={"network.numRequests": Exists()}, - msg="'network.numRequests' should exist", + msg="serverStatus should include network.numRequests", ), - # globalLock sub-fields DiagnosticTestCase( id="globalLock_totalTime_exists", checks={"globalLock.totalTime": Exists()}, - msg="'globalLock.totalTime' should exist", + msg="serverStatus should include globalLock.totalTime", ), DiagnosticTestCase( id="globalLock_currentQueue_is_object", checks={"globalLock.currentQueue": IsType("object")}, - msg="'globalLock.currentQueue' should be an object", + msg="serverStatus should return globalLock.currentQueue as an object", ), DiagnosticTestCase( id="globalLock_activeClients_is_object", checks={"globalLock.activeClients": IsType("object")}, - msg="'globalLock.activeClients' should be an object", + msg="serverStatus should return globalLock.activeClients as an object", ), - # storageEngine sub-fields DiagnosticTestCase( id="storageEngine_name_is_string", checks={"storageEngine.name": IsType("string")}, - msg="'storageEngine.name' should be a string", + msg="serverStatus should return storageEngine.name as a string", ), DiagnosticTestCase( id="storageEngine_name_is_nonempty", checks={"storageEngine.name": NonEmptyStr()}, - msg="'storageEngine.name' should be non-empty", + msg="serverStatus should return a non-empty storageEngine.name", ), - # mem sub-fields DiagnosticTestCase( id="mem_resident_exists", checks={"mem.resident": Exists()}, - msg="'mem.resident' should exist", + msg="serverStatus should include mem.resident", ), DiagnosticTestCase( id="mem_virtual_exists", checks={"mem.virtual": Exists()}, - msg="'mem.virtual' should exist", + msg="serverStatus should include mem.virtual", ), - # catalogStats sub-fields DiagnosticTestCase( id="catalogStats_collections_exists", checks={"catalogStats.collections": Exists()}, - msg="'catalogStats.collections' should exist", + msg="serverStatus should include catalogStats.collections", ), DiagnosticTestCase( id="catalogStats_capped_exists", checks={"catalogStats.capped": Exists()}, - msg="'catalogStats.capped' should exist", + msg="serverStatus should include catalogStats.capped", ), DiagnosticTestCase( id="catalogStats_views_exists", checks={"catalogStats.views": Exists()}, - msg="'catalogStats.views' should exist", + msg="serverStatus should include catalogStats.views", ), DiagnosticTestCase( id="catalogStats_timeseries_exists", checks={"catalogStats.timeseries": Exists()}, - msg="'catalogStats.timeseries' should exist", + msg="serverStatus should include catalogStats.timeseries", ), DiagnosticTestCase( id="catalogStats_internalCollections_exists", checks={"catalogStats.internalCollections": Exists()}, - msg="'catalogStats.internalCollections' should exist", + msg="serverStatus should include catalogStats.internalCollections", ), DiagnosticTestCase( id="catalogStats_internalViews_exists", checks={"catalogStats.internalViews": Exists()}, - msg="'catalogStats.internalViews' should exist", + msg="serverStatus should include catalogStats.internalViews", ), ] From fd54fa8d140a3d6af4061dc09ec7c28bfd79602b Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 16:11:22 -0700 Subject: [PATCH 03/12] add uptime_is_double Signed-off-by: Alina (Xi) Li --- .../serverStatus/test_serverStatus_response_structure.py | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py index 7c8d4f3cf..40a590962 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py @@ -51,6 +51,11 @@ checks={"uptime": Exists()}, msg="serverStatus should include uptime in response", ), + DiagnosticTestCase( + id="uptime_is_double", + checks={"uptime": IsType("double")}, + msg="serverStatus should return uptime as a double", + ), DiagnosticTestCase( id="uptimeMillis_is_long", checks={"uptimeMillis": IsType("long")}, From 182bbebec6bb6a4c87b615235ef4b5db293f3194 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 16:22:51 -0700 Subject: [PATCH 04/12] group errors/success together Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_error_conditions.py | 19 +------------------ .../test_serverStatus_field_toggle.py | 16 +++++++++++++++- 2 files changed, 16 insertions(+), 19 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py index ffd397b6d..9b20de509 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py @@ -1,8 +1,6 @@ """Tests for serverStatus command error conditions. Validates that invalid usages of serverStatus produce appropriate errors. -Note: serverStatus treats unrecognized top-level fields as section toggles, -so it does not reject unknown fields like most other commands do. """ from __future__ import annotations @@ -12,11 +10,10 @@ from documentdb_tests.compatibility.tests.system.diagnostic.utils.diagnostic_test_case import ( DiagnosticTestCase, ) -from documentdb_tests.framework.assertions import assertFailureCode, assertProperties +from documentdb_tests.framework.assertions import assertFailureCode from documentdb_tests.framework.error_codes import COMMAND_NOT_FOUND_ERROR from documentdb_tests.framework.executor import execute_admin_command from documentdb_tests.framework.parametrize import pytest_params -from documentdb_tests.framework.property_checks import Eq pytestmark = pytest.mark.admin @@ -37,17 +34,3 @@ def test_serverStatus_error_conditions(collection, test): """Verify serverStatus rejects invalid usages with appropriate error codes.""" result = execute_admin_command(collection, test.command) assertFailureCode(result, test.error_code, msg=test.msg) - - -# Property [Unrecognized Fields]: serverStatus accepts unknown fields as section toggles. - - -def test_serverStatus_unrecognized_field_accepted(collection): - """Verify serverStatus accepts unrecognized fields as section toggles.""" - result = execute_admin_command(collection, {"serverStatus": 1, "completelyFakeFieldName": 1}) - assertProperties( - result, - {"ok": Eq(1.0)}, - raw_res=True, - msg="serverStatus should accept unrecognized fields as section toggles", - ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 61cbefa64..9e14f06db 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -14,7 +14,7 @@ from documentdb_tests.framework.assertions import assertProperties from documentdb_tests.framework.executor import execute_admin_command from documentdb_tests.framework.parametrize import pytest_params -from documentdb_tests.framework.property_checks import Exists, IsType, NotExists +from documentdb_tests.framework.property_checks import Eq, Exists, IsType, NotExists pytestmark = pytest.mark.admin @@ -229,3 +229,17 @@ def test_serverStatus_mirroredReads_excluded_by_default(collection): raw_res=True, msg="serverStatus should exclude mirroredReads by default", ) + + +# Property [Unrecognized Fields]: serverStatus accepts unknown fields as section toggles. + + +def test_serverStatus_unrecognized_field_accepted(collection): + """Verify serverStatus accepts unrecognized fields as section toggles.""" + result = execute_admin_command(collection, {"serverStatus": 1, "completelyFakeFieldName": 1}) + assertProperties( + result, + {"ok": Eq(1.0)}, + raw_res=True, + msg="serverStatus should accept unrecognized fields as section toggles", + ) From 7acf9e09050eda1aeeb724d2be267bc1676d9d50 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 16:52:49 -0700 Subject: [PATCH 05/12] add missing toggle tests Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_field_toggle.py | 24 +++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 9e14f06db..15d6003be 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -185,6 +185,30 @@ def test_serverStatus_exclude_some_include_some(collection): checks={"metrics": IsType("object")}, msg="serverStatus should include section when toggle is negative int (truthy)", ), + DiagnosticTestCase( + id="toggle_string_includes", + command={"serverStatus": 1, "metrics": "hello"}, + checks={"metrics": IsType("object")}, + msg="serverStatus should include section when toggle is string (truthy)", + ), + DiagnosticTestCase( + id="toggle_null_excludes", + command={"serverStatus": 1, "metrics": None}, + checks={"metrics": NotExists()}, + msg="serverStatus should exclude section when toggle is null (falsy)", + ), + DiagnosticTestCase( + id="toggle_object_includes", + command={"serverStatus": 1, "metrics": {}}, + checks={"metrics": IsType("object")}, + msg="serverStatus should include section when toggle is empty object (truthy)", + ), + DiagnosticTestCase( + id="toggle_array_includes", + command={"serverStatus": 1, "metrics": []}, + checks={"metrics": IsType("object")}, + msg="serverStatus should include section when toggle is empty array (truthy)", + ), ] From 43dd0e52f84a086505457fd682923d928b310bc4 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 16:54:25 -0700 Subject: [PATCH 06/12] remove duplicate tests Signed-off-by: Alina (Xi) Li --- .../serverStatus/test_serverStatus_field_toggle.py | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 15d6003be..3511f31fb 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -167,18 +167,6 @@ def test_serverStatus_exclude_some_include_some(collection): checks={"metrics": IsType("object")}, msg="serverStatus should include section when toggle is boolean true", ), - DiagnosticTestCase( - id="toggle_int_0_excludes", - command={"serverStatus": 1, "metrics": 0}, - checks={"metrics": NotExists()}, - msg="serverStatus should exclude section when toggle is int 0", - ), - DiagnosticTestCase( - id="toggle_int_1_includes", - command={"serverStatus": 1, "metrics": 1}, - checks={"metrics": IsType("object")}, - msg="serverStatus should include section when toggle is int 1", - ), DiagnosticTestCase( id="toggle_negative_includes", command={"serverStatus": 1, "metrics": -1}, From 5b3c5bb580acda180d1cad742fd62b7ef04534b9 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 16:57:20 -0700 Subject: [PATCH 07/12] update no-ops Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_error_conditions.py | 2 +- .../test_serverStatus_field_toggle.py | 26 +++++++------------ 2 files changed, 11 insertions(+), 17 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py index 9b20de509..c3998f418 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py @@ -21,7 +21,7 @@ # Property [Case Sensitivity]: serverStatus command name is case-sensitive. ERROR_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( - id="case_sensitive", + id="case_ServerStatus", command={"ServerStatus": 1}, error_code=COMMAND_NOT_FOUND_ERROR, msg="serverStatus should reject case-mismatched command name", diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 3511f31fb..516081ae0 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -99,12 +99,6 @@ def test_serverStatus_exclude_section(collection, test): checks={"mirroredReads": Exists()}, msg="serverStatus should include mirroredReads when set to 1", ), - DiagnosticTestCase( - id="include_metrics_explicit", - command={"serverStatus": 1, "metrics": 1}, - checks={"metrics": IsType("object")}, - msg="serverStatus should include metrics when explicitly set to 1", - ), ] @@ -163,20 +157,20 @@ def test_serverStatus_exclude_some_include_some(collection): ), DiagnosticTestCase( id="toggle_true_includes", - command={"serverStatus": 1, "metrics": True}, - checks={"metrics": IsType("object")}, + command={"serverStatus": 1, "mirroredReads": True}, + checks={"mirroredReads": Exists()}, msg="serverStatus should include section when toggle is boolean true", ), DiagnosticTestCase( id="toggle_negative_includes", - command={"serverStatus": 1, "metrics": -1}, - checks={"metrics": IsType("object")}, + command={"serverStatus": 1, "mirroredReads": -1}, + checks={"mirroredReads": Exists()}, msg="serverStatus should include section when toggle is negative int (truthy)", ), DiagnosticTestCase( id="toggle_string_includes", - command={"serverStatus": 1, "metrics": "hello"}, - checks={"metrics": IsType("object")}, + command={"serverStatus": 1, "mirroredReads": "hello"}, + checks={"mirroredReads": Exists()}, msg="serverStatus should include section when toggle is string (truthy)", ), DiagnosticTestCase( @@ -187,14 +181,14 @@ def test_serverStatus_exclude_some_include_some(collection): ), DiagnosticTestCase( id="toggle_object_includes", - command={"serverStatus": 1, "metrics": {}}, - checks={"metrics": IsType("object")}, + command={"serverStatus": 1, "mirroredReads": {}}, + checks={"mirroredReads": Exists()}, msg="serverStatus should include section when toggle is empty object (truthy)", ), DiagnosticTestCase( id="toggle_array_includes", - command={"serverStatus": 1, "metrics": []}, - checks={"metrics": IsType("object")}, + command={"serverStatus": 1, "mirroredReads": []}, + checks={"mirroredReads": Exists()}, msg="serverStatus should include section when toggle is empty array (truthy)", ), ] From 548eed6d866a11b347f462166df4e11a0885f68d Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 17:01:04 -0700 Subject: [PATCH 08/12] merge identical tests together Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_core_behavior.py | 16 ++++--------- .../test_serverStatus_field_toggle.py | 24 ++++--------------- .../test_serverStatus_response_structure.py | 24 ++++--------------- 3 files changed, 15 insertions(+), 49 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py index 6f7136b8a..fa1f675c3 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py @@ -73,14 +73,6 @@ ), ] - -@pytest.mark.parametrize("test", pytest_params(POSITIVE_VALUE_TESTS)) -def test_serverStatus_positive_values(collection, test): - """Verifies serverStatus fields have expected positive/non-negative values.""" - result = execute_admin_command(collection, {"serverStatus": 1}) - assertProperties(result, test.checks, msg=test.msg, raw_res=True) - - # Property [Non-Negative Counters]: serverStatus counter fields are non-negative integers. COUNTER_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( @@ -170,10 +162,12 @@ def test_serverStatus_positive_values(collection, test): ), ] +VALUE_BOUND_TESTS = POSITIVE_VALUE_TESTS + COUNTER_TESTS + -@pytest.mark.parametrize("test", pytest_params(COUNTER_TESTS)) -def test_serverStatus_counters(collection, test): - """Verifies serverStatus counter fields are non-negative.""" +@pytest.mark.parametrize("test", pytest_params(VALUE_BOUND_TESTS)) +def test_serverStatus_value_bounds(collection, test): + """Verifies serverStatus fields have expected value bounds.""" result = execute_admin_command(collection, {"serverStatus": 1}) assertProperties(result, test.checks, msg=test.msg, raw_res=True) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 516081ae0..2cf461322 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -83,14 +83,6 @@ ), ] - -@pytest.mark.parametrize("test", pytest_params(EXCLUDE_TESTS)) -def test_serverStatus_exclude_section(collection, test): - """Verifies that setting a section to 0 excludes it from the response.""" - result = execute_admin_command(collection, test.command) - assertProperties(result, test.checks, msg=test.msg, raw_res=True) - - # Property [Section Inclusion]: serverStatus includes non-default sections when toggled to 1. INCLUDE_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( @@ -101,14 +93,6 @@ def test_serverStatus_exclude_section(collection, test): ), ] - -@pytest.mark.parametrize("test", pytest_params(INCLUDE_TESTS)) -def test_serverStatus_include_section(collection, test): - """Verifies that setting a section to 1 includes it in the response.""" - result = execute_admin_command(collection, test.command) - assertProperties(result, test.checks, msg=test.msg, raw_res=True) - - # Property [Multiple Toggles]: serverStatus respects multiple section toggles simultaneously. @@ -193,10 +177,12 @@ def test_serverStatus_exclude_some_include_some(collection): ), ] +TOGGLE_TESTS = EXCLUDE_TESTS + INCLUDE_TESTS + TOGGLE_COERCION_TESTS + -@pytest.mark.parametrize("test", pytest_params(TOGGLE_COERCION_TESTS)) -def test_serverStatus_toggle_coercion(collection, test): - """Verifies that toggle values are coerced to truthy/falsy correctly.""" +@pytest.mark.parametrize("test", pytest_params(TOGGLE_TESTS)) +def test_serverStatus_field_toggle(collection, test): + """Verifies serverStatus section toggle behavior.""" result = execute_admin_command(collection, test.command) assertProperties(result, test.checks, msg=test.msg, raw_res=True) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py index 40a590962..fcd557d27 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py @@ -73,14 +73,6 @@ ), ] - -@pytest.mark.parametrize("test", pytest_params(TOP_LEVEL_TESTS)) -def test_serverStatus_top_level_fields(collection, test): - """Verifies serverStatus top-level response fields have expected types.""" - result = execute_admin_command(collection, {"serverStatus": 1}) - assertProperties(result, test.checks, msg=test.msg, raw_res=True) - - # Property [Default Sections]: serverStatus includes standard sections as objects by default. DEFAULT_SECTION_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( @@ -160,14 +152,6 @@ def test_serverStatus_top_level_fields(collection, test): ), ] - -@pytest.mark.parametrize("test", pytest_params(DEFAULT_SECTION_TESTS)) -def test_serverStatus_default_sections(collection, test): - """Verifies serverStatus default sections are present with expected types.""" - result = execute_admin_command(collection, {"serverStatus": 1}) - assertProperties(result, test.checks, msg=test.msg, raw_res=True) - - # Property [Sub-Document Fields]: serverStatus sections contain expected nested fields. SUB_DOC_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( @@ -327,9 +311,11 @@ def test_serverStatus_default_sections(collection, test): ), ] +RESPONSE_STRUCTURE_TESTS = TOP_LEVEL_TESTS + DEFAULT_SECTION_TESTS + SUB_DOC_TESTS + -@pytest.mark.parametrize("test", pytest_params(SUB_DOC_TESTS)) -def test_serverStatus_sub_document_fields(collection, test): - """Verifies serverStatus sub-document fields exist with expected types.""" +@pytest.mark.parametrize("test", pytest_params(RESPONSE_STRUCTURE_TESTS)) +def test_serverStatus_response_structure(collection, test): + """Verifies serverStatus response fields exist with expected types.""" result = execute_admin_command(collection, {"serverStatus": 1}) assertProperties(result, test.checks, msg=test.msg, raw_res=True) From 0ac743688ef7e1f1af2fd421d5b746a05946c2bb Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Wed, 17 Jun 2026 17:05:05 -0700 Subject: [PATCH 09/12] check code style Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_argument_handling.py | 46 +++++++++---------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py index 43588c098..9fa765003 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_argument_handling.py @@ -25,139 +25,139 @@ # Property [BSON Type Acceptance]: serverStatus accepts any BSON type as the command argument value. ARGUMENT_TYPE_TESTS: list[DiagnosticTestCase] = [ DiagnosticTestCase( - "int_1", + id="int_1", command={"serverStatus": 1}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept int 1 as argument value", ), DiagnosticTestCase( - "int_0", + id="int_0", command={"serverStatus": 0}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept int 0 as argument value", ), DiagnosticTestCase( - "int_neg1", + id="int_neg1", command={"serverStatus": -1}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept negative int as argument value", ), DiagnosticTestCase( - "bool_true", + id="bool_true", command={"serverStatus": True}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept boolean true as argument value", ), DiagnosticTestCase( - "bool_false", + id="bool_false", command={"serverStatus": False}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept boolean false as argument value", ), DiagnosticTestCase( - "string", + id="string", command={"serverStatus": "hello"}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept string as argument value", ), DiagnosticTestCase( - "empty_string", + id="empty_string", command={"serverStatus": ""}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept empty string as argument value", ), DiagnosticTestCase( - "null", + id="null", command={"serverStatus": None}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept null as argument value", ), DiagnosticTestCase( - "empty_object", + id="empty_object", command={"serverStatus": {}}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept empty object as argument value", ), DiagnosticTestCase( - "empty_array", + id="empty_array", command={"serverStatus": []}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept empty array as argument value", ), DiagnosticTestCase( - "double", + id="double", command={"serverStatus": 1.5}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept double as argument value", ), DiagnosticTestCase( - "int64", + id="int64", command={"serverStatus": Int64(1)}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept int64 as argument value", ), DiagnosticTestCase( - "decimal128", + id="decimal128", command={"serverStatus": Decimal128("1")}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept Decimal128 as argument value", ), DiagnosticTestCase( - "decimal128_nan", + id="decimal128_nan", command={"serverStatus": Decimal128("NaN")}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept Decimal128 NaN as argument value", ), DiagnosticTestCase( - "infinity", + id="infinity", command={"serverStatus": float("inf")}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept infinity as argument value", ), DiagnosticTestCase( - "date", + id="date", command={"serverStatus": datetime(2024, 1, 1, tzinfo=timezone.utc)}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept datetime as argument value", ), DiagnosticTestCase( - "binData", + id="binData", command={"serverStatus": Binary(b"")}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept Binary as argument value", ), DiagnosticTestCase( - "objectId", + id="objectId", command={"serverStatus": ObjectId()}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept ObjectId as argument value", ), DiagnosticTestCase( - "regex", + id="regex", command={"serverStatus": Regex("test")}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept Regex as argument value", ), DiagnosticTestCase( - "timestamp", + id="timestamp", command={"serverStatus": Timestamp(0, 0)}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept Timestamp as argument value", ), DiagnosticTestCase( - "minKey", + id="minKey", command={"serverStatus": MinKey()}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept MinKey as argument value", ), DiagnosticTestCase( - "maxKey", + id="maxKey", command={"serverStatus": MaxKey()}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept MaxKey as argument value", ), DiagnosticTestCase( - "code", + id="code", command={"serverStatus": Code("function(){}")}, checks={"ok": Eq(1.0)}, msg="serverStatus should accept JavaScript Code as argument value", From 4d5f81dcebafbf6e4fc915001745df584bb07961 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Thu, 18 Jun 2026 10:56:07 -0700 Subject: [PATCH 10/12] convert to DiagnosticTestCase Signed-off-by: Alina (Xi) Li --- .../test_serverStatus_core_behavior.py | 16 +-- .../test_serverStatus_field_toggle.py | 115 ++++++++---------- .../test_serverStatus_response_structure.py | 5 - 3 files changed, 54 insertions(+), 82 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py index fa1f675c3..bb58d3c7b 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py @@ -71,6 +71,11 @@ checks={"globalLock.totalTime": Gte(0)}, msg="serverStatus should return globalLock.totalTime >= 0", ), + DiagnosticTestCase( + id="process_is_mongod", + checks={"process": Eq("mongod")}, + msg="serverStatus should return process as mongod on a mongod instance", + ), ] # Property [Non-Negative Counters]: serverStatus counter fields are non-negative integers. @@ -250,14 +255,3 @@ def test_serverStatus_cross_database_same_core_fields(collection): raw_res=True, msg="serverStatus should return the same core fields regardless of database", ) - - -def test_serverStatus_process_is_mongod(collection): - """Verify serverStatus process field is mongod.""" - result = execute_admin_command(collection, {"serverStatus": 1}) - assertProperties( - result, - {"process": Eq("mongod")}, - raw_res=True, - msg="serverStatus should return process as mongod on a mongod instance", - ) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py index 2cf461322..86e87e469 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_field_toggle.py @@ -94,42 +94,29 @@ ] # Property [Multiple Toggles]: serverStatus respects multiple section toggles simultaneously. - - -def test_serverStatus_exclude_multiple_sections(collection): - """Verify serverStatus excludes multiple sections simultaneously.""" - result = execute_admin_command( - collection, {"serverStatus": 1, "metrics": 0, "locks": 0, "asserts": 0} - ) - assertProperties( - result, - { +MULTIPLE_TOGGLE_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="exclude_multiple_sections", + command={"serverStatus": 1, "metrics": 0, "locks": 0, "asserts": 0}, + checks={ "metrics": NotExists(), "locks": NotExists(), "asserts": NotExists(), "connections": IsType("object"), "opcounters": IsType("object"), }, - raw_res=True, msg="serverStatus should exclude multiple sections when each is set to 0", - ) - - -def test_serverStatus_exclude_some_include_some(collection): - """Verify serverStatus handles mixed include and exclude toggles.""" - result = execute_admin_command( - collection, {"serverStatus": 1, "metrics": 0, "mirroredReads": 1} - ) - assertProperties( - result, - { + ), + DiagnosticTestCase( + id="exclude_some_include_some", + command={"serverStatus": 1, "metrics": 0, "mirroredReads": 1}, + checks={ "metrics": NotExists(), "mirroredReads": Exists(), }, - raw_res=True, msg="serverStatus should respect mixed include and exclude toggles", - ) - + ), +] # Property [Toggle Value Coercion]: serverStatus coerces toggle values to truthy or falsy. TOGGLE_COERCION_TESTS: list[DiagnosticTestCase] = [ @@ -177,25 +164,12 @@ def test_serverStatus_exclude_some_include_some(collection): ), ] -TOGGLE_TESTS = EXCLUDE_TESTS + INCLUDE_TESTS + TOGGLE_COERCION_TESTS - - -@pytest.mark.parametrize("test", pytest_params(TOGGLE_TESTS)) -def test_serverStatus_field_toggle(collection, test): - """Verifies serverStatus section toggle behavior.""" - result = execute_admin_command(collection, test.command) - assertProperties(result, test.checks, msg=test.msg, raw_res=True) - - # Property [Core Fields Preserved]: serverStatus core fields are unaffected by section toggles. - - -def test_serverStatus_core_fields_present_with_exclusions(collection): - """Verify serverStatus core fields are present despite section exclusions.""" - result = execute_admin_command(collection, {"serverStatus": 1, "metrics": 0, "locks": 0}) - assertProperties( - result, - { +CORE_FIELDS_PRESERVED_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="core_fields_present_with_exclusions", + command={"serverStatus": 1, "metrics": 0, "locks": 0}, + checks={ "ok": Exists(), "host": Exists(), "version": Exists(), @@ -204,34 +178,43 @@ def test_serverStatus_core_fields_present_with_exclusions(collection): "uptime": Exists(), "localTime": Exists(), }, - raw_res=True, msg="serverStatus should include core fields even when optional sections are excluded", - ) - + ), +] # Property [Default Exclusions]: serverStatus omits certain sections by default. - - -def test_serverStatus_mirroredReads_excluded_by_default(collection): - """Verify serverStatus excludes mirroredReads by default.""" - result = execute_admin_command(collection, {"serverStatus": 1}) - assertProperties( - result, - {"mirroredReads": NotExists()}, - raw_res=True, +DEFAULT_EXCLUSION_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="mirroredReads_excluded_by_default", + command={"serverStatus": 1}, + checks={"mirroredReads": NotExists()}, msg="serverStatus should exclude mirroredReads by default", - ) - + ), +] # Property [Unrecognized Fields]: serverStatus accepts unknown fields as section toggles. +UNRECOGNIZED_FIELD_TESTS: list[DiagnosticTestCase] = [ + DiagnosticTestCase( + id="unrecognized_field_accepted", + command={"serverStatus": 1, "completelyFakeFieldName": 1}, + checks={"ok": Eq(1.0)}, + msg="serverStatus should accept unrecognized fields as section toggles", + ), +] +TOGGLE_TESTS = ( + EXCLUDE_TESTS + + INCLUDE_TESTS + + MULTIPLE_TOGGLE_TESTS + + TOGGLE_COERCION_TESTS + + CORE_FIELDS_PRESERVED_TESTS + + DEFAULT_EXCLUSION_TESTS + + UNRECOGNIZED_FIELD_TESTS +) -def test_serverStatus_unrecognized_field_accepted(collection): - """Verify serverStatus accepts unrecognized fields as section toggles.""" - result = execute_admin_command(collection, {"serverStatus": 1, "completelyFakeFieldName": 1}) - assertProperties( - result, - {"ok": Eq(1.0)}, - raw_res=True, - msg="serverStatus should accept unrecognized fields as section toggles", - ) + +@pytest.mark.parametrize("test", pytest_params(TOGGLE_TESTS)) +def test_serverStatus_field_toggle(collection, test): + """Verifies serverStatus section toggle behavior.""" + result = execute_admin_command(collection, test.command) + assertProperties(result, test.checks, msg=test.msg, raw_res=True) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py index fcd557d27..bb74f0cd3 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_response_structure.py @@ -46,11 +46,6 @@ checks={"pid": IsType("long")}, msg="serverStatus should return pid as a long", ), - DiagnosticTestCase( - id="uptime_exists", - checks={"uptime": Exists()}, - msg="serverStatus should include uptime in response", - ), DiagnosticTestCase( id="uptime_is_double", checks={"uptime": IsType("double")}, From ecb1c94ab8a69e6d732aafebdf77afff6cea8c84 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Thu, 18 Jun 2026 11:04:09 -0700 Subject: [PATCH 11/12] explain why serverStatus has only 1 error test Signed-off-by: Alina (Xi) Li --- .../serverStatus/test_serverStatus_error_conditions.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py index c3998f418..4344447d4 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_error_conditions.py @@ -1,6 +1,10 @@ """Tests for serverStatus command error conditions. Validates that invalid usages of serverStatus produce appropriate errors. +serverStatus is highly permissive: it accepts any BSON type as the command +argument value, ignores unrecognized fields, and coerces toggle values to +truthy/falsy. The only error condition is a case-mismatched command name, +which is the generic unknown-command rejection, not serverStatus-specific. """ from __future__ import annotations From 36208121a252f294a42ba65d510f2185da5b3c68 Mon Sep 17 00:00:00 2001 From: "Alina (Xi) Li" Date: Fri, 19 Jun 2026 14:41:49 -0700 Subject: [PATCH 12/12] address review comment Signed-off-by: Alina (Xi) Li --- .../commands/serverStatus/test_serverStatus_core_behavior.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py index bb58d3c7b..659d79235 100644 --- a/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py +++ b/documentdb_tests/compatibility/tests/system/diagnostic/commands/serverStatus/test_serverStatus_core_behavior.py @@ -198,9 +198,9 @@ def test_serverStatus_uptimeMillis_consistent_with_uptime(collection): uptime_from_millis = result["uptimeMillis"] // 1000 assertProperties( result, - {"uptime": Gte(uptime_from_millis)}, + {"uptime": Gte(uptime_from_millis - 1)}, raw_res=True, - msg="serverStatus should return uptime >= uptimeMillis / 1000", + msg="serverStatus should return uptime >= uptimeMillis / 1000 (within 1s tolerance)", )