Skip to content

Commit 5505064

Browse files
duyetclaudeduyetbot
committed
fix(ralph-wiggum): remove associative arrays for bash compatibility
Replaced declare -A associative arrays with simple string-based keyword:score format. This fixes "unbound variable" errors on older bash versions when using set -u with associative arrays. Also changed from set -euo to set -eo to avoid nounset issues. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> Co-Authored-By: duyetbot <duyetbot@users.noreply.github.com>
1 parent 282a542 commit 5505064

1 file changed

Lines changed: 26 additions & 24 deletions

File tree

ralph-wiggum/lib/response_analyzer.sh

Lines changed: 26 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -3,25 +3,20 @@
33
# Response Analyzer for Ralph Wiggum
44
# Intelligent exit detection through semantic analysis of Claude's responses
55

6-
set -euo pipefail
6+
set -eo pipefail
77

88
ANALYSIS_STATE_FILE="${RALPH_STATE_DIR:-.claude}/ralph-analysis.json"
99
COMPLETION_CONFIDENCE_THRESHOLD=${RALPH_COMPLETION_THRESHOLD:-40}
1010
MAX_TEST_ONLY_LOOPS=${RALPH_MAX_TEST_ONLY:-5}
1111
MAX_STUCK_LOOPS=${RALPH_MAX_STUCK:-3}
1212

13-
declare -A COMPLETION_KEYWORDS=(
14-
["done"]=10 ["complete"]=15 ["completed"]=15 ["finished"]=12
15-
["success"]=10 ["successful"]=10 ["all tests pass"]=20
16-
["tests passing"]=18 ["implementation complete"]=20
17-
["task complete"]=20 ["project complete"]=25
18-
["ready for review"]=15 ["ready to deploy"]=15
19-
)
13+
# Completion keywords and their confidence scores (keyword:score format)
14+
COMPLETION_KEYWORDS="done:10 complete:15 completed:15 finished:12 success:10 successful:10"
15+
COMPLETION_KEYWORDS="$COMPLETION_KEYWORDS all_tests_pass:20 tests_passing:18 implementation_complete:20"
16+
COMPLETION_KEYWORDS="$COMPLETION_KEYWORDS task_complete:20 project_complete:25 ready_for_review:15 ready_to_deploy:15"
2017

21-
declare -A STUCK_KEYWORDS=(
22-
["stuck"]=1 ["blocked"]=1 ["cannot proceed"]=1 ["unable to"]=1
23-
["failed repeatedly"]=1 ["same error"]=1 ["infinite loop"]=1 ["going in circles"]=1
24-
)
18+
# Stuck keywords (presence indicates stuck state)
19+
STUCK_KEYWORDS="stuck blocked cannot_proceed unable_to failed_repeatedly same_error infinite_loop going_in_circles"
2520

2621
init_response_analyzer() {
2722
[[ -f "$ANALYSIS_STATE_FILE" ]] && return
@@ -47,20 +42,25 @@ detect_completion_signals() {
4742
local output="$1"
4843
local output_lower=$(echo "$output" | tr '[:upper:]' '[:lower:]')
4944
local confidence=0
50-
local signals_found=()
51-
52-
for keyword in "${!COMPLETION_KEYWORDS[@]}"; do
53-
if echo "$output_lower" | grep -qi "$keyword"; then
54-
((confidence += ${COMPLETION_KEYWORDS[$keyword]})) || true
55-
signals_found+=("$keyword")
45+
local signals_found=""
46+
47+
# Parse keyword:score pairs
48+
for pair in $COMPLETION_KEYWORDS; do
49+
local keyword="${pair%:*}"
50+
local score="${pair#*:}"
51+
# Convert underscores to spaces for matching
52+
local search_term="${keyword//_/ }"
53+
if echo "$output_lower" | grep -qi "$search_term"; then
54+
((confidence += score)) || true
55+
signals_found="${signals_found:+$signals_found,}$keyword"
5656
fi
5757
done
5858

59-
echo "$output" | grep -q "---RALPH_STATUS---" && { ((confidence += 15)) || true; signals_found+=("structured_status"); }
60-
echo "$output" | grep -qE '\[DONE\]|\[COMPLETE\]|\[FINISHED\]' && { ((confidence += 20)) || true; signals_found+=("explicit_marker"); }
59+
echo "$output" | grep -q "---RALPH_STATUS---" && { ((confidence += 15)) || true; signals_found="${signals_found:+$signals_found,}structured_status"; }
60+
echo "$output" | grep -qE '\[DONE\]|\[COMPLETE\]|\[FINISHED\]' && { ((confidence += 20)) || true; signals_found="${signals_found:+$signals_found,}explicit_marker"; }
6161

62-
jq -n --argjson confidence "$confidence" --arg signals "$(IFS=,; echo "${signals_found[*]}")" \
63-
'{confidence: $confidence, signals: ($signals | split(","))}'
62+
jq -n --argjson confidence "$confidence" --arg signals "$signals_found" \
63+
'{confidence: $confidence, signals: (if $signals == "" then [] else ($signals | split(",")) end)}'
6464
}
6565

6666
detect_test_only_loop() {
@@ -85,8 +85,10 @@ detect_stuck_state() {
8585
local output_lower=$(echo "$output" | tr '[:upper:]' '[:lower:]')
8686
local stuck_count=0
8787

88-
for keyword in "${!STUCK_KEYWORDS[@]}"; do
89-
echo "$output_lower" | grep -qi "$keyword" && ((stuck_count++)) || true
88+
for keyword in $STUCK_KEYWORDS; do
89+
# Convert underscores to spaces for matching
90+
local search_term="${keyword//_/ }"
91+
echo "$output_lower" | grep -qi "$search_term" && ((stuck_count++)) || true
9092
done
9193

9294
local error_mentions=$(echo "$output_lower" | grep -c "error\|failed\|exception" || echo "0")

0 commit comments

Comments
 (0)