import { describe, it, expect, vi } from 'vitest'
import { subscribeWebhook } from '../src/routes/webhooks'

function makeCtx(body: unknown) {
  return {
    tenantId: 'tenant-1',
    scopes: ['events:read'],
    userId: null,
    oauthClientId: null,
    request: new Request('https://api.zync.is/v1/webhooks', {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify(body),
    }),
    db: {
      insert: vi.fn(() => ({
        values: vi.fn(() => ({
          returning: vi.fn(async () => [{ id: 'wh_1' }]),
        })),
      })),
    },
  } as never
}

describe('subscribeWebhook SSRF guard', () => {
  it('rejects private target_url with 422', async () => {
    const ctx = makeCtx({
      event: 'invoice.paid',
      target_url: 'https://127.0.0.1/',
      name: 'zap',
    })

    const res = await subscribeWebhook(ctx)
    expect(res.status).toBe(422)
    const json = await res.json() as { field?: string; message?: string }
    expect(json.field).toBe('target_url')
    expect(ctx.db.insert).not.toHaveBeenCalled()
  })

  it('accepts public HTTPS target_url', async () => {
    const ctx = makeCtx({
      event: 'invoice.paid',
      target_url: 'https://hooks.zapier.com/hooks/123',
      name: 'zap',
    })

    const res = await subscribeWebhook(ctx)
    expect(res.status).toBe(201)
    expect(ctx.db.insert).toHaveBeenCalled()
  })
})
