OXYGENHUB

README as walkthroughs by task with a settings table, dated changelog entries, and a test that the docs keep up with the manifest cdcffe39dd9f

closes #4
Author
Andy McCall @andymccall <[email protected]>
When
· 2026-09-28 16:15 UTC
Signature
✔ signed by Andy McCall
Hash
cdcffe39dd9fb394683e779baccc1bbdf7575e1bf48e44325e0e3bc4dbd55611
Depends on
1f7fc1e3ae4a 44bfd5adfc9a 9020cf612749 9627171e23e2 b4626290e660 bed495a96408 f6bda77ecb9f
Depended on by
dac6876e4d08 013fefef11e3 196392053c9f f532c4266f21
In bookmarks
main
In tags
v0.16.0 v0.16.1 v0.17.0 v0.17.1 v0.18.0
Edits
13 atoms, 1 tree operation, 3 files

Browse the tree at this change

added test/docs.test.mjs +26 −0
1 +
// The documentation keeps up with the manifest: every setting is described
2 +
// in the README, and the CHANGELOG has a dated entry for this version.
3 +
4 +
import { test } from "node:test";
5 +
import assert from "node:assert/strict";
6 +
import { readFileSync } from "node:fs";
7 +
8 +
const pkg = JSON.parse(readFileSync(new URL("../package.json", import.meta.url), "utf8"));
9 +
const readme = readFileSync(new URL("../README.md", import.meta.url), "utf8");
10 +
const changelog = readFileSync(new URL("../CHANGELOG.md", import.meta.url), "utf8");
11 +
12 +
test("every setting is documented in the README's Settings table", () => {
13 +
  const cfg = pkg.contributes.configuration;
14 +
  const props = (Array.isArray(cfg) ? cfg : [cfg]).flatMap((c) => Object.keys(c.properties ?? {}));
15 +
  assert.ok(props.length > 0);
16 +
  const table = readme.slice(readme.indexOf("## Settings"));
17 +
  const missing = props.filter((p) => !table.includes("| `" + p + "` |"));
18 +
  assert.deepEqual(missing, [], "settings missing from the README");
19 +
});
20 +
21 +
test("the CHANGELOG's newest entry is this version, and every entry is dated", () => {
22 +
  const headings = [...changelog.matchAll(/^## (.+)$/gm)].map((m) => m[1]);
23 +
  assert.match(headings[0], new RegExp("^" + pkg.version.replace(/\./g, "\\.") + " \\(\\d{4}-\\d{2}-\\d{2}\\)$"));
24 +
  const undated = headings.filter((h) => !/^\d+\.\d+\.\d+ \(\d{4}-\d{2}-\d{2}\)$/.test(h));
25 +
  assert.deepEqual(undated, [], "entries without a version and date");
26 +
});
modified CHANGELOG.md +5 −5
1 1
# Changelog
2 2
3 -
## 0.10.0
3 +
## 0.10.0 (2026-09-28)
4 4
5 5
- **Line links:** right-click a line number, or inside the editor, for Open on Remote, Copy Remote Link and Copy Permalink.
6 6
  - The link covers the selection, or the line you clicked.
…
1 unchanged lines
8 8
  - If the file has uncommitted edits, a note says the lines may not match. Remote links also mention unpushed changes.
9 9
- Open on Remote in the editor title menu now includes the selected lines, not just the cursor line.
10 10
11 -
## 0.9.0
11 +
## 0.9.0 (2026-09-28)
12 12
13 13
- **Amend mode** (the pencil in the Source Control title bar): Ctrl+Enter amends the last change, and the box starts from its message.
14 14
- **Previous Commit Messages…** puts a recent message back in the box. Messages are remembered per repository as you commit.
15 15
- **Signing indicator**: the box says whether the next commit will be signed, sealed at push, or unsigned (no identity, or its key missing).
16 16
- **Conflict marker warning**: committing or amending files that still hold conflict markers (Oxygen's or Git's) asks first, and can open the first one.
17 17
18 -
## 0.8.0
18 +
## 0.8.0 (2026-09-28)
19 19
20 20
- The History graph rewrites history:
21 21
  - Split a head: the files you pick become a separate first change.
…
1 unchanged lines
23 23
  - Rebase a change onto a bookmark, change or tag.
24 24
- Use them from the change picker or by right-clicking a row. Each asks first, and afterwards offers Undo.
25 25
26 -
## 0.7.1
26 +
## 0.7.1 (2026-09-28)
27 27
28 28
- Messages write the forge's name as OxygenHub.
29 29
30 -
## 0.7.0
30 +
## 0.7.0 (2026-09-28)
31 31
32 32
- An exported API for other extensions (`vscode.extensions.getExtension("...").exports`): repositories with status, bookmarks, remotes and `json(args)`, change events, and `registerRemoteProvider` so a forge extension such as OxygenHub can say which remotes it understands and where things live on the web.
33 33
- "Open on Remote" and "Open Change on Remote" commands, shown once a provider is registered.
…
36 unchanged lines
modified README.md +103 −41
1 1
# Oxygen for Visual Studio Code
2 2
3 -
Source control integration for Oxygen (`oxy`) repositories: a
4 -
Source Control view with changes and conflicts, diffs against the working
5 -
copy's base, quick-diff gutters, explorer decorations, a status bar item, and
6 -
commit from the input box. The full design, milestone by milestone, is in
7 -
`docs/spec.md` in this repository.
3 +
Source control for Oxygen (`oxy`) repositories. It adds:
4 +
5 +
- a Source Control view with changes and conflicts
6 +
- diffs against the working copy's base and quick-diff gutters
7 +
- decorations in the explorer and a status bar item
8 +
- a history graph
9 +
- blame, bisect and trust views
10 +
- links to your forge
11 +
12 +
The design, milestone by milestone, is in `docs/spec.md` in this repository.
8 13
9 14
## Requirements
10 15
11 16
- Visual Studio Code 1.137 or later.
12 -
- `oxy` 0.1 or later on your PATH, at `~/.local/bin/oxy`, or named in the
13 -
  `oxygen.path` setting. The extension drives `oxy --json` and never reads
14 -
  `.oxy/` itself.
17 +
- `oxy` 0.1 or later. The extension looks for it in the `oxygen.path` setting first, then on your PATH, then at `~/.local/bin/oxy`.
18 +
- The extension drives `oxy --json` and never reads `.oxy/` itself, so anything it does, you can also do in a terminal.
19 +
20 +
## Getting started
21 +
22 +
1. Open a folder that is an Oxygen repository, or run **Oxygen: Initialize Repository** in a plain folder, or **Oxygen: Clone Repository** to start from a URL.
23 +
2. The Source Control view shows an **Oxygen** provider. The status bar shows the bookmark, the working copy and the state. Click it to switch, create, merge or delete bookmarks.
24 +
3. If you have no signing identity yet, the commit box says "unsigned: no identity". Run `oxy identity create` once in a terminal.
25 +
26 +
## Walkthroughs
27 +
28 +
### Commit
29 +
30 +
1. Edit files. They appear under **Changes**, with gutters in the editor and letters in the explorer.
31 +
2. Click a file to see its diff against the working copy's base.
32 +
3. Type a message in the commit box and press `Ctrl+Enter`. The box also tells you whether the change will be signed, sealed at push, or unsigned.
33 +
34 +
Variations:
35 +
36 +
- **Only some files:** right-click them and choose **Commit Selected**.
37 +
- **Only some hunks:** use **Commit Hunks…** from the view's menu. Anything a chosen hunk needs comes along with it.
38 +
- **Fix up the last change:** click the pencil in the view's title bar for **amend mode**. `Ctrl+Enter` then amends, and the box starts from the last change's message. Click the cross to leave amend mode.
39 +
- **Reuse a message:** **Previous Commit Messages…** puts a recent one back in the box.
40 +
41 +
If a file still holds conflict markers, whether Oxygen's or Git's, committing asks first and can open that file for you.
42 +
43 +
### Resolve a conflict
44 +
45 +
Conflicts are ordinary state in Oxygen. You can commit, push and pull them, and resolve them whenever you like.
46 +
47 +
1. Conflicted files appear under **Conflicts**.
48 +
2. In the editor, CodeLens actions above each marker accept one side, all sides, or a deletion.
49 +
3. For a conflict in the tree, such as two files given the same name, **Keep This Candidate** on the candidate you want.
50 +
4. Choose **Mark Resolved**, then commit. The commit box reads "Describe the resolution".
51 +
52 +
### Sync with a remote
53 +
54 +
- The status bar's sync counter shows changes to pull and to push. Click it to **Sync**.
55 +
- **Fetch**, **Pull**, **Push** and **Push Bookmark** are in the view's `…` menu.
56 +
- Pushing asks first unless `oxygen.confirmSync` is off.
57 +
58 +
### Read and rewrite history
59 +
60 +
1. **Show History** draws the bookmark's changes as a graph of dependencies. Independent changes sit side by side, and there are no merge nodes.
61 +
2. Click a change to diff it, check out its state, describe it, tag it or abandon it.
62 +
3. The same menu, or right-clicking a row, rewrites history:
63 +
   - **Split** a head: the files you choose become a separate first change.
64 +
   - **Squash** a change into one of its dependencies.
65 +
   - **Rebase** a change onto a bookmark, change or tag.
66 +
67 +
Every rewrite asks first and then offers **Undo**. The **Oxygen Operations** view can undo back to any point.
68 +
69 +
For one file:
70 +
71 +
- **File History** lists the changes that touched it, with diffs between versions.
72 +
- **Toggle Inline Blame** shows each line's change, author and age.
73 +
74 +
### Find a regression
75 +
76 +
The **Oxygen Bisect** view starts a bisection. Mark changes good, bad or skip, or give it a command to run. It shows the first bad change when it finds it.
77 +
78 +
### Link to lines on your forge
79 +
80 +
With a forge extension such as OxygenHub installed, right-click a line number, or inside the editor:
81 +
82 +
- **Open on Remote** opens the file at those lines.
83 +
- **Copy Remote Link** copies a link that follows the bookmark.
84 +
- **Copy Permalink** copies a link to the bookmark's current state, so it keeps showing these lines after later changes.
85 +
86 +
The link covers the line you clicked, or your selection. If the file has uncommitted edits, a note says the lines may not match the remote.
87 +
88 +
### Check trust
89 +
90 +
The **Oxygen Trust** view shows the repository's trust policy and each change's signature. **Verify Signatures** checks them all.
91 +
92 +
## Settings
93 +
94 +
| Setting | Default | What it does |
95 +
|---|---|---|
96 +
| `oxygen.path` | empty | Path to the `oxy` binary. Empty means `oxy` on PATH, then `~/.local/bin/oxy`. |
97 +
| `oxygen.autoRefresh` | `true` | Refresh the Source Control view when files in the workspace change. Off means refresh by hand. |
98 +
| `oxygen.decorations.enabled` | `true` | Status letters and colours in the explorer and on editor tabs. |
99 +
| `oxygen.inlineBlame` | `false` | Show each line's introducing change, author and age at the end of the line. Also toggled from the editor context menu. |
100 +
| `oxygen.confirmSync` | `true` | Ask before pushing. |
101 +
| `oxygen.showSnapshotOperations` | `false` | List snapshot operations in the Oxygen Operations view as well as commits, pulls and the rest. |
102 +
| `oxygen.statusBar.enabled` | `true` | Show the bookmark, working copy and state in the status bar. |
103 +
104 +
## For other extensions
105 +
106 +
The extension exports an API (`OxygenAPI`, version 1) with the repositories, their status and bookmarks, and a way to register a remote provider. It is what lets OxygenHub, or any forge, answer **Open on Remote**. See `src/api.ts`.
15 107
16 108
## Building
17 109
…
1 unchanged lines
19 111
npm install
20 112
npm run check          # typecheck, bundle, and test against the oxy binary
21 113
npm run package        # oxygen-vscode-<version>.vsix
22 -
code --install-extension oxygen-vscode-0.1.0.vsix
114 +
code --install-extension oxygen-vscode-<version>.vsix
23 115
```
24 -
25 -
`npm run watch` rebuilds on change; press F5 in VS Code to launch an
26 -
Extension Development Host with the bundle.
27 116
28 -
## What it does
29 -
30 -
- **Source Control view**: Changes, Conflicts and Subrepos groups; open
31 -
  changes as a diff against the working copy's base; discard, commit
32 -
  selected paths, commit chosen hunks, amend; `Ctrl+Enter` commits.
33 -
- **Editor**: quick-diff gutters, explorer and tab decorations, inline blame
34 -
  (toggle from the context menu), file history with diffs between versions,
35 -
  CodeLens actions over conflict markers (accept a side, all sides, or a
36 -
  deletion), keep-this-candidate for tree conflicts, Mark Resolved.
37 -
- **Status bar**: bookmark, working copy and state; click to switch, create,
38 -
  merge or delete bookmarks; a sync counter with Sync, Fetch, Pull, Push and
39 -
  Push Bookmark.
40 -
- **Commit box**: amend mode, previous messages, a note of whether the next
41 -
  commit is signed, sealed at push or unsigned, and a warning before
42 -
  committing leftover conflict markers.
43 -
- **Links**: Open on Remote, Copy Remote Link and Copy Permalink from the
44 -
  line-number gutter and the editor context menu, for a line or the
45 -
  selection; permalinks pin the bookmark's current state.
46 -
- **Views**: Oxygen Operations (undo to any point), Oxygen Bisect
47 -
  (start, good, bad, skip, run, reset), Oxygen Trust (policy, signatures),
48 -
  and a History graph with per-change actions (diff, check out, describe,
49 -
  tag, abandon, and split, squash and rebase from the picker or by
50 -
  right-clicking a row, each confirmed and undoable).
51 -
- **Commands**: Show History, File History, Tags, Create Tag, Add Workspace,
52 -
  Update Subrepos, Verify Signatures, Clone Repository, Initialize Repository,
53 -
  Show Output.
117 +
`npm run watch` rebuilds on change. Press F5 in VS Code to launch an Extension Development Host with the bundle. The tests run the real `oxy`; set `OXY_BIN` to choose which one.
54 118
55 119
## Status
56 120
57 -
Milestones 0.1 to 0.6 of the spec are implemented (see CHANGELOG.md). Left
58 -
for 1.0: tests on macOS and Windows, a Marketplace publisher, and the open
59 -
questions in the spec.
121 +
The spec's milestones 0.1 to 0.6 are done, and so are the additions listed in CHANGELOG.md. Left for 1.0: tests on macOS and Windows, a Marketplace publisher, and the spec's open questions.
60 122
61 123
## Licence
62 124
…
1 unchanged lines