scripts: add auth management and Termux widget scripts
This commit is contained in:
committed by
Peter Steinberger
parent
8f21f34b1c
commit
6484195bfe
63
scripts/README-termux-auth.md
Normal file
63
scripts/README-termux-auth.md
Normal file
@@ -0,0 +1,63 @@
|
||||
# Clawdbot Auth Management Scripts
|
||||
|
||||
## Current Setup (Jan 2025)
|
||||
|
||||
Using `claude setup-token` for **1-year long-lived token**. No daily re-auth needed.
|
||||
|
||||
- **Token expires**: January 9, 2027
|
||||
- **Check status**: `./claude-auth-status.sh`
|
||||
|
||||
## Scripts
|
||||
|
||||
| Script | Purpose |
|
||||
|--------|---------|
|
||||
| `claude-auth-status.sh` | Check Claude Code + Clawdbot auth status |
|
||||
| `mobile-reauth.sh` | Guided re-auth (only needed annually now) |
|
||||
| `auth-monitor.sh` | Cron-able expiry monitor with notifications |
|
||||
| `termux-quick-auth.sh` | Termux widget - one-tap status check |
|
||||
| `termux-auth-widget.sh` | Termux widget - full guided re-auth flow |
|
||||
| `setup-auth-system.sh` | Interactive setup wizard |
|
||||
|
||||
## Quick Commands
|
||||
|
||||
```bash
|
||||
# Check auth status
|
||||
~/clawdbot/scripts/claude-auth-status.sh
|
||||
|
||||
# Sync Claude Code token to Clawdbot
|
||||
clawdbot doctor --yes
|
||||
|
||||
# Renew long-lived token (run in terminal, not Claude Code)
|
||||
claude setup-token
|
||||
```
|
||||
|
||||
## Termux Widget Setup (if needed)
|
||||
|
||||
1. Install Termux + Termux:Widget from F-Droid
|
||||
2. Create shortcuts dir: `mkdir -p ~/.shortcuts`
|
||||
3. Copy widget script:
|
||||
```bash
|
||||
scp l36:~/clawdbot/scripts/termux-quick-auth.sh ~/.shortcuts/ClawdAuth
|
||||
chmod +x ~/.shortcuts/ClawdAuth
|
||||
```
|
||||
4. Set server: `echo 'export CLAWDBOT_SERVER=l36' >> ~/.bashrc`
|
||||
5. Add Termux:Widget to home screen
|
||||
|
||||
## How It Works
|
||||
|
||||
1. `claude setup-token` creates a 1-year token in `~/.claude/.credentials.json`
|
||||
2. `clawdbot doctor --yes` syncs it to `~/.clawdbot/agents/main/agent/auth-profiles.json`
|
||||
3. Clawdbot uses the `anthropic:claude-cli` profile automatically
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
```bash
|
||||
# Check what's happening
|
||||
~/clawdbot/scripts/claude-auth-status.sh full
|
||||
|
||||
# Force sync from Claude Code
|
||||
clawdbot doctor --yes
|
||||
|
||||
# If token expired (annually), run in terminal:
|
||||
claude setup-token
|
||||
```
|
||||
89
scripts/auth-monitor.sh
Executable file
89
scripts/auth-monitor.sh
Executable file
@@ -0,0 +1,89 @@
|
||||
#!/bin/bash
|
||||
# Auth Expiry Monitor
|
||||
# Run via cron or systemd timer to get proactive notifications
|
||||
# before Claude Code auth expires.
|
||||
#
|
||||
# Suggested cron: */30 * * * * /home/admin/clawdbot/scripts/auth-monitor.sh
|
||||
#
|
||||
# Environment variables:
|
||||
# NOTIFY_PHONE - Phone number to send Clawdbot notification (e.g., +1234567890)
|
||||
# NOTIFY_NTFY - ntfy.sh topic for push notifications (e.g., clawdbot-alerts)
|
||||
# WARN_HOURS - Hours before expiry to warn (default: 2)
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
CLAUDE_CREDS="$HOME/.claude/.credentials.json"
|
||||
STATE_FILE="$HOME/.clawdbot/auth-monitor-state"
|
||||
|
||||
# Configuration
|
||||
WARN_HOURS="${WARN_HOURS:-2}"
|
||||
NOTIFY_PHONE="${NOTIFY_PHONE:-}"
|
||||
NOTIFY_NTFY="${NOTIFY_NTFY:-}"
|
||||
|
||||
# State tracking to avoid spam
|
||||
mkdir -p "$(dirname "$STATE_FILE")"
|
||||
LAST_NOTIFIED=$(cat "$STATE_FILE" 2>/dev/null || echo "0")
|
||||
NOW=$(date +%s)
|
||||
|
||||
# Only notify once per hour max
|
||||
MIN_INTERVAL=3600
|
||||
|
||||
send_notification() {
|
||||
local message="$1"
|
||||
local priority="${2:-default}"
|
||||
|
||||
echo "$(date '+%Y-%m-%d %H:%M:%S') - $message"
|
||||
|
||||
# Check if we notified recently
|
||||
if [ $((NOW - LAST_NOTIFIED)) -lt $MIN_INTERVAL ]; then
|
||||
echo "Skipping notification (sent recently)"
|
||||
return
|
||||
fi
|
||||
|
||||
# Send via Clawdbot if phone configured and auth still valid
|
||||
if [ -n "$NOTIFY_PHONE" ]; then
|
||||
# Check if we can still use clawdbot
|
||||
if "$SCRIPT_DIR/claude-auth-status.sh" simple 2>/dev/null | grep -q "OK\|EXPIRING"; then
|
||||
echo "Sending via Clawdbot to $NOTIFY_PHONE..."
|
||||
clawdbot send --to "$NOTIFY_PHONE" --message "$message" 2>/dev/null || true
|
||||
fi
|
||||
fi
|
||||
|
||||
# Send via ntfy.sh if configured
|
||||
if [ -n "$NOTIFY_NTFY" ]; then
|
||||
echo "Sending via ntfy.sh to $NOTIFY_NTFY..."
|
||||
curl -s -o /dev/null \
|
||||
-H "Title: Clawdbot Auth Alert" \
|
||||
-H "Priority: $priority" \
|
||||
-H "Tags: warning,key" \
|
||||
-d "$message" \
|
||||
"https://ntfy.sh/$NOTIFY_NTFY" || true
|
||||
fi
|
||||
|
||||
# Update state
|
||||
echo "$NOW" > "$STATE_FILE"
|
||||
}
|
||||
|
||||
# Check auth status
|
||||
if [ ! -f "$CLAUDE_CREDS" ]; then
|
||||
send_notification "Claude Code credentials missing! Run: claude setup-token" "high"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
EXPIRES_AT=$(jq -r '.claudeAiOauth.expiresAt // 0' "$CLAUDE_CREDS")
|
||||
NOW_MS=$((NOW * 1000))
|
||||
DIFF_MS=$((EXPIRES_AT - NOW_MS))
|
||||
HOURS_LEFT=$((DIFF_MS / 3600000))
|
||||
MINS_LEFT=$(((DIFF_MS % 3600000) / 60000))
|
||||
|
||||
if [ "$DIFF_MS" -lt 0 ]; then
|
||||
send_notification "Claude Code auth EXPIRED! Clawdbot is down. Run: ssh l36 '~/clawdbot/scripts/mobile-reauth.sh'" "urgent"
|
||||
exit 1
|
||||
elif [ "$HOURS_LEFT" -lt "$WARN_HOURS" ]; then
|
||||
send_notification "Claude Code auth expires in ${HOURS_LEFT}h ${MINS_LEFT}m. Consider re-auth soon." "high"
|
||||
exit 0
|
||||
else
|
||||
echo "$(date '+%Y-%m-%d %H:%M:%S') - Auth OK: ${HOURS_LEFT}h ${MINS_LEFT}m remaining"
|
||||
exit 0
|
||||
fi
|
||||
194
scripts/claude-auth-status.sh
Executable file
194
scripts/claude-auth-status.sh
Executable file
@@ -0,0 +1,194 @@
|
||||
#!/bin/bash
|
||||
# Claude Code Authentication Status Checker
|
||||
# Checks both Claude Code and Clawdbot auth status
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
CLAUDE_CREDS="$HOME/.claude/.credentials.json"
|
||||
CLAWDBOT_AUTH="$HOME/.clawdbot/agents/main/agent/auth-profiles.json"
|
||||
|
||||
# Colors for terminal output
|
||||
RED='\033[0;31m'
|
||||
YELLOW='\033[1;33m'
|
||||
GREEN='\033[0;32m'
|
||||
NC='\033[0m' # No Color
|
||||
|
||||
# Output mode: "full" (default), "json", or "simple"
|
||||
OUTPUT_MODE="${1:-full}"
|
||||
|
||||
check_claude_code_auth() {
|
||||
if [ ! -f "$CLAUDE_CREDS" ]; then
|
||||
echo "MISSING"
|
||||
return 1
|
||||
fi
|
||||
|
||||
local expires_at
|
||||
expires_at=$(jq -r '.claudeAiOauth.expiresAt // 0' "$CLAUDE_CREDS")
|
||||
local now_ms=$(($(date +%s) * 1000))
|
||||
local diff_ms=$((expires_at - now_ms))
|
||||
local hours=$((diff_ms / 3600000))
|
||||
local mins=$(((diff_ms % 3600000) / 60000))
|
||||
|
||||
if [ "$diff_ms" -lt 0 ]; then
|
||||
echo "EXPIRED"
|
||||
return 1
|
||||
elif [ "$diff_ms" -lt 3600000 ]; then
|
||||
echo "EXPIRING:${mins}m"
|
||||
return 2
|
||||
else
|
||||
echo "OK:${hours}h${mins}m"
|
||||
return 0
|
||||
fi
|
||||
}
|
||||
|
||||
check_clawdbot_auth() {
|
||||
if [ ! -f "$CLAWDBOT_AUTH" ]; then
|
||||
echo "MISSING"
|
||||
return 1
|
||||
fi
|
||||
|
||||
# Find the best Anthropic profile (prefer claude-cli, then any with latest expiry)
|
||||
local expires
|
||||
expires=$(jq -r '
|
||||
[.profiles | to_entries[] | select(.value.provider == "anthropic") | .value.expires]
|
||||
| max // 0
|
||||
' "$CLAWDBOT_AUTH")
|
||||
|
||||
local now_ms=$(($(date +%s) * 1000))
|
||||
local diff_ms=$((expires - now_ms))
|
||||
local hours=$((diff_ms / 3600000))
|
||||
local mins=$(((diff_ms % 3600000) / 60000))
|
||||
|
||||
if [ "$diff_ms" -lt 0 ]; then
|
||||
echo "EXPIRED"
|
||||
return 1
|
||||
elif [ "$diff_ms" -lt 3600000 ]; then
|
||||
echo "EXPIRING:${mins}m"
|
||||
return 2
|
||||
else
|
||||
echo "OK:${hours}h${mins}m"
|
||||
return 0
|
||||
fi
|
||||
}
|
||||
|
||||
# JSON output mode
|
||||
if [ "$OUTPUT_MODE" = "json" ]; then
|
||||
claude_status=$(check_claude_code_auth 2>/dev/null || true)
|
||||
clawdbot_status=$(check_clawdbot_auth 2>/dev/null || true)
|
||||
|
||||
claude_expires=$(jq -r '.claudeAiOauth.expiresAt // 0' "$CLAUDE_CREDS" 2>/dev/null || echo "0")
|
||||
clawdbot_expires=$(jq -r '.profiles["anthropic:default"].expires // 0' "$CLAWDBOT_AUTH" 2>/dev/null || echo "0")
|
||||
|
||||
jq -n \
|
||||
--arg cs "$claude_status" \
|
||||
--arg ce "$claude_expires" \
|
||||
--arg bs "$clawdbot_status" \
|
||||
--arg be "$clawdbot_expires" \
|
||||
'{
|
||||
claude_code: {status: $cs, expires_at_ms: ($ce | tonumber)},
|
||||
clawdbot: {status: $bs, expires_at_ms: ($be | tonumber)},
|
||||
needs_reauth: (($cs | startswith("EXPIRED") or startswith("EXPIRING") or startswith("MISSING")) or ($bs | startswith("EXPIRED") or startswith("EXPIRING") or startswith("MISSING")))
|
||||
}'
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Simple output mode (for scripts/widgets)
|
||||
if [ "$OUTPUT_MODE" = "simple" ]; then
|
||||
claude_status=$(check_claude_code_auth 2>/dev/null || true)
|
||||
clawdbot_status=$(check_clawdbot_auth 2>/dev/null || true)
|
||||
|
||||
if [[ "$claude_status" == EXPIRED* ]] || [[ "$claude_status" == MISSING* ]]; then
|
||||
echo "CLAUDE_EXPIRED"
|
||||
exit 1
|
||||
elif [[ "$clawdbot_status" == EXPIRED* ]] || [[ "$clawdbot_status" == MISSING* ]]; then
|
||||
echo "CLAWDBOT_EXPIRED"
|
||||
exit 1
|
||||
elif [[ "$claude_status" == EXPIRING* ]]; then
|
||||
echo "CLAUDE_EXPIRING"
|
||||
exit 2
|
||||
elif [[ "$clawdbot_status" == EXPIRING* ]]; then
|
||||
echo "CLAWDBOT_EXPIRING"
|
||||
exit 2
|
||||
else
|
||||
echo "OK"
|
||||
exit 0
|
||||
fi
|
||||
fi
|
||||
|
||||
# Full output mode (default)
|
||||
echo "=== Claude Code Auth Status ==="
|
||||
echo ""
|
||||
|
||||
# Claude Code credentials
|
||||
echo "Claude Code (~/.claude/.credentials.json):"
|
||||
if [ -f "$CLAUDE_CREDS" ]; then
|
||||
expires_at=$(jq -r '.claudeAiOauth.expiresAt // 0' "$CLAUDE_CREDS")
|
||||
sub_type=$(jq -r '.claudeAiOauth.subscriptionType // "unknown"' "$CLAUDE_CREDS")
|
||||
rate_tier=$(jq -r '.claudeAiOauth.rateLimitTier // "unknown"' "$CLAUDE_CREDS")
|
||||
|
||||
now_ms=$(($(date +%s) * 1000))
|
||||
diff_ms=$((expires_at - now_ms))
|
||||
hours=$((diff_ms / 3600000))
|
||||
mins=$(((diff_ms % 3600000) / 60000))
|
||||
|
||||
echo " Subscription: $sub_type"
|
||||
echo " Rate tier: $rate_tier"
|
||||
|
||||
if [ "$diff_ms" -lt 0 ]; then
|
||||
echo -e " Status: ${RED}EXPIRED${NC}"
|
||||
echo " Action needed: Run 'claude setup-token' or re-authenticate"
|
||||
elif [ "$diff_ms" -lt 3600000 ]; then
|
||||
echo -e " Status: ${YELLOW}EXPIRING SOON (${mins}m remaining)${NC}"
|
||||
echo " Consider running: claude setup-token"
|
||||
else
|
||||
echo -e " Status: ${GREEN}OK${NC}"
|
||||
echo " Expires: $(date -d @$((expires_at/1000))) (${hours}h ${mins}m)"
|
||||
fi
|
||||
else
|
||||
echo -e " Status: ${RED}NOT FOUND${NC}"
|
||||
echo " Action needed: Run 'claude setup-token'"
|
||||
fi
|
||||
|
||||
echo ""
|
||||
echo "Clawdbot Auth (~/.clawdbot/agents/main/agent/auth-profiles.json):"
|
||||
if [ -f "$CLAWDBOT_AUTH" ]; then
|
||||
# Find best Anthropic profile
|
||||
best_profile=$(jq -r '
|
||||
.profiles | to_entries
|
||||
| map(select(.value.provider == "anthropic"))
|
||||
| sort_by(.value.expires) | reverse
|
||||
| .[0].key // "none"
|
||||
' "$CLAWDBOT_AUTH")
|
||||
|
||||
expires=$(jq -r '
|
||||
[.profiles | to_entries[] | select(.value.provider == "anthropic") | .value.expires]
|
||||
| max // 0
|
||||
' "$CLAWDBOT_AUTH")
|
||||
|
||||
now_ms=$(($(date +%s) * 1000))
|
||||
diff_ms=$((expires - now_ms))
|
||||
hours=$((diff_ms / 3600000))
|
||||
mins=$(((diff_ms % 3600000) / 60000))
|
||||
|
||||
echo " Profile: $best_profile"
|
||||
|
||||
if [ "$diff_ms" -lt 0 ]; then
|
||||
echo -e " Status: ${RED}EXPIRED${NC}"
|
||||
echo " Note: Run 'clawdbot doctor --yes' to sync from Claude Code"
|
||||
elif [ "$diff_ms" -lt 3600000 ]; then
|
||||
echo -e " Status: ${YELLOW}EXPIRING SOON (${mins}m remaining)${NC}"
|
||||
else
|
||||
echo -e " Status: ${GREEN}OK${NC}"
|
||||
echo " Expires: $(date -d @$((expires/1000))) (${hours}h ${mins}m)"
|
||||
fi
|
||||
else
|
||||
echo -e " Status: ${RED}NOT FOUND${NC}"
|
||||
fi
|
||||
|
||||
echo ""
|
||||
echo "=== Service Status ==="
|
||||
if systemctl --user is-active clawdbot >/dev/null 2>&1; then
|
||||
echo -e "Clawdbot service: ${GREEN}running${NC}"
|
||||
else
|
||||
echo -e "Clawdbot service: ${RED}NOT running${NC}"
|
||||
fi
|
||||
84
scripts/mobile-reauth.sh
Executable file
84
scripts/mobile-reauth.sh
Executable file
@@ -0,0 +1,84 @@
|
||||
#!/bin/bash
|
||||
# Mobile-friendly Claude Code re-authentication
|
||||
# Designed for use via SSH from Termux
|
||||
#
|
||||
# This script handles the authentication flow in a way that works
|
||||
# from a mobile device by:
|
||||
# 1. Checking if auth is needed
|
||||
# 2. Running claude setup-token for long-lived auth
|
||||
# 3. Outputting URLs that can be easily opened on phone
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
|
||||
# Colors
|
||||
RED='\033[0;31m'
|
||||
GREEN='\033[0;32m'
|
||||
YELLOW='\033[1;33m'
|
||||
CYAN='\033[0;36m'
|
||||
NC='\033[0m'
|
||||
|
||||
echo "=== Claude Code Mobile Re-Auth ==="
|
||||
echo ""
|
||||
|
||||
# Check current auth status
|
||||
echo "Checking auth status..."
|
||||
AUTH_STATUS=$("$SCRIPT_DIR/claude-auth-status.sh" simple 2>/dev/null || echo "ERROR")
|
||||
|
||||
case "$AUTH_STATUS" in
|
||||
OK)
|
||||
echo -e "${GREEN}Auth is valid!${NC}"
|
||||
"$SCRIPT_DIR/claude-auth-status.sh" full
|
||||
exit 0
|
||||
;;
|
||||
CLAUDE_EXPIRING|CLAWDBOT_EXPIRING)
|
||||
echo -e "${YELLOW}Auth is expiring soon.${NC}"
|
||||
echo ""
|
||||
;;
|
||||
*)
|
||||
echo -e "${RED}Auth needs refresh.${NC}"
|
||||
echo ""
|
||||
;;
|
||||
esac
|
||||
|
||||
echo "Starting long-lived token setup..."
|
||||
echo ""
|
||||
echo -e "${CYAN}Instructions:${NC}"
|
||||
echo "1. Open this URL on your phone:"
|
||||
echo ""
|
||||
echo -e " ${CYAN}https://console.anthropic.com/settings/api-keys${NC}"
|
||||
echo ""
|
||||
echo "2. Sign in if needed"
|
||||
echo "3. Create a new API key or use existing 'Claude Code' key"
|
||||
echo "4. Copy the key (starts with sk-ant-...)"
|
||||
echo "5. When prompted below, paste the key"
|
||||
echo ""
|
||||
echo "Press Enter when ready to continue..."
|
||||
read -r
|
||||
|
||||
# Run setup-token interactively
|
||||
echo ""
|
||||
echo "Running 'claude setup-token'..."
|
||||
echo "(Follow the prompts and paste your API key when asked)"
|
||||
echo ""
|
||||
|
||||
if claude setup-token; then
|
||||
echo ""
|
||||
echo -e "${GREEN}Authentication successful!${NC}"
|
||||
echo ""
|
||||
"$SCRIPT_DIR/claude-auth-status.sh" full
|
||||
|
||||
# Restart clawdbot service if running
|
||||
if systemctl --user is-active clawdbot >/dev/null 2>&1; then
|
||||
echo ""
|
||||
echo "Restarting clawdbot service..."
|
||||
systemctl --user restart clawdbot
|
||||
echo -e "${GREEN}Service restarted.${NC}"
|
||||
fi
|
||||
else
|
||||
echo ""
|
||||
echo -e "${RED}Authentication failed.${NC}"
|
||||
echo "Please try again or check the Claude Code documentation."
|
||||
exit 1
|
||||
fi
|
||||
119
scripts/setup-auth-system.sh
Executable file
119
scripts/setup-auth-system.sh
Executable file
@@ -0,0 +1,119 @@
|
||||
#!/bin/bash
|
||||
# Setup Clawdbot Auth Management System
|
||||
# Run this once to set up:
|
||||
# 1. Long-lived Claude Code token
|
||||
# 2. Auth monitoring with notifications
|
||||
# 3. Instructions for Termux widgets
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
|
||||
echo "=== Clawdbot Auth System Setup ==="
|
||||
echo ""
|
||||
|
||||
# Step 1: Check current auth status
|
||||
echo "Step 1: Checking current auth status..."
|
||||
"$SCRIPT_DIR/claude-auth-status.sh" full || true
|
||||
echo ""
|
||||
|
||||
# Step 2: Set up long-lived token
|
||||
echo "Step 2: Long-lived token setup"
|
||||
echo ""
|
||||
echo "Option A: Use 'claude setup-token' (recommended)"
|
||||
echo " - Creates a long-lived API token"
|
||||
echo " - No daily re-auth needed"
|
||||
echo " - Run: claude setup-token"
|
||||
echo ""
|
||||
echo "Would you like to set up a long-lived token now? [y/N]"
|
||||
read -r SETUP_TOKEN
|
||||
|
||||
if [[ "$SETUP_TOKEN" =~ ^[Yy] ]]; then
|
||||
echo ""
|
||||
echo "Opening https://console.anthropic.com/settings/api-keys"
|
||||
echo "Create a new key or copy existing one, then paste below."
|
||||
echo ""
|
||||
claude setup-token
|
||||
fi
|
||||
|
||||
echo ""
|
||||
|
||||
# Step 3: Set up auth monitoring
|
||||
echo "Step 3: Auth monitoring setup"
|
||||
echo ""
|
||||
echo "The auth monitor checks expiry every 30 minutes and notifies you."
|
||||
echo ""
|
||||
echo "Configure notification channels:"
|
||||
echo ""
|
||||
|
||||
# Check for ntfy
|
||||
echo " ntfy.sh: Free push notifications to your phone"
|
||||
echo " 1. Install ntfy app on your phone"
|
||||
echo " 2. Subscribe to a topic (e.g., 'clawdbot-alerts')"
|
||||
echo ""
|
||||
echo "Enter ntfy.sh topic (or leave blank to skip):"
|
||||
read -r NTFY_TOPIC
|
||||
|
||||
# Phone notification
|
||||
echo ""
|
||||
echo " Clawdbot message: Send warning via Clawdbot itself"
|
||||
echo "Enter your phone number for alerts (or leave blank to skip):"
|
||||
read -r PHONE_NUMBER
|
||||
|
||||
# Update service file
|
||||
SERVICE_FILE="$SCRIPT_DIR/systemd/clawdbot-auth-monitor.service"
|
||||
if [ -n "$NTFY_TOPIC" ]; then
|
||||
sed -i "s|# Environment=NOTIFY_NTFY=.*|Environment=NOTIFY_NTFY=$NTFY_TOPIC|" "$SERVICE_FILE"
|
||||
fi
|
||||
if [ -n "$PHONE_NUMBER" ]; then
|
||||
sed -i "s|# Environment=NOTIFY_PHONE=.*|Environment=NOTIFY_PHONE=$PHONE_NUMBER|" "$SERVICE_FILE"
|
||||
fi
|
||||
|
||||
# Install systemd units
|
||||
echo ""
|
||||
echo "Installing systemd timer..."
|
||||
mkdir -p ~/.config/systemd/user
|
||||
cp "$SCRIPT_DIR/systemd/clawdbot-auth-monitor.service" ~/.config/systemd/user/
|
||||
cp "$SCRIPT_DIR/systemd/clawdbot-auth-monitor.timer" ~/.config/systemd/user/
|
||||
systemctl --user daemon-reload
|
||||
systemctl --user enable --now clawdbot-auth-monitor.timer
|
||||
|
||||
echo "Auth monitor installed and running."
|
||||
echo ""
|
||||
|
||||
# Step 4: Termux widget setup
|
||||
echo "Step 4: Termux widget setup (for phone)"
|
||||
echo ""
|
||||
echo "To set up quick auth from your phone:"
|
||||
echo ""
|
||||
echo "1. Install Termux and Termux:Widget from F-Droid"
|
||||
echo "2. Create ~/.shortcuts/ directory in Termux:"
|
||||
echo " mkdir -p ~/.shortcuts"
|
||||
echo ""
|
||||
echo "3. Copy the widget scripts:"
|
||||
echo " scp $SCRIPT_DIR/termux-quick-auth.sh phone:~/.shortcuts/ClawdAuth"
|
||||
echo " scp $SCRIPT_DIR/termux-auth-widget.sh phone:~/.shortcuts/ClawdAuth-Full"
|
||||
echo ""
|
||||
echo "4. Make them executable on phone:"
|
||||
echo " ssh phone 'chmod +x ~/.shortcuts/Clawd*'"
|
||||
echo ""
|
||||
echo "5. Add Termux:Widget to your home screen"
|
||||
echo "6. Tap the widget to see your auth scripts"
|
||||
echo ""
|
||||
echo "The quick widget (ClawdAuth) shows status and opens auth URL if needed."
|
||||
echo "The full widget (ClawdAuth-Full) provides guided re-auth flow."
|
||||
echo ""
|
||||
|
||||
# Summary
|
||||
echo "=== Setup Complete ==="
|
||||
echo ""
|
||||
echo "What's configured:"
|
||||
echo " - Auth status: $SCRIPT_DIR/claude-auth-status.sh"
|
||||
echo " - Mobile re-auth: $SCRIPT_DIR/mobile-reauth.sh"
|
||||
echo " - Auth monitor: systemctl --user status clawdbot-auth-monitor.timer"
|
||||
echo ""
|
||||
echo "Quick commands:"
|
||||
echo " Check auth: $SCRIPT_DIR/claude-auth-status.sh"
|
||||
echo " Re-auth: $SCRIPT_DIR/mobile-reauth.sh"
|
||||
echo " Test monitor: $SCRIPT_DIR/auth-monitor.sh"
|
||||
echo ""
|
||||
14
scripts/systemd/clawdbot-auth-monitor.service
Normal file
14
scripts/systemd/clawdbot-auth-monitor.service
Normal file
@@ -0,0 +1,14 @@
|
||||
[Unit]
|
||||
Description=Clawdbot Auth Expiry Monitor
|
||||
After=network.target
|
||||
|
||||
[Service]
|
||||
Type=oneshot
|
||||
ExecStart=/home/admin/clawdbot/scripts/auth-monitor.sh
|
||||
# Configure notification channels via environment
|
||||
Environment=WARN_HOURS=2
|
||||
# Environment=NOTIFY_PHONE=+1234567890
|
||||
# Environment=NOTIFY_NTFY=clawdbot-alerts
|
||||
|
||||
[Install]
|
||||
WantedBy=default.target
|
||||
10
scripts/systemd/clawdbot-auth-monitor.timer
Normal file
10
scripts/systemd/clawdbot-auth-monitor.timer
Normal file
@@ -0,0 +1,10 @@
|
||||
[Unit]
|
||||
Description=Check Clawdbot auth expiry every 30 minutes
|
||||
|
||||
[Timer]
|
||||
OnBootSec=5min
|
||||
OnUnitActiveSec=30min
|
||||
Persistent=true
|
||||
|
||||
[Install]
|
||||
WantedBy=timers.target
|
||||
81
scripts/termux-auth-widget.sh
Normal file
81
scripts/termux-auth-widget.sh
Normal file
@@ -0,0 +1,81 @@
|
||||
#!/data/data/com.termux/files/usr/bin/bash
|
||||
# Clawdbot Auth Widget for Termux
|
||||
# Place in ~/.shortcuts/ for Termux:Widget
|
||||
#
|
||||
# This widget checks auth status and helps with re-auth if needed.
|
||||
# It's designed for quick one-tap checking from phone home screen.
|
||||
|
||||
# Server hostname (via Tailscale or SSH config)
|
||||
SERVER="${CLAWDBOT_SERVER:-l36}"
|
||||
|
||||
# Check auth status
|
||||
termux-toast "Checking Clawdbot auth..."
|
||||
|
||||
STATUS=$(ssh "$SERVER" '$HOME/clawdbot/scripts/claude-auth-status.sh simple' 2>&1)
|
||||
EXIT_CODE=$?
|
||||
|
||||
case "$STATUS" in
|
||||
OK)
|
||||
# Get remaining time
|
||||
DETAILS=$(ssh "$SERVER" '$HOME/clawdbot/scripts/claude-auth-status.sh json' 2>&1)
|
||||
HOURS=$(echo "$DETAILS" | jq -r '.claude_code.status' | grep -oP '\d+(?=h)' || echo "?")
|
||||
|
||||
termux-vibrate -d 50
|
||||
termux-toast "Auth OK (${HOURS}h left)"
|
||||
;;
|
||||
|
||||
CLAUDE_EXPIRING|CLAWDBOT_EXPIRING)
|
||||
termux-vibrate -d 100
|
||||
|
||||
# Ask if user wants to re-auth now
|
||||
CHOICE=$(termux-dialog radio -t "Auth Expiring Soon" -v "Re-auth now,Check later,Dismiss")
|
||||
SELECTED=$(echo "$CHOICE" | jq -r '.text // "Dismiss"')
|
||||
|
||||
case "$SELECTED" in
|
||||
"Re-auth now")
|
||||
termux-toast "Opening auth page..."
|
||||
termux-open-url "https://console.anthropic.com/settings/api-keys"
|
||||
|
||||
# Show instructions
|
||||
termux-dialog confirm -t "Re-auth Instructions" -i "1. Create/copy API key from browser
|
||||
2. Return here and tap OK
|
||||
3. SSH to server and paste key"
|
||||
|
||||
# Open terminal to server
|
||||
am start -n com.termux/com.termux.app.TermuxActivity -a android.intent.action.MAIN
|
||||
termux-toast "Run: ssh $SERVER '$HOME/clawdbot/scripts/mobile-reauth.sh'"
|
||||
;;
|
||||
*)
|
||||
termux-toast "Reminder: Auth expires soon"
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
|
||||
CLAUDE_EXPIRED|CLAWDBOT_EXPIRED)
|
||||
termux-vibrate -d 300
|
||||
|
||||
CHOICE=$(termux-dialog radio -t "Auth Expired!" -v "Re-auth now,Dismiss")
|
||||
SELECTED=$(echo "$CHOICE" | jq -r '.text // "Dismiss"')
|
||||
|
||||
case "$SELECTED" in
|
||||
"Re-auth now")
|
||||
termux-toast "Opening auth page..."
|
||||
termux-open-url "https://console.anthropic.com/settings/api-keys"
|
||||
|
||||
termux-dialog confirm -t "Re-auth Steps" -i "1. Create/copy API key from browser
|
||||
2. Return here and tap OK to SSH"
|
||||
|
||||
am start -n com.termux/com.termux.app.TermuxActivity -a android.intent.action.MAIN
|
||||
termux-toast "Run: ssh $SERVER '$HOME/clawdbot/scripts/mobile-reauth.sh'"
|
||||
;;
|
||||
*)
|
||||
termux-toast "Warning: Clawdbot won't work until re-auth"
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
|
||||
*)
|
||||
termux-vibrate -d 200
|
||||
termux-toast "Error: $STATUS"
|
||||
;;
|
||||
esac
|
||||
30
scripts/termux-quick-auth.sh
Normal file
30
scripts/termux-quick-auth.sh
Normal file
@@ -0,0 +1,30 @@
|
||||
#!/data/data/com.termux/files/usr/bin/bash
|
||||
# Quick Auth Check - Minimal widget for Termux
|
||||
# Place in ~/.shortcuts/ for Termux:Widget
|
||||
#
|
||||
# One-tap: shows status toast
|
||||
# If expired: directly opens auth URL
|
||||
|
||||
SERVER="${CLAWDBOT_SERVER:-l36}"
|
||||
|
||||
STATUS=$(ssh -o ConnectTimeout=5 "$SERVER" '$HOME/clawdbot/scripts/claude-auth-status.sh simple' 2>&1)
|
||||
|
||||
case "$STATUS" in
|
||||
OK)
|
||||
termux-toast -s "Auth OK"
|
||||
;;
|
||||
*EXPIRING*)
|
||||
termux-vibrate -d 100
|
||||
termux-toast "Auth expiring soon - tap again if needed"
|
||||
;;
|
||||
*EXPIRED*|*MISSING*)
|
||||
termux-vibrate -d 200
|
||||
termux-toast "Auth expired - opening console..."
|
||||
termux-open-url "https://console.anthropic.com/settings/api-keys"
|
||||
sleep 2
|
||||
termux-notification -t "Clawdbot Re-Auth" -c "After getting key, run: ssh $SERVER '~/clawdbot/scripts/mobile-reauth.sh'" --id clawd-auth
|
||||
;;
|
||||
*)
|
||||
termux-toast "Connection error"
|
||||
;;
|
||||
esac
|
||||
24
scripts/termux-sync-widget.sh
Normal file
24
scripts/termux-sync-widget.sh
Normal file
@@ -0,0 +1,24 @@
|
||||
#!/data/data/com.termux/files/usr/bin/bash
|
||||
# Clawdbot OAuth Sync Widget
|
||||
# Syncs Claude Code tokens to Clawdbot on l36 server
|
||||
# Place in ~/.shortcuts/ on phone for Termux:Widget
|
||||
|
||||
termux-toast "Syncing Clawdbot auth..."
|
||||
|
||||
# Run sync on l36 server
|
||||
RESULT=$(ssh l36 '/home/admin/clawdbot/scripts/sync-claude-code-auth.sh' 2>&1)
|
||||
EXIT_CODE=$?
|
||||
|
||||
if [ $EXIT_CODE -eq 0 ]; then
|
||||
# Extract expiry time from output
|
||||
EXPIRY=$(echo "$RESULT" | grep "Token expires:" | cut -d: -f2-)
|
||||
|
||||
termux-vibrate -d 100
|
||||
termux-toast "Clawdbot synced! Expires:${EXPIRY}"
|
||||
|
||||
# Optional: restart clawdbot service
|
||||
ssh l36 'systemctl --user restart clawdbot' 2>/dev/null
|
||||
else
|
||||
termux-vibrate -d 300
|
||||
termux-toast "Sync failed: ${RESULT}"
|
||||
fi
|
||||
Reference in New Issue
Block a user