138 lines
3.2 KiB
TypeScript
138 lines
3.2 KiB
TypeScript
import { QueryInterface, DataTypes } from 'sequelize';
|
|
|
|
export async function up(queryInterface: QueryInterface): Promise<void> {
|
|
// Create priority enum type
|
|
await queryInterface.sequelize.query(`
|
|
DO $$ BEGIN
|
|
CREATE TYPE notification_priority_enum AS ENUM ('LOW', 'MEDIUM', 'HIGH', 'URGENT');
|
|
EXCEPTION
|
|
WHEN duplicate_object THEN null;
|
|
END $$;
|
|
`);
|
|
|
|
// Create notifications table
|
|
await queryInterface.createTable('notifications', {
|
|
notification_id: {
|
|
type: DataTypes.UUID,
|
|
defaultValue: DataTypes.UUIDV4,
|
|
primaryKey: true
|
|
},
|
|
user_id: {
|
|
type: DataTypes.UUID,
|
|
allowNull: false,
|
|
references: {
|
|
model: 'users',
|
|
key: 'user_id'
|
|
},
|
|
onUpdate: 'CASCADE',
|
|
onDelete: 'CASCADE'
|
|
},
|
|
request_id: {
|
|
type: DataTypes.UUID,
|
|
allowNull: true,
|
|
references: {
|
|
model: 'workflow_requests',
|
|
key: 'request_id'
|
|
},
|
|
onUpdate: 'CASCADE',
|
|
onDelete: 'SET NULL'
|
|
},
|
|
notification_type: {
|
|
type: DataTypes.STRING(50),
|
|
allowNull: false
|
|
},
|
|
title: {
|
|
type: DataTypes.STRING(255),
|
|
allowNull: false
|
|
},
|
|
message: {
|
|
type: DataTypes.TEXT,
|
|
allowNull: false
|
|
},
|
|
is_read: {
|
|
type: DataTypes.BOOLEAN,
|
|
defaultValue: false,
|
|
allowNull: false
|
|
},
|
|
priority: {
|
|
type: 'notification_priority_enum',
|
|
defaultValue: 'MEDIUM',
|
|
allowNull: false
|
|
},
|
|
action_url: {
|
|
type: DataTypes.STRING(500),
|
|
allowNull: true
|
|
},
|
|
action_required: {
|
|
type: DataTypes.BOOLEAN,
|
|
defaultValue: false,
|
|
allowNull: false
|
|
},
|
|
metadata: {
|
|
type: DataTypes.JSONB,
|
|
allowNull: true,
|
|
defaultValue: {}
|
|
},
|
|
sent_via: {
|
|
type: DataTypes.ARRAY(DataTypes.STRING),
|
|
defaultValue: [],
|
|
allowNull: false
|
|
},
|
|
email_sent: {
|
|
type: DataTypes.BOOLEAN,
|
|
defaultValue: false,
|
|
allowNull: false
|
|
},
|
|
sms_sent: {
|
|
type: DataTypes.BOOLEAN,
|
|
defaultValue: false,
|
|
allowNull: false
|
|
},
|
|
push_sent: {
|
|
type: DataTypes.BOOLEAN,
|
|
defaultValue: false,
|
|
allowNull: false
|
|
},
|
|
read_at: {
|
|
type: DataTypes.DATE,
|
|
allowNull: true
|
|
},
|
|
expires_at: {
|
|
type: DataTypes.DATE,
|
|
allowNull: true
|
|
},
|
|
created_at: {
|
|
type: DataTypes.DATE,
|
|
allowNull: false,
|
|
defaultValue: DataTypes.NOW
|
|
}
|
|
});
|
|
|
|
// Create indexes for better query performance
|
|
await queryInterface.addIndex('notifications', ['user_id'], {
|
|
name: 'idx_notifications_user_id'
|
|
});
|
|
|
|
await queryInterface.addIndex('notifications', ['user_id', 'is_read'], {
|
|
name: 'idx_notifications_user_unread'
|
|
});
|
|
|
|
await queryInterface.addIndex('notifications', ['request_id'], {
|
|
name: 'idx_notifications_request_id'
|
|
});
|
|
|
|
await queryInterface.addIndex('notifications', ['created_at'], {
|
|
name: 'idx_notifications_created_at'
|
|
});
|
|
|
|
await queryInterface.addIndex('notifications', ['notification_type'], {
|
|
name: 'idx_notifications_type'
|
|
});
|
|
}
|
|
|
|
export async function down(queryInterface: QueryInterface): Promise<void> {
|
|
await queryInterface.dropTable('notifications');
|
|
await queryInterface.sequelize.query('DROP TYPE IF EXISTS notification_priority_enum;');
|
|
}
|
|
|