Repository navigation
feat(renderer)!: propagate errors from render callbacks - #324
sundermann wants to merge 1 commit into
Conversation
Custom render steps currently have to save callback failures in shared state and report them after rendering. Return renderer errors from every callback and stop at the first failure instead, discarding partial output. Preserve application error sources through a custom error wrapper and add the step name, a typed callback phase, and the schema type to diagnostics. Keep the callback's renderer error available as a typed source. Report cause text through the source chain without repeating it in each wrapper. Update built-in steps and custom-renderer examples without changing their generated code. The VSME callback now reports a missing type path through the renderer instead of panicking. Cover all callback phases through the low-level renderer and public generation functions, including callback ordering, short-circuiting, source chains, and default callbacks. BREAKING CHANGE: RenderStep::initialize, render_type, and finish return Result<(), RendererError>. Renderer::finish returns Result<Module, RendererError>. Existing custom implementations must return Ok(()) on success, and direct Renderer callers must handle the result. RendererError adds Custom and RenderStep variants; exhaustive matches must handle them.
Bergmann89
left a comment
There was a problem hiding this comment.
Thanks for the PR! Before we go into the details I'd like to understand the use case, because this goes against an idea the pipeline is built on.
The generator is meant to take care of everything that can fail, so the renderer can render the code without errors afterwards. That's why Renderer::finish is infallible today: the only renderer errors come from validating the config in exec_render, before anything is rendered. With this PR every callback becomes fallible, which is a breaking change for all custom steps and would require a new major version, while all built-in steps just return Ok(()).
So the change only helps custom steps that do something fallible on their own (I/O, external lookups, ...). These can already validate their input up front, or keep the error in shared state (e.g. an Arc<Mutex<Option<Error>>>) and check it after generate returned.
What is the concrete case you ran into? If there is one that can't be solved this way, I'm happy to discuss it, but I'd rather not make the whole render step API fallible for it.
|
Thanks, that makes sense. Our concrete case is documentation cleanup step that parses the rendered module with |
Allows custom render steps to return errors directly instead of storing failures for later reporting. Rendering stops at the first error and preserves its source chain.
Changes
Breaking changes:
RenderStep::initialize,render_type, andfinishnow returnResult<(), renderer::Error>. Custom implementations must returnOk(())on success.Renderer::finishnow returnsResult<Module, renderer::Error>, which callers must handle. The error enum addsCustomandRenderStepvariants, requiring updates to exhaustive matches. Finish callbacks do not run after an earlier failure.Checklist
update-expectationsand reviewedcargo fmt,cargo clippyandcargo testpass (see CONTRIBUTING.md)