import {Service} from '../../../di/src/decorator/Service.ts' import {Logging} from '../service/logging/Logging.ts' import LifecycleUnit from './Unit.ts' import {container, make} from '../../../di/src/global.ts' import {DependencyKey} from '../../../di/src/type/DependencyKey.ts' import RunLevelErrorHandler from '../error/RunLevelErrorHandler.ts' import {Status} from '../const/status.ts' import Instantiable from "../../../di/src/type/Instantiable.ts"; import {Collection} from "../collection/Collection.ts"; @Service() export default class Application { protected instantiated_units: Collection = new Collection() constructor( protected logger: Logging, protected rleh: RunLevelErrorHandler, protected units: (Instantiable)[], ) {} make(token: DependencyKey) { return make(token) } container() { return container } async up() { this.logger.info('Starting Daton...', true) for ( const unit_class of this.units ) { const unit = this.make(unit_class) this.instantiated_units.push(unit) await this.start_unit(unit) } } async down() { } async run() { try { await this.up() await this.down() } catch (e) { await this.app_error(e) } } async app_error(e: Error) { this.rleh.handle(e) } protected async start_unit(unit: LifecycleUnit) { try { unit.status = Status.Starting this.logger.info(`Starting ${unit.constructor.name}...`) await unit.up() this.logger.verbose(`Successfully started ${unit.constructor.name}`) unit.status = Status.Running } catch (e) { unit.status = Status.Error this.logger.error(`Error encountered while starting ${unit.constructor.name}. Will attempt to proceed.`) this.logger.debug(e.message) this.logger.verbose(e) } } }