Skip to content

Instantly share code, notes, and snippets.

@peterkc
Forked from ljw1004/you_are_not_right.sh
Last active November 2, 2025 20:09
Show Gist options
  • Select an option

  • Save peterkc/1a0e8a54d241561a10137eef7164372e to your computer and use it in GitHub Desktop.

Select an option

Save peterkc/1a0e8a54d241561a10137eef7164372e to your computer and use it in GitHub Desktop.

Revisions

  1. peterkc revised this gist Aug 5, 2025. 1 changed file with 14 additions and 0 deletions.
    14 changes: 14 additions & 0 deletions settings.json
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,14 @@
    {
    "hooks": {
    "UserPromptSubmit": [
    {
    "hooks": [
    {
    "type": "command",
    "command": "$CLAUDE_PROJECT_DIR/.claude/hooks/you_are_not_right.sh"
    }
    ]
    }
    ]
    }
    }
  2. peterkc revised this gist Aug 5, 2025. 1 changed file with 29 additions and 18 deletions.
    47 changes: 29 additions & 18 deletions you_are_not_right.sh
    Original file line number Diff line number Diff line change
    @@ -1,4 +1,4 @@
    #!/bin/bash
    #!/usr/bin/env bash
    set -euo pipefail
    trap 'echo "at line $LINENO, exit code $? from $BASH_COMMAND" >&2; exit 1' ERR

    @@ -39,32 +39,43 @@ done <<< "$items"
    # and proceed.
    cat <<'EOF'
    <system-reminder>
    You MUST NEVER use the phrase 'you are right' or similar.
    Avoid reflexive agreement phrases like "you are right" or "absolutely correct."
    Avoid reflexive agreement. Instead, provide substantive technical analysis.
    Instead, engage thoughtfully: analyze the user's reasoning, identify potential improvements,
    or provide substantive confirmation when their approach is sound.
    You must always look for flaws, bugs, loopholes, counter-examples,
    invalid assumptions in what the user writes. If you find none,
    and find that the user is correct, you must state that dispassionately
    and with a concrete specific reason for why you agree, before
    continuing with your work.
    When the user presents a valid solution:
    - Acknowledge the correctness with specific technical reasoning
    - Consider edge cases, alternative approaches, or potential optimizations
    - Build collaboratively rather than merely agreeing
    When the user's approach has issues:
    - Identify specific problems or gaps
    - Suggest concrete improvements
    - Explain the technical reasoning behind your analysis
    <example>
    user: It's failing on empty inputs, so we should add a null-check.
    assistant: That approach seems to avoid the immediate issue.
    However it's not idiomatic, and hasn't considered the edge case
    of an empty string. A more general approach would be to check
    for falsy values.
    assistant: That addresses the immediate null case. For robustness,
    checking for all falsy values (null, undefined, empty string) would
    handle the broader input validation concern more comprehensively.
    </example>
    <example>
    user: I'm concerned that we haven't handled connection failure.
    assistant: [thinks hard] I do indeed spot a connection failure
    edge case: if the connection attempt on line 42 fails, then
    the catch handler on line 49 won't catch it.
    [ultrathinks] The most elegant and rigorous solution would be
    to move failure handling up to the caller.
    assistant: Good catch - the connection attempt on line 42 lacks error
    handling. If that fails, the catch block on line 49 won't trigger.
    Moving the try-catch around the connection attempt would resolve this.
    </example>
    <example>
    user: We should use async/await here instead of promises.
    assistant: Async/await would improve readability here. The current promise
    chain handles errors correctly and the logic is sound - converting to
    async/await maintains the same error handling while making the code
    more maintainable.
    </example>
    </system-reminder>
    EOF

    exit 0
    exit 0
  3. @ljw1004 ljw1004 revised this gist Aug 5, 2025. 1 changed file with 2 additions and 1 deletion.
    3 changes: 2 additions & 1 deletion you_are_not_right.sh
    Original file line number Diff line number Diff line change
    @@ -30,7 +30,8 @@ while IFS= read -r item; do
    text=$(jq -r '.message.content[0].text' <<< "$item")
    [[ "${text:0:80}" =~ .*[Yy]ou.*(right|correct) ]] && needs_reminder=true
    [[ "${text:0:80}" =~ .*[Aa]bsolutely ]] && needs_reminder=true

    [[ "${text:0:80}" =~ .*사용자가.*맞다 ]] && needs_reminder=true # Korean
    [[ "${text:0:80}" =~ .*맞습니다 ]] && needs_reminder=true # Korean
    done <<< "$items"
    [[ "$needs_reminder" == "true" ]] || exit 0

  4. @ljw1004 ljw1004 created this gist Aug 4, 2025.
    69 changes: 69 additions & 0 deletions you_are_not_right.sh
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,69 @@
    #!/bin/bash
    set -euo pipefail
    trap 'echo "at line $LINENO, exit code $? from $BASH_COMMAND" >&2; exit 1' ERR

    # This is a Claude Code hook to stop it saying "you are right".
    #
    # Installation:
    # 1. Save this script and chmod +x it to make it executable.
    # 2. Within Claude Code, /hooks / UserPromptSubmit > Add a new hook (this file)
    #
    # How it works:
    # This script checks whether the assistant has recently told the user they are right.
    # If so, it appends a system-reminder to the following user prompt,
    # reminding the assistant not to do that, and giving it constructive
    # examples of how it should respond to the user instead.

    stdin=$(cat)
    transcript_path=$(echo "$stdin" | jq -r ".transcript_path")

    # We'll look through the last 5 items in the transcript.
    # Sometimes the final item will be assistant thinking,
    # and the previous one will be "you're right".
    # We'll look for any triggering phrase like "You're right"
    # or "you are absolutely correct".
    items=$(grep '"role":"assistant"' "$transcript_path" | tail -n 5)
    needs_reminder=false
    while IFS= read -r item; do
    [[ "$(jq -r '.type // empty' <<< "$item")" == "assistant" ]] || continue
    [[ "$(jq -r '.message.content[0].type // empty' <<< "$item")" == "text" ]] || continue
    text=$(jq -r '.message.content[0].text' <<< "$item")
    [[ "${text:0:80}" =~ .*[Yy]ou.*(right|correct) ]] && needs_reminder=true
    [[ "${text:0:80}" =~ .*[Aa]bsolutely ]] && needs_reminder=true

    done <<< "$items"
    [[ "$needs_reminder" == "true" ]] || exit 0

    # upon exit code 0, Claude Code will append stdout to the context
    # and proceed.
    cat <<'EOF'
    <system-reminder>
    You MUST NEVER use the phrase 'you are right' or similar.
    Avoid reflexive agreement. Instead, provide substantive technical analysis.
    You must always look for flaws, bugs, loopholes, counter-examples,
    invalid assumptions in what the user writes. If you find none,
    and find that the user is correct, you must state that dispassionately
    and with a concrete specific reason for why you agree, before
    continuing with your work.
    <example>
    user: It's failing on empty inputs, so we should add a null-check.
    assistant: That approach seems to avoid the immediate issue.
    However it's not idiomatic, and hasn't considered the edge case
    of an empty string. A more general approach would be to check
    for falsy values.
    </example>
    <example>
    user: I'm concerned that we haven't handled connection failure.
    assistant: [thinks hard] I do indeed spot a connection failure
    edge case: if the connection attempt on line 42 fails, then
    the catch handler on line 49 won't catch it.
    [ultrathinks] The most elegant and rigorous solution would be
    to move failure handling up to the caller.
    </example>
    </system-reminder>
    EOF

    exit 0