/**
 * Resource Service Tests
 */

import { describe, it, expect, beforeEach, vi } from 'vitest'
import * as resourceService from '../resource'
import type { Context } from '../../types/context'
import type { Pool } from 'pg'

describe('Resource Service', () => {
  let mockContext: Context
  let mockDb: any

  beforeEach(() => {
    mockDb = {
      query: vi.fn(),
    }

    mockContext = {
      db: mockDb as any,
      user: {
        id: 'user-1',
        email: 'test@example.com',
        name: 'Test User',
        role: 'ADMIN',
      },
    } as Context
  })

  describe('getResources', () => {
    it('should return empty array when no resources exist', async () => {
      mockDb.query.mockResolvedValue({ rows: [] })

      const result = await resourceService.getResources(mockContext)

      expect(result).toEqual([])
      expect(mockDb.query).toHaveBeenCalledWith(
        expect.stringContaining('SELECT * FROM resources'),
        []
      )
    })

    it('should filter by type when provided', async () => {
      mockDb.query.mockResolvedValue({ rows: [] })

      await resourceService.getResources(mockContext, { type: 'VM' })

      expect(mockDb.query).toHaveBeenCalledWith(
        expect.stringContaining("type = $1"),
        ['VM']
      )
    })

    it('should filter by status when provided', async () => {
      mockDb.query.mockResolvedValue({ rows: [] })

      await resourceService.getResources(mockContext, { status: 'RUNNING' })

      expect(mockDb.query).toHaveBeenCalledWith(
        expect.stringContaining("status = $1"),
        ['RUNNING']
      )
    })
  })

  describe('createResource', () => {
    it('should create a resource with correct parameters', async () => {
      const input = {
        name: 'test-resource',
        type: 'VM',
        siteId: 'site-1',
        metadata: { cpu: 4 },
      }

      const mockRow = {
        id: 'resource-1',
        name: input.name,
        type: input.type,
        status: 'PENDING',
        site_id: input.siteId,
        metadata: JSON.stringify(input.metadata),
        created_at: new Date(),
        updated_at: new Date(),
      }

      mockDb.query.mockResolvedValueOnce({
        rows: [mockRow],
      })

      // Mock site query
      mockDb.query.mockResolvedValueOnce({
        rows: [{
          id: 'site-1',
          name: 'Test Site',
          region: 'us-east-1',
          status: 'ACTIVE',
          created_at: new Date(),
          updated_at: new Date(),
        }],
      })

      const result = await resourceService.createResource(mockContext, input)

      expect(result).toBeDefined()
      expect(result.name).toBe(input.name)
      expect(mockDb.query).toHaveBeenCalledWith(
        expect.stringContaining('INSERT INTO resources'),
        expect.arrayContaining([input.name, input.type, 'PENDING', input.siteId])
      )
    })
  })
})

