mirror of
https://github.com/clusterio/clusterio.git
synced 2026-11-11 23:04:52 +09:00
Set default values for mod settings on export
Add missing mod settings set to their default values to a mod pack when performing a data export based on the settings prototypes that were extracted from the game. This mirrors the behaviour of Factorio when new setting prototypes are added by a mod.
This commit is contained in:
1 parent
39ed098a64
commit
ddc548f590
3 files changed
+133
No files matched your search
@@ -316,6 +316,40 @@ class ModPack {
|
||||
propertyTreeBytes(this.toJSON().settings),
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Fill in missing settings with their default values
|
||||
*
|
||||
* Uses the provided setting prototypes to add any missing mod settings
|
||||
* in the mod pack with the default value from the prototype.
|
||||
*
|
||||
* @param {Object<string, object>} settingPrototypes -
|
||||
* Setting prototypes exported from the game.
|
||||
* @param {Logger} logger - Logger used to report warnings on.
|
||||
*/
|
||||
fillDefaultSettings(settingPrototypes, logger) {
|
||||
const knownTypes = ["bool-setting", "int-setting", "double-setting", "string-setting"];
|
||||
let prototypes = Object.entries(settingPrototypes)
|
||||
.filter(([type, _]) => knownTypes.includes(type))
|
||||
.flatMap(([_, settings]) => Object.values(settings))
|
||||
;
|
||||
|
||||
for (let prototype of prototypes) {
|
||||
if (!["startup", "runtime-global", "runtime-per-user"].includes(prototype.setting_type)) {
|
||||
logger.warn(`Ignoring ${prototype.name} with unknown setting_type ${prototype.setting_type}`);
|
||||
continue;
|
||||
}
|
||||
if (prototype.default_value === undefined) {
|
||||
logger.warn(`Ignoring ${prototype.name} with missing default_value`);
|
||||
continue;
|
||||
}
|
||||
if (this.settings[prototype.setting_type].get(prototype.name)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
this.settings[prototype.setting_type].set(prototype.name, { value: prototype.default_value });
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = ModPack;
|
||||
@@ -220,12 +220,17 @@ async function uploadExport(req, res) {
|
||||
];
|
||||
|
||||
let assets = {};
|
||||
let settingPrototypes = {};
|
||||
for (let filePath of exportFiles) {
|
||||
let file = zip.file(filePath);
|
||||
if (!file) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (filePath === "export/settings.json") {
|
||||
settingPrototypes = JSON.parse(await file.async("text"));
|
||||
}
|
||||
|
||||
let { name, ext } = path.posix.parse(filePath);
|
||||
let hash = await libHash.hashStream(file.nodeStream());
|
||||
assets[name] = `${name}.${hash}${ext}`;
|
||||
@@ -233,6 +238,7 @@ async function uploadExport(req, res) {
|
||||
}
|
||||
|
||||
modPack.exportManifest = new libData.ExportManifest({ assets });
|
||||
modPack.fillDefaultSettings(settingPrototypes, logger);
|
||||
res.app.locals.master.modPackUpdated(modPack);
|
||||
|
||||
res.sendStatus(200);
|
||||
|
||||
@@ -76,6 +76,99 @@ describe("lib/data/ModPack", function() {
|
||||
assert.deepEqual(factorioMods.map(mod => mod.factorioVersion), sortedVersions);
|
||||
});
|
||||
|
||||
describe(".fillDefaultSettings()", function() {
|
||||
const prototypes = {
|
||||
"bool-setting": {
|
||||
"bool": {
|
||||
name: "bool",
|
||||
type: "bool-setting",
|
||||
setting_type: "startup",
|
||||
default_value: true,
|
||||
},
|
||||
},
|
||||
"double-setting": {
|
||||
"number": {
|
||||
name: "number",
|
||||
type: "double-setting",
|
||||
setting_type: "runtime-global",
|
||||
default_value: 123,
|
||||
},
|
||||
},
|
||||
"string-setting": {
|
||||
"string": {
|
||||
name: "string",
|
||||
type: "string-setting",
|
||||
setting_type: "runtime-per-user",
|
||||
default_value: "a string",
|
||||
},
|
||||
},
|
||||
};
|
||||
const mockLogger = { warn: () => {} };
|
||||
it("should fill in defaults for settings", function() {
|
||||
const pack = new ModPack();
|
||||
pack.fillDefaultSettings(prototypes, mockLogger);
|
||||
assert.deepEqual(pack.toJSON().settings, {
|
||||
"startup": {
|
||||
"bool": { "value": true },
|
||||
},
|
||||
"runtime-global": {
|
||||
"number": { "value": 123 },
|
||||
},
|
||||
"runtime-per-user": {
|
||||
"string": { "value": "a string" },
|
||||
},
|
||||
});
|
||||
});
|
||||
it("should not overwrite existing values", function() {
|
||||
const pack = new ModPack({ settings: {
|
||||
"startup": {
|
||||
"bool": { "value": false },
|
||||
},
|
||||
"runtime-global": {
|
||||
"number": { "value": 2 },
|
||||
},
|
||||
"runtime-per-user": {
|
||||
"string": { "value": "spam" },
|
||||
},
|
||||
}});
|
||||
pack.fillDefaultSettings(prototypes, mockLogger);
|
||||
assert.deepEqual(pack.toJSON().settings, {
|
||||
"startup": {
|
||||
"bool": { "value": false },
|
||||
},
|
||||
"runtime-global": {
|
||||
"number": { "value": 2 },
|
||||
},
|
||||
"runtime-per-user": {
|
||||
"string": { "value": "spam" },
|
||||
},
|
||||
});
|
||||
});
|
||||
it("should ignore unknown setting_type and missing default_value", function() {
|
||||
const pack = new ModPack();
|
||||
pack.fillDefaultSettings({
|
||||
"string-setting": {
|
||||
"foo": {
|
||||
name: "foo",
|
||||
type: "string-setting",
|
||||
setting_type: "magic-that-does-not-exist",
|
||||
default_value: "a string",
|
||||
},
|
||||
"bar": {
|
||||
name: "bar",
|
||||
type: "string-setting",
|
||||
setting_type: "startup",
|
||||
},
|
||||
},
|
||||
}, mockLogger);
|
||||
assert.deepEqual(pack.toJSON().settings, {
|
||||
"startup": {},
|
||||
"runtime-global": {},
|
||||
"runtime-per-user": {},
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe(".fromModPackString()", function() {
|
||||
it("should handle malformed strings", function() {
|
||||
assert.throws(
|
||||
|
||||
Reference in new issue
Block a user