loki-mode 6.7.0 → 6.8.0
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/SKILL.md +2 -2
- package/VERSION +1 -1
- package/autonomy/loki +121 -7
- package/autonomy/run.sh +36 -39
- package/dashboard/__init__.py +1 -1
- package/docs/INSTALLATION.md +1 -1
- package/mcp/__init__.py +1 -1
- package/package.json +1 -1
- package/providers/aider.sh +8 -6
- package/providers/claude.sh +14 -11
- package/providers/cline.sh +7 -5
- package/providers/codex.sh +4 -3
- package/providers/gemini.sh +8 -5
package/SKILL.md
CHANGED
|
@@ -3,7 +3,7 @@ name: loki-mode
|
|
|
3
3
|
description: Multi-agent autonomous startup system. Triggers on "Loki Mode". Takes PRD to deployed product with minimal human intervention. Requires --dangerously-skip-permissions flag.
|
|
4
4
|
---
|
|
5
5
|
|
|
6
|
-
# Loki Mode v6.
|
|
6
|
+
# Loki Mode v6.8.0
|
|
7
7
|
|
|
8
8
|
**You are an autonomous agent. You make decisions. You do not ask questions. You do not stop.**
|
|
9
9
|
|
|
@@ -267,4 +267,4 @@ The following features are documented in skill modules but not yet fully automat
|
|
|
267
267
|
| Quality gates 3-reviewer system | Implemented (v5.35.0) | 5 specialist reviewers in `skills/quality-gates.md`; execution in run.sh |
|
|
268
268
|
| Benchmarks (HumanEval, SWE-bench) | Infrastructure only | Runner scripts and datasets exist in `benchmarks/`; no published results |
|
|
269
269
|
|
|
270
|
-
**v6.
|
|
270
|
+
**v6.8.0 | [Autonomi](https://www.autonomi.dev/) flagship product | ~260 lines core**
|
package/VERSION
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
6.
|
|
1
|
+
6.8.0
|
package/autonomy/loki
CHANGED
|
@@ -1647,6 +1647,9 @@ cmd_provider() {
|
|
|
1647
1647
|
info)
|
|
1648
1648
|
cmd_provider_info "$@"
|
|
1649
1649
|
;;
|
|
1650
|
+
models)
|
|
1651
|
+
cmd_provider_models
|
|
1652
|
+
;;
|
|
1650
1653
|
*)
|
|
1651
1654
|
echo -e "${BOLD}Loki Mode Provider Management${NC}"
|
|
1652
1655
|
echo ""
|
|
@@ -1657,6 +1660,7 @@ cmd_provider() {
|
|
|
1657
1660
|
echo " set Set provider for this project"
|
|
1658
1661
|
echo " list List available providers"
|
|
1659
1662
|
echo " info Show provider details"
|
|
1663
|
+
echo " models Show resolved model configuration for all providers"
|
|
1660
1664
|
echo ""
|
|
1661
1665
|
echo "Examples:"
|
|
1662
1666
|
echo " loki provider show"
|
|
@@ -1664,6 +1668,7 @@ cmd_provider() {
|
|
|
1664
1668
|
echo " loki provider set codex"
|
|
1665
1669
|
echo " loki provider list"
|
|
1666
1670
|
echo " loki provider info gemini"
|
|
1671
|
+
echo " loki provider models"
|
|
1667
1672
|
;;
|
|
1668
1673
|
esac
|
|
1669
1674
|
}
|
|
@@ -1899,6 +1904,89 @@ cmd_provider_info() {
|
|
|
1899
1904
|
esac
|
|
1900
1905
|
}
|
|
1901
1906
|
|
|
1907
|
+
# Show resolved model configuration for all providers with source attribution
|
|
1908
|
+
cmd_provider_models() {
|
|
1909
|
+
local script_dir
|
|
1910
|
+
script_dir="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
|
|
1911
|
+
|
|
1912
|
+
echo -e "${BOLD}Model Configuration (resolved):${NC}"
|
|
1913
|
+
echo ""
|
|
1914
|
+
|
|
1915
|
+
local providers=("claude" "codex" "gemini" "cline" "aider")
|
|
1916
|
+
for provider in "${providers[@]}"; do
|
|
1917
|
+
local provider_file="$script_dir/providers/${provider}.sh"
|
|
1918
|
+
[ -f "$provider_file" ] || continue
|
|
1919
|
+
|
|
1920
|
+
echo -e " ${BOLD}Provider: $provider${NC}"
|
|
1921
|
+
|
|
1922
|
+
# Source in subshell to get resolved values
|
|
1923
|
+
local planning dev fast
|
|
1924
|
+
planning=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_MODEL_PLANNING")
|
|
1925
|
+
dev=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_MODEL_DEVELOPMENT")
|
|
1926
|
+
fast=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_MODEL_FAST")
|
|
1927
|
+
|
|
1928
|
+
# Determine source for each tier
|
|
1929
|
+
local provider_upper
|
|
1930
|
+
provider_upper=$(echo "$provider" | tr '[:lower:]' '[:upper:]')
|
|
1931
|
+
|
|
1932
|
+
for tier in planning development fast; do
|
|
1933
|
+
local tier_upper
|
|
1934
|
+
tier_upper=$(echo "$tier" | tr '[:lower:]' '[:upper:]')
|
|
1935
|
+
local provider_var="LOKI_${provider_upper}_MODEL_${tier_upper}"
|
|
1936
|
+
local generic_var="LOKI_MODEL_${tier_upper}"
|
|
1937
|
+
local source="default"
|
|
1938
|
+
|
|
1939
|
+
# Check provider-specific var
|
|
1940
|
+
eval "local pval=\${$provider_var+x}"
|
|
1941
|
+
if [ -n "$pval" ]; then
|
|
1942
|
+
source="$provider_var"
|
|
1943
|
+
else
|
|
1944
|
+
# Check generic var
|
|
1945
|
+
eval "local gval=\${$generic_var+x}"
|
|
1946
|
+
if [ -n "$gval" ]; then
|
|
1947
|
+
source="$generic_var"
|
|
1948
|
+
fi
|
|
1949
|
+
fi
|
|
1950
|
+
|
|
1951
|
+
# Special cases: codex uses single LOKI_CODEX_MODEL, aider/cline too
|
|
1952
|
+
if [ "$provider" = "codex" ] && [ -n "${LOKI_CODEX_MODEL+x}" ] && [ "$source" = "default" ]; then
|
|
1953
|
+
source="LOKI_CODEX_MODEL"
|
|
1954
|
+
elif [ "$provider" = "aider" ] && [ -n "${LOKI_AIDER_MODEL+x}" ] && [ "$source" = "default" ]; then
|
|
1955
|
+
source="LOKI_AIDER_MODEL"
|
|
1956
|
+
elif [ "$provider" = "cline" ] && [ -n "${LOKI_CLINE_MODEL+x}" ] && [ "$source" = "default" ]; then
|
|
1957
|
+
source="LOKI_CLINE_MODEL"
|
|
1958
|
+
fi
|
|
1959
|
+
|
|
1960
|
+
local value
|
|
1961
|
+
case "$tier" in
|
|
1962
|
+
planning) value="$planning" ;;
|
|
1963
|
+
development) value="$dev" ;;
|
|
1964
|
+
fast) value="$fast" ;;
|
|
1965
|
+
esac
|
|
1966
|
+
|
|
1967
|
+
printf " %-12s %-30s (source: %s)\n" "${tier^}:" "$value" "$source"
|
|
1968
|
+
done
|
|
1969
|
+
|
|
1970
|
+
# Show extra info per provider
|
|
1971
|
+
if [ "$provider" = "codex" ]; then
|
|
1972
|
+
local effort_p effort_d effort_f
|
|
1973
|
+
effort_p=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_EFFORT_PLANNING")
|
|
1974
|
+
effort_d=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_EFFORT_DEVELOPMENT")
|
|
1975
|
+
effort_f=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_EFFORT_FAST")
|
|
1976
|
+
echo " Effort: planning=$effort_p, development=$effort_d, fast=$effort_f"
|
|
1977
|
+
elif [ "$provider" = "gemini" ]; then
|
|
1978
|
+
local think_p think_d think_f fb
|
|
1979
|
+
think_p=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_THINKING_PLANNING")
|
|
1980
|
+
think_d=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_THINKING_DEVELOPMENT")
|
|
1981
|
+
think_f=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_THINKING_FAST")
|
|
1982
|
+
fb=$(bash -c "source '$provider_file' 2>/dev/null; echo \$PROVIDER_MODEL_FALLBACK")
|
|
1983
|
+
echo " Thinking: planning=$think_p, development=$think_d, fast=$think_f"
|
|
1984
|
+
echo " Fallback: $fb"
|
|
1985
|
+
fi
|
|
1986
|
+
echo ""
|
|
1987
|
+
done
|
|
1988
|
+
}
|
|
1989
|
+
|
|
1902
1990
|
# Dashboard server management - project-local, unified with run.sh
|
|
1903
1991
|
DASHBOARD_PID_DIR="${LOKI_DIR}/dashboard"
|
|
1904
1992
|
DASHBOARD_PID_FILE="${DASHBOARD_PID_DIR}/dashboard.pid"
|
|
@@ -8576,8 +8664,16 @@ if count == 0:
|
|
|
8576
8664
|
echo -e "${BOLD}Memory Search: $query${NC}"
|
|
8577
8665
|
echo ""
|
|
8578
8666
|
|
|
8667
|
+
# Use python3.12 for ML packages (3.14 lacks sentence-transformers)
|
|
8668
|
+
local _search_py="python3"
|
|
8669
|
+
if command -v /opt/homebrew/bin/python3.12 &>/dev/null; then
|
|
8670
|
+
_search_py="/opt/homebrew/bin/python3.12"
|
|
8671
|
+
elif command -v python3.12 &>/dev/null; then
|
|
8672
|
+
_search_py="python3.12"
|
|
8673
|
+
fi
|
|
8674
|
+
|
|
8579
8675
|
# Try vector search first, fall back to keyword
|
|
8580
|
-
|
|
8676
|
+
$_search_py << PYEOF
|
|
8581
8677
|
import os, json, sys, glob
|
|
8582
8678
|
|
|
8583
8679
|
query = """$query"""
|
|
@@ -8631,14 +8727,26 @@ try:
|
|
|
8631
8727
|
from memory.storage import MemoryStorage
|
|
8632
8728
|
storage = MemoryStorage('.loki/memory')
|
|
8633
8729
|
retriever = MemoryRetrieval(storage)
|
|
8634
|
-
|
|
8635
|
-
for
|
|
8636
|
-
|
|
8730
|
+
retriever.build_indices()
|
|
8731
|
+
for coll in ['episodic', 'semantic', 'skills']:
|
|
8732
|
+
try:
|
|
8733
|
+
vr = retriever.retrieve_by_similarity(query, coll, top_k=3)
|
|
8734
|
+
for item in vr:
|
|
8735
|
+
if isinstance(item, dict):
|
|
8736
|
+
item['_collection'] = coll
|
|
8737
|
+
vector_results.append(item)
|
|
8738
|
+
except Exception:
|
|
8739
|
+
continue
|
|
8637
8740
|
if vector_results:
|
|
8638
8741
|
print(" [Vector Search Results]")
|
|
8639
8742
|
for item in vector_results[:5]:
|
|
8640
8743
|
if isinstance(item, dict):
|
|
8641
|
-
|
|
8744
|
+
coll = item.get('_collection', '?')
|
|
8745
|
+
title = item.get('title', item.get('name', item.get('id', '?')))
|
|
8746
|
+
summary = item.get('summary', item.get('pattern', ''))[:80]
|
|
8747
|
+
print(f" [{coll}] {title}")
|
|
8748
|
+
if summary:
|
|
8749
|
+
print(f" {summary}")
|
|
8642
8750
|
else:
|
|
8643
8751
|
print(f" {str(item)[:80]}")
|
|
8644
8752
|
print()
|
|
@@ -9081,7 +9189,7 @@ except Exception as e:
|
|
|
9081
9189
|
# Build initial index if memory files exist
|
|
9082
9190
|
echo ""
|
|
9083
9191
|
echo -n " Building vector indices... "
|
|
9084
|
-
|
|
9192
|
+
$py_ml -c "
|
|
9085
9193
|
try:
|
|
9086
9194
|
import sys
|
|
9087
9195
|
sys.path.insert(0, '.')
|
|
@@ -9104,7 +9212,13 @@ except Exception as e:
|
|
|
9104
9212
|
;;
|
|
9105
9213
|
|
|
9106
9214
|
rebuild)
|
|
9107
|
-
|
|
9215
|
+
local py_rb="python3"
|
|
9216
|
+
if command -v /opt/homebrew/bin/python3.12 &>/dev/null; then
|
|
9217
|
+
py_rb="/opt/homebrew/bin/python3.12"
|
|
9218
|
+
elif command -v python3.12 &>/dev/null; then
|
|
9219
|
+
py_rb="python3.12"
|
|
9220
|
+
fi
|
|
9221
|
+
$py_rb -c "
|
|
9108
9222
|
try:
|
|
9109
9223
|
import sys
|
|
9110
9224
|
sys.path.insert(0, '.')
|
package/autonomy/run.sh
CHANGED
|
@@ -287,6 +287,9 @@ parse_simple_yaml() {
|
|
|
287
287
|
set_from_yaml "$file" "model.prompt_repetition" "LOKI_PROMPT_REPETITION"
|
|
288
288
|
set_from_yaml "$file" "model.confidence_routing" "LOKI_CONFIDENCE_ROUTING"
|
|
289
289
|
set_from_yaml "$file" "model.autonomy_mode" "LOKI_AUTONOMY_MODE"
|
|
290
|
+
set_from_yaml "$file" "model.planning" "LOKI_MODEL_PLANNING"
|
|
291
|
+
set_from_yaml "$file" "model.development" "LOKI_MODEL_DEVELOPMENT"
|
|
292
|
+
set_from_yaml "$file" "model.fast" "LOKI_MODEL_FAST"
|
|
290
293
|
set_from_yaml "$file" "model.compaction_interval" "LOKI_COMPACTION_INTERVAL"
|
|
291
294
|
|
|
292
295
|
# Parallel
|
|
@@ -673,8 +676,8 @@ fi
|
|
|
673
676
|
# Track worktree PIDs for cleanup (requires bash 4+ for associative arrays)
|
|
674
677
|
# BASH_VERSION_MAJOR is defined at script startup
|
|
675
678
|
if [ "$BASH_VERSION_MAJOR" -ge 4 ] 2>/dev/null; then
|
|
676
|
-
declare -A WORKTREE_PIDS
|
|
677
|
-
declare -A WORKTREE_PATHS
|
|
679
|
+
declare -A WORKTREE_PIDS=()
|
|
680
|
+
declare -A WORKTREE_PATHS=()
|
|
678
681
|
else
|
|
679
682
|
# Fallback: parallel mode will check and warn
|
|
680
683
|
# shellcheck disable=SC2178
|
|
@@ -1369,12 +1372,7 @@ get_provider_tier_param() {
|
|
|
1369
1372
|
if type resolve_model_for_tier &>/dev/null; then
|
|
1370
1373
|
local resolved
|
|
1371
1374
|
resolved=$(resolve_model_for_tier "$tier")
|
|
1372
|
-
|
|
1373
|
-
if [ "${PROVIDER_NAME:-claude}" = "claude" ]; then
|
|
1374
|
-
echo "$resolved" | sed 's/claude-\([a-z]*\).*/\1/'
|
|
1375
|
-
else
|
|
1376
|
-
echo "$resolved"
|
|
1377
|
-
fi
|
|
1375
|
+
echo "$resolved"
|
|
1378
1376
|
return
|
|
1379
1377
|
fi
|
|
1380
1378
|
|
|
@@ -1382,9 +1380,9 @@ get_provider_tier_param() {
|
|
|
1382
1380
|
case "${PROVIDER_NAME:-claude}" in
|
|
1383
1381
|
claude)
|
|
1384
1382
|
case "$tier" in
|
|
1385
|
-
planning) echo "${PROVIDER_MODEL_PLANNING:-opus}"
|
|
1386
|
-
development) echo "${PROVIDER_MODEL_DEVELOPMENT:-
|
|
1387
|
-
fast) echo "${PROVIDER_MODEL_FAST:-
|
|
1383
|
+
planning) echo "${PROVIDER_MODEL_PLANNING:-opus}" ;;
|
|
1384
|
+
development) echo "${PROVIDER_MODEL_DEVELOPMENT:-opus}" ;;
|
|
1385
|
+
fast) echo "${PROVIDER_MODEL_FAST:-sonnet}" ;;
|
|
1388
1386
|
*) echo "sonnet" ;;
|
|
1389
1387
|
esac
|
|
1390
1388
|
;;
|
|
@@ -1405,12 +1403,10 @@ get_provider_tier_param() {
|
|
|
1405
1403
|
esac
|
|
1406
1404
|
;;
|
|
1407
1405
|
cline)
|
|
1408
|
-
|
|
1409
|
-
echo "${LOKI_CLINE_MODEL:-default}"
|
|
1406
|
+
echo "${CLINE_DEFAULT_MODEL:-${LOKI_CLINE_MODEL:-default}}"
|
|
1410
1407
|
;;
|
|
1411
1408
|
aider)
|
|
1412
|
-
|
|
1413
|
-
echo "${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}"
|
|
1409
|
+
echo "${AIDER_DEFAULT_MODEL:-${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}}"
|
|
1414
1410
|
;;
|
|
1415
1411
|
*)
|
|
1416
1412
|
echo "development"
|
|
@@ -2584,7 +2580,10 @@ run_parallel_orchestrator() {
|
|
|
2584
2580
|
"worktrees": {
|
|
2585
2581
|
$(for stream in "${!WORKTREE_PATHS[@]}"; do
|
|
2586
2582
|
local path="${WORKTREE_PATHS[$stream]}"
|
|
2587
|
-
local pid="
|
|
2583
|
+
local pid="null"
|
|
2584
|
+
if [ -n "${WORKTREE_PIDS[$stream]+x}" ]; then
|
|
2585
|
+
pid="${WORKTREE_PIDS[$stream]}"
|
|
2586
|
+
fi
|
|
2588
2587
|
local status="stopped"
|
|
2589
2588
|
if [ "$pid" != "null" ] && kill -0 "$pid" 2>/dev/null; then
|
|
2590
2589
|
status="running"
|
|
@@ -2879,9 +2878,9 @@ _write_pricing_json() {
|
|
|
2879
2878
|
"updated": "${updated}",
|
|
2880
2879
|
"source": "static",
|
|
2881
2880
|
"models": {
|
|
2882
|
-
"opus": {"input": 5.00, "output": 25.00, "label": "Opus
|
|
2883
|
-
"sonnet": {"input": 3.00, "output": 15.00, "label": "Sonnet
|
|
2884
|
-
"haiku": {"input": 1.00, "output": 5.00, "label": "Haiku
|
|
2881
|
+
"opus": {"input": 5.00, "output": 25.00, "label": "Opus (latest)", "provider": "claude"},
|
|
2882
|
+
"sonnet": {"input": 3.00, "output": 15.00, "label": "Sonnet (latest)", "provider": "claude"},
|
|
2883
|
+
"haiku": {"input": 1.00, "output": 5.00, "label": "Haiku (latest)", "provider": "claude"},
|
|
2885
2884
|
"gpt-5.3-codex": {"input": 1.50, "output": 12.00, "label": "GPT-5.3 Codex", "provider": "codex"},
|
|
2886
2885
|
"gemini-3-pro": {"input": 1.25, "output": 10.00, "label": "Gemini 3 Pro", "provider": "gemini"},
|
|
2887
2886
|
"gemini-3-flash": {"input": 0.10, "output": 0.40, "label": "Gemini 3 Flash", "provider": "gemini"}
|
|
@@ -2902,8 +2901,8 @@ invoke_gemini() {
|
|
|
2902
2901
|
local prompt="$1"
|
|
2903
2902
|
shift
|
|
2904
2903
|
|
|
2905
|
-
local model="${PROVIDER_MODEL:-gemini-3-pro-preview}"
|
|
2906
|
-
local fallback="${PROVIDER_MODEL_FALLBACK:-gemini-3-flash-preview}"
|
|
2904
|
+
local model="${PROVIDER_MODEL:-${GEMINI_DEFAULT_PRO:-gemini-3-pro-preview}}"
|
|
2905
|
+
local fallback="${PROVIDER_MODEL_FALLBACK:-${GEMINI_DEFAULT_FLASH:-gemini-3-flash-preview}}"
|
|
2907
2906
|
|
|
2908
2907
|
# Create temp file for output to preserve streaming while checking for rate limit
|
|
2909
2908
|
local tmp_output
|
|
@@ -2933,8 +2932,8 @@ invoke_gemini_capture() {
|
|
|
2933
2932
|
local prompt="$1"
|
|
2934
2933
|
shift
|
|
2935
2934
|
|
|
2936
|
-
local model="${PROVIDER_MODEL:-gemini-3-pro-preview}"
|
|
2937
|
-
local fallback="${PROVIDER_MODEL_FALLBACK:-gemini-3-flash-preview}"
|
|
2935
|
+
local model="${PROVIDER_MODEL:-${GEMINI_DEFAULT_PRO:-gemini-3-pro-preview}}"
|
|
2936
|
+
local fallback="${PROVIDER_MODEL_FALLBACK:-${GEMINI_DEFAULT_FLASH:-gemini-3-flash-preview}}"
|
|
2938
2937
|
local output
|
|
2939
2938
|
|
|
2940
2939
|
# Try primary model first
|
|
@@ -2987,7 +2986,7 @@ invoke_cline_capture() {
|
|
|
2987
2986
|
invoke_aider() {
|
|
2988
2987
|
local prompt="$1"
|
|
2989
2988
|
shift
|
|
2990
|
-
local model="${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}"
|
|
2989
|
+
local model="${AIDER_DEFAULT_MODEL:-${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}}"
|
|
2991
2990
|
local extra_flags="${LOKI_AIDER_FLAGS:-}"
|
|
2992
2991
|
# shellcheck disable=SC2086
|
|
2993
2992
|
# < /dev/null prevents aider from blocking on stdin in non-interactive mode
|
|
@@ -3000,7 +2999,7 @@ invoke_aider() {
|
|
|
3000
2999
|
invoke_aider_capture() {
|
|
3001
3000
|
local prompt="$1"
|
|
3002
3001
|
shift
|
|
3003
|
-
local model="${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}"
|
|
3002
|
+
local model="${AIDER_DEFAULT_MODEL:-${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}}"
|
|
3004
3003
|
local extra_flags="${LOKI_AIDER_FLAGS:-}"
|
|
3005
3004
|
# shellcheck disable=SC2086
|
|
3006
3005
|
aider --message "$prompt" --yes-always --no-auto-commits \
|
|
@@ -3515,17 +3514,15 @@ track_iteration_complete() {
|
|
|
3515
3514
|
|
|
3516
3515
|
# Write efficiency tracking file for /api/cost endpoint
|
|
3517
3516
|
mkdir -p .loki/metrics/efficiency
|
|
3518
|
-
local model_tier="sonnet"
|
|
3519
|
-
if [ "${PROVIDER_NAME:-claude}" = "
|
|
3520
|
-
model_tier="
|
|
3521
|
-
elif [ "${PROVIDER_NAME:-claude}" = "codex" ]; then
|
|
3522
|
-
model_tier="gpt-5.3-codex"
|
|
3517
|
+
local model_tier="${PROVIDER_MODEL_DEVELOPMENT:-sonnet}"
|
|
3518
|
+
if [ "${PROVIDER_NAME:-claude}" = "codex" ]; then
|
|
3519
|
+
model_tier="${PROVIDER_MODEL_DEVELOPMENT:-${CODEX_DEFAULT_MODEL:-gpt-5.3-codex}}"
|
|
3523
3520
|
elif [ "${PROVIDER_NAME:-claude}" = "gemini" ]; then
|
|
3524
|
-
model_tier="gemini-3-pro"
|
|
3521
|
+
model_tier="${PROVIDER_MODEL_DEVELOPMENT:-${GEMINI_DEFAULT_PRO:-gemini-3-pro}}"
|
|
3525
3522
|
elif [ "${PROVIDER_NAME:-claude}" = "cline" ]; then
|
|
3526
|
-
model_tier="${LOKI_CLINE_MODEL:-sonnet}"
|
|
3523
|
+
model_tier="${CLINE_DEFAULT_MODEL:-${LOKI_CLINE_MODEL:-sonnet}}"
|
|
3527
3524
|
elif [ "${PROVIDER_NAME:-claude}" = "aider" ]; then
|
|
3528
|
-
model_tier="${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}"
|
|
3525
|
+
model_tier="${AIDER_DEFAULT_MODEL:-${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}}"
|
|
3529
3526
|
fi
|
|
3530
3527
|
local phase="${LAST_KNOWN_PHASE:-}"
|
|
3531
3528
|
[ -z "$phase" ] && phase=$(python3 -c "import json; print(json.load(open('.loki/state/orchestrator.json')).get('currentPhase', 'unknown'))" 2>/dev/null || echo "unknown")
|
|
@@ -5119,7 +5116,7 @@ COMPOUND_SCRIPT
|
|
|
5119
5116
|
enforce_static_analysis() {
|
|
5120
5117
|
local loki_dir="${TARGET_DIR:-.}/.loki"
|
|
5121
5118
|
local quality_dir="$loki_dir/quality"
|
|
5122
|
-
mkdir -p "$quality_dir"
|
|
5119
|
+
mkdir -p "$quality_dir" "$loki_dir/signals"
|
|
5123
5120
|
|
|
5124
5121
|
local changed_files
|
|
5125
5122
|
changed_files=$(git -C "${TARGET_DIR:-.}" diff --name-only HEAD~1 2>/dev/null || \
|
|
@@ -5262,7 +5259,7 @@ SAFEOF
|
|
|
5262
5259
|
enforce_test_coverage() {
|
|
5263
5260
|
local loki_dir="${TARGET_DIR:-.}/.loki"
|
|
5264
5261
|
local quality_dir="$loki_dir/quality"
|
|
5265
|
-
mkdir -p "$quality_dir"
|
|
5262
|
+
mkdir -p "$quality_dir" "$loki_dir/signals"
|
|
5266
5263
|
|
|
5267
5264
|
local min_coverage="${LOKI_MIN_COVERAGE:-80}"
|
|
5268
5265
|
local test_passed=true
|
|
@@ -8184,8 +8181,8 @@ if __name__ == "__main__":
|
|
|
8184
8181
|
gemini)
|
|
8185
8182
|
# Gemini: Degraded mode - no stream-json, no agent tracking
|
|
8186
8183
|
# Uses invoke_gemini helper for rate limit fallback to flash model
|
|
8187
|
-
local model="${PROVIDER_MODEL:-gemini-3-pro-preview}"
|
|
8188
|
-
local fallback="${PROVIDER_MODEL_FALLBACK:-gemini-3-flash-preview}"
|
|
8184
|
+
local model="${PROVIDER_MODEL:-${GEMINI_DEFAULT_PRO:-gemini-3-pro-preview}}"
|
|
8185
|
+
local fallback="${PROVIDER_MODEL_FALLBACK:-${GEMINI_DEFAULT_FLASH:-gemini-3-flash-preview}}"
|
|
8189
8186
|
echo "[loki] Gemini model: $model (fallback: $fallback), tier: $tier_param" >> "$log_file"
|
|
8190
8187
|
echo "[loki] Gemini model: $model (fallback: $fallback), tier: $tier_param" >> "$agent_log"
|
|
8191
8188
|
|
|
@@ -8213,8 +8210,8 @@ if __name__ == "__main__":
|
|
|
8213
8210
|
;;
|
|
8214
8211
|
aider)
|
|
8215
8212
|
# Aider: Tier 3 - degraded mode, 18+ providers
|
|
8216
|
-
echo "[loki] Aider model: ${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}, tier: $tier_param" >> "$log_file"
|
|
8217
|
-
echo "[loki] Aider model: ${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}, tier: $tier_param" >> "$agent_log"
|
|
8213
|
+
echo "[loki] Aider model: ${AIDER_DEFAULT_MODEL:-${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}}, tier: $tier_param" >> "$log_file"
|
|
8214
|
+
echo "[loki] Aider model: ${AIDER_DEFAULT_MODEL:-${LOKI_AIDER_MODEL:-claude-sonnet-4-5-20250929}}, tier: $tier_param" >> "$agent_log"
|
|
8218
8215
|
{ invoke_aider "$prompt" 2>&1 | tee -a "$log_file" "$agent_log"; \
|
|
8219
8216
|
} && exit_code=0 || exit_code=$?
|
|
8220
8217
|
;;
|
package/dashboard/__init__.py
CHANGED
package/docs/INSTALLATION.md
CHANGED
package/mcp/__init__.py
CHANGED
package/package.json
CHANGED
package/providers/aider.sh
CHANGED
|
@@ -49,9 +49,11 @@ PROVIDER_MAX_PARALLEL=1
|
|
|
49
49
|
# Model Configuration
|
|
50
50
|
# Aider supports 18+ providers; model configured via LOKI_AIDER_MODEL env var
|
|
51
51
|
# or provider-specific env vars (OPENAI_API_KEY, OPENAI_API_BASE, etc.)
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
52
|
+
# NOTE: Aider uses litellm for model routing, so full model strings are needed (not CLI aliases)
|
|
53
|
+
AIDER_DEFAULT_MODEL="${LOKI_AIDER_MODEL:-${LOKI_MODEL_DEVELOPMENT:-claude-sonnet-4-5-20250929}}"
|
|
54
|
+
PROVIDER_MODEL_PLANNING="$AIDER_DEFAULT_MODEL"
|
|
55
|
+
PROVIDER_MODEL_DEVELOPMENT="$AIDER_DEFAULT_MODEL"
|
|
56
|
+
PROVIDER_MODEL_FAST="$AIDER_DEFAULT_MODEL"
|
|
55
57
|
|
|
56
58
|
# No Task tool - model is configured externally
|
|
57
59
|
PROVIDER_TASK_MODEL_PARAM=""
|
|
@@ -95,7 +97,7 @@ provider_version() {
|
|
|
95
97
|
provider_invoke() {
|
|
96
98
|
local prompt="$1"
|
|
97
99
|
shift
|
|
98
|
-
local model="$
|
|
100
|
+
local model="$AIDER_DEFAULT_MODEL"
|
|
99
101
|
local extra_flags="${LOKI_AIDER_FLAGS:-}"
|
|
100
102
|
# shellcheck disable=SC2086
|
|
101
103
|
aider --message "$prompt" \
|
|
@@ -108,7 +110,7 @@ provider_invoke() {
|
|
|
108
110
|
# Model tier to parameter (Aider uses single model, returns model name)
|
|
109
111
|
provider_get_tier_param() {
|
|
110
112
|
local tier="$1"
|
|
111
|
-
echo "$
|
|
113
|
+
echo "$AIDER_DEFAULT_MODEL"
|
|
112
114
|
}
|
|
113
115
|
|
|
114
116
|
# Dynamic model resolution (v6.0.0)
|
|
@@ -116,7 +118,7 @@ provider_get_tier_param() {
|
|
|
116
118
|
# just returns the configured model name. maxTier has no effect.
|
|
117
119
|
resolve_model_for_tier() {
|
|
118
120
|
local tier="$1"
|
|
119
|
-
echo "$
|
|
121
|
+
echo "$AIDER_DEFAULT_MODEL"
|
|
120
122
|
}
|
|
121
123
|
|
|
122
124
|
# Tier-aware invocation
|
package/providers/claude.sh
CHANGED
|
@@ -45,15 +45,21 @@ PROVIDER_MAX_PARALLEL=10
|
|
|
45
45
|
|
|
46
46
|
# Model Configuration (Abstract Tiers)
|
|
47
47
|
# Default: Haiku disabled for quality. Use --allow-haiku or LOKI_ALLOW_HAIKU=true to enable.
|
|
48
|
-
|
|
49
|
-
|
|
48
|
+
# Claude Code CLI resolves aliases (opus/sonnet/haiku) to latest versions automatically.
|
|
49
|
+
CLAUDE_DEFAULT_PLANNING="opus"
|
|
50
|
+
CLAUDE_DEFAULT_DEVELOPMENT="opus" # Opus for dev (was sonnet)
|
|
51
|
+
CLAUDE_DEFAULT_FAST="sonnet"
|
|
52
|
+
|
|
50
53
|
if [ "${LOKI_ALLOW_HAIKU:-false}" = "true" ]; then
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
else
|
|
54
|
-
PROVIDER_MODEL_FAST="claude-sonnet-4-5-20250929" # Sonnet for fast (no haiku)
|
|
54
|
+
CLAUDE_DEFAULT_DEVELOPMENT="sonnet" # Sonnet for dev when haiku enabled
|
|
55
|
+
CLAUDE_DEFAULT_FAST="haiku"
|
|
55
56
|
fi
|
|
56
57
|
|
|
58
|
+
# Resolution order: provider-specific env > generic env > haiku-aware default
|
|
59
|
+
PROVIDER_MODEL_PLANNING="${LOKI_CLAUDE_MODEL_PLANNING:-${LOKI_MODEL_PLANNING:-$CLAUDE_DEFAULT_PLANNING}}"
|
|
60
|
+
PROVIDER_MODEL_DEVELOPMENT="${LOKI_CLAUDE_MODEL_DEVELOPMENT:-${LOKI_MODEL_DEVELOPMENT:-$CLAUDE_DEFAULT_DEVELOPMENT}}"
|
|
61
|
+
PROVIDER_MODEL_FAST="${LOKI_CLAUDE_MODEL_FAST:-${LOKI_MODEL_FAST:-$CLAUDE_DEFAULT_FAST}}"
|
|
62
|
+
|
|
57
63
|
# Model Selection (for Task tool)
|
|
58
64
|
PROVIDER_TASK_MODEL_PARAM="model"
|
|
59
65
|
if [ "${LOKI_ALLOW_HAIKU:-false}" = "true" ]; then
|
|
@@ -168,15 +174,12 @@ resolve_model_for_tier() {
|
|
|
168
174
|
echo "$model"
|
|
169
175
|
}
|
|
170
176
|
|
|
171
|
-
# Tier-aware invocation (
|
|
177
|
+
# Tier-aware invocation (values are already aliases like opus/sonnet/haiku)
|
|
172
178
|
provider_invoke_with_tier() {
|
|
173
179
|
local tier="$1"
|
|
174
180
|
local prompt="$2"
|
|
175
181
|
shift 2
|
|
176
182
|
local model
|
|
177
183
|
model=$(resolve_model_for_tier "$tier")
|
|
178
|
-
|
|
179
|
-
local short_model
|
|
180
|
-
short_model=$(echo "$model" | sed 's/claude-\([a-z]*\).*/\1/')
|
|
181
|
-
claude --dangerously-skip-permissions --model "$short_model" -p "$prompt" "$@"
|
|
184
|
+
claude --dangerously-skip-permissions --model "$model" -p "$prompt" "$@"
|
|
182
185
|
}
|
package/providers/cline.sh
CHANGED
|
@@ -50,9 +50,11 @@ PROVIDER_MAX_PARALLEL=1
|
|
|
50
50
|
# Model Configuration
|
|
51
51
|
# Cline supports 12+ providers; model configured via LOKI_CLINE_MODEL env var
|
|
52
52
|
# or `cline auth` one-time setup. Defaults are placeholders.
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
53
|
+
# NOTE: Cline uses its own model routing, so full model strings are needed (not CLI aliases)
|
|
54
|
+
CLINE_DEFAULT_MODEL="${LOKI_CLINE_MODEL:-${LOKI_MODEL_DEVELOPMENT:-claude-sonnet-4-5-20250929}}"
|
|
55
|
+
PROVIDER_MODEL_PLANNING="$CLINE_DEFAULT_MODEL"
|
|
56
|
+
PROVIDER_MODEL_DEVELOPMENT="$CLINE_DEFAULT_MODEL"
|
|
57
|
+
PROVIDER_MODEL_FAST="$CLINE_DEFAULT_MODEL"
|
|
56
58
|
|
|
57
59
|
# No Task tool - model is configured externally
|
|
58
60
|
PROVIDER_TASK_MODEL_PARAM=""
|
|
@@ -101,7 +103,7 @@ provider_invoke() {
|
|
|
101
103
|
# Model tier to parameter (Cline uses single model, returns model name)
|
|
102
104
|
provider_get_tier_param() {
|
|
103
105
|
local tier="$1"
|
|
104
|
-
echo "$
|
|
106
|
+
echo "$CLINE_DEFAULT_MODEL"
|
|
105
107
|
}
|
|
106
108
|
|
|
107
109
|
# Dynamic model resolution (v6.0.0)
|
|
@@ -109,7 +111,7 @@ provider_get_tier_param() {
|
|
|
109
111
|
# just returns the configured model name. maxTier has no effect.
|
|
110
112
|
resolve_model_for_tier() {
|
|
111
113
|
local tier="$1"
|
|
112
|
-
echo "$
|
|
114
|
+
echo "$CLINE_DEFAULT_MODEL"
|
|
113
115
|
}
|
|
114
116
|
|
|
115
117
|
# Tier-aware invocation
|
package/providers/codex.sh
CHANGED
|
@@ -50,9 +50,10 @@ PROVIDER_MAX_PARALLEL=1
|
|
|
50
50
|
# Model Configuration
|
|
51
51
|
# Codex uses single model with effort parameter
|
|
52
52
|
# NOTE: gpt-5.3-codex is the official model name for Codex CLI v0.98+
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
53
|
+
CODEX_DEFAULT_MODEL="gpt-5.3-codex"
|
|
54
|
+
PROVIDER_MODEL_PLANNING="${LOKI_CODEX_MODEL:-${LOKI_MODEL_PLANNING:-$CODEX_DEFAULT_MODEL}}"
|
|
55
|
+
PROVIDER_MODEL_DEVELOPMENT="${LOKI_CODEX_MODEL:-${LOKI_MODEL_DEVELOPMENT:-$CODEX_DEFAULT_MODEL}}"
|
|
56
|
+
PROVIDER_MODEL_FAST="${LOKI_CODEX_MODEL:-${LOKI_MODEL_FAST:-$CODEX_DEFAULT_MODEL}}"
|
|
56
57
|
|
|
57
58
|
# Effort levels (Codex-specific: maps to reasoning time, not model capability)
|
|
58
59
|
PROVIDER_EFFORT_PLANNING="xhigh"
|
package/providers/gemini.sh
CHANGED
|
@@ -51,11 +51,14 @@ PROVIDER_MAX_PARALLEL=1
|
|
|
51
51
|
# Gemini CLI supports --model flag to specify model
|
|
52
52
|
# Primary: gemini-3-pro-preview (preview names - may change when GA is released)
|
|
53
53
|
# Fallback: gemini-3-flash-preview (for rate limit scenarios)
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
54
|
+
GEMINI_DEFAULT_PRO="gemini-3-pro-preview"
|
|
55
|
+
GEMINI_DEFAULT_FLASH="gemini-3-flash-preview"
|
|
56
|
+
|
|
57
|
+
PROVIDER_MODEL_PLANNING="${LOKI_GEMINI_MODEL_PLANNING:-${LOKI_MODEL_PLANNING:-$GEMINI_DEFAULT_PRO}}"
|
|
58
|
+
PROVIDER_MODEL_DEVELOPMENT="${LOKI_GEMINI_MODEL_DEVELOPMENT:-${LOKI_MODEL_DEVELOPMENT:-$GEMINI_DEFAULT_PRO}}"
|
|
59
|
+
PROVIDER_MODEL_FAST="${LOKI_GEMINI_MODEL_FAST:-${LOKI_MODEL_FAST:-$GEMINI_DEFAULT_FLASH}}"
|
|
60
|
+
PROVIDER_MODEL="${PROVIDER_MODEL_PLANNING}"
|
|
61
|
+
PROVIDER_MODEL_FALLBACK="${LOKI_GEMINI_MODEL_FALLBACK:-$GEMINI_DEFAULT_FLASH}"
|
|
59
62
|
|
|
60
63
|
# Thinking levels (Gemini-specific: maps to reasoning depth)
|
|
61
64
|
PROVIDER_THINKING_PLANNING="high"
|