mirror of
https://github.com/clusterio/clusterio.git
synced 2026-11-11 15:04:52 +09:00
Fix metrics broken by comma and equal in labels
The logic for turning a key back into the labelles that defined it would not account for the labels values possibly including a comma or equal sign, which in turn broke the logic for handling these metrics. Fix by properly parsing the keys.
This commit is contained in:
1 parent
b0595a6502
commit
f6eb55163f
2 files changed
+30
-8
No files matched your search
@@ -272,18 +272,27 @@ function labelsToKey(labels: LabelValues, metricLabels: string[]) {
|
||||
function keyToLabels(key: string) {
|
||||
let labels = new Map<string, string>();
|
||||
|
||||
if (key !== "") {
|
||||
for (let pair of key.split(",")) {
|
||||
let [name, value] = pair.split("=", 2);
|
||||
if (!name || value === undefined) {
|
||||
continue;
|
||||
let pos = 0;
|
||||
let matchLabel = /([^=]+)="(([^\\"]|\\["n\\])+)"/y;
|
||||
while (pos < key.length) {
|
||||
if (pos !== 0) {
|
||||
if (key[pos] !== ",") {
|
||||
throw Error(`Expected , at pos ${pos} in "${key}"`);
|
||||
}
|
||||
pos += 1;
|
||||
}
|
||||
matchLabel.lastIndex = pos;
|
||||
const match = matchLabel.exec(key);
|
||||
if (match) {
|
||||
let [, name, value] = match;
|
||||
labels.set(name, value
|
||||
.slice(1, -1)
|
||||
.replace(/\\"/g, "\"")
|
||||
.replace(/\\n/g, "\n")
|
||||
.replace(/\\\\/g, "\\")
|
||||
);
|
||||
pos += match[0].length;
|
||||
} else {
|
||||
throw new Error(`Failed to parse label at pos ${pos} in "${key}"`);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+15
-2
@@ -651,8 +651,21 @@ describe("lib/prometheus", function() {
|
||||
let gauge = new prometheus.Gauge(
|
||||
"test", "Help", { register: false, labels: ["a", "b"] }
|
||||
);
|
||||
gauge.labels('x\\\\\n\"\"\n\\', "2");
|
||||
gauge.removeAll({ a: 'x\\\\\n\"\"\n\\' });
|
||||
|
||||
let labelValue = "";
|
||||
for (let i = 0; i < 128; i++) {
|
||||
const char = String.fromCodePoint(i);
|
||||
if (!/[1-9B-Zb-z]/.test(char)) { // exclude boring characters
|
||||
labelValue += char;
|
||||
}
|
||||
}
|
||||
labelValue += "©💣";
|
||||
|
||||
gauge.labels(labelValue, "2");
|
||||
gauge.removeAll({ a: labelValue });
|
||||
assert(gauge._values.size === 0, "Matching labels remained");
|
||||
gauge.labels("1", labelValue);
|
||||
gauge.removeAll({ a: "1" });
|
||||
assert(gauge._values.size === 0, "Matching labels remained");
|
||||
});
|
||||
});
|
||||
|
||||
Reference in new issue
Block a user