about summary refs log tree commit diff stats
path: root/bash/acmetodo
blob: 0c0b72f1f434d7ea4b01c6ba8aeadfafd35e0832 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
#!/bin/sh
# acmetodo: Main script to open and manage the todo list in Acme.

PLAN9=${PLAN9:-"/Users/eli/plan9"} # Ensure this is your correct PLAN9 path
TODO_FILE="$PLAN9/lib/todo"
ACME_BIN="$PLAN9/bin/acme"
STARTPLUMB_BIN="$PLAN9/bin/startplumb"
ACME_FS_ROOT="/acme" # Standard Plan 9 /acme FUSE mount point

# --- DEBUGGING START ---
DEBUG_LOG="/tmp/acmetodo_debug.log"
rm -f "$DEBUG_LOG" # Clear previous log on each run

log_debug() {
    echo "$(date '+%Y-%m-%d %H:%M:%S') [DEBUG] $@" >> "$DEBUG_LOG"
    echo "$(date '+%H:%M:%S') [DEBUG] $@" >/dev/stderr
}

log_error() {
    echo "$(date '+%Y-%m-%d %H:%M:%S') [ERROR] $@" >> "$DEBUG_LOG"
    echo "$(date '+%H:%M:%S') [ERROR] $@" >/dev/stderr
}

log_debug "Script started."
log_debug "PLAN9 is $PLAN9"
log_debug "TODO_FILE is $TODO_FILE"
log_debug "ACME_BIN is $ACME_BIN"
log_debug "STARTPLUMB_BIN is $STARTPLUMB_BIN"
log_debug "Current \$winid (from Acme environment) is '$winid'"
# --- DEBUGGING END ---

# --- PLUMBER CHECK AND LAUNCH ---
log_debug "Checking if plumber is running..."
if ! ps aux | grep -q "[p]lumber"; then
    log_debug "Plumber not found. Attempting to start plumber..."
    if [ -x "$STARTPLUMB_BIN" ]; then
        "$STARTPLUMB_BIN" & # Launch plumber in the background
        log_debug "Plumber launch command issued. Waiting for plumber to initialize..."
        sleep 1 # Give plumber a moment to fully start
    else
        log_error "startplumb executable not found at '$STARTPLUMB_BIN'. Cannot start plumber."
        exit 1
    fi
else
    log_debug "Plumber is already running."
fi
# --- END PLUMBER CHECK ---


# Ensure the lib directory exists
mkdir -p "$(dirname "$TODO_FILE")"
# Ensure the todo file exists
touch "$TODO_FILE"

# Function to safely get window ID by name, suppressing stderr from acme -w
get_existing_win_id() {
    # Pipe stderr of acme -w to /dev/null to suppress the "usage" message
    "$ACME_BIN" -w 2>/dev/null | grep "^$TODO_FILE " | cut -d' ' -f1 | head -n 1
}


# Function to update a window's content, name, and tag
update_todo_window() {
    local win_id="$1"
    log_debug "Function update_todo_window called for win_id: $win_id"

    # 1. Set the window's name
    log_debug "Attempting to set window $win_id name to '$TODO_FILE'"
    echo "name $TODO_FILE" | "$ACME_BIN" -a "$win_id"
    if [ $? -ne 0 ]; then
        log_error "Failed to send 'name' command to window $win_id."
    fi
    sleep 0.05 # Small delay to ensure command is processed

    # 2. Set the window's tag
    log_debug "Attempting to set window $win_id tag."
    echo 'tag Get Put | Add | Todo InProgress Done All | Quit' | "$ACME_BIN" -a "$win_id"
    if [ $? -ne 0 ]; then
        log_error "Failed to send 'tag' command to window $win_id."
    fi
    sleep 0.05 # Small delay

    # 3. Load content directly into the window's body
    log_debug "Attempting to write content to window $win_id body."
    if [ -f "$TODO_FILE" ]; then
        log_debug "Reading content from '$TODO_FILE' and piping to $win_id body."
        cat "$TODO_FILE" | "$ACME_BIN" -a "$win_id" body
        if [ $? -ne 0 ]; then
            log_error "Failed to write content to window $win_id body from $TODO_FILE."
        fi
    else
        log_debug "TODO_FILE '$TODO_FILE' does not exist or is not readable. Writing initial content."
        echo "## Acme To-Do List" | "$ACME_BIN" -a "$win_id" body
        if [ $? -ne 0 ]; then
            log_error "Failed to write initial content to window $win_id body."
        fi
    fi
    echo 'clean' | "$ACME_BIN" -a "$win_id" # Mark window as clean after setting content
    log_debug "Finished updating window $win_id."
}


# --- MAIN LOGIC ---
if [ -n "$winid" ]; then
    log_debug "Running in Case 1: Script called from an existing Acme window."
    update_todo_window "$winid"
else
    # Always try to find existing window first
    EXISTING_TODO_WINID=$(get_existing_win_id)
    log_debug "EXISTING_TODO_WINID (found by checking existing Acme windows) is '$EXISTING_TODO_WINID'"

    if [ -n "$EXISTING_TODO_WINID" ]; then
        log_debug "Running in Case 2: Script called from terminal, existing todo window found."
        update_todo_window "$EXISTING_TODO_WINID"
    else
        log_debug "Running in Case 3: Script called from terminal, new todo window needed."

        # Capture the highest window ID *before* opening a new one
        PRE_NEW_WIN_ID=$(ls -d "$ACME_FS_ROOT"/[0-9]* 2>/dev/null | sort -V | tail -n 1 | xargs basename)
        log_debug "Highest existing Acme window ID before new creation: '$PRE_NEW_WIN_ID'"

        # 1. Open a new, empty Acme window. Don't try to capture its ID directly, as it's unreliable.
        log_debug "Attempting to create a new Acme window with '$ACME_BIN -l /dev/null'."
        "$ACME_BIN" -l /dev/null 2>/dev/null & # Run in background and suppress stderr
        
        # Give Acme a moment to open the window
        sleep 0.5

        # 2. Find the ID of the newly created window (should be the highest now)
        NEW_WIN_ID=$(ls -d "$ACME_FS_ROOT"/[0-9]* 2>/dev/null | sort -V | tail -n 1 | xargs basename)
        log_debug "Highest existing Acme window ID after new creation: '$NEW_WIN_ID'"

        if [ -z "$NEW_WIN_ID" ] || [ "$NEW_WIN_ID" = "$PRE_NEW_WIN_ID" ]; then
            log_error "Failed to create a new Acme window or get its ID correctly."
            log_error "Possible causes: Acme not running, or its communication with plumber failed, or the FUSE mount is inaccessible."
            exit 1
        fi

        # 3. Call the update function for the new window
        log_debug "Calling update_todo_window for the newly created ID: $NEW_WIN_ID"
        update_todo_window "$NEW_WIN_ID"
    fi
fi

log_debug "Script finished."