Repository navigation
v0.6.0
·
1339 commits
to master
since this release
Breaking and behaviour changes
- The three library listings (
GET /api/workflows,/api/prompts,
/api/assets) share one envelope. Removed:workflow_dir,prompt_dir,
asset_dir,sources(workflows),prompt_dirs,asset_dirsand
origins(prompts). The writable root is now thelibrariesentry with
writable: trueandorigin: "workspace". Renamed: assets
libraries[].dirisroot, and the MCP compact workflow listing's
sourcesislibraries. Added to all three:libraries: [{origin, root, writable}]in search order,shadowed: [{name, origin, shadowed_by}], and
origin/writableon every entry. Item keys,details,folders, sort
order and the single-item reads are unchanged. - The
teacachepipelineconfigurationkey is removed. A workflow that
sets it fails validation ('teacache' was unexpected). Usecache
(first_block,mag,taylorseer; docs/ACCELERATION.md). The guide's
"TeaCache" sections are gone, soget_guide(section="TeaCache")no longer
resolves. POST /api/jobs,POST /api/jobs/{id}/rerunand a workflow save whose
validation itself crashes answer 500internal error - the server log has the detailwhen something fails after the request was admitted. They
used to answer 400 for any exception. A refused request is still 400. A
crashing validation check is onecheck '<name>' failed (<ExcType>) - the server log has the detailfinding and every other check still reports; a
crashing warning check is a warning and never refuses. A null-path error no
longer starts withNone:.- The REPL is removed (
dw-repl,python -m dw.repl; the guide is now
docs/WORKER_GUIDE.md).python -m dw.runis an HTTP client of a running
dw.serveand takes--server,--workspace(a server workspace name, no
longer a directory) and--token.-o/--output_dir,--prompt-dir,
--asset-dir,--output-layout,--trust-workflowsand-l/--log_level
are gone; set them ondw.serve.httpxis a base dependency. save_workflow,save_prompt,upload_assetandkeep_outputno longer
return the server's absolute path. They return the name, workspace, origin
andreference(#527).- A job runs the definition admission checked. Editing or deleting the file
while the job waits does not change it; a rerun admits the file afresh. An
asset, output, prompt or sub-workflow that changes or disappears while a
job waits now fails at the step that reads it, not at job start. - A rerun rechecks its
asset:/prompt:/output:references and answers
400 when one no longer resolves. Admission refuses anasset:whose
workspace copy is a symlink out of the library. - Upload, keep and delete with no asset library all answer 409
This workspace has no asset library; upload used to write intooutputs.
Deleting a read-only library entry is one 403 message for all three
libraries. - In a named workspace,
prompt:resolves against the server's prompt
library everywhere, including plan building; creating a workspace no
longer makes an emptyprompts/.prompt:name.jsonnow resolves. - More is caught at validate: a
vram_estimateis checked even when the
workflow has nocostblock (#552), and only against the pipeline it was
measured for (#516); a{"location": ...}media entry is size-checked and
probed like a plain path (#518), so a too-shortdissolve_videosinput is
refused; a literal numericsample_rateonslice_audiois honoured as a
relabel; a literalnullthresholdorindexonselectis refused;
audio_bleed_mswith only one input warns (#565). get_output_framesrefusesnamesorboundarieswithoutseams. They
used to be dropped silently (#554).concat_videosfills a silent input with silence for its length instead
of shifting later shots' audio early (#553), and fits each input's audio
to its own frame count, warningaudio_frame_driftfor one that runs long
(#562). A step's declaredresult.fpsis handed on to later steps, and
join_into_songrefuses a contradictingfps(#513). A frame-addressed
slice_audioend is rounded once, which can move it by a sample (#557).- A composed
for_eachmember whose parent saves the result now gets its
template's fps and audio fit. LTX-2.5 image-to-video members were written
at 8 fps (#561). - Embedded image metadata no longer carries a
generatorstring, keeps
lorasandip_adapter(so "open as workflow" works for adapter steps),
and a composed child's steps no longer carryargument_template. - After upgrading: every plan fingerprint changes once, so a bound
acknowledgement made before the deploy gets one 409.base-and-refiner,
ltx2/generative-upscale,ltx2/refine-clipandltx2/two-stagemiss
the step cache once.
New
templates/ltx2/upscale-clip: generative 2x upscale of the caller's clip,
with its soundtrack paired back on (#548).templates/ltx2/refine-clip:
2x latent refine of the caller's clip, about 2.9 min cold on an RTX 3090;
the source is trimmed tonum_framesfirst (#549).- The
join_into_songtask joins dialogue shots into a song, placing the
song from the measured dialogue length at run time (#513). The
minimax-h3skill and the workflows guide carry the recipe (#514). - The
find_loop_bedtask ranks room-tone loop windows as they sound
looped (near-programme material, lap-rate modulation, ticks). It is
shot-aware: no candidate crosses a shot boundary.shot_dead_air, the
minimax-h3andseries-episodesskills point at it (#544/#545). keep_outputrecords the source job, run, version and workspace, so
get_gallery_metadataon a kept asset reports its job (#556).- A composed sub-workflow's manifest entries carry
parent_step(#560). pair_audiowarnsshot_position_regriddedwhen it moves a measured
shot start by 5 ms or more (#563), and loads a stringvideopath.- A job records the full warning set
/api/validatereports, and
validate's argument-error 400 carries warnings.workflow.jsonrecords
the folded variables: realized constants, resolved list entries and
snapped values. get_job_workflowand the job export answer with the admitted
definition when the workflow file has since moved or stopped parsing.dw.runprints a job's whole event tail and its warnings, exits 130 on
Ctrl-C before a job id, and reports a timeout as one error line.- A fully cached rerun no longer loads released pipelines:
ltx2/two-stage
with the same seed went from 78.8 s to 0.77 s on an RTX 3090. - Clearer error text: the
image_crferror names the video passed where an
image was expected (#511); an image task given a video, and a join size
mismatch, name the route throughvideo_framesandresize_rescale
(#550/#551); the frame-size error names every mismatched video by its
index;dissolve_videosnames every too-short input in one error.
Audio shaping steps log seam fades, score offset and fade-out (#564), and
audio_bleedlogs each bled seam (#566). - The plugin skills tell an agent to pass
plan.estimateplus a margin as
wait_for_job'stimeout_seconds(#546).
Fixes
- Validation and
workflow.jsonsee constraint-snapped values. - Sub-workflow warnings are strings at the author's step and use the
caller's arguments; the web UI showed[object Object]. - Validation, submit and the worker check
asset:references against the
job's own workspace, not the default one. - A run's directory and version are claimed atomically under a lock in
dw's settings directory, so two runs of one workflow cannot share a
number, and a gallery delete no longer races an opening run. - A
prompt:name that climbs out of the prompt library is refused without
probing the disk outside it. A missing file there used to be reported as
not found. manifest.jsonis written atomically, so a killed worker leaves the
previous manifest (#517).- Step cache: a step that borrows a pipeline (
pipeline_reference,
reused_components) misses when anything up its borrow chain changes, and
a stale resident pipeline is no longer reused. - Whisper
transcribe_audiono longer truncates a multi-line clip in
plain-text mode (#559). mix_audio's dB-typo warning ignores non-integer gains such as
find_loop_bed's (#555).- The shot-name collision warning drops its doubled step prefix and no
longer repeats onpair_audio/interpolate_frames(#568). - Detail-cache pruning is safe under concurrent requests; a warning helper
that raises never refuses a job;model_namerefusals use one wording
(#529).
Internal (for developers using dw as a Python library)
None of this reaches the HTTP API or MCP.
- Import cycles are gone, no module is over 1,000 lines and no function over
150. Reference prefixes are spelled only indw/references.py. dw.workflow_sourcesisdw.library(WorkflowSourceisLibraryRoot,
plusLibraryPath).dw.loudness,dw.media_audio,dw.media_infoanddw.teacacheare
gone; their contents are indw.dspanddw.media.normalize_audioand
the other dynamics tasks are indw.tasks.audio_dynamics, the join
helpers indw.tasks.joins.result.pysplit intodw.writers,dw.audio_qcand
dw.output_extraction.pipeline_processors/pipeline.pysplit into
placement,components,adaptersandprogress.Workflow.run's
phases are indw.workflow_run, pipeline ownership in
dw.pipeline_ownership, validation indw.validation(which absorbed
dw.result_fps,dw.null_mediaanddw.select_validation), the trust
gate indw.trust.pipeline_cache_keyandstep_pipeline_keysare indw.step_cache;
dw.planno longer re-exportsunseeded_cache_warnings.create_appis a factory overdw/server/routes/*, and
app.dependency_overridesdoes not reach their routes. Worker messages
are typed indw/worker_protocol.py(probe_idisrequest_id;
ping/pongremoved). MCP tools are indw_mcp/tools_*.py.- An object passed to
Workflow.runis the object the steps use, so an
in-place write is visible to the caller. A composed child no longer
deep-copies its handed arguments.