fix(web): show artifact paths relative to the workspace

This commit is contained in:
yudshj
2026-09-09 15:26:34 +08:00
committed by imccyu
parent b27d861741
commit 5b671d7df3
19 changed files with 80 additions and 36 deletions
@@ -2,5 +2,5 @@
# side as of the last confirmed-consistent state. Both languages carry equal authority;
# after editing either side, bring the other along and re-record with:
# pnpm run verify-translation-pairing --write packages/util/workspace-path/README.md
README.md: ed7cb3bc5089ac76058bd4c7447b1656b0ab2b24
README.zh.md: 471f04af640d1121d8a0dc4f39da0d8c1f5a62d6
README.md: ab7787f3649c8f75a0f0e0745bc78ea32edb5925
README.zh.md: 270c79f7bb57def13a7656e8f76f900c1e094f4f
+1 -1
View File
@@ -9,7 +9,7 @@ English | [中文](README.zh.md)
## Summary
Browser-safe path helpers shared by Workspace-facing client and controller packages. The package joins Workspace-relative paths, abbreviates POSIX home directories for display, derives Workspace titles from POSIX or Windows paths, splits a path into its directories and final segment for display, and owns the `dsh-resource://file/…` address grammar that names a workspace file across the Sidebar and the resource model. It has no Cordis service or runtime state.
Browser-safe path helpers shared by Workspace-facing client and controller packages. The package joins Workspace-relative paths, abbreviates POSIX home directories for display, derives Workspace titles from POSIX or Windows paths, splits a path into its directories and final segment for display, and owns the `dsh-resource://file/…` address grammar that names a workspace file across the Sidebar and the resource model. `relativizeToCwd` removes the workspace prefix for display while preserving paths outside that directory. It has no Cordis service or runtime state.
## Table of Contents
+1 -1
View File
@@ -9,7 +9,7 @@ kind: "package-library"
## 概述
供 Workspace 相关客户端和控制器包共享、可在浏览器使用的路径辅助函数。该包负责拼接 Workspace 相对路径、缩写用于展示的 POSIX 主目录、从 POSIX 或 Windows 路径提取 Workspace 标题、把路径拆成目录部分与末段供展示,并拥有在 Sidebar 与资源模型之间命名工作区文件的 `dsh-resource://file/…` 地址语法它不提供 Cordis service,也不持有运行时状态。
供 Workspace 相关客户端和控制器包共享、可在浏览器使用的路径辅助函数。该包负责拼接 Workspace 相对路径、缩写用于展示的 POSIX 主目录、从 POSIX 或 Windows 路径提取 Workspace 标题、把路径拆成目录部分与末段供展示,并拥有在 Sidebar 与资源模型之间命名工作区文件的 `dsh-resource://file/…` 地址语法`relativizeToCwd` 在显示时省略工作区前缀,并保留该目录以外的路径。它不提供 Cordis service,也不持有运行时状态。
## 目录
+13
View File
@@ -97,3 +97,16 @@ export function fileAddressFor(sessionId: string, cwd: string | undefined, path:
if (root !== '' && normalized.startsWith(`${root}/`)) return sessionFileAddress(sessionId, normalized.slice(root.length + 1))
return sessionFileAddress(sessionId, normalized)
}
/**
* Strip the workspace root from a workspace-rooted absolute path (display only).
* @param text - the path to shorten.
* @param cwd - session workspace root; absent or empty leaves the path unchanged.
* @returns the path relative to the workspace root, or unchanged when it is not rooted there.
*/
export function relativizeToCwd(text: string, cwd: string | undefined): string {
if (cwd === undefined || cwd === '') return text
const root = cwd.replace(/[/\\]+$/, '')
if (text.startsWith(`${root}/`) || text.startsWith(`${root}\\`)) return text.slice(root.length + 1)
return text
}
@@ -1,7 +1,7 @@
import { describe, expect, it } from 'vitest'
import {
abbreviateHomePath, fileAddressFor, isAbsoluteWorkspacePath, parseFileAddress, pathPartsOf, resolveWorkspacePath,
workspaceTitleOf,
abbreviateHomePath, fileAddressFor, isAbsoluteWorkspacePath, parseFileAddress, pathPartsOf, relativizeToCwd,
resolveWorkspacePath, workspaceTitleOf,
} from '@deepseek-ai/dsh-util-workspace-path'
describe('Workspace path helpers', () => {
@@ -78,4 +78,19 @@ describe('Workspace path helpers', () => {
expect(pathPartsOf('notes.md')).toEqual({ directory: '', name: 'notes.md' })
expect(pathPartsOf('/')).toEqual({ directory: '', name: '/' })
})
it.each([
['/work/report.txt', '/work', 'report.txt'],
['/work/reports/result.pdf', '/work/', 'reports/result.pdf'],
['/work-other/report.txt', '/work', '/work-other/report.txt'],
['/other/report.txt', '/work', '/other/report.txt'],
['report.txt', '/work', 'report.txt'],
['/work/report.txt', undefined, '/work/report.txt'],
['/work/report.txt', '', '/work/report.txt'],
['/report.txt', '/', 'report.txt'],
[String.raw`C:\work\reports\result.pdf`, String.raw`C:\work`, String.raw`reports\result.pdf`],
[String.raw`\\server\share\report.txt`, String.raw`\\server\share`, 'report.txt'],
])('displays %s relative to %s only within that workspace', (path, cwd, label) => {
expect(relativizeToCwd(path, cwd)).toBe(label)
})
})