loki-mode 6.2.0 → 6.2.1
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/README.md +1 -1
- package/SKILL.md +2 -2
- package/VERSION +1 -1
- package/autonomy/bmad-adapter.py +3 -2
- package/autonomy/loki +39 -14
- package/autonomy/prd-analyzer.py +3 -3
- package/autonomy/run.sh +20 -4
- package/autonomy/sandbox.sh +26 -18
- package/dashboard/__init__.py +1 -1
- package/docs/INSTALLATION.md +19 -24
- package/mcp/__init__.py +1 -1
- package/mcp/server.py +7 -2
- package/package.json +1 -1
package/README.md
CHANGED
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.2.
|
|
6
|
+
# Loki Mode v6.2.1
|
|
7
7
|
|
|
8
8
|
**You are an autonomous agent. You make decisions. You do not ask questions. You do not stop.**
|
|
9
9
|
|
|
@@ -263,4 +263,4 @@ The following features are documented in skill modules but not yet fully automat
|
|
|
263
263
|
| Quality gates 3-reviewer system | Implemented (v5.35.0) | 5 specialist reviewers in `skills/quality-gates.md`; execution in run.sh |
|
|
264
264
|
| Benchmarks (HumanEval, SWE-bench) | Infrastructure only | Runner scripts and datasets exist in `benchmarks/`; no published results |
|
|
265
265
|
|
|
266
|
-
**v6.2.
|
|
266
|
+
**v6.2.1 | [Autonomi](https://www.autonomi.dev/) flagship product | ~260 lines core**
|
package/VERSION
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
6.2.
|
|
1
|
+
6.2.1
|
package/autonomy/bmad-adapter.py
CHANGED
|
@@ -80,7 +80,7 @@ def parse_frontmatter(text: str) -> Tuple[Dict[str, Any], str]:
|
|
|
80
80
|
"""Extract YAML frontmatter from a markdown document.
|
|
81
81
|
|
|
82
82
|
Returns (metadata_dict, body_without_frontmatter).
|
|
83
|
-
Handles simple YAML: scalars, lists (flow
|
|
83
|
+
Handles simple YAML: scalars, lists (flow-style only; block-style not supported), quoted strings.
|
|
84
84
|
Does NOT require PyYAML -- uses regex-based extraction.
|
|
85
85
|
"""
|
|
86
86
|
stripped = text.lstrip()
|
|
@@ -514,9 +514,10 @@ def validate_chain(
|
|
|
514
514
|
"message": "PRD frontmatter has no inputDocuments -- cannot verify product-brief linkage.",
|
|
515
515
|
})
|
|
516
516
|
else:
|
|
517
|
+
docs = input_docs if isinstance(input_docs, list) else [input_docs] if input_docs else []
|
|
517
518
|
findings.append({
|
|
518
519
|
"level": "info",
|
|
519
|
-
"message": f"PRD references input documents: {', '.join(
|
|
520
|
+
"message": f"PRD references input documents: {', '.join(docs)}",
|
|
520
521
|
})
|
|
521
522
|
|
|
522
523
|
# 2. Missing artifacts
|
package/autonomy/loki
CHANGED
|
@@ -646,8 +646,9 @@ cmd_start() {
|
|
|
646
646
|
if [[ -n "$bmad_project_path" ]]; then
|
|
647
647
|
# Resolve to absolute path
|
|
648
648
|
if [[ ! "$bmad_project_path" = /* ]]; then
|
|
649
|
+
local original_bmad_path="$bmad_project_path"
|
|
649
650
|
bmad_project_path="$(cd "$bmad_project_path" 2>/dev/null && pwd)" || {
|
|
650
|
-
echo -e "${RED}Error: BMAD project path does not exist: $
|
|
651
|
+
echo -e "${RED}Error: BMAD project path does not exist: $original_bmad_path${NC}"
|
|
651
652
|
exit 1
|
|
652
653
|
}
|
|
653
654
|
fi
|
|
@@ -2754,10 +2755,12 @@ cmd_run() {
|
|
|
2754
2755
|
|
|
2755
2756
|
# Write PRD first so background process can use it
|
|
2756
2757
|
mkdir -p "$LOKI_DIR"
|
|
2757
|
-
local prd_content_detach
|
|
2758
|
-
prd_content_detach=$(echo "$issue_json" | generate_prd_from_issue)
|
|
2759
2758
|
local detach_prd="$LOKI_DIR/prd-issue-${number}.md"
|
|
2760
|
-
echo "$
|
|
2759
|
+
echo "$prd_content" > "$detach_prd"
|
|
2760
|
+
|
|
2761
|
+
if [[ -z "${branch_name:-}" ]]; then
|
|
2762
|
+
branch_name="issue/detach-$(date +%s)"
|
|
2763
|
+
fi
|
|
2761
2764
|
|
|
2762
2765
|
nohup bash -c "
|
|
2763
2766
|
cd $(pwd)
|
|
@@ -2765,6 +2768,24 @@ cmd_run() {
|
|
|
2765
2768
|
export LOKI_PARALLEL_MODE=true
|
|
2766
2769
|
export LOKI_WORKTREE_BRANCH=\"$branch_name\"
|
|
2767
2770
|
$(command -v loki || echo "$0") start \"$detach_prd\" --parallel ${start_args[*]+"${start_args[*]}"}
|
|
2771
|
+
|
|
2772
|
+
# Post-completion: create PR if requested
|
|
2773
|
+
if [[ \"$create_pr\" == \"true\" ]]; then
|
|
2774
|
+
branch_current=\$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo \"\")
|
|
2775
|
+
if [[ -n \"\$branch_current\" && \"\$branch_current\" != \"main\" && \"\$branch_current\" != \"master\" ]]; then
|
|
2776
|
+
git push origin \"\$branch_current\" 2>/dev/null || true
|
|
2777
|
+
gh pr create --title \"${title:-Implementation for issue ${issue_ref}}\" --body \"Implemented by Loki Mode\" --head \"\$branch_current\" 2>/dev/null || true
|
|
2778
|
+
fi
|
|
2779
|
+
fi
|
|
2780
|
+
# Post-completion: auto-merge if requested
|
|
2781
|
+
if [[ \"$auto_merge\" == \"true\" ]]; then
|
|
2782
|
+
branch_current=\$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo \"\")
|
|
2783
|
+
if gh pr merge \"\$branch_current\" --squash --delete-branch 2>/dev/null; then
|
|
2784
|
+
if [[ -n \"${number:-}\" ]]; then
|
|
2785
|
+
gh issue close \"$number\" --comment \"Resolved by Loki Mode\" 2>/dev/null || true
|
|
2786
|
+
fi
|
|
2787
|
+
fi
|
|
2788
|
+
fi
|
|
2768
2789
|
" > "$log_file" 2>&1 &
|
|
2769
2790
|
|
|
2770
2791
|
local bg_pid=$!
|
|
@@ -2862,11 +2883,13 @@ $(git log --oneline "main..HEAD" 2>/dev/null || echo "See diff")"
|
|
|
2862
2883
|
github)
|
|
2863
2884
|
local branch_current
|
|
2864
2885
|
branch_current=$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo "")
|
|
2865
|
-
gh pr merge "$branch_current" --squash --delete-branch 2>/dev/null
|
|
2866
|
-
echo -e "${GREEN}PR merged and branch deleted${NC}"
|
|
2886
|
+
if gh pr merge "$branch_current" --squash --delete-branch 2>/dev/null; then
|
|
2887
|
+
echo -e "${GREEN}PR merged and branch deleted${NC}"
|
|
2888
|
+
if [[ -n "${number:-}" ]]; then
|
|
2889
|
+
gh issue close "$number" --comment "Resolved by Loki Mode" 2>/dev/null || true
|
|
2890
|
+
fi
|
|
2891
|
+
else
|
|
2867
2892
|
echo -e "${YELLOW}Auto-merge failed. PR remains open.${NC}"
|
|
2868
|
-
if [[ -n "${number:-}" ]]; then
|
|
2869
|
-
gh issue close "$number" --comment "Resolved by Loki Mode" 2>/dev/null || true
|
|
2870
2893
|
fi
|
|
2871
2894
|
;;
|
|
2872
2895
|
gitlab)
|
|
@@ -6964,7 +6987,6 @@ except: print('?')
|
|
|
6964
6987
|
local errors
|
|
6965
6988
|
errors=$(python3 -c "
|
|
6966
6989
|
import json, sys
|
|
6967
|
-
sys.path.insert(0, '$(dirname "$SKILL_DIR/swarm/")')
|
|
6968
6990
|
sys.path.insert(0, '$SKILL_DIR')
|
|
6969
6991
|
from swarm.patterns import TopologyValidator
|
|
6970
6992
|
errors = TopologyValidator.validate_file(sys.argv[1])
|
|
@@ -7026,17 +7048,20 @@ for a in d.get('agents', []):
|
|
|
7026
7048
|
return 1
|
|
7027
7049
|
fi
|
|
7028
7050
|
# Validate first
|
|
7029
|
-
local
|
|
7030
|
-
|
|
7051
|
+
local result
|
|
7052
|
+
result=$(python3 -c "
|
|
7031
7053
|
import json, sys
|
|
7032
7054
|
sys.path.insert(0, '$SKILL_DIR')
|
|
7033
7055
|
from swarm.patterns import TopologyValidator
|
|
7034
7056
|
errors = TopologyValidator.validate_file(sys.argv[1])
|
|
7035
|
-
|
|
7057
|
+
if errors:
|
|
7058
|
+
for e in errors: print(f'ERROR: {e}')
|
|
7059
|
+
else:
|
|
7060
|
+
print('VALID')
|
|
7036
7061
|
" "$template_file" 2>&1)
|
|
7037
|
-
if
|
|
7062
|
+
if ! echo "$result" | grep -q "^VALID$"; then
|
|
7038
7063
|
echo -e "${RED}Template validation failed:${NC}"
|
|
7039
|
-
echo "$
|
|
7064
|
+
echo "$result"
|
|
7040
7065
|
return 1
|
|
7041
7066
|
fi
|
|
7042
7067
|
echo -e "${GREEN}Cluster template: $template_name${NC}"
|
package/autonomy/prd-analyzer.py
CHANGED
|
@@ -114,7 +114,6 @@ DIMENSIONS = {
|
|
|
114
114
|
"weight": 0.75,
|
|
115
115
|
"heading_patterns": [
|
|
116
116
|
r"(?i)#+\s.*(?:deploy|hosting|infra|ci.?cd|environment)",
|
|
117
|
-
r"(?i)^##\s+Non-Functional\s+Requirements",
|
|
118
117
|
],
|
|
119
118
|
"content_patterns": [
|
|
120
119
|
r"(?i)\b(?:deploy|hosting|ci.?cd|pipeline|staging|production)\b",
|
|
@@ -259,8 +258,9 @@ class PrdAnalyzer:
|
|
|
259
258
|
if in_feature_section and re.match(r"^\s*#+\s", line):
|
|
260
259
|
in_feature_section = False
|
|
261
260
|
continue
|
|
262
|
-
if
|
|
263
|
-
|
|
261
|
+
if in_feature_section:
|
|
262
|
+
if re.match(r"^\s*[-*]\s+\S", line) or re.match(r"^\s*\d+\.\s+\S", line):
|
|
263
|
+
count += 1
|
|
264
264
|
|
|
265
265
|
self.feature_count = count
|
|
266
266
|
for threshold, label in SCOPE_THRESHOLDS:
|
package/autonomy/run.sh
CHANGED
|
@@ -7043,7 +7043,19 @@ except: pass
|
|
|
7043
7043
|
fi
|
|
7044
7044
|
local bmad_tasks=""
|
|
7045
7045
|
if [[ -f ".loki/bmad-tasks.json" ]]; then
|
|
7046
|
-
bmad_tasks=$(
|
|
7046
|
+
bmad_tasks=$(python3 -c "
|
|
7047
|
+
import json, sys
|
|
7048
|
+
try:
|
|
7049
|
+
with open('.loki/bmad-tasks.json') as f:
|
|
7050
|
+
data = json.load(f)
|
|
7051
|
+
out = json.dumps(data, indent=None)
|
|
7052
|
+
if len(out) > 32000 and isinstance(data, list):
|
|
7053
|
+
while len(json.dumps(data, indent=None)) > 32000 and data:
|
|
7054
|
+
data.pop()
|
|
7055
|
+
out = json.dumps(data, indent=None)
|
|
7056
|
+
print(out[:32000])
|
|
7057
|
+
except: pass
|
|
7058
|
+
" 2>/dev/null)
|
|
7047
7059
|
fi
|
|
7048
7060
|
local bmad_validation=""
|
|
7049
7061
|
if [[ -f ".loki/bmad-validation.md" ]]; then
|
|
@@ -7100,7 +7112,7 @@ populate_bmad_queue() {
|
|
|
7100
7112
|
mkdir -p ".loki/queue"
|
|
7101
7113
|
|
|
7102
7114
|
# Read BMAD tasks and create queue entries
|
|
7103
|
-
python3 << 'BMAD_QUEUE_EOF'
|
|
7115
|
+
python3 << 'BMAD_QUEUE_EOF'
|
|
7104
7116
|
import json
|
|
7105
7117
|
import os
|
|
7106
7118
|
import sys
|
|
@@ -7155,12 +7167,16 @@ if os.path.exists(pending_path):
|
|
|
7155
7167
|
except (json.JSONDecodeError, FileNotFoundError):
|
|
7156
7168
|
existing = []
|
|
7157
7169
|
|
|
7158
|
-
# Convert BMAD stories to queue task format
|
|
7170
|
+
# Convert BMAD stories to queue task format (with deduplication)
|
|
7171
|
+
existing_ids = {t.get("id") for t in existing if isinstance(t, dict)}
|
|
7159
7172
|
for i, story in enumerate(stories):
|
|
7160
7173
|
if not isinstance(story, dict):
|
|
7161
7174
|
continue
|
|
7175
|
+
task_id = f"bmad-{i+1}"
|
|
7176
|
+
if task_id in existing_ids:
|
|
7177
|
+
continue
|
|
7162
7178
|
task = {
|
|
7163
|
-
"id":
|
|
7179
|
+
"id": task_id,
|
|
7164
7180
|
"title": story.get("title", story.get("name", f"BMAD Story {i+1}")),
|
|
7165
7181
|
"description": story.get("description", story.get("action", "")),
|
|
7166
7182
|
"priority": story.get("priority", "medium"),
|
package/autonomy/sandbox.sh
CHANGED
|
@@ -70,9 +70,10 @@ PROMPT_INJECTION_ENABLED="${LOKI_PROMPT_INJECTION:-false}"
|
|
|
70
70
|
# Container runs as user 'loki' (UID 1000), so mount to /home/loki/
|
|
71
71
|
declare -A DOCKER_MOUNT_PRESETS
|
|
72
72
|
DOCKER_MOUNT_PRESETS=(
|
|
73
|
+
# Note: gh and git are also hardcoded in start_sandbox() defaults
|
|
73
74
|
[gh]="$HOME/.config/gh:/home/loki/.config/gh:ro"
|
|
74
75
|
[git]="$HOME/.gitconfig:/home/loki/.gitconfig:ro"
|
|
75
|
-
[ssh]="$HOME/.ssh:/home/loki/.ssh:ro"
|
|
76
|
+
[ssh]="$HOME/.ssh/known_hosts:/home/loki/.ssh/known_hosts:ro"
|
|
76
77
|
[aws]="$HOME/.aws:/home/loki/.aws:ro"
|
|
77
78
|
[azure]="$HOME/.azure:/home/loki/.azure:ro"
|
|
78
79
|
[kube]="$HOME/.kube:/home/loki/.kube:ro"
|
|
@@ -799,7 +800,7 @@ docker_desktop_sandbox_run() {
|
|
|
799
800
|
# Reads from: .loki/config/settings.json dockerMounts, LOKI_DOCKER_MOUNTS env var
|
|
800
801
|
# Returns: string of -v and -e flags for docker run
|
|
801
802
|
resolve_docker_mounts() {
|
|
802
|
-
|
|
803
|
+
RESOLVED_MOUNTS=()
|
|
803
804
|
|
|
804
805
|
# Read configured presets (JSON array of strings)
|
|
805
806
|
local presets_json=""
|
|
@@ -807,10 +808,10 @@ resolve_docker_mounts() {
|
|
|
807
808
|
presets_json=$(python3 -c "
|
|
808
809
|
import json, sys
|
|
809
810
|
try:
|
|
810
|
-
with open('
|
|
811
|
+
with open(sys.argv[1] + '/.loki/config/settings.json') as f:
|
|
811
812
|
print(json.dumps(json.load(f).get('dockerMounts', [])))
|
|
812
813
|
except: print('[]')
|
|
813
|
-
" 2>/dev/null || echo "[]")
|
|
814
|
+
" "${PROJECT_DIR}" 2>/dev/null || echo "[]")
|
|
814
815
|
fi
|
|
815
816
|
|
|
816
817
|
# Override with env var if set
|
|
@@ -846,12 +847,16 @@ except: pass
|
|
|
846
847
|
local container_path="${parts[1]}"
|
|
847
848
|
local mode="${parts[2]:-ro}"
|
|
848
849
|
|
|
849
|
-
#
|
|
850
|
-
|
|
850
|
+
# Safe tilde expansion (no eval)
|
|
851
|
+
if [[ "$host_path" == "~/"* ]]; then
|
|
852
|
+
host_path="$HOME/${host_path#\~/}"
|
|
853
|
+
elif [[ "$host_path" == "~" ]]; then
|
|
854
|
+
host_path="$HOME"
|
|
855
|
+
fi
|
|
851
856
|
|
|
852
857
|
# Only mount if host path exists
|
|
853
858
|
if [[ -e "$host_path" ]]; then
|
|
854
|
-
|
|
859
|
+
RESOLVED_MOUNTS+=("-v" "${host_path}:${container_path}:${mode}")
|
|
855
860
|
log_info " Mount preset [$name]: $host_path -> $container_path ($mode)"
|
|
856
861
|
fi
|
|
857
862
|
|
|
@@ -865,18 +870,18 @@ except: pass
|
|
|
865
870
|
# Wildcard: pass all matching env vars
|
|
866
871
|
local prefix="${env_name%\*}"
|
|
867
872
|
while IFS='=' read -r key val; do
|
|
868
|
-
[[ "$key" == "$prefix"* ]] && [[ -n "$val" ]] &&
|
|
869
|
-
|
|
873
|
+
[[ "$key" == "$prefix"* ]] && [[ -n "$val" ]] && {
|
|
874
|
+
RESOLVED_MOUNTS+=("-e" "$key")
|
|
875
|
+
log_info " Env wildcard [$name]: passing $key"
|
|
876
|
+
}
|
|
870
877
|
done < <(env)
|
|
871
878
|
elif [[ -n "${!env_name:-}" ]]; then
|
|
872
|
-
|
|
879
|
+
RESOLVED_MOUNTS+=("-e" "$env_name")
|
|
873
880
|
fi
|
|
874
881
|
done
|
|
875
882
|
fi
|
|
876
883
|
done <<< "$preset_names"
|
|
877
884
|
fi
|
|
878
|
-
|
|
879
|
-
echo "$mount_args"
|
|
880
885
|
}
|
|
881
886
|
|
|
882
887
|
start_sandbox() {
|
|
@@ -1037,11 +1042,9 @@ start_sandbox() {
|
|
|
1037
1042
|
|
|
1038
1043
|
# Apply Docker credential mount presets (additive on top of defaults above)
|
|
1039
1044
|
if [[ "$no_mounts" != "true" ]] && [[ "${LOKI_NO_DOCKER_MOUNTS:-}" != "true" ]]; then
|
|
1040
|
-
|
|
1041
|
-
|
|
1042
|
-
|
|
1043
|
-
# shellcheck disable=SC2206
|
|
1044
|
-
docker_args+=($preset_mounts)
|
|
1045
|
+
resolve_docker_mounts
|
|
1046
|
+
if [[ ${#RESOLVED_MOUNTS[@]} -gt 0 ]]; then
|
|
1047
|
+
docker_args+=("${RESOLVED_MOUNTS[@]}")
|
|
1045
1048
|
fi
|
|
1046
1049
|
fi
|
|
1047
1050
|
|
|
@@ -1054,7 +1057,12 @@ start_sandbox() {
|
|
|
1054
1057
|
local c_container="${mount_parts[1]:-}"
|
|
1055
1058
|
local c_mode="${mount_parts[2]:-ro}"
|
|
1056
1059
|
if [[ -n "$c_host" ]] && [[ -n "$c_container" ]]; then
|
|
1057
|
-
|
|
1060
|
+
# Safe tilde expansion (no eval)
|
|
1061
|
+
if [[ "$c_host" == "~/"* ]]; then
|
|
1062
|
+
c_host="$HOME/${c_host#\~/}"
|
|
1063
|
+
elif [[ "$c_host" == "~" ]]; then
|
|
1064
|
+
c_host="$HOME"
|
|
1065
|
+
fi
|
|
1058
1066
|
if [[ -e "$c_host" ]]; then
|
|
1059
1067
|
docker_args+=("--volume" "${c_host}:${c_container}:${c_mode}")
|
|
1060
1068
|
log_info " Custom mount: $c_host -> $c_container ($c_mode)"
|
package/dashboard/__init__.py
CHANGED
package/docs/INSTALLATION.md
CHANGED
|
@@ -2,33 +2,28 @@
|
|
|
2
2
|
|
|
3
3
|
The flagship product of [Autonomi](https://www.autonomi.dev/). Complete installation instructions for all platforms and use cases.
|
|
4
4
|
|
|
5
|
-
**Version:** v6.2.
|
|
5
|
+
**Version:** v6.2.1
|
|
6
6
|
|
|
7
7
|
---
|
|
8
8
|
|
|
9
|
-
## What's New in
|
|
10
|
-
|
|
11
|
-
###
|
|
12
|
-
-
|
|
13
|
-
-
|
|
14
|
-
-
|
|
15
|
-
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
-
|
|
24
|
-
-
|
|
25
|
-
-
|
|
26
|
-
|
|
27
|
-
### Workflow Protection (v5.38.0)
|
|
28
|
-
- Branch protection: agent sessions auto-create feature branches
|
|
29
|
-
- PR creation via `gh` on session completion
|
|
30
|
-
- OpenClaw bridge foundation for external integrations
|
|
31
|
-
- Network security documentation (Docker/Kubernetes)
|
|
9
|
+
## What's New in v6.2.1
|
|
10
|
+
|
|
11
|
+
### Dual-Mode Architecture (v6.0.0)
|
|
12
|
+
- `loki run` command for direct autonomous execution
|
|
13
|
+
- Dual-mode: skill mode (inside Claude Code) and standalone mode
|
|
14
|
+
- Dynamic model resolution across all providers
|
|
15
|
+
- Multi-provider issue fixes and stability improvements
|
|
16
|
+
|
|
17
|
+
### ChromaDB Semantic Code Search (v6.1.0)
|
|
18
|
+
- Semantic code search via ChromaDB vector database
|
|
19
|
+
- MCP integration with `loki_code_search` and `loki_code_search_stats` tools
|
|
20
|
+
- Automatic codebase indexing with `tools/index-codebase.py`
|
|
21
|
+
|
|
22
|
+
### Memory System (v5.15.0+)
|
|
23
|
+
- Episodic, semantic, and procedural memory layers
|
|
24
|
+
- Progressive disclosure with 3-layer loading
|
|
25
|
+
- Token economics tracking for discovery vs read tokens
|
|
26
|
+
- Optional vector search with sentence-transformers
|
|
32
27
|
|
|
33
28
|
---
|
|
34
29
|
|
package/mcp/__init__.py
CHANGED
package/mcp/server.py
CHANGED
|
@@ -1231,10 +1231,15 @@ def _get_chroma_collection():
|
|
|
1231
1231
|
"""Get or create ChromaDB collection (lazy connection)."""
|
|
1232
1232
|
global _chroma_client, _chroma_collection
|
|
1233
1233
|
if _chroma_collection is not None:
|
|
1234
|
-
|
|
1234
|
+
try:
|
|
1235
|
+
_chroma_client.heartbeat()
|
|
1236
|
+
return _chroma_collection
|
|
1237
|
+
except Exception:
|
|
1238
|
+
_chroma_client = None
|
|
1239
|
+
_chroma_collection = None
|
|
1235
1240
|
try:
|
|
1236
1241
|
import chromadb
|
|
1237
|
-
_chroma_client = chromadb.HttpClient(host=CHROMA_HOST, port=
|
|
1242
|
+
_chroma_client = chromadb.HttpClient(host=CHROMA_HOST, port=CHROMA_PORT)
|
|
1238
1243
|
_chroma_collection = _chroma_client.get_collection(name=CHROMA_COLLECTION)
|
|
1239
1244
|
return _chroma_collection
|
|
1240
1245
|
except Exception as e:
|