diff options
| author | Danilo M. <danix@danix.xyz> | 2026-10-16 11:01:26 +0200 |
|---|---|---|
| committer | Danilo M. <danix@danix.xyz> | 2026-10-16 11:01:26 +0200 |
| commit | 807d454d53f377a6bed753a50c1a5952524db429 (patch) | |
| tree | e5b7e9596254aee130a8f3d7b8ac4551f13365f3 /docs/superpowers/specs | |
| parent | 33a20ad0b33467c6980399bb618485b74d66dc04 (diff) | |
| download | quickshell-807d454d53f377a6bed753a50c1a5952524db429.tar.gz quickshell-807d454d53f377a6bed753a50c1a5952524db429.zip | |
docs(git): design for the global git config page
A drawer page, reached from the user page, listing every global git key and
editing, adding and removing values through git config itself, so the file
keeps its comments and quoting. --fixed-value lets each write target one
value of a multi-valued key.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Diffstat (limited to 'docs/superpowers/specs')
| -rw-r--r-- | docs/superpowers/specs/2026-10-16-git-config-design.md | 83 |
1 files changed, 83 insertions, 0 deletions
diff --git a/docs/superpowers/specs/2026-10-16-git-config-design.md b/docs/superpowers/specs/2026-10-16-git-config-design.md new file mode 100644 index 0000000..e9975fc --- /dev/null +++ b/docs/superpowers/specs/2026-10-16-git-config-design.md @@ -0,0 +1,83 @@ +# Global git config in the drawer + +## Goal + +Review and edit the user's global git configuration from the drawer: every +key, not only the three the user page derives. Per-repository, system and +`[include]`d configs are out of scope. + +## Measured + +- The global config is `~/.gitconfig`: 59 keys over 20 sections, one of + them (`versionsort.prereleasesuffix`) set six times. `~/.config/git/` + holds no `config`, so there is one global file. +- git 2.55: `--fixed-value` (2.30+) makes a value argument a literal rather + than a regex, so a write can target one value of a multi-valued key. +- `git config --global -z --list` separates entries with NUL and key from + value with the first newline, so values holding `=` or newlines survive. +- The editor is `/usr/bin/sublime_text`; there is no `subl` on PATH. + +## Approach + +All reads and writes go through `git config`. git keeps the file's comments, +layout and quoting; the shell never parses or writes `~/.gitconfig` itself. +Rewriting the file from QML was rejected: it loses comments and has to +reimplement git's quoting. + +## Module: `desktop/modules/git/` + +- `GitModule.qml`: name `git`, label `Git config`, `tiled: false`, a page, + and `up: "user"` (see Drawer below). +- `gitcfg`: bash helper, the only thing that touches git. Every write puts + `--` before the key, so a key or value starting with `-` is an argument, + not an option (checked against git 2.55 with `--add`, `--replace-all` and + `--unset`). + - `list`: `git config --global -z --list`, printed as is. + - `set <key> <old> <new>`: `git config --global --fixed-value + --replace-all <key> <new> <old>`. Only the value equal to `<old>` + changes, even on a multi-valued key. + - `add <key> <value>`: `git config --global --add <key> <value>`. + - `unset <key> <value>`: `git config --global --fixed-value --unset <key> + <value>`. Removes only that value. + - git's stderr passes through and its exit status is the helper's. +- `Git.js` (`.pragma library`): `parse(text)` turns the `-z` output into + `[{section, key, value}]` in file order, `section` being everything before + the last dot (`color.branch.remote` is section `color.branch`). Tested by + `test_git.js` under node, as `User.js` is. +- `GitPage.qml`: + - Top: an "Edit in editor" button running `sublime_text ~/.gitconfig`, + detached, so the drawer can close while it stays open. + - The keys grouped under their section, one row per value: the key name, + then the value as an inline text field. Enter saves through `set`, + Escape restores the old value; Escape on an unfocused page still steps + back as on every page. + - A remove button per row, through `unset`. No confirmation: a removed + value is re-added from the Add row. + - An Add row at the bottom: `section.key` and value, through `add`. + - After every write, and when the page opens, the list is read again from + git. A failed write shows git's stderr under the row it came from and + the list is reloaded, so the field shows what git really holds. + +## User page link + +The user page's Git section gains a "More git settings" button that opens +the git page. + +## Drawer + +- `Page.qml` gains a `go(name)` signal; the drawer connects it to + `show(name)`, so a page can open another module's page. +- `Module.qml` gains `property string up: ""`: the page `back()` returns to. + Empty means the grid, today's behaviour. `back()` sets `page` to + `current.up`, and the page's back arrow calls `back()` rather than + clearing `page` itself, so the arrow, Escape and the mouse back button + agree. + +## Checks + +- `test-gitcfg.sh` runs `gitcfg` against a throwaway `GIT_CONFIG_GLOBAL` in + a temp directory: `list` of a multi-valued key, `set` of one value of + three, `unset` of one value of three, `add`, a value containing `=`, and a + value starting with `-`. +- `node desktop/modules/git/test_git.js` for `parse`. +- The page is checked by the user, by hand. |
