aboutsummaryrefslogtreecommitdiffstats
path: root/desktop/modules/qtmaildir/test_ini.js
blob: 2e7fb03e2646ed5e80815f8eb97c305ac533bf33 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
// Copyright (C) 2026 Danilo M. <danix@danix.xyz>
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 2 as
// published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.

// Run: node desktop/modules/qtmaildir/test_ini.js
// Ini.js is a QML library, so its .pragma line is stripped before node
// evaluates it.

const fs = require("fs");
const assert = require("assert");

const src = fs.readFileSync(__dirname + "/Ini.js", "utf8")
    .replace(/^\.pragma library$/m, "");
const I = new Function(src + "\nreturn { sections, entries, get, set, remove, addSection, removeSection };")();

const file = [
    "[general]",
    "; startup_query = Unread",
    "toolbar_icon_size = 32",
    "date_format = dd/MM/yyyy hh:mm",
    "",
    "[account.gmail]",
    "maildir = gmail        ; relative to notmuch's mail root",
    "drafts = [Gmail]/Bozze",
    'send_command = "/usr/bin/msmtp -a x ; y"',
    "label = GM",
    "",
    "[tagcolors]",
    "shopping/amazon = #ff9900",
    "",
].join("\n");

// A value holding brackets is not a section header (AGENTS.md: three of
// five accounts once lost their label to exactly that).
assert.deepStrictEqual(I.sections(file), ["general", "account.gmail", "tagcolors"]);
assert.strictEqual(I.get(file, "account.gmail", "drafts"), "[Gmail]/Bozze");
assert.strictEqual(I.get(file, "account.gmail", "label"), "GM");
// An inline comment is not part of the value; a quoted ; is.
assert.strictEqual(I.get(file, "account.gmail", "maildir"), "gmail");
assert.strictEqual(I.get(file, "account.gmail", "send_command"), "/usr/bin/msmtp -a x ; y");
// A commented key is unset.
assert.strictEqual(I.get(file, "general", "startup_query"), undefined);
assert.deepStrictEqual(I.entries(file, "tagcolors"), [{ key: "shopping/amazon", value: "#ff9900" }]);

// Replacing keeps the inline comment and every other line.
let t = I.set(file, "account.gmail", "maildir", "gm2");
assert.strictEqual(t.split("\n")[6], "maildir = gm2        ; relative to notmuch's mail root");
assert.strictEqual(t.split("\n").length, file.split("\n").length);
// Setting a commented key activates its line.
t = I.set(file, "general", "startup_query", "Inbox");
assert.strictEqual(t.split("\n")[1], "startup_query = Inbox");
// Unsetting comments a key out in place.
t = I.set(file, "general", "toolbar_icon_size", null);
assert.strictEqual(t.split("\n")[2], "; toolbar_icon_size = 32");
assert.strictEqual(I.get(t, "general", "toolbar_icon_size"), undefined);
// A new key lands at the end of its section, before the blank line.
t = I.set(file, "general", "language", "it");
assert.strictEqual(t.split("\n")[4], "language = it");
assert.strictEqual(t.split("\n")[5], "");
assert.strictEqual(I.get(t, "general", "language"), "it");
// A value with a ; or a quote is quoted, and reads back the same.
t = I.set(file, "account.gmail", "send_command", 'a "b" ; c');
assert.strictEqual(I.get(t, "account.gmail", "send_command"), 'a "b" ; c');
// A missing section is appended.
t = I.set(file, "compose", "send_html", "false");
assert.ok(t.endsWith("\n[compose]\nsend_html = false\n"), JSON.stringify(t));
assert.strictEqual(I.get(t, "compose", "send_html"), "false");
// The same key in another section is untouched.
t = I.set("[a]\nx = 1\n\n[b]\nx = 2\n", "b", "x", "3");
assert.strictEqual(t, "[a]\nx = 1\n\n[b]\nx = 3\n");

// remove deletes the line, where set(null) would comment it out.
t = I.remove(file, "tagcolors", "shopping/amazon");
assert.deepStrictEqual(I.entries(t, "tagcolors"), []);
assert.ok(!t.includes("amazon"));
assert.strictEqual(I.remove(file, "tagcolors", "nope"), file);

// Whole sections, for accounts.
t = I.addSection(file, "account.new", [["maildir", "new"], ["trash", "Trash"]]);
assert.deepStrictEqual(I.sections(t), ["general", "account.gmail", "tagcolors", "account.new"]);
assert.strictEqual(I.get(t, "account.new", "trash"), "Trash");
t = I.removeSection(file, "account.gmail");
assert.deepStrictEqual(I.sections(t), ["general", "tagcolors"]);
assert.strictEqual(t, "[general]\n; startup_query = Unread\ntoolbar_icon_size = 32\ndate_format = dd/MM/yyyy hh:mm\n\n[tagcolors]\nshopping/amazon = #ff9900\n");

console.log("test_ini: ok");