orbit/js/config/ConfigLoader.js

34 lines
1.2 KiB
JavaScript

/**
* Loads the config manifest and every JSON file it references.
*
* data/manifest.json: { "files": ["game.json", "menu.json", "ship.json"] }
*
* Adding a config file = drop the .json in /data + one line in the manifest.
* Each file becomes a section keyed by its file name (without .json), so
* `ship.json` is available as `config.get('ship.thrust')`.
*/
export class ConfigLoader {
static async load(manifestPath = 'data/manifest.json') {
const manifest = await this.fetchJson(manifestPath);
const files = Array.isArray(manifest?.files) ? manifest.files : [];
// Resolve config files relative to the manifest's own location,
// so this works with relative or absolute manifest paths.
const base = manifestPath.replace(/[^/]*$/, '');
const data = {};
for (const file of files) {
const name = file.split('/').pop().replace(/\.json$/i, '');
data[name] = await this.fetchJson(base + file);
}
return data;
}
static async fetchJson(path) {
const res = await fetch(path);
if (!res.ok) {
throw new Error(`Could not load config "${path}" (${res.status} ${res.statusText})`);
}
return res.json();
}
}