/** * PreToolUse hook event. * * Fires before Claude Code executes a tool call. A handler can return * `allow`, `deny`, `ask`, or `defer` to control whether the tool is run. * Supports a regex matcher on `tool_name`. See * https://code.claude.com/docs/en/hooks#pretooluse. * * @since 0.1.0 */ import * as Effect from 'effect/Effect'; import * as Schema from 'effect/Schema'; import { HookToolDecodeError } from '../../Errors.js'; import type { HookContext } from '../Context.js'; import type { HookDefinition } from '../Runner.js'; import * as Tool from '../Tool.js'; declare const Input_base: Schema.Class; readonly tool_name: Schema.String; readonly tool_input: Schema.$Record; readonly tool_use_id: Schema.optional; readonly session_id: Schema.String; readonly transcript_path: Schema.String; readonly cwd: Schema.String; readonly permission_mode: Schema.optionalKey; readonly effort: Schema.optionalKey; readonly agent_id: Schema.optionalKey; readonly agent_type: Schema.optionalKey; }>, {}>; /** * Decoded PreToolUse hook input received on stdin. * * @category Schemas * @since 0.1.0 */ export declare class Input extends Input_base { } /** * Valid `permissionDecision` values. `defer` suspends a headless tool call * for later resumption; omit output entirely for a neutral no-op. * * @category Schemas * @since 0.1.0 */ export declare const PermissionDecision: Schema.Literals; declare const HookSpecificOutput_base: Schema.Class; readonly permissionDecision: Schema.Literals; readonly permissionDecisionReason: Schema.optional; readonly updatedInput: Schema.optional>; readonly additionalContext: Schema.optional; }>, {}>; /** * `hookSpecificOutput` payload for a PreToolUse hook. This is where the * permission decision lives. * * @category Schemas * @since 0.1.0 */ export declare class HookSpecificOutput extends HookSpecificOutput_base { } declare const Output_base: Schema.Class; readonly stopReason: Schema.optional; readonly suppressOutput: Schema.optional; readonly systemMessage: Schema.optional; readonly terminalSequence: Schema.optional; readonly hookSpecificOutput: Schema.optional; }>, {}>; /** * Full PreToolUse hook output, including universal fields. * * @category Schemas * @since 0.1.0 */ export declare class Output extends Output_base { } /** * Build an `allow` decision. The tool call proceeds. * * @category Decisions * @since 0.1.0 */ export declare const allow: (reason?: string) => Output; /** * Build a no-op output. The tool proceeds through normal permission flow. * * @category Decisions * @since 0.1.0 */ export declare const passthrough: () => Output; /** * Build a `deny` decision with a required explanation. The tool call * is blocked and the reason is fed back to Claude. * * @category Decisions * @since 0.1.0 */ export declare const deny: (reason: string) => Output; /** * Build an `ask` decision. Claude Code shows the user a permission * prompt for the tool call. * * @category Decisions * @since 0.1.0 */ export declare const ask: (reason?: string) => Output; /** * Build a `defer` decision. In headless mode, Claude Code exits with * `stop_reason: "tool_deferred"` so an outer process can resume later. * Use `passthrough()` for a neutral no-op. * * @category Decisions * @since 0.1.0 */ export declare const defer: (reason?: string) => Output; /** * Build an `allow` decision that replaces the tool input with a * modified version. * * @category Decisions * @since 0.1.0 */ export declare const allowWithUpdatedInput: (updatedInput: Readonly>, reason?: string) => Output; /** * Build a runnable PreToolUse hook from a handler effect. * * @category Constructors * @since 0.1.0 * @example * ```ts * import * as Effect from 'effect/Effect' * import { Hook } from 'effect-claudecode' * * const hook = Hook.PreToolUse.define({ * handler: (input) => Effect.gen(function* () { * if (input.tool_name !== 'Bash') return Hook.PreToolUse.passthrough() * const cmd = (input.tool_input as { command?: string }).command ?? '' * return cmd.includes('rm -rf /') * ? Hook.PreToolUse.deny('destructive') * : Hook.PreToolUse.passthrough() * }) * }) * * Hook.runMain(hook) * ``` */ export declare const define: (config: { readonly handler: (input: Input) => Effect.Effect; }) => HookDefinition; /** * Build a PreToolUse hook that only handles a specific supported tool. * Non-matching tool invocations default to `passthrough()`. * * @category Constructors * @since 0.1.0 */ export type OnToolConfig = { readonly toolName: T; readonly handler: (input: Tool.DecodedPreToolUse) => Effect.Effect; readonly onMismatch?: (input: Input) => Effect.Effect; readonly onDecodeError?: (error: HookToolDecodeError, input: Input) => Effect.Effect; }; export declare const onTool: (config: OnToolConfig) => HookDefinition; /** * Build a PreToolUse hook that only handles matching `tool_name` values. * Non-matching tool invocations default to `passthrough()`. * * @category Constructors * @since 0.1.0 */ export declare const onMatcher: (config: { readonly matcher: string | RegExp; readonly handler: (input: Input) => Effect.Effect; readonly onMismatch?: (input: Input) => Effect.Effect; }) => HookDefinition; /** * Build a PreToolUse hook from a custom typed tool adapter. * Non-matching tool invocations default to `passthrough()`. * * @category Constructors * @since 0.1.0 */ export declare const onAdapter: (config: { readonly adapter: Tool.PreToolAdapter; readonly handler: (input: Tool.DecodedPreToolUseWith) => Effect.Effect; readonly onMismatch?: (input: Input) => Effect.Effect; readonly onDecodeError?: (error: HookToolDecodeError, input: Input) => Effect.Effect; }) => HookDefinition; export {}; //# sourceMappingURL=PreToolUse.d.ts.map