import { DynamicModule, Global, Module } from '@nestjs/common';
import { TypeOrmModule } from '@nestjs/typeorm';
import { LocationBroadcastCoreModule } from '../../core/location_broadcast_core/location_broadcast_core.module';
import { LoginCoreModule } from '../../core/login_core/login_core.module';
import { RedisModule } from '../../core/redis/redis.module';
import { PlayerTaskProgress } from './player_task_progress.entity';
import { TaskActivityAudit } from './task_activity_audit.entity';
import { TASK_ACTIVITY_AUDIT_STORE } from './task_activity_audit.store';
import { TaskActivityAuditDatabaseService } from './task_activity_audit_database.service';
import { TaskActivityAuditMemoryService } from './task_activity_audit_memory.service';
import { TaskActivityAuthorityService } from './task_activity_authority.service';
import { TaskProgressDatabaseService } from './task_progress_database.service';
import { TaskProgressMemoryService } from './task_progress_memory.service';
import { TaskService } from './task.service';
import { TasksController } from './tasks.controller';

@Global()
@Module({})
export class TasksModule {
  static forDatabase(): DynamicModule {
    return {
      module: TasksModule,
      global: true,
      imports: [LoginCoreModule, RedisModule, LocationBroadcastCoreModule, TypeOrmModule.forFeature([PlayerTaskProgress, TaskActivityAudit])],
      controllers: [TasksController],
      providers: [
        TaskProgressDatabaseService,
        { provide: 'ITaskProgressStore', useExisting: TaskProgressDatabaseService },
        TaskActivityAuditDatabaseService,
        { provide: TASK_ACTIVITY_AUDIT_STORE, useExisting: TaskActivityAuditDatabaseService },
        TaskActivityAuthorityService,
        TaskService,
      ],
      exports: [TaskService, 'ITaskProgressStore'],
    };
  }

  static forMemory(): DynamicModule {
    return {
      module: TasksModule,
      global: true,
      imports: [LoginCoreModule, RedisModule, LocationBroadcastCoreModule],
      controllers: [TasksController],
      providers: [
        TaskProgressMemoryService,
        { provide: 'ITaskProgressStore', useExisting: TaskProgressMemoryService },
        TaskActivityAuditMemoryService,
        { provide: TASK_ACTIVITY_AUDIT_STORE, useExisting: TaskActivityAuditMemoryService },
        TaskActivityAuthorityService,
        TaskService,
      ],
      exports: [TaskService, 'ITaskProgressStore'],
    };
  }

  static forRoot(useMemory?: boolean): DynamicModule {
    const shouldUseMemory = useMemory ?? (
      process.env.NODE_ENV === 'test' ||
      process.env.USE_MEMORY_STORAGE === 'true' ||
      !process.env.DB_HOST
    );
    return shouldUseMemory ? this.forMemory() : this.forDatabase();
  }
}
