diff --git a/@sammo/game_logic/src/Command/index.ts b/@sammo/game_logic/src/Command/index.ts index 4ba1985..bed2305 100644 --- a/@sammo/game_logic/src/Command/index.ts +++ b/@sammo/game_logic/src/Command/index.ts @@ -19,7 +19,7 @@ export const enum CompensateType { Negative = -1, } -export abstract class BaseCommand>{ +export abstract class BaseCommand>{ abstract readonly actionName: string; abstract readonly className: string; abstract readonly type: CommandType; @@ -57,12 +57,40 @@ export abstract class BaseCommand>{ protected abstract fullConditionConstraints: IConstraint[] | undefined; protected abstract errorInvoker: string | undefined; + protected abstract readonly argSchema: {} extends ArgType ? undefined : z.ZodObject; + protected _arg: ArgType | undefined; + protected readonly reasonArgTestFailed?: string; + public get arg(): Readonly { + return must(this._arg); + } + + public constructor( public readonly general: General, public readonly env: GameEnv, - public readonly arg: ArgType + arg: ArgType ) { this.init(); + + this.reasonArgTestFailed = this.testArg(arg); + if(this.reasonArgTestFailed === undefined){ + this.initWithArg(); + } + } + + private testArg(rawArg: ArgType): string | undefined { + if(this.argSchema === undefined){ + if(Object.keys(rawArg).length === 0){ + return undefined; + } + return "이 커맨드는 인자를 받지 않습니다"; + } + const result = must(this.argSchema).safeParse(this.arg); + if(!result.success){ + return result.error.errors[0].message; + } + this._arg = result.data as unknown as ArgType; + return undefined; } protected abstract init(): void; @@ -128,10 +156,14 @@ export abstract class BaseCommand>{ } public testMinConditionMet(): string | undefined { - if (this.minConditionConstraints === undefined) { + if (this.argSchema === undefined && this.minConditionConstraints === undefined) { return this.testFullConditionMet(); } + if(this.minConditionConstraints === undefined){ + throw new InvalidArgument("minConditionConstraints가 제대로 설정되지 않았습니다"); + } + if (this.cachedMinConditionMet) { return this.reasonNotMinConditionMet; } @@ -153,6 +185,12 @@ export abstract class BaseCommand>{ } public testFullConditionMet(): string | undefined { + if(this.reasonArgTestFailed !== undefined){ + this.reasonNotFullConditionMet = this.reasonArgTestFailed; + this.cachedFullConditionMet = true; + return this.reasonNotFullConditionMet; + } + if (this.fullConditionConstraints === undefined) { throw new InvalidArgument('fullConditionConstraints가 제대로 설정되지 않았습니다'); }