/**
 * User validation integration tests.
 *
 * Verifies that WebhookServer.handleMessageUpsert correctly validates
 * and persists user records, handles DB errors gracefully, and
 * normalizes sender IDs before passing them to command services.
 */
import { describe, test, expect } from 'bun:test';
import { WebhookServer } from '../../src/server';
import { initializeDatabase } from '../../src/db';
import { SimulatedResponseQueue } from '../helpers/queue';
import { createTestRequest, registerServerTestLifecycle } from '../helpers/server-test-harness';

const testDb = registerServerTestLifecycle();

// ── Tests ──────────────────────────────────────────────────────────────

describe('User validation in handleMessageUpsert', () => {
	test('should proceed with valid user', async () => {
		const payload = {
			event: 'messages.upsert',
			instance: 'test-instance',
			data: {
				key: {
					remoteJid: 'group-id@g.us',
					participant: '1234567890@s.whatsapp.net',
				},
				message: { conversation: 'tarea nueva Test' },
			},
		};
		const request = createTestRequest(payload);
		const response = await WebhookServer.handleRequest(request);
		expect(response.status).toBe(200);
		expect(SimulatedResponseQueue.get().length).toBeGreaterThan(0);

		const user = testDb.query('SELECT * FROM users WHERE id = ?').get('1234567890');
		expect(user).toBeDefined();
		expect((user as any).id).toBe('1234567890');
	});

	test('should ignore message if user validation fails', async () => {
		const payload = {
			event: 'messages.upsert',
			instance: 'test-instance',
			data: {
				key: {
					remoteJid: 'group-id@g.us',
					participant: 'invalid!user@s.whatsapp.net',
				},
				message: { conversation: 'tarea nueva Test' },
			},
		};
		const request = createTestRequest(payload);
		const response = await WebhookServer.handleRequest(request);
		expect(response.status).toBe(200);
		expect(SimulatedResponseQueue.get().length).toBe(0);

		const userCount = testDb.query('SELECT COUNT(*) as count FROM users').get();
		expect((userCount as any).count).toBe(0);
	});

	test('should handle database errors during user validation', async () => {
		testDb.exec('DROP TABLE users');

		const payload = {
			event: 'messages.upsert',
			instance: 'test-instance',
			data: {
				key: {
					remoteJid: 'group-id@g.us',
					participant: '1234567890@s.whatsapp.net',
				},
				message: { conversation: 'tarea nueva Test' },
			},
		};
		const request = createTestRequest(payload);
		const response = await WebhookServer.handleRequest(request);
		expect(response.status).toBe(200);
		expect(SimulatedResponseQueue.get().length).toBe(0);

		// Reinitialize database for subsequent tests
		testDb.exec('DROP TABLE IF EXISTS schema_migrations');
		initializeDatabase(testDb);
	});

	test('should integrate user validation completely in handleMessageUpsert with valid user', async () => {
		const payload = {
			event: 'messages.upsert',
			instance: 'test-instance',
			data: {
				key: {
					remoteJid: 'group-id@g.us',
					participant: '1234567890@s.whatsapp.net',
				},
				message: { conversation: 'tarea nueva Test' },
			},
		};
		const request = createTestRequest(payload);
		const response = await WebhookServer.handleRequest(request);
		expect(response.status).toBe(200);
		expect(SimulatedResponseQueue.get().length).toBeGreaterThan(0);

		const user = testDb.query('SELECT * FROM users WHERE id = ?').get('1234567890');
		expect(user).toBeDefined();
		expect((user as any).id).toBe('1234567890');
		expect((user as any).first_seen).toBeDefined();
		expect((user as any).last_seen).toBeDefined();
	});

	test('should use normalized ID in command service', async () => {
		const payload = {
			event: 'messages.upsert',
			instance: 'test-instance',
			data: {
				key: {
					remoteJid: 'group-id@g.us',
					participant: '1234567890:12@s.whatsapp.net',
				},
				message: { conversation: 'tarea nueva Test' },
			},
		};

		const request = createTestRequest(payload);
		await WebhookServer.handleRequest(request);
		expect(SimulatedResponseQueue.get().length).toBeGreaterThan(0);
	});

	test('should handle end-to-end flow with valid user and command processing', async () => {
		const payload = {
			event: 'messages.upsert',
			instance: 'test-instance',
			data: {
				key: {
					remoteJid: 'group-id@g.us',
					participant: '1234567890@s.whatsapp.net',
				},
				message: { conversation: 'tarea nueva Test task' },
			},
		};

		const request = createTestRequest(payload);
		const response = await WebhookServer.handleRequest(request);
		expect(response.status).toBe(200);

		const user = testDb.query('SELECT * FROM users WHERE id = ?').get('1234567890');
		expect(user).toBeDefined();
		expect(SimulatedResponseQueue.get().length).toBeGreaterThan(0);
	});
});
