fix(deploy): resolve SQL timeouts, YAML drift, and orphaned tmux sessions
- lib.sh: update atomic_dump_yaml to sync with YAML on any active session status change; set reader timeouts to 60.0s - create_session.sh: add exit trap cleanup_tmux_on_error to rollback spawned tmux sessions on initialization failures - reconcile.sh, update_yaml_resumed.sh, status.sh, stop_session.sh: align SQLite connection timeout values to 60.0s
This commit is contained in:
+11
-9
@@ -115,7 +115,7 @@ yaml_path = os.environ['YAML_PATH']
|
||||
db_path = os.path.splitext(yaml_path)[0] + '.db'
|
||||
try:
|
||||
if os.path.exists(db_path):
|
||||
conn = sqlite3.connect(db_path, timeout=10.0)
|
||||
conn = sqlite3.connect(db_path, timeout=60.0)
|
||||
try:
|
||||
row = conn.execute('SELECT data FROM sessions WHERE name=?', (name,)).fetchone()
|
||||
if row:
|
||||
@@ -315,6 +315,9 @@ def _validate(d):
|
||||
def get_terminal_set(d):
|
||||
return {s.get('name'): s.get('status') for s in d.get('tmux_sessions', []) if s.get('status') in ('stopped', 'terminated', 'archived')}
|
||||
|
||||
def get_all_sessions_status(d):
|
||||
return {s.get('name'): s.get('status') for s in d.get('tmux_sessions', [])}
|
||||
|
||||
os.makedirs(os.path.dirname(db_path) or '.', exist_ok=True)
|
||||
conn = sqlite3.connect(db_path, timeout=60.0)
|
||||
|
||||
@@ -367,7 +370,7 @@ try:
|
||||
elif 'tmux_sessions' not in d:
|
||||
d['tmux_sessions'] = []
|
||||
|
||||
old_terminals = get_terminal_set(d)
|
||||
old_sessions = get_all_sessions_status(d)
|
||||
old_roles = {s.get('name'): s.get('role') for s in db_sessions if s.get('role')}
|
||||
|
||||
# --- caller mutation (module scope: sees d, yaml, os, glob, subprocess) ---
|
||||
@@ -400,13 +403,12 @@ try:
|
||||
else:
|
||||
conn.execute('DELETE FROM sessions')
|
||||
|
||||
new_terminals = get_terminal_set(d)
|
||||
new_sessions = get_all_sessions_status(d)
|
||||
|
||||
conn.commit()
|
||||
|
||||
# Write to YAML ONLY when a session transitions to a finished state
|
||||
# (Moved after conn.commit() per Claude's feedback)
|
||||
if new_terminals != old_terminals:
|
||||
# Write to YAML when sessions status or session list changes (e.g. create/stop/resume)
|
||||
if new_sessions != old_sessions:
|
||||
if os.path.exists(yaml_path):
|
||||
try:
|
||||
shutil.copy2(yaml_path, yaml_path + '.bak')
|
||||
@@ -509,7 +511,7 @@ def emit(u):
|
||||
sessions = []
|
||||
try:
|
||||
if os.path.exists(db_path):
|
||||
conn = sqlite3.connect(db_path, timeout=10.0)
|
||||
conn = sqlite3.connect(db_path, timeout=60.0)
|
||||
has_sessions_table = False
|
||||
try:
|
||||
cursor = conn.execute('SELECT data FROM sessions WHERE pane_cwd=?', (ws,))
|
||||
@@ -621,7 +623,7 @@ elif agent == 'cline':
|
||||
ai = {}
|
||||
try:
|
||||
if os.path.exists(db_path):
|
||||
conn = sqlite3.connect(db_path, timeout=10.0)
|
||||
conn = sqlite3.connect(db_path, timeout=60.0)
|
||||
row = conn.execute('SELECT data FROM state WHERE id=1').fetchone()
|
||||
if row:
|
||||
ai = json.loads(row[0]).get('agent_identities', {})
|
||||
@@ -687,7 +689,7 @@ yaml_path = os.environ['YAML_PATH']
|
||||
db_path = os.path.splitext(yaml_path)[0] + '.db'
|
||||
try:
|
||||
if os.path.exists(db_path):
|
||||
conn = sqlite3.connect(db_path, timeout=10.0)
|
||||
conn = sqlite3.connect(db_path, timeout=60.0)
|
||||
has_sessions_table = False
|
||||
try:
|
||||
row = conn.execute('SELECT status, data FROM sessions WHERE name=?', (name,)).fetchone()
|
||||
|
||||
Reference in New Issue
Block a user