import * as plugins from '../../plugins.js';
import type { OpsServer } from '../classes.opsserver.js';
import * as interfaces from '../../../ts_interfaces/index.js';
import { requireOpsAuth } from '../helpers/auth.js';

export class EmailSettingsHandler {
  public typedrouter = new plugins.typedrequest.TypedRouter();

  constructor(private opsServerRef: OpsServer) {
    this.opsServerRef.typedrouter.addTypedRouter(this.typedrouter);
    this.registerHandlers();
  }

  private registerHandlers(): void {
    this.typedrouter.addTypedHandler(
      new plugins.typedrequest.TypedHandler<interfaces.requests.IReq_GetEmailServerSettings>(
        'getEmailServerSettings',
        async (dataArg) => {
          await requireOpsAuth(this.opsServerRef, dataArg, { scope: 'email-domains:read' as any });
          return { settings: this.getSettings() };
        },
      ),
    );

    this.typedrouter.addTypedHandler(
      new plugins.typedrequest.TypedHandler<interfaces.requests.IReq_UpdateEmailServerSettings>(
        'updateEmailServerSettings',
        async (dataArg) => {
          const auth = await requireOpsAuth(this.opsServerRef, dataArg, {
            scope: 'email-domains:write' as any,
            requireAdminIdentity: true,
          });
          const manager = this.opsServerRef.dcRouterRef.emailSettingsManager;
          if (!manager) {
            return { success: false, message: 'EmailSettingsManager not initialized' };
          }
          try {
            const settings = await this.opsServerRef.dcRouterRef.updateEmailServerSettings(
              dataArg.settings,
              auth.userId,
            );
            return { success: true, settings };
          } catch (err: unknown) {
            return { success: false, message: (err as Error).message };
          }
        },
      ),
    );
  }

  private getSettings(): interfaces.data.IEmailServerSettings {
    const manager = this.opsServerRef.dcRouterRef.emailSettingsManager;
    if (manager) {
      return manager.getPublicSettings();
    }
    const emailConfig = this.opsServerRef.dcRouterRef.options.emailConfig;
    const emailPortConfig = this.opsServerRef.dcRouterRef.options.emailPortConfig;
    return {
      enabled: Boolean(emailConfig),
      hostname: emailConfig?.hostname || null,
      ports: [...(emailConfig?.ports || [])],
      portMapping: emailPortConfig?.portMapping ? { ...emailPortConfig.portMapping } : null,
      receivedEmailsPath: emailPortConfig?.receivedEmailsPath || null,
      maxMessageSize: emailConfig?.maxMessageSize ?? null,
      domainCount: emailConfig?.domains?.length || 0,
      routeCount: emailConfig?.routes?.length || 0,
      authUserCount: emailConfig?.auth?.users?.length || 0,
      updatedAt: 0,
      updatedBy: 'runtime-options',
    };
  }
}
