import { describe, expect, it } from 'vitest';
import {
  AutomodConfigDashboardPatchSchema,
  CaseListQuerySchema,
  EconomyConfigDashboardPatchSchema,
  FunConfigDashboardSchema,
  GiveawayCreateDashboardSchema,
  LoggingConfigDashboardPatchSchema,
  ModerationDashboardPatchSchema,
  OptionalSnowflakeSchema,
  ScheduledMessageDashboardCreateSchema,
  SelfRolePanelDashboardCreateSchema,
  SocialFeedDashboardCreateSchema,
  StarboardConfigDashboardPatchSchema,
  SuggestionActionSchema,
  TagDashboardCreateSchema,
  TicketCategoryDashboardCreateSchema,
  TicketCategoryDashboardUpdateSchema,
  TicketConfigDashboardPatchSchema,
  WelcomeConfigDashboardPatchSchema
} from './dashboard.js';

describe('dashboard schemas', () => {
  it('accepts moderation patches with escalations', () => {
    const parsed = ModerationDashboardPatchSchema.parse({
      moderationEnabled: true,
      escalations: [{ warnCount: 3, action: 'TIMEOUT', durationMs: 60_000, enabled: true }]
    });
    expect(parsed.escalations?.[0]?.action).toBe('TIMEOUT');
  });

  it('rejects empty moderation patches', () => {
    expect(() => ModerationDashboardPatchSchema.parse({})).toThrow();
  });

  it('validates automod patches', () => {
    const parsed = AutomodConfigDashboardPatchSchema.parse({
      antiRaidEnabled: true,
      antiRaidJoinThreshold: 15
    });
    expect(parsed.antiRaidJoinThreshold).toBe(15);
  });

  it('validates logging patches with channel mappings', () => {
    const parsed = LoggingConfigDashboardPatchSchema.parse({
      logChannels: [{ eventType: 'MEMBER_JOIN', channelId: '123456789012345678' }]
    });
    expect(parsed.logChannels?.[0]?.eventType).toBe('MEMBER_JOIN');
  });

  it('rejects invalid log channel ids', () => {
    expect(() =>
      LoggingConfigDashboardPatchSchema.parse({
        logChannels: [{ eventType: 'MEMBER_JOIN', channelId: 'not-a-snowflake' }]
      })
    ).toThrow();
  });

  it('accepts empty string or a valid snowflake as optional id', () => {
    expect(OptionalSnowflakeSchema.parse('')).toBe('');
    expect(OptionalSnowflakeSchema.parse('123456789012345678')).toBe('123456789012345678');
    expect(() => OptionalSnowflakeSchema.parse('abc')).toThrow();
  });

  it('validates welcome patches', () => {
    const parsed = WelcomeConfigDashboardPatchSchema.parse({
      welcomeEnabled: true,
      welcomeChannelId: '123456789012345678'
    });
    expect(parsed.welcomeEnabled).toBe(true);
  });

  it('validates economy patches', () => {
    const parsed = EconomyConfigDashboardPatchSchema.parse({ currencyName: 'Gems', dailyAmount: 100 });
    expect(parsed.currencyName).toBe('Gems');
  });

  it('validates fun config', () => {
    const parsed = FunConfigDashboardSchema.parse({ enabled: true, mediaEnabled: false });
    expect(parsed.mediaEnabled).toBe(false);
  });

  it('applies default limit for case list queries', () => {
    const parsed = CaseListQuerySchema.parse({});
    expect(parsed.limit).toBe(25);
  });

  it('validates ticket config patches', () => {
    const parsed = TicketConfigDashboardPatchSchema.parse({ mode: 'THREAD', inactivityHours: 24 });
    expect(parsed.mode).toBe('THREAD');
  });

  it('validates ticket category creation', () => {
    const parsed = TicketCategoryDashboardCreateSchema.parse({
      name: 'Support',
      description: null,
      emoji: '🎫',
      supportRoleIds: ['123456789012345678']
    });
    expect(parsed.supportRoleIds).toHaveLength(1);
  });

  it('validates ticket category update with support roles', () => {
    const parsed = TicketCategoryDashboardUpdateSchema.parse({
      supportRoleIds: ['123456789012345678', '234567890123456789']
    });
    expect(parsed.supportRoleIds).toEqual(['123456789012345678', '234567890123456789']);
  });

  it('rejects invalid support role ids on ticket category create', () => {
    expect(() =>
      TicketCategoryDashboardCreateSchema.parse({
        name: 'Support',
        supportRoleIds: ['not-a-snowflake']
      })
    ).toThrow();
  });

  it('validates giveaway creation input', () => {
    const parsed = GiveawayCreateDashboardSchema.parse({
      channelId: '123456789012345678',
      prize: 'Nitro',
      winnerCount: 1,
      endsAt: new Date(Date.now() + 60_000).toISOString()
    });
    expect(parsed.prize).toBe('Nitro');
  });

  it('rejects giveaway creation with invalid date', () => {
    expect(() =>
      GiveawayCreateDashboardSchema.parse({
        channelId: '123456789012345678',
        prize: 'Nitro',
        winnerCount: 1,
        endsAt: 'not-a-date'
      })
    ).toThrow();
  });

  it('validates self role panel creation', () => {
    const parsed = SelfRolePanelDashboardCreateSchema.parse({
      channelId: '123456789012345678',
      title: 'Colors',
      mode: 'BUTTONS',
      behavior: 'NORMAL',
      roles: [{ roleId: '123456789012345678', label: 'Red' }]
    });
    expect(parsed.roles).toHaveLength(1);
  });

  it('validates tag creation', () => {
    const parsed = TagDashboardCreateSchema.parse({
      name: 'rules',
      content: 'Please read the rules',
      responseType: 'TEXT',
      allowedRoleIds: [],
      allowedChannelIds: []
    });
    expect(parsed.name).toBe('rules');
    expect(parsed.cooldownSeconds).toBe(15);
  });

  it('accepts custom tag cooldown', () => {
    const parsed = TagDashboardCreateSchema.parse({
      name: 'rules',
      content: 'Please read the rules',
      responseType: 'TEXT',
      cooldownSeconds: 30,
      allowedRoleIds: [],
      allowedChannelIds: []
    });
    expect(parsed.cooldownSeconds).toBe(30);
  });

  it('validates starboard patches', () => {
    const parsed = StarboardConfigDashboardPatchSchema.parse({ threshold: 5 });
    expect(parsed.threshold).toBe(5);
  });

  it('validates suggestion staff actions', () => {
    const parsed = SuggestionActionSchema.parse({ status: 'APPROVED', staffReason: 'Great idea' });
    expect(parsed.status).toBe('APPROVED');
  });

  it('validates social feed creation', () => {
    const parsed = SocialFeedDashboardCreateSchema.parse({
      type: 'TWITCH',
      sourceId: 'somechannel',
      channelId: '123456789012345678',
      enabled: true
    });
    expect(parsed.type).toBe('TWITCH');
  });

  it('validates scheduled message creation requires cron or runAt', () => {
    expect(() =>
      ScheduledMessageDashboardCreateSchema.parse({
        channelId: '123456789012345678',
        content: 'Hello'
      })
    ).toThrow();

    const parsed = ScheduledMessageDashboardCreateSchema.parse({
      channelId: '123456789012345678',
      content: 'Hello',
      runAt: new Date(Date.now() + 60_000).toISOString()
    });
    expect(parsed.content).toBe('Hello');
  });
});
