'use strict';

/** @type {import('sequelize-cli').Migration} */
module.exports = {
  async up(queryInterface, Sequelize) {
    // Create integrations table
    await queryInterface.createTable('integrations', {
      id: {
        type: Sequelize.UUID,
        defaultValue: Sequelize.UUIDV4,
        primaryKey: true,
      },
      organization_id: {
        type: Sequelize.UUID,
        allowNull: false,
        references: {
          model: 'organizations',
          key: 'id',
        },
        onUpdate: 'CASCADE',
        onDelete: 'CASCADE',
      },
      type: {
        type: Sequelize.ENUM('slack', 'email'),
        allowNull: false,
      },
      name: {
        type: Sequelize.STRING(255),
        allowNull: false,
      },
      config: {
        type: Sequelize.JSONB,
        allowNull: false,
        defaultValue: {},
      },
      enabled: {
        type: Sequelize.BOOLEAN,
        allowNull: false,
        defaultValue: true,
      },
      created_by: {
        type: Sequelize.UUID,
        allowNull: true,
        references: {
          model: 'users',
          key: 'id',
        },
        onUpdate: 'CASCADE',
        onDelete: 'SET NULL',
      },
      created_at: {
        type: Sequelize.DATE,
        allowNull: false,
        defaultValue: Sequelize.literal('CURRENT_TIMESTAMP'),
      },
      updated_at: {
        type: Sequelize.DATE,
        allowNull: false,
        defaultValue: Sequelize.literal('CURRENT_TIMESTAMP'),
      },
    });

    // Create notification_rules table
    await queryInterface.createTable('notification_rules', {
      id: {
        type: Sequelize.UUID,
        defaultValue: Sequelize.UUIDV4,
        primaryKey: true,
      },
      integration_id: {
        type: Sequelize.UUID,
        allowNull: false,
        references: {
          model: 'integrations',
          key: 'id',
        },
        onUpdate: 'CASCADE',
        onDelete: 'CASCADE',
      },
      event_type: {
        type: Sequelize.ENUM(
          'session_failed',
          'session_timeout',
          'node_offline',
          'node_online',
          'build_started',
          'build_complete',
          'daily_report',
          'weekly_report',
          'device_flagged'
        ),
        allowNull: false,
      },
      conditions: {
        type: Sequelize.JSONB,
        allowNull: true,
      },
      schedule: {
        type: Sequelize.STRING(100),
        allowNull: true,
      },
      recipients: {
        type: Sequelize.ARRAY(Sequelize.STRING),
        allowNull: true,
      },
      template: {
        type: Sequelize.TEXT,
        allowNull: true,
      },
      enabled: {
        type: Sequelize.BOOLEAN,
        allowNull: false,
        defaultValue: true,
      },
      created_at: {
        type: Sequelize.DATE,
        allowNull: false,
        defaultValue: Sequelize.literal('CURRENT_TIMESTAMP'),
      },
      updated_at: {
        type: Sequelize.DATE,
        allowNull: false,
        defaultValue: Sequelize.literal('CURRENT_TIMESTAMP'),
      },
    });

    // Create notification_logs table
    await queryInterface.createTable('notification_logs', {
      id: {
        type: Sequelize.UUID,
        defaultValue: Sequelize.UUIDV4,
        primaryKey: true,
      },
      integration_id: {
        type: Sequelize.UUID,
        allowNull: false,
        references: {
          model: 'integrations',
          key: 'id',
        },
        onUpdate: 'CASCADE',
        onDelete: 'CASCADE',
      },
      rule_id: {
        type: Sequelize.UUID,
        allowNull: true,
        references: {
          model: 'notification_rules',
          key: 'id',
        },
        onUpdate: 'CASCADE',
        onDelete: 'SET NULL',
      },
      event_type: {
        type: Sequelize.STRING(50),
        allowNull: false,
      },
      status: {
        type: Sequelize.ENUM('pending', 'sent', 'failed'),
        allowNull: false,
        defaultValue: 'pending',
      },
      payload: {
        type: Sequelize.JSONB,
        allowNull: true,
      },
      response: {
        type: Sequelize.JSONB,
        allowNull: true,
      },
      error_message: {
        type: Sequelize.TEXT,
        allowNull: true,
      },
      sent_at: {
        type: Sequelize.DATE,
        allowNull: true,
      },
      created_at: {
        type: Sequelize.DATE,
        allowNull: false,
        defaultValue: Sequelize.literal('CURRENT_TIMESTAMP'),
      },
    });

    // Add indexes
    await queryInterface.addIndex('integrations', ['organization_id']);
    await queryInterface.addIndex('integrations', ['type']);
    await queryInterface.addIndex('integrations', ['enabled']);
    await queryInterface.addIndex('notification_rules', ['integration_id']);
    await queryInterface.addIndex('notification_rules', ['event_type']);
    await queryInterface.addIndex('notification_rules', ['enabled']);
    await queryInterface.addIndex('notification_logs', ['integration_id']);
    await queryInterface.addIndex('notification_logs', ['status']);
    await queryInterface.addIndex('notification_logs', ['created_at']);
  },

  async down(queryInterface, Sequelize) {
    // Drop tables in reverse order due to foreign key constraints
    await queryInterface.dropTable('notification_logs');
    await queryInterface.dropTable('notification_rules');
    await queryInterface.dropTable('integrations');

    // Drop enum types
    await queryInterface.sequelize.query('DROP TYPE IF EXISTS "enum_integrations_type";');
    await queryInterface.sequelize.query(
      'DROP TYPE IF EXISTS "enum_notification_rules_event_type";'
    );
    await queryInterface.sequelize.query('DROP TYPE IF EXISTS "enum_notification_logs_status";');
  },
};
