File links keep line ranges and readable state-address permalinks; API types brought up to date; 0.6.2 426ddc5039b5
refs andymccall/oxygen-vscode#3
- Author
- Andy McCall @andymccall <[email protected]>
- When
- · 2026-09-28 16:12 UTC
- Signature
- ✔ signed by Andy McCall
- Hash
426ddc5039b50be714335419d8b8f1416740e27644c365b0a26e714d186bb46c
- Depends on
- 092b8bf9f2ac 95f69b4a3ac2 b2dd082c57e4 f0b06deac4b9
- Depended on by
- 991516a107fa d21a85954a34 263de209e5ba 5888949525ec e04950748142
- In bookmarks
- main
- In tags
- v0.10.0 v0.10.1 v0.10.2 v0.11.0 v0.11.1 v0.11.2 v0.13.0
- Edits
- 11 atoms, 0 tree operations, 6 files
Browse the tree at this change
modified
CHANGELOG.md
+5 −0
| 1 |
1 |
|
# Changelog |
| 2 |
2 |
|
|
|
3 |
+ |
## 0.6.2 |
|
4 |
+ |
|
|
5 |
+ |
- File links keep line ranges (`#L10-L20`) and permalinks to a state (`hash+hash`) readable, for Oxygen's Copy Permalink. |
|
6 |
+ |
- API types match OxygenHub 0.1 with issue editing, labels and projects. |
|
7 |
+ |
|
| 3 |
8 |
|
## 0.6.1 |
| 4 |
9 |
|
|
| 5 |
10 |
|
- The name is written OxygenHub throughout. |
|
|
… |
48 unchanged lines |
modified
package.json
+1 −1
|
|
… |
1 unchanged lines |
| 2 |
2 |
|
"name": "oxygenhub-vscode", |
| 3 |
3 |
|
"displayName": "OxygenHub", |
| 4 |
4 |
|
"description": "Proposals, reviews, issues and checks from an OxygenHub, in the editor. Builds on the Oxygen extension.", |
| 5 |
|
- |
"version": "0.6.1", |
|
5 |
+ |
"version": "0.6.2", |
| 6 |
6 |
|
"publisher": "andymccall", |
| 7 |
7 |
|
"license": "MIT OR Apache-2.0", |
| 8 |
8 |
|
"icon": "assets/images/oxygenhub.png", |
|
|
… |
366 unchanged lines |
modified
src/hub.ts
+2 −1
|
|
… |
203 unchanged lines |
| 204 |
204 |
|
case "file": { |
| 205 |
205 |
|
const end = typeof target.endLine === "number" && target.endLine !== target.line ? `-L${target.endLine}` : ""; |
| 206 |
206 |
|
const line = typeof target.line === "number" ? `#L${target.line}${end}` : ""; |
| 207 |
|
- |
return `${repo}/file/${encodeURIComponent(String(target.reference))}/${String(target.path)}${line}`; |
|
207 |
+ |
// A state address (`hash+hash`) keeps its `+`, as the hub writes permalinks. |
|
208 |
+ |
return `${repo}/file/${encodeURIComponent(String(target.reference)).replace(/%2B/g, "+")}/${String(target.path)}${line}`; |
| 208 |
209 |
|
} |
| 209 |
210 |
|
case "proposals": |
| 210 |
211 |
|
return `${repo}/proposals`; |
|
|
… |
79 unchanged lines |
modified
src/hubapi.d.ts
+70 −0
|
|
… |
334 unchanged lines |
| 335 |
335 |
|
}; |
| 336 |
336 |
|
|
| 337 |
337 |
|
export type NewIssue = { |
|
338 |
+ |
assignees?: string[]; |
| 338 |
339 |
|
body?: string; |
|
340 |
+ |
labels?: string[]; |
|
341 |
+ |
milestone?: string | null; |
|
342 |
+ |
title: string; |
|
343 |
+ |
}; |
|
344 |
+ |
|
|
345 |
+ |
export type IssueEdit = { |
|
346 |
+ |
assignees?: string[] | null; |
|
347 |
+ |
body?: string | null; |
|
348 |
+ |
labels?: string[] | null; |
|
349 |
+ |
milestone?: string | null; |
|
350 |
+ |
title?: string | null; |
|
351 |
+ |
}; |
|
352 |
+ |
|
|
353 |
+ |
export type NewLabel = { |
|
354 |
+ |
colour?: string | null; |
|
355 |
+ |
description?: string; |
|
356 |
+ |
name: string; |
|
357 |
+ |
}; |
|
358 |
+ |
|
|
359 |
+ |
export type Project = { |
|
360 |
+ |
closed: boolean; |
|
361 |
+ |
description: string; |
|
362 |
+ |
number: number; |
|
363 |
+ |
owner: string; |
|
364 |
+ |
public: boolean; |
|
365 |
+ |
title: string; |
|
366 |
+ |
updated_ms: number; |
|
367 |
+ |
url: string; |
|
368 |
+ |
}; |
|
369 |
+ |
|
|
370 |
+ |
export type ProjectCard = { |
|
371 |
+ |
id: number; |
|
372 |
+ |
kind: string; |
|
373 |
+ |
reference: string; |
|
374 |
+ |
state: string; |
|
375 |
+ |
title: string; |
|
376 |
+ |
}; |
|
377 |
+ |
|
|
378 |
+ |
export type ProjectColumn = { |
|
379 |
+ |
cards: ProjectCard[]; |
|
380 |
+ |
id: number; |
|
381 |
+ |
name: string; |
|
382 |
+ |
}; |
|
383 |
+ |
|
|
384 |
+ |
export type Board = { |
|
385 |
+ |
columns: ProjectColumn[]; |
|
386 |
+ |
project: Project; |
|
387 |
+ |
}; |
|
388 |
+ |
|
|
389 |
+ |
export type NewProject = { |
|
390 |
+ |
description?: string; |
|
391 |
+ |
private?: boolean; |
| 339 |
392 |
|
title: string; |
|
393 |
+ |
}; |
|
394 |
+ |
|
|
395 |
+ |
export type ProjectEdit = { |
|
396 |
+ |
closed?: boolean | null; |
|
397 |
+ |
description?: string | null; |
|
398 |
+ |
private?: boolean | null; |
|
399 |
+ |
title?: string | null; |
|
400 |
+ |
}; |
|
401 |
+ |
|
|
402 |
+ |
export type NewCard = { |
|
403 |
+ |
column?: string | null; |
|
404 |
+ |
note?: string; |
|
405 |
+ |
reference?: string; |
|
406 |
+ |
}; |
|
407 |
+ |
|
|
408 |
+ |
export type CardMove = { |
|
409 |
+ |
column: string; |
| 340 |
410 |
|
}; |
| 341 |
411 |
|
|
| 342 |
412 |
|
export type NewComment = { |
|
|
… |
69 unchanged lines |
modified
src/oxygenapi.ts
+1 −1
|
|
… |
11 unchanged lines |
| 12 |
12 |
|
| { kind: "repository" } |
| 13 |
13 |
|
| { kind: "bookmark"; name: string } |
| 14 |
14 |
|
| { kind: "change"; hash: string } |
| 15 |
|
- |
| { kind: "file"; reference: string; path: string; line?: number } |
|
15 |
+ |
| { kind: "file"; reference: string; path: string; line?: number; endLine?: number } |
| 16 |
16 |
|
| { kind: "proposals" } |
| 17 |
17 |
|
| { kind: "issues" }; |
| 18 |
18 |
|
|
|
|
… |
19 unchanged lines |
modified
test/hub.test.mjs
+11 −0
|
|
… |
136 unchanged lines |
| 137 |
137 |
|
assert.ok(!looksPrerelease(t), t); |
| 138 |
138 |
|
} |
| 139 |
139 |
|
}); |
|
140 |
+ |
|
|
141 |
+ |
test("file links: line ranges and state-address permalinks", async () => { |
|
142 |
+ |
const { hubUrl } = await import("../out/hub.mjs"); |
|
143 |
+ |
const a = "a".repeat(64), b = "b".repeat(64); |
|
144 |
+ |
assert.equal( |
|
145 |
+ |
hubUrl("https://h:7343", "andy", "oxy", { kind: "file", reference: `${a}+${b}`, path: "src/main.rs", line: 10, endLine: 20 }), |
|
146 |
+ |
`https://h:7343/andy/oxy/file/${a}+${b}/src/main.rs#L10-L20`, |
|
147 |
+ |
); |
|
148 |
+ |
assert.equal(hubUrl("https://h", "a", "r", { kind: "file", reference: "main", path: "x.rs", line: 3, endLine: 3 }), "https://h/a/r/file/main/x.rs#L3"); |
|
149 |
+ |
assert.equal(hubUrl("https://h", "a", "r", { kind: "file", reference: "feature/x", path: "x.rs" }), "https://h/a/r/file/feature%2Fx/x.rs"); |
|
150 |
+ |
}); |