Master dimensions move from a 2048 long-edge rule to a total-pixel budget (normalizedImageMaxPixels, default 2048x2048) with an 8192 long-edge cap, so extreme aspect ratios keep short-edge resolution. The shared quality ladder and lazy execution move to encoding.ts, review-round doc fixes land across attachment and llm packages, and the superseded facts in the unified-image-pipeline note now describe the shipped routing. |
||
|---|---|---|
| .. | ||
| src | ||
| tests | ||
| package.json | ||
| README.i18n.yaml | ||
| README.md | ||
| README.zh.md | ||
| tsconfig.json | ||
@deepseek-ai/dsh-attachment
English | 中文
The durable attachment seam. ctx.attachments validates and durably commits a provider-independent normalized image, then returns a serializable ImageAttachmentRef; consumers never persist browser paths, object URLs, provider URLs, local storage paths, or base64 in session events.
Unsent composer images remain browser-owned temporary drafts. validateImage runs the complete admission policy without persisting. saveImages owns batch count and aggregate-byte limits, prepares every normalized attachment before publishing any member, then commits in order and returns references only after the complete batch succeeds. A later storage failure returns no partial references, although an earlier immutable content-addressed object may remain unreachable until reference-aware garbage collection exists. AttachmentError.code uses the closed AttachmentErrorCode string union. Its ImageAdmissionErrorCode subset marks caller-correctable image-input failures; isImageAdmissionError recognizes that subset at runtime so each protocol adapter can map its own error vocabulary. saveImage commits one accepted image before any model-visible session event is published and returns its ImageAttachmentRef. When normalization reduces the raster, the reference records the orientation-applied input size in originalDimensions. readImage verifies the normalized attachment against its logged metadata. readImageRequest deterministically derives a route-sized request version whose identity covers the attachment id, transform version, pixel and byte budgets, and encoder settings. imageHostPath optionally exposes the provider-owned object's absolute host path; it makes no claim that the current model tools can read that path. An LLM consumer combines this location with the mounted filesystem's execution-world mapping when it serializes a request. That current access path remains separate from the request version and its variantId. Callers compose ordered batches with Promise.all(refs.map(...)); the local implementation still bounds compression through its instance limiter, cache, and singleflight. Callers may cancel reads and projections; implementations preserve cancellation instead of translating it into a storage failure.
admitEncodedImages(attachments, images) is the shared wire entry used by every RPC endpoint that accepts browser uploads (the session prompt endpoint and the command executor): it enforces canonical base64 on every member, then delegates batch admission — limits, validation, ordered commit — to saveImages. The base64 upload form is EncodedImageAttachment, exported from @deepseek-ai/dsh-attachment/types so wire contracts can reference it.
Model Experience
Indirectly, through the role-neutral core ImageBlock and provider adapters that resolve its durable reference into an exact request version. Request descriptors expose the complete attachment id and actual request dimensions. When the attachment backend exposes a host object and the current execution filesystem maps it, the descriptor also exposes the resulting read-only path; it states that normalization may have resized or re-encoded the upload.
KV Cache effect
Adding an image changes the provider request and therefore invalidates the affected request suffix. A changed execution-world path can also change historical descriptor text without changing the deterministic request version.
Known Limitations and Deferred Work
- Version one accepts PNG, JPEG, WebP, and GIF only.
- Retention and garbage collection are deferred because resumed and forked sessions may share immutable objects.
- Generic files, audio, video, and persistent unsent drafts require separate lifecycle and provider contracts.