Introduction

The plugin system of DeepSeek Harness (DSH) allows extending the Web GUI. Currently, the system natively supports image uploads, but for arbitrary files (such as PDFs, code files, binary data, etc.), users must manually provide download links or read them via model tools. The dsh-upload-file plugin solves this by injecting upload controls on the browser side and providing persistent storage and reading tools on the host side.

What Is It

This is a DSH client plugin maintained by OctKwong30. It adds file upload capability to the composer input field in the Web GUI. Users can upload files to the host process by clicking the attachment button or dragging local files, and reference these files in a session via cards or tools.

Installation

The installation process is completed through the dsh plugin command. Run the following command to install from GitHub:

dsh plugin --profile web add github:OctKwong30/dsh-upload-file

After installation, restart the Web GUI (dsh web or the corresponding startup method) to load the plugin.

Core Features

The plugin mainly includes the following capabilities:

  • UI Entry Point: Adds an attachment button (SVG paperclip icon) to the composer input field toolbar, supporting multiple file selection; supports dragging OS files directly into the composer area to upload them.
  • Pending-Send State: Uploaded files are displayed as capsule chips above the input field (pending-send file bar), including filename, size, and a remove button.
  • Message Integration: The send hook merges file links into message text in the format 📎 [Name (Size)](http://…/dsh-upload/raw/<id>).
  • Session Rendering: File links in user messages are rendered as file cards (icon + name + size + open link). If rendering crashes, it automatically falls back to the official renderer.
  • Model Tools: The host provides the read_uploaded_file tool, allowing the model to read file content (text or binary metadata).
  • Persistence and Download: Files are stored using SHA256 content addressing in ~/.dsh/uploads/, and a GET /dsh-upload/raw/<id> endpoint is provided for downloading or previewing.

Usage

1. Upload by Button

Open any session, click the paperclip button in the composer input field toolbar, and select local files. After upload, the files are displayed in the “pending-send file bar”. After sending, the message text includes the file link.

2. Drag-and-Drop Upload

Drag one or more files from the file manager into the Web GUI composer area. After releasing the mouse, non-image files are automatically uploaded and added to the pending-send file bar; image files are handled by the shell’s built-in pipeline and do not cause conflicts.

3. Model Invocation

After the model receives a message containing file links, it can call the read_uploaded_file tool. The tool supports accepting a bare id, JSON annotation, markdown link, or raw URL path as an argument.

Configuration and Security

In Settings → Plugin Configuration → dsh-upload-file, the following parameters can be adjusted:

  • maxFileBytes: Maximum file size in bytes (default 20 MiB).
  • maxTextReadBytes: Maximum bytes read by read_uploaded_file for text content (default 256 KiB).
  • uploadsDir: Upload root directory, default ~/.dsh/uploads.

For security, the plugin strictly validates file IDs using SHA256 and sanitizes filenames to prevent path traversal attacks.

Notes

  • Log Handling: File bytes are not included in conversation logs; only references are included, consistent with the logic of the official describe-image plugin.
  • UI Drift Risk: File cards in sessions rely on manually replicated official bubble styles. As the shell version upgrades, official CSS class names may change, causing card style drift. The plugin includes an automatic fallback mechanism, but updates should be monitored.
  • Theme Adaptation: The drop hint bar uses inline styles and does not follow the GUI skin theme.
  • Storage Cleanup: Uploaded files are not automatically cleaned up periodically; the ~/.dsh/uploads/ directory must be managed manually.

Ecosystem Background

DSH plugins combine host and client code through the dsh.bundle.patch mechanism. This plugin is implemented in pure JavaScript (ESM) and can run without a build step. Its architecture references the attach route and sendSession send hook pattern of the official describe-image plugin.