@misterhuydo/sentinel 1.5.1 → 1.5.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
|
@@ -259,17 +259,19 @@ def _run_claude_attempt(
|
|
|
259
259
|
cwd: str | None = None,
|
|
260
260
|
claude_log_path: Path | None = None,
|
|
261
261
|
on_progress=None,
|
|
262
|
+
cmd_override: list | None = None,
|
|
262
263
|
) -> tuple[str, bool]:
|
|
263
264
|
"""
|
|
264
265
|
Run claude CLI with the given env. Returns (output, timed_out).
|
|
265
266
|
Raises FileNotFoundError if binary is missing.
|
|
266
267
|
If on_progress is given, calls on_progress(msg) for meaningful output lines
|
|
267
268
|
(deduped — same message not repeated consecutively).
|
|
269
|
+
cmd_override: if provided, use this command list instead of _claude_cmd() default.
|
|
268
270
|
"""
|
|
269
271
|
import threading as _threading
|
|
270
272
|
|
|
271
273
|
proc = subprocess.Popen(
|
|
272
|
-
_claude_cmd(bin_path, prompt),
|
|
274
|
+
cmd_override if cmd_override is not None else _claude_cmd(bin_path, prompt),
|
|
273
275
|
stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
|
|
274
276
|
text=True, env=env, cwd=cwd or None,
|
|
275
277
|
)
|
|
@@ -171,12 +171,27 @@ def run_repo_task(
|
|
|
171
171
|
if on_progress:
|
|
172
172
|
on_progress(f":mag: Exploring `{repo.repo_name}`...")
|
|
173
173
|
|
|
174
|
+
import os as _os
|
|
175
|
+
skip_perms = _os.getuid() != 0
|
|
176
|
+
# OAuth attempt: no --bare so the stored OAuth session is used naturally
|
|
177
|
+
oauth_cmd = (
|
|
178
|
+
[cfg.claude_code_bin, "--dangerously-skip-permissions", "--print", prompt]
|
|
179
|
+
if skip_perms else
|
|
180
|
+
[cfg.claude_code_bin, "--print", prompt]
|
|
181
|
+
)
|
|
182
|
+
# API key fallback: --bare forces API-key-only auth
|
|
183
|
+
api_cmd = (
|
|
184
|
+
[cfg.claude_code_bin, "--dangerously-skip-permissions", "--bare", "--print", prompt]
|
|
185
|
+
if skip_perms else
|
|
186
|
+
[cfg.claude_code_bin, "--bare", "--print", prompt]
|
|
187
|
+
)
|
|
188
|
+
api_env = {**env, "ANTHROPIC_API_KEY": cfg.anthropic_api_key} if cfg.anthropic_api_key else None
|
|
189
|
+
|
|
174
190
|
try:
|
|
175
191
|
output, timed_out = _run_claude_attempt(
|
|
176
192
|
cfg.claude_code_bin, prompt, env,
|
|
177
|
-
cwd=local_path,
|
|
178
|
-
|
|
179
|
-
on_progress=on_progress,
|
|
193
|
+
cwd=local_path, claude_log_path=claude_log, on_progress=on_progress,
|
|
194
|
+
cmd_override=oauth_cmd,
|
|
180
195
|
)
|
|
181
196
|
except FileNotFoundError:
|
|
182
197
|
return "error", f"Claude binary not found: {cfg.claude_code_bin}"
|
|
@@ -187,7 +202,26 @@ def run_repo_task(
|
|
|
187
202
|
stripped = output.strip()
|
|
188
203
|
|
|
189
204
|
if _is_auth_error(stripped):
|
|
190
|
-
|
|
205
|
+
# Silent fallback: OAuth session expired — retry with API key
|
|
206
|
+
if api_env:
|
|
207
|
+
logger.warning("repo_task/%s: OAuth session issue — retrying with API key", repo.repo_name)
|
|
208
|
+
if on_progress:
|
|
209
|
+
on_progress(":key: Auth refreshed — retrying...")
|
|
210
|
+
try:
|
|
211
|
+
output, timed_out = _run_claude_attempt(
|
|
212
|
+
cfg.claude_code_bin, prompt, api_env,
|
|
213
|
+
cwd=local_path, claude_log_path=claude_log, on_progress=on_progress,
|
|
214
|
+
cmd_override=api_cmd,
|
|
215
|
+
)
|
|
216
|
+
except FileNotFoundError:
|
|
217
|
+
return "error", f"Claude binary not found: {cfg.claude_code_bin}"
|
|
218
|
+
if timed_out:
|
|
219
|
+
return "error", "Claude timed out after 15 minutes."
|
|
220
|
+
stripped = output.strip()
|
|
221
|
+
if _is_auth_error(stripped):
|
|
222
|
+
return "error", "Claude authentication failed — check ANTHROPIC_API_KEY."
|
|
223
|
+
else:
|
|
224
|
+
return "error", "Claude authentication error — run `claude login` on the server or set ANTHROPIC_API_KEY."
|
|
191
225
|
|
|
192
226
|
if stripped.upper().startswith("SKIP:"):
|
|
193
227
|
reason = stripped[5:].strip()
|
|
@@ -2929,23 +2929,30 @@ async def _run_tool(name: str, inputs: dict, cfg_loader, store, slack_client=Non
|
|
|
2929
2929
|
f"Question / Task: {question}"
|
|
2930
2930
|
)
|
|
2931
2931
|
from .fix_engine import _is_auth_error
|
|
2932
|
-
|
|
2932
|
+
skip_perms = os.getuid() != 0
|
|
2933
|
+
# OAuth attempt: no --bare so the stored OAuth session is used naturally
|
|
2934
|
+
oauth_cmd = (
|
|
2935
|
+
[cfg.claude_code_bin, "--dangerously-skip-permissions", "--print", prompt]
|
|
2936
|
+
if skip_perms else
|
|
2937
|
+
[cfg.claude_code_bin, "--print", prompt]
|
|
2938
|
+
)
|
|
2939
|
+
# API key fallback: --bare forces API-key-only auth (no OAuth/hooks)
|
|
2940
|
+
api_cmd = (
|
|
2933
2941
|
[cfg.claude_code_bin, "--dangerously-skip-permissions", "--bare", "--print", prompt]
|
|
2934
|
-
if
|
|
2942
|
+
if skip_perms else
|
|
2935
2943
|
[cfg.claude_code_bin, "--bare", "--print", prompt]
|
|
2936
2944
|
)
|
|
2937
2945
|
run_kwargs = dict(capture_output=True, text=True, timeout=300,
|
|
2938
2946
|
cwd=str(local_path), stdin=subprocess.DEVNULL)
|
|
2939
2947
|
try:
|
|
2940
|
-
|
|
2941
|
-
r = subprocess.run(cmd, env=env, **run_kwargs)
|
|
2948
|
+
r = subprocess.run(oauth_cmd, env=env, **run_kwargs)
|
|
2942
2949
|
output = (r.stdout or "").strip()
|
|
2943
2950
|
auth_failed = _is_auth_error(output) or _is_auth_error(r.stderr or "")
|
|
2944
2951
|
|
|
2945
|
-
# Silent fallback: retry with API key
|
|
2952
|
+
# Silent fallback: OAuth session expired — retry with API key
|
|
2946
2953
|
if auth_failed and api_env:
|
|
2947
2954
|
logger.warning("ask_codebase/%s: OAuth session issue — retrying with API key", repo_name)
|
|
2948
|
-
r = subprocess.run(
|
|
2955
|
+
r = subprocess.run(api_cmd, env=api_env, **run_kwargs)
|
|
2949
2956
|
output = (r.stdout or "").strip()
|
|
2950
2957
|
|
|
2951
2958
|
logger.info("Boss ask_codebase %s mode=%s rc=%d len=%d", repo_name, mode, r.returncode, len(output))
|