* Copyright (C) 2022 SUSE LLC
* SPDX-License-Identifier: LGPL-2.1-or-later
*/
import { ConfigFile } from './config-client.js';
* and monitor it for changes
*/
export class ConfigFileSUSE extends ConfigFile {
* if a line has a valid key=value format, use the key in _internal structure
* and also store original line, line index, value and optional line suffix / comment
* if value was quoted it will be stripped of quotes in `value` and `quoted` flag will
* be used when writing the file to keep original formatting
* e.g. for line 'someKey="foo" # comment'
* outputObject._internal["someKey"] = {
* index: 0,
* value: "foo",
* quoted: true,
* origLine: 'someKey="foo" # comment',
* suffix: "# comment"
* }
* skipNotify: Don't notify about changes, e.g.to avoid multiple updates when writing a file
*/
_parseText(rawContent, skipNotify = false) {
this._dataAvailableResolve();
if (!rawContent) {
this._originalSettings = null;
this.settings = null;
if (!skipNotify)
this.dispatchEvent("kdumpConfigChanged", this.settings);
return;
}
if (rawContent === this._rawContent)
return;
this._rawContent = rawContent;
this.settings = {
_internal: {},
targets: {},
compression: { enabled: false, allowed: true },
nfs_supports_directory: false,
};
this._lines = rawContent.split(/\r?\n/);
this._lines.forEach((line, index) => {
const trimmed = line.trim();
if (trimmed.indexOf("#") === 0 || trimmed.length === 0)
return;
let parts = trimmed.match(/^([A-Z_]+)\s*=\s*(.*)$/);
if (parts === null) {
console.warn("Malformed kdump config line:", trimmed, "in", this.filename);
return;
}
const key = parts[1];
let value = parts[2];
let quoted = false;
if (value.startsWith('"')) {
quoted = true;
parts = value.match(/^"([^"]*)"\s*(.*)$/);
if (parts === null) {
console.warn("Incorrectly quoted value in kdump config line:", line, "in", this.filename);
return;
}
} else {
parts = value.match(/^([^#]+?)\s*(#.*)?$/);
if (parts === null)
parts = ["", ""];
}
value = parts[1];
const suffix = (parts[2] || "").trim();
this.settings._internal[key] = {
index,
value,
origLine: line,
quoted,
suffix
};
});
this._originalSettings = { };
Object.keys(this.settings._internal).forEach((key) => {
this._originalSettings[key] = { ...this.settings._internal[key] };
});
this._extractSettings();
if (!skipNotify)
this.dispatchEvent("kdumpConfigChanged", this.settings);
}
*/
_extractSettings() {
if ("KDUMP_SAVEDIR" in this.settings._internal && this.settings._internal.KDUMP_SAVEDIR.value) {
let savedir = this.settings._internal.KDUMP_SAVEDIR.value;
if (savedir.startsWith("/"))
savedir = "file://" + savedir;
const parts = savedir.match(/^(.*):\/\/([^/]*)(\/.*)$/);
if (parts === null) {
console.warn("Malformed KDUMP_SAVEDIR entry:", savedir, "in", this.filename);
return;
}
const [, scheme, server, path] = parts;
if (scheme === "file") {
this.settings.targets.local = {
type: "local",
path,
};
} else if (scheme === "nfs") {
this.settings.targets.nfs = {
type: scheme,
export: path,
server,
};
} else {
this.settings.targets[scheme] = {
type: scheme,
path,
server,
};
if ("KDUMP_SSH_IDENTITY" in this.settings._internal) {
this.settings.targets[scheme].sshkey =
this.settings._internal.KDUMP_SSH_IDENTITY.value;
}
}
}
if (Object.keys(this.settings.targets).length === 0)
this.settings.targets.local = { type: "local" };
this.settings.compression.enabled = (
!("KDUMP_DUMPFORMAT" in this.settings._internal) ||
this.settings._internal.KDUMP_DUMPFORMAT.value === "compressed"
);
}
* make sure setting exists if value is not empty
* don't delete existing settings
*/
_updateSetting(settings, key, value) {
if (key in settings._internal) {
settings._internal[key].value = value;
} else {
if (value)
settings._internal[key] = { value };
}
}
* this.settings = current state from file
* settings = in-memory state from UI
*/
_persistSettings(settings) {
if (Object.keys(settings.targets).length > 0) {
const target = Object.values(settings.targets)[0];
if ("sshkey" in target)
this._updateSetting(settings, "KDUMP_SSH_IDENTITY", target.sshkey);
let savedir;
let path = target.path || "/var/crash";
if (path && !path.startsWith("/"))
path = "/" + path;
if (target.type === "local") {
savedir = "file://" + path;
} else if (target.type === "nfs") {
if (!target.path)
path = "";
let exprt = target.export;
if (!exprt.startsWith("/"))
exprt = "/" + exprt;
savedir = "nfs://" + target.server + exprt + path;
} else {
savedir = target.type + "://" + target.server + path;
}
this._updateSetting(settings, "KDUMP_SAVEDIR", savedir);
}
if (this.settings.compression.enabled !== settings.compression.enabled) {
if (settings.compression.enabled) {
this._updateSetting(settings, "KDUMP_DUMPFORMAT", "compressed");
} else {
this._updateSetting(settings, "KDUMP_DUMPFORMAT", "ELF");
}
}
return settings;
}
*/
generateConfig(settings) {
settings = this._persistSettings(settings);
const lines = this._lines.slice(0);
Object.keys(settings._internal).forEach((key) => {
const entry = settings._internal[key];
let value = entry.value !== undefined ? entry.value : "";
if (entry.quoted || value === "" || value.includes(" "))
value = '"' + value + '"';
let line = key + "=" + value;
if (entry.suffix)
line = line + " " + entry.suffix;
if (!(key in this._originalSettings)) {
lines.push(line);
return;
}
const origEntry = this._originalSettings[key];
lines[origEntry.index] = line;
});
if (lines[lines.length - 1] !== "")
lines.push("");
return lines.join("\n");
}
}