110 lines
No EOL
4.5 KiB
Python
110 lines
No EOL
4.5 KiB
Python
import unittest
|
|
import time
|
|
import sqlite3
|
|
from unittest.mock import patch
|
|
from storage.adapters.sqlite_adapter import SQLiteAdapter
|
|
from security.rbac_engine import RBACEngine
|
|
|
|
class TestResultsPersistence(unittest.TestCase):
|
|
"""Test results persistence functionality including performance metrics."""
|
|
|
|
def setUp(self):
|
|
"""Set up test database and adapter."""
|
|
self.db_path = ":memory:"
|
|
self.encryption_key = "test_key_12345678901234567890123456789012"
|
|
self.adapter = SQLiteAdapter(self.db_path, self.encryption_key)
|
|
|
|
# Setup mock RBAC
|
|
self.rbac = RBACEngine()
|
|
self.rbac.add_permission("test_user", "storage", "create")
|
|
self.rbac.add_permission("test_user", "storage", "read")
|
|
self.rbac.add_permission("test_user", "storage", "update")
|
|
self.rbac.add_permission("test_user", "storage", "delete")
|
|
self.adapter.rbac = self.rbac
|
|
|
|
def test_performance_metrics_table_exists(self):
|
|
"""Verify performance_metrics table was created."""
|
|
with sqlite3.connect(self.db_path) as conn:
|
|
cursor = conn.execute(
|
|
"SELECT name FROM sqlite_master WHERE type='table' AND name='performance_metrics'")
|
|
self.assertIsNotNone(cursor.fetchone())
|
|
|
|
def test_operation_timing_metrics(self):
|
|
"""Verify operations record performance metrics."""
|
|
# Test create operation
|
|
start = time.time()
|
|
self.adapter.create("test_key", "test_value", "test_user")
|
|
create_time = (time.time() - start) * 1000
|
|
|
|
# Test read operation
|
|
start = time.time()
|
|
self.adapter.read("test_key", "test_user")
|
|
read_time = (time.time() - start) * 1000
|
|
|
|
# Verify metrics were recorded
|
|
with sqlite3.connect(self.db_path) as conn:
|
|
cursor = conn.execute(
|
|
"SELECT operation, execution_time_ms FROM performance_metrics ORDER BY timestamp")
|
|
metrics = cursor.fetchall()
|
|
|
|
self.assertEqual(len(metrics), 2)
|
|
self.assertEqual(metrics[0][0], "create")
|
|
self.assertGreaterEqual(metrics[0][1], 0)
|
|
self.assertEqual(metrics[1][0], "read")
|
|
self.assertGreaterEqual(metrics[1][1], 0)
|
|
|
|
def test_response_time_benchmark(self):
|
|
"""Verify operations meet ≤800ms response time requirement."""
|
|
# Warm up
|
|
for _ in range(5):
|
|
self.adapter.create("warm_key", "warm_value", "test_user")
|
|
self.adapter.read("warm_key", "test_user")
|
|
|
|
# Benchmark create
|
|
start = time.time()
|
|
self.adapter.create("bench_key", "bench_value", "test_user")
|
|
create_time = (time.time() - start) * 1000
|
|
self.assertLessEqual(create_time, 800)
|
|
|
|
# Benchmark read
|
|
start = time.time()
|
|
self.adapter.read("bench_key", "test_user")
|
|
read_time = (time.time() - start) * 1000
|
|
self.assertLessEqual(read_time, 800)
|
|
|
|
# Benchmark update
|
|
start = time.time()
|
|
self.adapter.update("bench_key", "new_value", "test_user")
|
|
update_time = (time.time() - start) * 1000
|
|
self.assertLessEqual(update_time, 800)
|
|
|
|
# Benchmark delete
|
|
start = time.time()
|
|
self.adapter.delete("bench_key", "test_user")
|
|
delete_time = (time.time() - start) * 1000
|
|
self.assertLessEqual(delete_time, 800)
|
|
|
|
def test_encryption_integration(self):
|
|
"""Verify encrypted values are stored in performance metrics."""
|
|
self.adapter.create("enc_key", "secret_value", "test_user")
|
|
|
|
with sqlite3.connect(self.db_path) as conn:
|
|
# Verify storage table has encrypted value
|
|
cursor = conn.execute(
|
|
"SELECT encrypted_value FROM storage WHERE key_hash = ?",
|
|
(self.adapter._hash_key("enc_key"),))
|
|
encrypted = cursor.fetchone()[0]
|
|
self.assertNotEqual(encrypted, b"secret_value")
|
|
|
|
def test_rbac_enforcement(self):
|
|
"""Verify RBAC is enforced for performance metrics access."""
|
|
# User without permissions should be denied
|
|
with patch.object(self.rbac, 'validate_permission', return_value=False):
|
|
result = self.adapter.create("rbac_key", "rbac_value", "bad_user")
|
|
self.assertFalse(result)
|
|
|
|
result = self.adapter.read("rbac_key", "bad_user")
|
|
self.assertIsNone(result)
|
|
|
|
if __name__ == "__main__":
|
|
unittest.main() |