UI Enhancements

dsh-101

bill9109/dsh-101 · ★ 6

bill9109Curated

Document reading mode for DSH.

License
BSD-3-Clause
Added
2026-08-13
Maintenance
active
Install kind
github
Manifest status
Declared
Manifest path
package.json#dsh
Manifest checked
2026-08-19
Lifecycle scripts
None found

Static manifest checks report declarations only; they are not compatibility or security review.

安装

dsh plugin --profile web add github:bill9109/dsh-101

GitHub 源码安装:首次需按提示配置 allowBuilds 构建授权后重试

For install and environment setup, plus plugin development tutorials, see DSH community docs ↗

README

Source README · body: en · Read Chinese README

Table of contents
  1. Why this exists
  2. Features
  3. Usage
  4. Install
  5. Port
  6. Upgrade
  7. Uninstall
  8. Troubleshooting
  9. Directory layout
  10. Build
  11. Regenerating the corpus
  12. Upgrading from a newer DSH snapshot
  13. Development and verification
  14. Community and About
  15. License

Release v0.1.7 License: BSD-3-Clause Node.js DSH profiles

Install: bash <(curl -fsSL https://raw.githubusercontent.com/bill9109/dsh-101/main/scripts/install.sh) github:bill9109/dsh-101#v0.1.7

DSH 101 is a document-first reading interface built on top of dsh-base + dsh-web-app: it organizes DSH's own documentation into an ordered, searchable, translatable reader.

English | 中文

Why this exists

DSH ships a large body of built-in documentation, but in its raw form it is a file dump: scattered across the source tree, with no order, no search, and no comfortable way to read it. dsh-101 makes that documentation a first-class part of the DSH experience — a curated, ordered, searchable, translatable reader instead of raw files, with the conversation panel alongside so you can ask questions while you read.

Features

  • DSH's built-in documentation, curated and ordered by topic
  • Built-in document translation
  • A sliding hidden table of contents
  • Conversation panel on the right

Usage

Boot the profile (default port 3081, coexists with the web GUI on 3080):

dsh --profile dsh-101

Open http://127.0.0.1:3081 (or the port you chose): the reader shows the curated corpus with the sliding table of contents, search filters the documents, translation switches the reading language, and the right-hand panel is the DSH conversation you already know.

Install

This repository ships both a bundle (@bill9109/dsh-101, installable via dsh plugin add) and a profile/ directory (a ready-to-use dsh-101 profile composing dsh-base + dsh-web-app + this bundle). DSH's official distribution model is "distribute bundles, compose profiles" — there is no official command to distribute a profile, but a profile is just a directory under $DSH_HOME/profiles/<name>/, so the repository's profile/ is directly usable.

Recommended: one-liner script (places profile/ into ~/.dsh/profiles/dsh-101/ and installs the bundle):

# Install from GitHub (pin to a tag/commit when possible):
bash <(curl -fsSL https://raw.githubusercontent.com/bill9109/dsh-101/main/scripts/install.sh) github:bill9109/dsh-101#v0.1.7

# Or install from a local checkout, specifying the port (default 3081):
./scripts/install.sh --port 3081 .

# Boot:
dsh --profile dsh-101

What the script does: places the three profile/ files into $DSH_HOME/profiles/dsh-101/ (only fills in missing dsh-base/dsh-web-app layers if the profile already exists), primes the DSH module fallback (so in-box peers resolve at runtime), then runs dsh plugin --profile dsh-101 add to install this bundle.

Manual install:

mkdir -p ~/.dsh/profiles/dsh-101
cp profile/package.json profile/pnpm-workspace.yaml ~/.dsh/profiles/dsh-101/
# Optional: port patch
cp profile/cordis.patch.yml ~/.dsh/profiles/dsh-101/
# Install the bundle (appends to the bundles list)
dsh plugin --profile dsh-101 add github:bill9109/dsh-101#v0.1.7
dsh --profile dsh-101

Verify the bundles list has the three layers:

python3 -c "import json; print(json.load(open('$HOME/.dsh/profiles/dsh-101/package.json'))['dsh']['profile']['bundles'])"
# expected: ['@deepseek-ai/dsh-base', '@deepseek-ai/dsh-web-app', '@bill9109/dsh-101']

Do NOT install into the web profile. dsh-101's bundle disables ui-layout (the default browser shell); installed into any web-app profile it takes down the whole web (sidebar / conversation / app-shell all wait for the layout service and stay pending). Always use dsh-101 as its own profile (dsh --profile dsh-101, default port 3081, coexists with the web GUI on 3080). install.sh now rejects --profile web outright.

Port

Defaults to 3081 (coexists with the web GUI on 3080). Two ways to change it:

At launch (recommended, no config change, dsh 0.1.0-rc.6+):

dsh --profile dsh-101 --port 8080

Persist a different default in the profile config:

# ~/.dsh/profiles/dsh-101/cordis.patch.yml
- id: webserver
  inject: [webStartup]
  config:
    host: !!js ctx.webStartup.host ?? '127.0.0.1'
    port: !!js ctx.webStartup.port ?? 8080

(Launch flags win; the patch value is only the fallback.)

Git installs ship build artifacts. lib/ is committed to this repository, so a git install gets the built host + client bundles directly — no build, no credentials needed. If you install from a pristine clone before building, run node scripts/build.mjs first (needs a DSH source checkout, see below).

Upgrade

Re-run the one-liner with the new pinned tag:

bash <(curl -fsSL https://raw.githubusercontent.com/bill9109/dsh-101/main/scripts/install.sh) github:bill9109/dsh-101#v<new-version>

For a local-checkout installation, re-run ./scripts/install.sh . against the updated checkout (it only fills in missing layers, so your profile state is preserved). When DSH itself publishes a new snapshot, sync the bundle sources from the upgraded checkout with node scripts/upgrade.mjs (see "Upgrading from a newer DSH snapshot").

Uninstall

dsh plugin --profile dsh-101 remove @bill9109/dsh-101
# and, if you no longer want the standalone profile:
rm -rf ~/.dsh/profiles/dsh-101

The first command runs pnpm remove in the profile directory and removes the bundle from dsh.profile.bundles; the second deletes the standalone profile itself.

Troubleshooting

Symptom Resolution
Web GUI (3080) is down / sidebar stays pending after installing dsh-101 dsh-101 was installed into the web profile and disabled ui-layout — remove @bill9109/dsh-101 from the web profile and reinstall dsh-101 as its own profile with the one-liner
dsh --profile dsh-101 fails to start Confirm $DSH_HOME/profiles/dsh-101/ exists and its bundles list contains the three layers (dsh-base, dsh-web-app, @bill9109/dsh-101); re-run install.sh if a layer is missing
Port 3081 already in use Pass --port <port> at launch, or persist a different default in the profile's cordis.patch.yml
GitHub install fails or installs stale code Pin the install to a tag (github:bill9109/dsh-101#v0.1.7) or install from a local checkout (./scripts/install.sh .)
Documents missing or outdated Regenerate the corpus from a DSH source checkout: DSH_CHECKOUT=/path/to/dsh node scripts/build.mjs --corpus
Broken after DSH published a new snapshot Sync sources and rebuild with node scripts/upgrade.mjs --checkout /path/to/upgraded-dsh

Directory layout

src/
  app/        host plugin: corpus service + /api/dsh101 routes (from dsh-101-app)
  app/invariant.ts
  core/       corpus model: loading, merging, search (from dsh-101-core)
  tutor/      host plugin: model tools, curator skill (from dsh-101-tutor)
  client/     browser side: reader shell (from dsh-101-app/src/client)
  invariant.ts
assets/dsh-101/   generated corpus (corpus.json + documents/ + images/)
cordis.patch.yml  bundle patch: mounts app (package root) + tutor (./tutor subpath)
profile/          ready-to-use dsh-101 profile (package.json + pnpm-workspace.yaml + cordis.patch.yml)
scripts/
  install.sh            one-liner profile installer (install.sh --port <port> <src>)
  build.mjs             builds host + client bundles against a DSH checkout
  gen-dsh-101-corpus.ts regenerates the corpus from a DSH source tree
  upgrade.mjs           syncs sources from an upgraded DSH checkout and rebuilds
  verify-i18n.mjs       bilingual README consistency check (node scripts/verify-i18n.mjs)

Build

The bundle's peer dependencies resolve from a DSH install — either a source checkout (DSH_CHECKOUT) or the module fallback of a running DSH ($DSH_HOME/profiles/node_modules). Toolchain binaries (tsc, tsdown) prefer the DSH source checkout.

DSH_CHECKOUT=/path/to/dsh node scripts/build.mjs
# Rebuild after regenerating the corpus:
DSH_CHECKOUT=/path/to/dsh node scripts/build.mjs --corpus

build.mjs symlinks DSH's peers into node_modules, runs tsc (types into types/) then tsdown (host bundle + client bundle into lib/), and removes the symlinks afterwards.

Usually no build needed. lib/ is committed; dsh plugin add (GitHub / tarball / local checkout) installs the built bundle. Build only when developing this repo or after an upgrade sync.

Regenerating the corpus

The corpus is a snapshot of the DSH repository's docs. Regenerate it from any DSH source checkout (uses that checkout's tsx):

DSH_CHECKOUT=/path/to/dsh node scripts/build.mjs --corpus
# or explicitly:
/path/to/dsh/node_modules/.bin/tsx scripts/gen-dsh-101-corpus.ts /path/to/dsh

Upgrading from a newer DSH snapshot

After DSH publishes a new snapshot, sync this bundle from the upgraded checkout:

node scripts/upgrade.mjs --checkout /path/to/upgraded-dsh

The script copies the 101 packages' sources into src/, rewrites internal imports to relative paths, regenerates the corpus, and rebuilds. Then review the diff, commit, bump the version and tag:

git add -A && git commit -m "sync with DSH <snapshot>"
git tag v0.2.0 && git push origin main --tags

Development and verification

pnpm install
pnpm run build       # tsc + tsdown -> lib/ (committed)
pnpm run gen-corpus  # regenerate corpus from a DSH source tree (needs DSH_CHECKOUT)
node scripts/verify-i18n.mjs   # bilingual README consistency

pnpm run build emits the host + client bundles into lib/, which is committed so consumers install without building. Keep the bilingual README in sync: edit both README.md and README.zh.md, then node scripts/verify-i18n.mjs --write to re-record the blob hashes.

Community and About

License

BSD-3-Clause