Adding pre_command_substitution and post_expansion_pre_dispatch hooks#935
Adding pre_command_substitution and post_expansion_pre_dispatch hooks#935k2tomasz wants to merge 18 commits intoreubeno:mainfrom
Conversation
Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
Add PolicyDecision, CommandSubstitutionContext, SubstitutionSyntax, and CommandSubstitutionDecision types for the experimental-filters feature. Also add Debug derive to ExecutionExitCode. These types support the post-expansion policy hook (task 1.2) and pre-command-substitution hook per the design spec.
… handling - Add detailed module documentation explaining command execution and policy hook types - Document post-expansion policy hook system for security/policy enforcement - Add pre-command-substitution hook types and context structures - Document performance characteristics and feature gating of policy hooks - Implement `convert_redirect_to_info()` function to convert AST redirections to structured format - Replace `.unwrap()` calls with proper error handling using `if let Ok` pattern in custom-extensions example - Improve code robustness by gracefully handling mutex poisoning in extension hooks - Add comprehensive documentation for redirection conversion including arguments, returns, and feature flags - Update inline documentation with backtick formatting for code references
|
@reubeno let me know if you like having hooks like these and I can improve/clean this up and then create a PR for main once your filters PR gets merged. |
feat(expansion): handle errors marked as reported by extensions feat(shell): suppress duplicate error messages for reported errors test(suppression): add tests for error suppression behavior
…CommandSubstitutionDecision
|
Thanks for proposing this! I like the idea of more hooks, provided we can keep the cost/complexity managed. My real goal is to remove the feature flag once we make A command substitution hook definitely makes sense. I'll need to skim through your changes to understand the pipeline and redirection context getting built up. Let me get back to you on that. |
|
As an update -- I've merged in #941, which introduces |
Two hooks were added to the ShellExtensions trait:
Additionally, a supporting method was added:
needs_command_context() - An opt-in method (defaults to false) that extensions override to signal they want the post-expansion hook invoked. This enables lazy context construction for near-zero overhead when unused.
All of these are gated behind the experimental-filters feature flag.
How would this work?
flowchart TD A[Parse Command] --> B[Expand Words] B --> C{Command Substitution?} C -->|Yes| D[pre_command_substitution] D -->|Allow| E[Execute Substitution Body] D -->|Replace Output| F[Use Replacement Output] D -->|Error| X[Abort Expansion] C -->|No| G[Continue Expansion] E --> H[Build SimpleCommand] F --> H G --> H H --> I[Run pre_exec_simple_command filter chain] I --> J{Any extension needs context?} J -->|No| K[Dispatch/Execute] J -->|Yes| L["Resolve DispatchTarget (cheap)"] L --> M[Build CommandContext] M --> N["post_expansion_pre_dispatch_simple_command (policy)"] N -->|Continue| K N -->|Return early| O[Skip dispatch] K --> P[post_exec_simple_command] O --> P