// k6 Load Testing Configuration
// Comprehensive load test for Sankofa Phoenix API
// Usage: k6 run k6-load-test.js

import http from 'k6/http';
import { check, sleep } from 'k6';
import { Rate, Trend, Counter } from 'k6/metrics';

// Custom metrics
const errorRate = new Rate('errors');
const apiLatency = new Trend('api_latency');
const graphqlLatency = new Trend('graphql_latency');
const requestCount = new Counter('requests_total');

// Configuration
const API_URL = __ENV.API_URL || 'https://api.sankofa.nexus';
const TEST_DURATION = __ENV.TEST_DURATION || '5m';
const VUS = parseInt(__ENV.VUS || '10');

export const options = {
    stages: [
        // Ramp up to 10 VUs over 1 minute
        { duration: '1m', target: 10 },
        // Stay at 10 VUs for 2 minutes
        { duration: '2m', target: 10 },
        // Ramp up to 50 VUs over 2 minutes
        { duration: '2m', target: 50 },
        // Stay at 50 VUs for 2 minutes
        { duration: '2m', target: 50 },
        // Ramp up to 100 VUs over 2 minutes
        { duration: '2m', target: 100 },
        // Stay at 100 VUs for 2 minutes
        { duration: '2m', target: 100 },
        // Ramp down to 0 VUs over 2 minutes
        { duration: '2m', target: 0 },
    ],
    thresholds: {
        // 95% of requests should be below 200ms
        'http_req_duration': ['p(95)<200', 'p(99)<500'],
        // Error rate should be less than 1%
        'http_req_failed': ['rate<0.01'],
        'errors': ['rate<0.01'],
        // API latency should be below 200ms
        'api_latency': ['p(95)<200'],
        // GraphQL latency should be below 300ms
        'graphql_latency': ['p(95)<300'],
    },
};

// Test data
const graphqlQueries = [
    {
        query: '{ __typename }',
    },
    {
        query: `
            query {
                me {
                    id
                    email
                    name
                }
            }
        `,
    },
    {
        query: `
            query {
                sites {
                    id
                    name
                    region
                    status
                }
            }
        `,
    },
];

// Helper function to get random query
function getRandomQuery() {
    return graphqlQueries[Math.floor(Math.random() * graphqlQueries.length)];
}

export default function () {
    // Test 1: Health endpoint
    const healthStart = Date.now();
    const healthRes = http.get(`${API_URL}/health`, {
        tags: { name: 'HealthCheck' },
    });
    const healthDuration = Date.now() - healthStart;
    
    const healthCheck = check(healthRes, {
        'health status is 200': (r) => r.status === 200,
        'health response time < 100ms': (r) => r.timings.duration < 100,
    });
    
    errorRate.add(!healthCheck);
    apiLatency.add(healthDuration);
    requestCount.add(1, { endpoint: 'health' });
    
    sleep(0.5);
    
    // Test 2: GraphQL endpoint
    const graphqlQuery = getRandomQuery();
    const graphqlStart = Date.now();
    const graphqlRes = http.post(
        `${API_URL}/graphql`,
        JSON.stringify(graphqlQuery),
        {
            headers: { 'Content-Type': 'application/json' },
            tags: { name: 'GraphQL' },
        }
    );
    const graphqlDuration = Date.now() - graphqlStart;
    
    const graphqlCheck = check(graphqlRes, {
        'graphql status is 200': (r) => r.status === 200,
        'graphql response time < 300ms': (r) => r.timings.duration < 300,
        'graphql has data': (r) => {
            try {
                const body = JSON.parse(r.body);
                return body.data !== undefined || body.errors === undefined;
            } catch (e) {
                return false;
            }
        },
    });
    
    errorRate.add(!graphqlCheck);
    graphqlLatency.add(graphqlDuration);
    requestCount.add(1, { endpoint: 'graphql' });
    
    sleep(1);
}

export function handleSummary(data) {
    return {
        'stdout': textSummary(data, { indent: ' ', enableColors: true }),
        'summary.json': JSON.stringify(data),
    };
}

function textSummary(data, options) {
    const indent = options.indent || '';
    const enableColors = options.enableColors || false;
    
    let summary = '';
    summary += `${indent}Test Summary\n`;
    summary += `${indent}============\n\n`;
    
    // Metrics summary
    summary += `${indent}Metrics:\n`;
    summary += `${indent}  - Total Requests: ${data.metrics.requests_total.values.count}\n`;
    summary += `${indent}  - Failed Requests: ${data.metrics.http_req_failed.values.rate * 100}%\n`;
    summary += `${indent}  - p95 Latency: ${data.metrics.http_req_duration.values['p(95)']}ms\n`;
    summary += `${indent}  - p99 Latency: ${data.metrics.http_req_duration.values['p(99)']}ms\n`;
    
    return summary;
}

