61 lines
1.8 KiB
TypeScript
61 lines
1.8 KiB
TypeScript
import fs from 'node:fs/promises';
|
|
import path from 'node:path';
|
|
|
|
import {
|
|
parseScenarioDefaults,
|
|
parseScenarioDefinition,
|
|
type ScenarioDefaults,
|
|
type ScenarioDefinition,
|
|
} from '@sammo-ts/logic';
|
|
|
|
export interface ScenarioLoaderOptions {
|
|
scenarioRoot: string;
|
|
defaultsFileName?: string;
|
|
}
|
|
|
|
const readJsonFile = async (filePath: string): Promise<unknown> => {
|
|
const raw = await fs.readFile(filePath, 'utf8');
|
|
return JSON.parse(raw) as unknown;
|
|
};
|
|
|
|
export const resolveScenarioDefaultsPath = (
|
|
options: ScenarioLoaderOptions
|
|
): string =>
|
|
path.resolve(
|
|
options.scenarioRoot,
|
|
options.defaultsFileName ?? 'default.json'
|
|
);
|
|
|
|
export const resolveScenarioPath = (
|
|
options: ScenarioLoaderOptions,
|
|
scenarioId: number
|
|
): string => path.resolve(options.scenarioRoot, `scenario_${scenarioId}.json`);
|
|
|
|
export const loadScenarioDefaults = async (
|
|
defaultsPath: string
|
|
): Promise<ScenarioDefaults> => {
|
|
// 기본 시나리오 파일을 읽고 정규화한다.
|
|
const raw = await readJsonFile(defaultsPath);
|
|
return parseScenarioDefaults(raw);
|
|
};
|
|
|
|
export const loadScenarioDefinition = async (
|
|
scenarioPath: string,
|
|
defaults: ScenarioDefaults
|
|
): Promise<ScenarioDefinition> => {
|
|
// 시나리오 본문을 읽고 기본값과 합쳐서 파싱한다.
|
|
const raw = await readJsonFile(scenarioPath);
|
|
return parseScenarioDefinition(raw, defaults);
|
|
};
|
|
|
|
export const loadScenarioDefinitionById = async (
|
|
scenarioId: number,
|
|
options: ScenarioLoaderOptions
|
|
): Promise<ScenarioDefinition> => {
|
|
// 시나리오 번호로 파일을 찾고 파싱한다.
|
|
const defaultsPath = resolveScenarioDefaultsPath(options);
|
|
const scenarioPath = resolveScenarioPath(options, scenarioId);
|
|
const defaults = await loadScenarioDefaults(defaultsPath);
|
|
return loadScenarioDefinition(scenarioPath, defaults);
|
|
};
|