import * as Sequelize from 'sequelize';
import { DataTypes, Model, Optional } from 'sequelize';

export interface ClientAttributes {
	id: string;
	app_code: string;
	client_id: string;
	client_secret_hash: string | null;
	name: string;
	redirect_uris: string[];
	post_logout_redirect_uris: string[];
	grant_types: string[];
	response_types: string[];
	scopes: string[];
	token_endpoint_auth_method: string;
	require_pkce: boolean;
	status: string;
	created_at: Date;
}

export type ClientPk = 'id';
export type ClientId = Client[ClientPk];
export type ClientOptionalAttributes = 'id' | 'created_at';
export type ClientCreationAttributes = Optional<ClientAttributes, ClientOptionalAttributes>;

export class Client extends Model<ClientAttributes> implements ClientAttributes {
	declare id: string;
	declare app_code: string;
	declare client_id: string;
	declare client_secret_hash: string | null;
	declare name: string;
	declare redirect_uris: string[];
	declare post_logout_redirect_uris: string[];
	declare grant_types: string[];
	declare response_types: string[];
	declare scopes: string[];
	declare token_endpoint_auth_method: string;
	declare require_pkce: boolean;
	declare status: string;
	declare created_at: Date;

	static initModel(sequelize: Sequelize.Sequelize): typeof Client {
		return Client.init(
			{
				id: {
					type: DataTypes.UUID,
					allowNull: false,
					defaultValue: DataTypes.UUIDV4,
					primaryKey: true,
				},
				app_code: {
					type: DataTypes.TEXT,
					allowNull: false,
					unique: true,
				},
				client_id: {
					type: DataTypes.TEXT,
					allowNull: false,
					unique: true,
				},
				client_secret_hash: {
					type: DataTypes.TEXT,
					allowNull: true,
				},
				name: {
					type: DataTypes.TEXT,
					allowNull: false,
				},
				redirect_uris: {
					type: DataTypes.ARRAY(DataTypes.TEXT),
					allowNull: false,
					defaultValue: [],
				},
				post_logout_redirect_uris: {
					type: DataTypes.ARRAY(DataTypes.TEXT),
					allowNull: false,
					defaultValue: [],
				},
				grant_types: {
					type: DataTypes.ARRAY(DataTypes.TEXT),
					allowNull: false,
					defaultValue: ['authorization_code', 'refresh_token'],
				},
				response_types: {
					type: DataTypes.ARRAY(DataTypes.TEXT),
					allowNull: false,
					defaultValue: ['code'],
				},
				scopes: {
					type: DataTypes.ARRAY(DataTypes.TEXT),
					allowNull: false,
					defaultValue: ['openid', 'profile', 'email'],
				},
				token_endpoint_auth_method: {
					type: DataTypes.TEXT,
					allowNull: false,
					defaultValue: 'none',
				},
				require_pkce: {
					type: DataTypes.BOOLEAN,
					allowNull: false,
					defaultValue: true,
				},
				status: {
					type: DataTypes.TEXT,
					allowNull: false,
					defaultValue: 'active',
				},
				created_at: {
					type: DataTypes.DATE,
					allowNull: false,
					defaultValue: Sequelize.Sequelize.literal('CURRENT_TIMESTAMP'),
				},
			},
			{
				sequelize,
				tableName: 'clients',
				schema: 'public',
				timestamps: false,
				indexes: [
					{ name: 'idx_clients_app_code', fields: ['app_code'] },
					{ name: 'idx_clients_client_id', fields: ['client_id'] },
					{ name: 'idx_clients_status', fields: ['status'] },
				],
			},
		);
	}
}
