-- Common Audit Queries for Foxhunt Services
-- Quick reference for service integration and debugging
-- Database: foxhunt_test (PostgreSQL 16.10)

-- ============================================================================
-- CONNECTION TEST QUERIES
-- ============================================================================

-- Test 1: Basic connectivity
SELECT version();

-- Test 2: Count audit tables
SELECT COUNT(*) as audit_table_count
FROM information_schema.tables
WHERE (table_name LIKE '%audit%' OR
       table_name IN ('best_execution_analysis', 'mifid_transaction_report', 'compliance_rule_executions'))
AND table_schema = 'public';

-- Test 3: List all audit tables with sizes
SELECT
  tablename as table_name,
  pg_size_pretty(pg_total_relation_size('public.'||tablename)) as size,
  (SELECT COUNT(*) FROM pg_indexes WHERE schemaname = 'public' AND tablename = t.tablename) as index_count
FROM pg_tables t
WHERE schemaname = 'public'
  AND (tablename LIKE '%audit%' OR
       tablename IN ('best_execution_analysis', 'mifid_transaction_report', 'compliance_rule_executions'))
ORDER BY tablename;

-- ============================================================================
-- SECURITY AUDIT LOG QUERIES
-- ============================================================================

-- Insert security event
INSERT INTO security_audit_log (event_type, success, error_message, ip_address, user_agent)
VALUES ('admin_action', true, 'Test event', '127.0.0.1', 'curl/7.0')
RETURNING id, event_type, created_at;

-- Query recent security events
SELECT
  event_type,
  success,
  error_message,
  ip_address,
  created_at
FROM security_audit_log
ORDER BY created_at DESC
LIMIT 100;

-- Count events by type
SELECT
  event_type,
  COUNT(*) as event_count,
  SUM(CASE WHEN success THEN 1 ELSE 0 END) as success_count,
  SUM(CASE WHEN NOT success THEN 1 ELSE 0 END) as failure_count
FROM security_audit_log
GROUP BY event_type
ORDER BY event_count DESC;

-- Find failed login attempts
SELECT
  ip_address,
  COUNT(*) as failed_attempts,
  MAX(created_at) as last_attempt
FROM security_audit_log
WHERE event_type = 'login_failure'
  AND created_at > NOW() - INTERVAL '1 hour'
GROUP BY ip_address
HAVING COUNT(*) > 3
ORDER BY failed_attempts DESC;

-- ============================================================================
-- SOX TRADE AUDIT QUERIES
-- ============================================================================

-- Log SOX trade activity (use function)
SELECT log_sox_trade_activity(
  'f47ac10b-58cc-4372-a567-0e02b2c3d479'::uuid,  -- trade_id
  'a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a11'::uuid,  -- user_id
  'AAPL',                                          -- symbol
  'BUY',                                           -- side
  100.0,                                           -- quantity
  150.25,                                          -- price
  'LIMIT',                                         -- order_type
  15025.00,                                        -- trade_value
  NOW(),                                           -- order_timestamp
  '{"var": 0.02}'::jsonb,                          -- risk_assessment
  '{"flags": []}'::jsonb                           -- compliance_flags
);

-- Query recent trades
SELECT
  trade_id,
  symbol,
  side,
  quantity,
  price,
  trade_value,
  order_timestamp,
  trade_status
FROM sox_trade_audit
ORDER BY order_timestamp DESC
LIMIT 100;

-- Find large trades
SELECT
  trade_id,
  symbol,
  quantity,
  trade_value,
  order_timestamp
FROM sox_trade_audit
WHERE trade_value > 100000
ORDER BY trade_value DESC
LIMIT 50;

-- Daily trade summary
SELECT
  DATE(order_timestamp) as trade_date,
  COUNT(*) as total_trades,
  SUM(CASE WHEN side = 'BUY' THEN 1 ELSE 0 END) as buy_count,
  SUM(CASE WHEN side = 'SELL' THEN 1 ELSE 0 END) as sell_count,
  SUM(trade_value) as total_value,
  AVG(trade_value) as avg_value
FROM sox_trade_audit
WHERE order_timestamp > NOW() - INTERVAL '30 days'
GROUP BY DATE(order_timestamp)
ORDER BY trade_date DESC;

-- ============================================================================
-- TRANSACTION AUDIT EVENTS QUERIES
-- ============================================================================

-- Insert transaction audit event
INSERT INTO transaction_audit_events (
  event_id,
  event_type,
  timestamp,
  timestamp_nanos,
  transaction_id,
  order_id,
  actor,
  details,
  risk_level,
  checksum,
  compliance_tags
) VALUES (
  'evt_' || gen_random_uuid()::text,
  'order_submitted',
  NOW(),
  EXTRACT(EPOCH FROM NOW())::bigint * 1000000000,
  'txn_' || gen_random_uuid()::text,
  'ord_' || gen_random_uuid()::text,
  'trading_service',
  '{"symbol": "AAPL", "quantity": 100}'::jsonb,
  'Low',
  encode(digest('test_checksum', 'sha256'), 'hex'),
  ARRAY['SOX', 'MIFID2']
);

-- Query using the helper function
SELECT * FROM query_audit_events(
  NOW() - INTERVAL '1 hour',  -- start_time
  NOW(),                       -- end_time
  NULL,                        -- transaction_id
  NULL,                        -- order_id
  NULL,                        -- actor
  NULL,                        -- event_type
  NULL,                        -- risk_level
  100,                         -- limit
  0                            -- offset
);

-- Get audit statistics
SELECT * FROM get_audit_event_statistics(
  NOW() - INTERVAL '24 hours',
  NOW()
);

-- Find high-risk events
SELECT
  event_id,
  event_type,
  transaction_id,
  actor,
  risk_level,
  timestamp
FROM transaction_audit_events
WHERE risk_level IN ('High', 'Critical')
ORDER BY timestamp DESC
LIMIT 100;

-- Verify audit event integrity
SELECT verify_audit_event_integrity('evt_some_event_id');

-- ============================================================================
-- KILL SWITCH AUDIT QUERIES
-- ============================================================================

-- Activate kill switch (use function)
SELECT activate_kill_switch(
  'AUTOMATIC',                              -- switch_type
  'Daily loss limit exceeded',              -- trigger_reason
  'HIGH',                                   -- severity_level
  'a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a11'::uuid,  -- triggered_by_user
  1000000.00,                               -- portfolio_value
  -50000.00                                 -- daily_pnl
);

-- Query kill switch history
SELECT
  switch_type,
  trigger_reason,
  severity_level,
  portfolio_value,
  daily_pnl,
  trigger_timestamp,
  resolution_timestamp
FROM kill_switch_audit
ORDER BY trigger_timestamp DESC
LIMIT 50;

-- Count activations by type
SELECT
  switch_type,
  COUNT(*) as activation_count,
  AVG(EXTRACT(EPOCH FROM (resolution_timestamp - trigger_timestamp))) as avg_downtime_seconds
FROM kill_switch_audit
WHERE resolution_timestamp IS NOT NULL
GROUP BY switch_type;

-- ============================================================================
-- POSITION LIMITS AUDIT QUERIES
-- ============================================================================

-- Check position limits (use function)
SELECT check_position_limits(
  'a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a11'::uuid,  -- user_id
  'AAPL',                                         -- instrument_id
  10000.0,                                        -- position_size
  8000.0                                          -- position_limit (will be breach)
);

-- Find limit breaches
SELECT
  instrument_id,
  position_size,
  position_limit,
  limit_utilization,
  breach_percentage,
  assessment_timestamp
FROM position_limits_audit
WHERE is_breach = true
ORDER BY assessment_timestamp DESC
LIMIT 100;

-- Position utilization by instrument
SELECT
  instrument_id,
  COUNT(*) as checks_count,
  MAX(limit_utilization) as max_utilization,
  AVG(limit_utilization) as avg_utilization,
  SUM(CASE WHEN is_breach THEN 1 ELSE 0 END) as breach_count
FROM position_limits_audit
WHERE assessment_timestamp > NOW() - INTERVAL '24 hours'
GROUP BY instrument_id
ORDER BY max_utilization DESC;

-- ============================================================================
-- MIFID II COMPLIANCE QUERIES
-- ============================================================================

-- Create MiFID II transaction report (use function)
SELECT create_mifid_transaction_report(
  'f47ac10b-58cc-4372-a567-0e02b2c3d479'::uuid,  -- trade_id
  'AAPL',                                         -- instrument_id
  'USD',                                          -- currency
  150.25,                                         -- price
  100.0,                                          -- quantity
  'NASDAQ',                                       -- trading_venue
  NOW()                                           -- transaction_timestamp
);

-- Query pending reports
SELECT
  trade_id,
  instrument_id,
  price,
  quantity,
  trading_venue,
  transaction_timestamp,
  reporting_status
FROM mifid_transaction_report
WHERE reporting_status = 'PENDING'
ORDER BY transaction_timestamp DESC;

-- Best execution analysis
SELECT
  trade_id,
  primary_venue,
  execution_quality_grade,
  price_improvement_percentage,
  total_transaction_costs,
  overall_score,
  meets_best_execution
FROM best_execution_analysis
ORDER BY analysis_timestamp DESC
LIMIT 100;

-- Execution quality distribution
SELECT
  execution_quality_grade,
  COUNT(*) as trade_count,
  AVG(overall_score) as avg_score,
  AVG(price_improvement_percentage) as avg_price_improvement
FROM best_execution_analysis
WHERE analysis_timestamp > NOW() - INTERVAL '30 days'
GROUP BY execution_quality_grade
ORDER BY execution_quality_grade;

-- ============================================================================
-- COMPLIANCE RULES QUERIES
-- ============================================================================

-- Get active compliance rules
SELECT * FROM get_active_compliance_rules()
LIMIT 100;

-- Get rules by type
SELECT * FROM get_compliance_rules_by_type('POSITION_LIMIT')
LIMIT 50;

-- Query rule executions
SELECT
  rule_id,
  execution_status,
  COUNT(*) as execution_count,
  AVG(execution_time_ms) as avg_execution_time,
  SUM(CASE WHEN execution_status = 'VIOLATED' THEN 1 ELSE 0 END) as violation_count
FROM compliance_rule_executions
WHERE executed_at > NOW() - INTERVAL '24 hours'
GROUP BY rule_id, execution_status;

-- Find recent violations
SELECT
  r.name as rule_name,
  e.rule_id,
  e.violation_details,
  e.executed_at
FROM compliance_rule_executions e
JOIN compliance_rules r ON e.rule_id = r.rule_id
WHERE e.execution_status = 'VIOLATED'
ORDER BY e.executed_at DESC
LIMIT 100;

-- ============================================================================
-- MONITORING AND STATISTICS
-- ============================================================================

-- Database size by table
SELECT
  schemaname,
  tablename,
  pg_size_pretty(pg_total_relation_size(schemaname||'.'||tablename)) AS total_size,
  pg_size_pretty(pg_relation_size(schemaname||'.'||tablename)) AS data_size,
  pg_size_pretty(pg_total_relation_size(schemaname||'.'||tablename) - pg_relation_size(schemaname||'.'||tablename)) AS index_size
FROM pg_tables
WHERE schemaname = 'public'
  AND (tablename LIKE '%audit%' OR
       tablename IN ('best_execution_analysis', 'mifid_transaction_report', 'compliance_rule_executions'))
ORDER BY pg_total_relation_size(schemaname||'.'||tablename) DESC;

-- Index usage statistics
SELECT
  schemaname,
  tablename,
  indexname,
  idx_scan as index_scans,
  idx_tup_read as tuples_read,
  idx_tup_fetch as tuples_fetched
FROM pg_stat_user_indexes
WHERE schemaname = 'public'
  AND tablename LIKE '%audit%'
ORDER BY idx_scan DESC
LIMIT 50;

-- Table statistics
SELECT
  schemaname,
  relname as table_name,
  n_live_tup as live_rows,
  n_dead_tup as dead_rows,
  n_tup_ins as inserts,
  n_tup_upd as updates,
  n_tup_del as deletes,
  last_vacuum,
  last_autovacuum,
  last_analyze,
  last_autoanalyze
FROM pg_stat_user_tables
WHERE schemaname = 'public'
  AND (relname LIKE '%audit%' OR
       relname IN ('best_execution_analysis', 'mifid_transaction_report', 'compliance_rule_executions'))
ORDER BY n_live_tup DESC;

-- Active queries on audit tables
SELECT
  pid,
  usename,
  application_name,
  client_addr,
  state,
  query,
  query_start,
  state_change
FROM pg_stat_activity
WHERE state != 'idle'
  AND query ILIKE '%audit%'
ORDER BY query_start DESC;

-- ============================================================================
-- CLEANUP AND MAINTENANCE
-- ============================================================================

-- Clean up old audit logs (example - adjust retention as needed)
-- WARNING: Only run in non-production or with proper backup

-- Delete security audit logs older than 1 year
-- DELETE FROM security_audit_log WHERE created_at < NOW() - INTERVAL '1 year';

-- Archive old SOX trade audit (move to archive table first)
-- DELETE FROM sox_trade_audit WHERE order_timestamp < NOW() - INTERVAL '7 years';

-- Vacuum analyze audit tables
VACUUM ANALYZE security_audit_log;
VACUUM ANALYZE sox_trade_audit;
VACUUM ANALYZE transaction_audit_events;
VACUUM ANALYZE kill_switch_audit;
VACUUM ANALYZE position_limits_audit;
VACUUM ANALYZE mifid_transaction_report;
VACUUM ANALYZE best_execution_analysis;
VACUUM ANALYZE compliance_rule_executions;

-- Reindex audit tables (for performance maintenance)
-- REINDEX TABLE security_audit_log;
-- REINDEX TABLE sox_trade_audit;
-- REINDEX TABLE transaction_audit_events;

-- ============================================================================
-- NOTES
-- ============================================================================
/*
1. All timestamps are in UTC (TIMESTAMP WITH TIME ZONE)
2. Audit tables are designed to be append-only (no DELETE in production)
3. Use VACUUM ANALYZE regularly to maintain performance
4. Consider partitioning transaction_audit_events by date for large datasets
5. Implement proper backup strategy for regulatory compliance
6. Keep audit logs for 7 years minimum (SOX requirement)
7. Use prepared statements in application code to prevent SQL injection
*/
