Skip to content

Commit af794d6

Browse files
committed
fix: stopReason/suppressOutputのマージ処理追加
Notification hookでcommand actionが返すstopReason/suppressOutputが 最終JSON出力に反映されていなかった問題を修正 - ExecuteNotificationAction: ActionOutputにStopReason/SuppressOutputをコピー - executeNotificationHooksJSON: PostToolUseパターンに倣ってマージ処理追加 - StopReason: 最後の非空値が勝ち - SuppressOutput: 最後の値が勝ち - テスト追加: executor_test.go/hooks_test.goで検証
1 parent 6702574 commit af794d6

File tree

4 files changed

+86
-21
lines changed

4 files changed

+86
-21
lines changed

executor.go

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -88,9 +88,11 @@ func (e *ActionExecutor) ExecuteNotificationAction(action Action, input *Notific
8888

8989
// Build ActionOutput from parsed JSON
9090
result := &ActionOutput{
91-
Continue: cmdOutput.Continue,
92-
HookEventName: cmdOutput.HookSpecificOutput.HookEventName,
93-
SystemMessage: cmdOutput.SystemMessage,
91+
Continue: cmdOutput.Continue,
92+
HookEventName: cmdOutput.HookSpecificOutput.HookEventName,
93+
SystemMessage: cmdOutput.SystemMessage,
94+
StopReason: cmdOutput.StopReason,
95+
SuppressOutput: cmdOutput.SuppressOutput,
9496
}
9597

9698
// Set AdditionalContext

executor_test.go

Lines changed: 63 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -3213,13 +3213,15 @@ func TestExecuteSubagentStopAction_TypeCommand(t *testing.T) {
32133213

32143214
func TestExecuteNotificationAction_TypeOutput(t *testing.T) {
32153215
tests := []struct {
3216-
name string
3217-
action Action
3218-
wantContinue bool
3219-
wantHookEventName string
3220-
wantAdditionalCtx string
3221-
wantSystemMessage string
3222-
wantErr bool
3216+
name string
3217+
action Action
3218+
wantContinue bool
3219+
wantHookEventName string
3220+
wantAdditionalCtx string
3221+
wantSystemMessage string
3222+
wantStopReason string
3223+
wantSuppressOutput bool
3224+
wantErr bool
32233225
}{
32243226
{
32253227
name: "Message with continue unspecified defaults to true",
@@ -3330,23 +3332,33 @@ func TestExecuteNotificationAction_TypeOutput(t *testing.T) {
33303332
if tt.wantSystemMessage != "" && output.SystemMessage != tt.wantSystemMessage {
33313333
t.Errorf("SystemMessage = %q, want %q", output.SystemMessage, tt.wantSystemMessage)
33323334
}
3335+
3336+
if tt.wantStopReason != "" && output.StopReason != tt.wantStopReason {
3337+
t.Errorf("StopReason = %q, want %q", output.StopReason, tt.wantStopReason)
3338+
}
3339+
3340+
if output.SuppressOutput != tt.wantSuppressOutput {
3341+
t.Errorf("SuppressOutput = %v, want %v", output.SuppressOutput, tt.wantSuppressOutput)
3342+
}
33333343
})
33343344
}
33353345
}
33363346

33373347
func TestExecuteNotificationAction_TypeCommand(t *testing.T) {
33383348
tests := []struct {
3339-
name string
3340-
action Action
3341-
stubStdout string
3342-
stubStderr string
3343-
stubExitCode int
3344-
stubErr error
3345-
wantContinue bool
3346-
wantHookEventName string
3347-
wantAdditionalCtx string
3348-
wantSystemMessage string
3349-
wantErr bool
3349+
name string
3350+
action Action
3351+
stubStdout string
3352+
stubStderr string
3353+
stubExitCode int
3354+
stubErr error
3355+
wantContinue bool
3356+
wantHookEventName string
3357+
wantAdditionalCtx string
3358+
wantSystemMessage string
3359+
wantStopReason string
3360+
wantSuppressOutput bool
3361+
wantErr bool
33503362
}{
33513363
{
33523364
name: "Command success with valid JSON and all fields",
@@ -3419,6 +3431,31 @@ func TestExecuteNotificationAction_TypeCommand(t *testing.T) {
34193431
wantSystemMessage: "",
34203432
wantErr: false,
34213433
},
3434+
{
3435+
name: "Command with stopReason and suppressOutput",
3436+
action: Action{
3437+
Type: "command",
3438+
Command: "get-notification-with-flags.sh",
3439+
},
3440+
stubStdout: `{
3441+
"continue": true,
3442+
"stopReason": "test_stop_reason",
3443+
"suppressOutput": true,
3444+
"hookSpecificOutput": {
3445+
"hookEventName": "Notification",
3446+
"additionalContext": "Notification with flags"
3447+
}
3448+
}`,
3449+
stubStderr: "",
3450+
stubExitCode: 0,
3451+
wantContinue: true,
3452+
wantHookEventName: "Notification",
3453+
wantAdditionalCtx: "Notification with flags",
3454+
wantSystemMessage: "",
3455+
wantStopReason: "test_stop_reason",
3456+
wantSuppressOutput: true,
3457+
wantErr: false,
3458+
},
34223459
}
34233460

34243461
for _, tt := range tests {
@@ -3469,6 +3506,14 @@ func TestExecuteNotificationAction_TypeCommand(t *testing.T) {
34693506
if tt.wantSystemMessage != "" && output.SystemMessage != tt.wantSystemMessage {
34703507
t.Errorf("SystemMessage = %q, want %q", output.SystemMessage, tt.wantSystemMessage)
34713508
}
3509+
3510+
if tt.wantStopReason != "" && output.StopReason != tt.wantStopReason {
3511+
t.Errorf("StopReason = %q, want %q", output.StopReason, tt.wantStopReason)
3512+
}
3513+
3514+
if output.SuppressOutput != tt.wantSuppressOutput {
3515+
t.Errorf("SuppressOutput = %v, want %v", output.SuppressOutput, tt.wantSuppressOutput)
3516+
}
34723517
})
34733518
}
34743519
}

hooks.go

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -627,6 +627,14 @@ func executeNotificationHooksJSON(config *Config, input *NotificationInput, rawJ
627627
systemMessageBuilder.WriteString(actionOutput.SystemMessage)
628628
}
629629

630+
// StopReason: 最後の非空値が勝ち
631+
if actionOutput.StopReason != "" {
632+
finalOutput.StopReason = actionOutput.StopReason
633+
}
634+
635+
// SuppressOutput: 最後の値が勝ち
636+
finalOutput.SuppressOutput = actionOutput.SuppressOutput
637+
630638
// No early return for Notification (cannot block)
631639
}
632640
}

hooks_test.go

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3681,6 +3681,8 @@ func TestExecuteNotificationHooksJSON(t *testing.T) {
36813681
wantHookEventName string
36823682
wantAdditionalContext string
36833683
wantSystemMessage string
3684+
wantStopReason string
3685+
wantSuppressOutput bool
36843686
wantErr bool
36853687
wantErrContains string
36863688
}{
@@ -3825,6 +3827,14 @@ func TestExecuteNotificationHooksJSON(t *testing.T) {
38253827
if tt.wantSystemMessage != "" && output.SystemMessage != tt.wantSystemMessage {
38263828
t.Errorf("SystemMessage = %q, want %q", output.SystemMessage, tt.wantSystemMessage)
38273829
}
3830+
3831+
if tt.wantStopReason != "" && output.StopReason != tt.wantStopReason {
3832+
t.Errorf("StopReason = %q, want %q", output.StopReason, tt.wantStopReason)
3833+
}
3834+
3835+
if output.SuppressOutput != tt.wantSuppressOutput {
3836+
t.Errorf("SuppressOutput = %v, want %v", output.SuppressOutput, tt.wantSuppressOutput)
3837+
}
38283838
}
38293839
})
38303840
}

0 commit comments

Comments
 (0)