ltcai 12.2.1 → 12.4.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/README.md +40 -33
- package/docs/CHANGELOG.md +65 -0
- package/docs/COMMUNITY_AND_PLUGINS.md +1 -1
- package/docs/DEVELOPMENT.md +11 -11
- package/docs/ONBOARDING.md +1 -1
- package/docs/OPERATIONS.md +1 -1
- package/docs/ROADMAP.md +1 -1
- package/docs/TRUST_MODEL.md +1 -1
- package/docs/WHY_LATTICE.md +1 -1
- package/docs/kg-schema.md +1 -1
- package/lattice_brain/__init__.py +1 -1
- package/latticeai/__init__.py +1 -1
- package/latticeai/core/embedding_providers/autodetect.py +0 -1
- package/latticeai/core/model_compat.py +2 -2
- package/latticeai/models/model_providers.py +12 -11
- package/latticeai/services/architecture_readiness.py +1 -1
- package/latticeai/services/model_capability_registry.py +79 -2
- package/latticeai/services/model_catalog.py +38 -12
- package/latticeai/services/model_engines.py +29 -15
- package/latticeai/services/model_runtime/download.py +53 -6
- package/latticeai/services/product_readiness.py +1 -1
- package/package.json +6 -8
- package/requirements.txt +3 -1
- package/scripts/check_current_release_docs.mjs +1 -1
- package/scripts/release_screen_claims.json +24 -0
- package/src-tauri/Cargo.lock +10 -10
- package/src-tauri/Cargo.toml +1 -1
- package/src-tauri/tauri.conf.json +1 -1
- package/static/app/asset-manifest.json +46 -47
- package/static/app/assets/Act-inLiZfDE.js +2 -0
- package/static/app/assets/AdminConsole-iLFwSJSg.js +1 -0
- package/static/app/assets/Brain-Cb7noiNc.js +2 -0
- package/static/app/assets/BrainHome-CfiJ4tau.js +2 -0
- package/static/app/assets/BrainSignals-ShxKNNqr.js +1 -0
- package/static/app/assets/Capture-Cajj1Trf.js +1 -0
- package/static/app/assets/Chronicle-CPd8GP_O.js +1 -0
- package/static/app/assets/CommandPalette-Cb_GWoYC.js +1 -0
- package/static/app/assets/DigitalBrainExplorer-Df6KVrBz.js +321 -0
- package/static/app/assets/Library-Dk5Mefl_.js +1 -0
- package/static/app/assets/LivingBrain-u9X_XGC2.js +1 -0
- package/static/app/assets/{ProductFlow-DeBGF6qz.js → ProductFlow-CpX0BMr9.js} +1 -1
- package/static/app/assets/{QueryClientProvider-B3OjqSyJ.js → QueryClientProvider-CTiSBeU6.js} +1 -1
- package/static/app/assets/ReviewCard-C64YFHOR.js +3 -0
- package/static/app/assets/RunsListPanel-DKZEJcxF.js +1 -0
- package/static/app/assets/System-Dretrknf.js +1 -0
- package/static/app/assets/WorkflowGraph-CE6XgWjJ.js +1 -0
- package/static/app/assets/WorkflowsPanel-MKU05J7_.js +2 -0
- package/static/app/assets/actHelpers-BjMnKMCI.js +1 -0
- package/static/app/assets/arrow-left-Cbck4Ig2.js +1 -0
- package/static/app/assets/{bot-Dm3fmXAE.js → bot-Qgvc2PGU.js} +1 -1
- package/static/app/assets/{brain-C2XwdQL1.js → brain-BwGnubn8.js} +1 -1
- package/static/app/assets/{button-xXPeemQr.js → button-DEloiIsj.js} +1 -1
- package/static/app/assets/circle-check-CDygnRMn.js +1 -0
- package/static/app/assets/{circle-pause-B_lmNicW.js → circle-pause-CkkmXxA9.js} +1 -1
- package/static/app/assets/{circle-play-DSYCP0RD.js → circle-play-rnb6A1zq.js} +1 -1
- package/static/app/assets/{cpu-D7x-dtxi.js → cpu-CzcGFQQq.js} +1 -1
- package/static/app/assets/{download-BHuJr-5V.js → download-BTQigJvp.js} +1 -1
- package/static/app/assets/{folder-open-BiO31EwS.js → folder-open-CIXPPhhm.js} +1 -1
- package/static/app/assets/{hard-drive-CFEaZ-wP.js → hard-drive-CZXxdIcT.js} +1 -1
- package/static/app/assets/index-CHQbWj9a.js +13 -0
- package/static/app/assets/index-C_dThdD6.css +2 -0
- package/static/app/assets/{input-D3YrgxvO.js → input-CTZHuOXe.js} +1 -1
- package/static/app/assets/jsx-runtime-CU_pEDDh.js +1 -0
- package/static/app/assets/{link-2-3O-By3qc.js → link-2-BsG1NQUA.js} +1 -1
- package/static/app/assets/{permissionCopy-CNK2tfkz.js → permissionCopy-klyWL3ai.js} +1 -1
- package/static/app/assets/primitives-ZmN4jzq-.js +1 -0
- package/static/app/assets/search-xjKVb4Nh.js +1 -0
- package/static/app/assets/{share-2-BljIPAku.js → share-2-Cuv9rj7A.js} +1 -1
- package/static/app/assets/{shield-alert-WDP2DSTM.js → shield-alert-KKySFd03.js} +1 -1
- package/static/app/assets/{textarea-5v8vtDlK.js → textarea-CBwqgGSA.js} +1 -1
- package/static/app/assets/useFocusTrap-D93vds_Z.js +1 -0
- package/static/app/assets/{useMutation-Bi0PXQMC.js → useMutation-B9hHPD0p.js} +1 -1
- package/static/app/assets/{workspace-BsxrRYQI.js → workspace-JGzrc0D8.js} +1 -1
- package/static/app/index.html +4 -4
- package/static/sw.js +1 -1
- package/static/app/assets/Act-DC676bqE.js +0 -2
- package/static/app/assets/AdminConsole-aCxQgD2L.js +0 -1
- package/static/app/assets/Brain-Dbd0xvsc.js +0 -2
- package/static/app/assets/BrainHome-N00B-MAJ.js +0 -2
- package/static/app/assets/BrainSignals-CNA0d6xS.js +0 -1
- package/static/app/assets/Capture-BB19fo7P.js +0 -1
- package/static/app/assets/Chronicle-D8p3dqxZ.js +0 -1
- package/static/app/assets/CommandPalette-uVFYAa-6.js +0 -1
- package/static/app/assets/DigitalBrainExplorer-mH6ZSuvK.js +0 -321
- package/static/app/assets/Library-0q8Sdke7.js +0 -1
- package/static/app/assets/LivingBrain-wess-qJZ.js +0 -1
- package/static/app/assets/ReviewCard-DyTrDpy0.js +0 -3
- package/static/app/assets/RunsListPanel-CHJv2Qyw.js +0 -1
- package/static/app/assets/System-CyKGHQrW.js +0 -1
- package/static/app/assets/WorkflowGraph-B5nKCCGa.js +0 -1
- package/static/app/assets/WorkflowsPanel-C7RZNRGo.js +0 -2
- package/static/app/assets/actHelpers-6MYDH2kW.js +0 -1
- package/static/app/assets/arrow-left-DOnpwsVV.js +0 -1
- package/static/app/assets/circle-check-D44VI2ZE.js +0 -1
- package/static/app/assets/index-C8gwOf0C.css +0 -2
- package/static/app/assets/index-DCT79wzR.js +0 -13
- package/static/app/assets/jsx-runtime-bzQ4Vb5N.js +0 -1
- package/static/app/assets/primitives-B6DzQC3H.js +0 -1
- package/static/app/assets/search-BwMK0hjs.js +0 -1
- package/static/app/assets/sourceMeta-By2WIjlN.js +0 -1
- package/static/app/assets/useFocusTrap-ssiDeh6P.js +0 -1
|
@@ -102,11 +102,17 @@ ENGINE_MODEL_CATALOG: Dict[str, List[Dict[str, Any]]] = {}
|
|
|
102
102
|
# gated — the download could never succeed without Hub credentials.
|
|
103
103
|
|
|
104
104
|
|
|
105
|
-
def _gguf_routes(
|
|
105
|
+
def _gguf_routes(
|
|
106
|
+
mlx_repo: str,
|
|
107
|
+
gguf_repo: str,
|
|
108
|
+
hf_repo: str,
|
|
109
|
+
*,
|
|
110
|
+
ollama_tag: str = "Q4_K_M",
|
|
111
|
+
) -> Dict[str, str]:
|
|
106
112
|
"""One model's engine map: MLX weights, a GGUF repo, and the upstream HF repo."""
|
|
107
113
|
return {
|
|
108
114
|
"local_mlx": mlx_repo,
|
|
109
|
-
"ollama": f"hf.co/{gguf_repo}:
|
|
115
|
+
"ollama": f"hf.co/{gguf_repo}:{ollama_tag}",
|
|
110
116
|
"vllm": hf_repo,
|
|
111
117
|
"lmstudio": gguf_repo,
|
|
112
118
|
"llamacpp": gguf_repo,
|
|
@@ -119,36 +125,51 @@ _ENGINE_ROUTES: Dict[str, Dict[str, str]] = {
|
|
|
119
125
|
),
|
|
120
126
|
"mlx-community/gemma-4-e2b-it-4bit": _gguf_routes(
|
|
121
127
|
"mlx-community/gemma-4-e2b-it-4bit", "ggml-org/gemma-4-E2B-it-GGUF", "google/gemma-4-E2B-it",
|
|
128
|
+
ollama_tag="Q4_0",
|
|
122
129
|
),
|
|
123
130
|
"mlx-community/gemma-4-e4b-it-4bit": _gguf_routes(
|
|
124
131
|
"mlx-community/gemma-4-e4b-it-4bit", "ggml-org/gemma-4-E4B-it-GGUF", "google/gemma-4-E4B-it",
|
|
132
|
+
ollama_tag="Q4_0",
|
|
125
133
|
),
|
|
126
134
|
"mlx-community/gemma-4-12B-it-4bit": _gguf_routes(
|
|
127
135
|
"mlx-community/gemma-4-12B-it-4bit", "ggml-org/gemma-4-12B-it-GGUF", "google/gemma-4-12B-it",
|
|
136
|
+
ollama_tag="Q4_0",
|
|
137
|
+
),
|
|
138
|
+
"mlx-community/gemma-4-26B-A4B-it-qat-4bit": _gguf_routes(
|
|
139
|
+
"mlx-community/gemma-4-26B-A4B-it-qat-4bit", "google/gemma-4-26B-A4B-it-qat-q4_0-gguf",
|
|
140
|
+
"google/gemma-4-26B-A4B-it-qat-q4_0-unquantized",
|
|
141
|
+
ollama_tag="Q4_0",
|
|
128
142
|
),
|
|
129
143
|
"mlx-community/gemma-4-26b-a4b-it-4bit": _gguf_routes(
|
|
130
144
|
"mlx-community/gemma-4-26b-a4b-it-4bit", "ggml-org/gemma-4-26B-A4B-it-GGUF",
|
|
131
145
|
"google/gemma-4-26B-A4B-it",
|
|
146
|
+
ollama_tag="Q4_0",
|
|
147
|
+
),
|
|
148
|
+
"mlx-community/gemma-4-26B-A4B-it-qat-OptiQ-4bit": _gguf_routes(
|
|
149
|
+
"mlx-community/gemma-4-26B-A4B-it-qat-OptiQ-4bit", "unsloth/gemma-4-26B-A4B-it-GGUF",
|
|
150
|
+
"google/gemma-4-26B-A4B-it-qat-q4_0-unquantized",
|
|
151
|
+
ollama_tag="Q4_0",
|
|
132
152
|
),
|
|
133
153
|
"mlx-community/gemma-4-31b-it-4bit": _gguf_routes(
|
|
134
154
|
"mlx-community/gemma-4-31b-it-4bit", "ggml-org/gemma-4-31B-it-GGUF", "google/gemma-4-31B-it",
|
|
155
|
+
ollama_tag="Q4_0",
|
|
156
|
+
),
|
|
157
|
+
"mlx-community/Qwen3.8-27B-4bit": _gguf_routes(
|
|
158
|
+
"mlx-community/Qwen3.8-27B-4bit", "ggml-org/Qwen3.8-27B-GGUF", "Qwen/Qwen3.8-27B",
|
|
135
159
|
),
|
|
136
160
|
"mlx-community/Qwen3.6-27B-4bit": _gguf_routes(
|
|
137
161
|
"mlx-community/Qwen3.6-27B-4bit", "ggml-org/Qwen3.6-27B-GGUF", "Qwen/Qwen3.6-27B",
|
|
138
162
|
),
|
|
139
163
|
"mlx-community/gpt-oss-20b-MXFP4-Q8": _gguf_routes(
|
|
140
164
|
"mlx-community/gpt-oss-20b-MXFP4-Q8", "ggml-org/gpt-oss-20b-GGUF", "openai/gpt-oss-20b",
|
|
165
|
+
ollama_tag="MXFP4",
|
|
166
|
+
),
|
|
167
|
+
"mlx-community/Qwen3.5-9B-MLX-4bit": _gguf_routes(
|
|
168
|
+
"mlx-community/Qwen3.5-9B-MLX-4bit", "unsloth/Qwen3.5-9B-GGUF", "Qwen/Qwen3.5-9B",
|
|
169
|
+
),
|
|
170
|
+
"mlx-community/Qwen3.6-35B-A3B-4bit": _gguf_routes(
|
|
171
|
+
"mlx-community/Qwen3.6-35B-A3B-4bit", "ggml-org/Qwen3.6-35B-A3B-GGUF", "Qwen/Qwen3.6-35B-A3B",
|
|
141
172
|
),
|
|
142
|
-
# No community GGUF build verified for these two, so they offer the MLX
|
|
143
|
-
# weights and the upstream repo only rather than a route that would 404.
|
|
144
|
-
"mlx-community/Qwen3.5-9B-MLX-4bit": {
|
|
145
|
-
"local_mlx": "mlx-community/Qwen3.5-9B-MLX-4bit",
|
|
146
|
-
"vllm": "Qwen/Qwen3.5-9B",
|
|
147
|
-
},
|
|
148
|
-
"mlx-community/Qwen3.6-35B-A3B-4bit": {
|
|
149
|
-
"local_mlx": "mlx-community/Qwen3.6-35B-A3B-4bit",
|
|
150
|
-
"vllm": "Qwen/Qwen3.6-35B-A3B",
|
|
151
|
-
},
|
|
152
173
|
}
|
|
153
174
|
|
|
154
175
|
# Names people actually type that are not the repo's own short name. Kept
|
|
@@ -156,6 +177,11 @@ _ENGINE_ROUTES: Dict[str, Dict[str, str]] = {
|
|
|
156
177
|
# is no other Gemma 4 26B — and resolving that to nothing would be pedantry.
|
|
157
178
|
_COMMON_MISNAMES: Dict[str, str] = {
|
|
158
179
|
"gemma-4-26b-it-4bit": "mlx-community/gemma-4-26b-a4b-it-4bit",
|
|
180
|
+
"gemma-4-26b-qat-4bit": "mlx-community/gemma-4-26B-A4B-it-qat-4bit",
|
|
181
|
+
"gemma-4-26b-a4b-qat-4bit": "mlx-community/gemma-4-26B-A4B-it-qat-4bit",
|
|
182
|
+
"gemma-4-26b-optiq-4bit": "mlx-community/gemma-4-26B-A4B-it-qat-OptiQ-4bit",
|
|
183
|
+
"qwen-3.8-27b-4bit": "mlx-community/Qwen3.8-27B-4bit",
|
|
184
|
+
"qwen3.8-27b": "mlx-community/Qwen3.8-27B-4bit",
|
|
159
185
|
}
|
|
160
186
|
|
|
161
187
|
# Keyed by both the lowercase short name ("gemma-4-12b-it-4bit") and the
|
|
@@ -112,6 +112,8 @@ def _json_request(
|
|
|
112
112
|
payload: Optional[Dict[str, Any]] = None,
|
|
113
113
|
timeout: float = 10.0,
|
|
114
114
|
) -> Dict[str, Any]:
|
|
115
|
+
if not str(url).startswith(("http://", "https://")):
|
|
116
|
+
raise ValueError(f"Unsupported URL scheme in {url!r}")
|
|
115
117
|
data = None
|
|
116
118
|
req_headers = dict(headers or {})
|
|
117
119
|
if payload is not None:
|
|
@@ -225,7 +227,7 @@ def get_openai_compatible_server_models(provider: str) -> List[str]:
|
|
|
225
227
|
config = OPENAI_COMPATIBLE_PROVIDERS.get(provider) or {}
|
|
226
228
|
base_url = os.getenv(config.get("base_url_env", "")) if config.get("base_url_env") else None
|
|
227
229
|
base_url = (base_url or config.get("base_url") or "").rstrip("/")
|
|
228
|
-
if not base_url:
|
|
230
|
+
if not base_url or not base_url.startswith(("http://", "https://")):
|
|
229
231
|
return []
|
|
230
232
|
|
|
231
233
|
api_key = os.getenv(config.get("env_key", "")) or config.get("api_key_fallback") or provider
|
|
@@ -332,6 +334,10 @@ def ensure_llamacpp_server(model_name: str) -> None:
|
|
|
332
334
|
hf_model_dir,
|
|
333
335
|
hf_model_ready,
|
|
334
336
|
)
|
|
337
|
+
from latticeai.services.model_runtime.download import (
|
|
338
|
+
GGUF_QUANT_PREFERENCE,
|
|
339
|
+
is_auxiliary_gguf,
|
|
340
|
+
)
|
|
335
341
|
|
|
336
342
|
served_models = get_openai_compatible_server_models("llamacpp")
|
|
337
343
|
if model_name in served_models:
|
|
@@ -347,23 +353,31 @@ def ensure_llamacpp_server(model_name: str) -> None:
|
|
|
347
353
|
download_hf_model(model_name, "llamacpp")
|
|
348
354
|
|
|
349
355
|
gguf_files = sorted(hf_model_dir(model_name).rglob("*.gguf"))
|
|
350
|
-
if not
|
|
356
|
+
primary_ggufs = [p for p in gguf_files if not is_auxiliary_gguf(p.name)]
|
|
357
|
+
if not primary_ggufs:
|
|
351
358
|
raise ModelRuntimeError(status_code=500, detail="다운로드된 GGUF 파일을 찾지 못했습니다.")
|
|
352
359
|
|
|
353
|
-
preferred = next(
|
|
354
|
-
|
|
360
|
+
preferred = next(
|
|
361
|
+
(p for pref in GGUF_QUANT_PREFERENCE for p in primary_ggufs if pref in p.name.lower()),
|
|
362
|
+
None,
|
|
363
|
+
)
|
|
364
|
+
model_file = preferred or primary_ggufs[0]
|
|
365
|
+
command = [
|
|
366
|
+
"llama-server",
|
|
367
|
+
"-m",
|
|
368
|
+
str(model_file),
|
|
369
|
+
"--alias",
|
|
370
|
+
model_name,
|
|
371
|
+
"--host",
|
|
372
|
+
"127.0.0.1",
|
|
373
|
+
"--port",
|
|
374
|
+
"8080",
|
|
375
|
+
]
|
|
376
|
+
mmprojs = [p for p in gguf_files if p.name.lower().startswith("mmproj-")]
|
|
377
|
+
if mmprojs:
|
|
378
|
+
command.extend(["--mmproj", str(mmprojs[0])])
|
|
355
379
|
LOCAL_SERVER_PROCESSES["llamacpp"] = subprocess.Popen(
|
|
356
|
-
|
|
357
|
-
"llama-server",
|
|
358
|
-
"-m",
|
|
359
|
-
str(model_file),
|
|
360
|
-
"--alias",
|
|
361
|
-
model_name,
|
|
362
|
-
"--host",
|
|
363
|
-
"127.0.0.1",
|
|
364
|
-
"--port",
|
|
365
|
-
"8080",
|
|
366
|
-
],
|
|
380
|
+
command,
|
|
367
381
|
stdout=subprocess.DEVNULL,
|
|
368
382
|
stderr=subprocess.DEVNULL,
|
|
369
383
|
start_new_session=True,
|
|
@@ -10,6 +10,7 @@ differently.
|
|
|
10
10
|
from __future__ import annotations
|
|
11
11
|
|
|
12
12
|
import importlib.util
|
|
13
|
+
import json
|
|
13
14
|
import logging
|
|
14
15
|
import time
|
|
15
16
|
from pathlib import Path
|
|
@@ -19,6 +20,29 @@ from latticeai.core.quiet import quiet
|
|
|
19
20
|
from latticeai.models.router import hf_cache_model_dir, hf_model_dir
|
|
20
21
|
from latticeai.services.model_errors import ModelRuntimeError
|
|
21
22
|
|
|
23
|
+
_AUXILIARY_GGUF_PREFIXES = ("mmproj-", "mtp-", "dflash-", "eagle3-")
|
|
24
|
+
GGUF_QUANT_PREFERENCE = ("q4_k_m", "q4_0", "mxfp4", "q4_k_s", "q3_k_m", "q2_k", "q8_0")
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
def is_auxiliary_gguf(filename: str) -> bool:
|
|
28
|
+
base = Path(str(filename)).name.lower()
|
|
29
|
+
return base.startswith(_AUXILIARY_GGUF_PREFIXES) or "imatrix" in base
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
def _shards_complete(model_dir: Path) -> bool:
|
|
33
|
+
index_file = model_dir / "model.safetensors.index.json"
|
|
34
|
+
if not index_file.exists():
|
|
35
|
+
return True
|
|
36
|
+
try:
|
|
37
|
+
payload = json.loads(index_file.read_text(encoding="utf-8"))
|
|
38
|
+
weight_map = payload.get("weight_map") if isinstance(payload, dict) else None
|
|
39
|
+
if isinstance(weight_map, dict) and weight_map:
|
|
40
|
+
shards = {str(shard) for shard in weight_map.values() if shard}
|
|
41
|
+
return all((model_dir / shard).exists() for shard in shards)
|
|
42
|
+
except Exception:
|
|
43
|
+
quiet()
|
|
44
|
+
return True
|
|
45
|
+
|
|
22
46
|
|
|
23
47
|
def hf_model_ready(repo_id: str, provider: str = "local_mlx") -> bool:
|
|
24
48
|
model_dir = hf_model_dir(repo_id)
|
|
@@ -32,9 +56,11 @@ def hf_model_ready(repo_id: str, provider: str = "local_mlx") -> bool:
|
|
|
32
56
|
if not model_dir.exists() or not model_dir.is_dir():
|
|
33
57
|
return False
|
|
34
58
|
if provider == "llamacpp":
|
|
35
|
-
return any(model_dir.rglob("*.gguf"))
|
|
59
|
+
return any(not is_auxiliary_gguf(p.name) for p in model_dir.rglob("*.gguf"))
|
|
36
60
|
has_config = (model_dir / "config.json").exists()
|
|
37
|
-
has_weights =
|
|
61
|
+
has_weights = (
|
|
62
|
+
any(model_dir.glob("*.safetensors")) or any(model_dir.glob("*.bin"))
|
|
63
|
+
) and _shards_complete(model_dir)
|
|
38
64
|
has_tokenizer = (
|
|
39
65
|
(model_dir / "tokenizer.json").exists()
|
|
40
66
|
or (model_dir / "tokenizer.model").exists()
|
|
@@ -139,15 +165,36 @@ def download_hf_model(
|
|
|
139
165
|
[item for item in all_files if str(item["name"]).lower().endswith(".gguf")],
|
|
140
166
|
key=lambda item: str(item["name"]),
|
|
141
167
|
)
|
|
142
|
-
if not
|
|
168
|
+
primary_ggufs = [item for item in ggufs if not is_auxiliary_gguf(str(item["name"]))]
|
|
169
|
+
if not primary_ggufs:
|
|
143
170
|
raise RuntimeError("GGUF 파일을 찾지 못했습니다.")
|
|
144
|
-
preference = ("q4_k_m", "q4_0", "q4_k_s", "q3_k_m", "q2_k")
|
|
145
171
|
selected_files = [
|
|
146
172
|
next(
|
|
147
|
-
(
|
|
148
|
-
|
|
173
|
+
(
|
|
174
|
+
item
|
|
175
|
+
for pref in GGUF_QUANT_PREFERENCE
|
|
176
|
+
for item in primary_ggufs
|
|
177
|
+
if pref in str(item["name"]).lower()
|
|
178
|
+
),
|
|
179
|
+
primary_ggufs[0],
|
|
149
180
|
)
|
|
150
181
|
]
|
|
182
|
+
mmprojs = [
|
|
183
|
+
item
|
|
184
|
+
for item in ggufs
|
|
185
|
+
if Path(str(item["name"])).name.lower().startswith("mmproj-")
|
|
186
|
+
]
|
|
187
|
+
if mmprojs:
|
|
188
|
+
preferred_mmproj = next(
|
|
189
|
+
(
|
|
190
|
+
item
|
|
191
|
+
for pref in ("bf16", "f16", "f32")
|
|
192
|
+
for item in mmprojs
|
|
193
|
+
if pref in str(item["name"]).lower()
|
|
194
|
+
),
|
|
195
|
+
mmprojs[0],
|
|
196
|
+
)
|
|
197
|
+
selected_files.append(preferred_mmproj)
|
|
151
198
|
else:
|
|
152
199
|
selected_files = all_files
|
|
153
200
|
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ltcai",
|
|
3
|
-
"version": "12.
|
|
3
|
+
"version": "12.4.0",
|
|
4
4
|
"description": "Lattice AI — local-first Digital Brain that keeps your knowledge durable across any AI model.",
|
|
5
5
|
"homepage": "https://github.com/TaeSooPark-PTS/LatticeAI#readme",
|
|
6
6
|
"repository": {
|
|
@@ -111,16 +111,14 @@
|
|
|
111
111
|
"!TOOLS.md",
|
|
112
112
|
"!USER.md",
|
|
113
113
|
"!docs/images/tmp_frames/",
|
|
114
|
-
"
|
|
115
|
-
"
|
|
116
|
-
"
|
|
114
|
+
"!{latticeai,lattice_brain,skills,plugins,scripts}/**/__pycache__/",
|
|
115
|
+
"!{latticeai,lattice_brain,skills,plugins,scripts}/**/*.pyc",
|
|
116
|
+
"!static/**/*.map",
|
|
117
117
|
"README.md",
|
|
118
118
|
"static/vendor/",
|
|
119
119
|
"src-tauri/",
|
|
120
120
|
"!src-tauri/gen/",
|
|
121
|
-
"!src-tauri/gen/**",
|
|
122
121
|
"!src-tauri/target/",
|
|
123
|
-
"!src-tauri/target/**",
|
|
124
122
|
"docs/*.md",
|
|
125
123
|
"!docs/assets/",
|
|
126
124
|
"!docs/images/"
|
|
@@ -142,7 +140,7 @@
|
|
|
142
140
|
"@types/react": "^19.2.17",
|
|
143
141
|
"@types/react-dom": "^19.2.3",
|
|
144
142
|
"@vitejs/plugin-react": "^6.0.2",
|
|
145
|
-
"@vitest/coverage-v8": "^4.1.
|
|
143
|
+
"@vitest/coverage-v8": "^4.1.12",
|
|
146
144
|
"autoprefixer": "^10.5.0",
|
|
147
145
|
"class-variance-authority": "^0.7.1",
|
|
148
146
|
"clsx": "^2.1.1",
|
|
@@ -159,7 +157,7 @@
|
|
|
159
157
|
"tailwindcss": "^4.3.0",
|
|
160
158
|
"typescript": "^5.9.3",
|
|
161
159
|
"vite": "^8.0.16",
|
|
162
|
-
"vitest": "^4.1.
|
|
160
|
+
"vitest": "^4.1.12",
|
|
163
161
|
"zustand": "^5.0.14"
|
|
164
162
|
},
|
|
165
163
|
"overrides": {
|
package/requirements.txt
CHANGED
|
@@ -2,10 +2,12 @@ fastapi>=0.110,<1
|
|
|
2
2
|
uvicorn>=0.29,<1
|
|
3
3
|
pydantic>=2.7,<3
|
|
4
4
|
httpx>=0.27,<1
|
|
5
|
-
pillow>=
|
|
5
|
+
pillow>=13,<14
|
|
6
6
|
openai>=1.30,<3
|
|
7
7
|
python-docx>=1.1,<2
|
|
8
8
|
openpyxl>=3.1,<4
|
|
9
9
|
python-pptx>=0.6.23,<2
|
|
10
10
|
keyring>=24,<26
|
|
11
11
|
pdfplumber>=0.11,<0.12
|
|
12
|
+
reportlab>=4,<5
|
|
13
|
+
huggingface_hub>=1.0,<2
|
|
@@ -6,7 +6,7 @@ const root = process.cwd();
|
|
|
6
6
|
const pkg = JSON.parse(readFileSync(path.join(root, "package.json"), "utf8"));
|
|
7
7
|
const version = pkg.version;
|
|
8
8
|
const releaseDir = `output/release/v${version}`;
|
|
9
|
-
const releaseTheme = "
|
|
9
|
+
const releaseTheme = "Sharp Weight";
|
|
10
10
|
const title = `${version} — ${releaseTheme}`;
|
|
11
11
|
const escapedVersion = version.replaceAll(".", "\\.");
|
|
12
12
|
|
|
@@ -20,6 +20,30 @@
|
|
|
20
20
|
"whole-image delta: naming where the change is makes the claim more",
|
|
21
21
|
"specific, not less."
|
|
22
22
|
],
|
|
23
|
+
"12.4.0": {
|
|
24
|
+
"_why": [
|
|
25
|
+
"Sharp Weight is a model catalog and security audit release: Qwen 3.8 27B",
|
|
26
|
+
"4-bit and Gemma 4 26B A4B QAT / QAT-OptiQ 4-bit catalog expansion,",
|
|
27
|
+
"Pillow 13.0.0 and npm lockfile vulnerability closure, model_engines",
|
|
28
|
+
"URL scheme validation, and scoped Tailwind CSS v4 source scanning.",
|
|
29
|
+
"",
|
|
30
|
+
"No screen was redesigned. Empty claim set on purpose. Unclaimed screens",
|
|
31
|
+
"are still measured and printed; they are not gated."
|
|
32
|
+
]
|
|
33
|
+
},
|
|
34
|
+
"12.3.0": {
|
|
35
|
+
"_why": [
|
|
36
|
+
"Live Wire is a backend and runtime release: verified Hugging Face GGUF",
|
|
37
|
+
"quantization tags (Q4_0 for gemma-4, MXFP4 for gpt-oss-20b), Qwen3.5-9B",
|
|
38
|
+
"and Qwen3.6-35B-A3B GGUF routing, auxiliary GGUF filtering + companion",
|
|
39
|
+
"mmproj- download for llama-server, shard-index verification, small-model",
|
|
40
|
+
"tool/MCP argument recovery and fenced HTML salvage, full HTML structure",
|
|
41
|
+
"inspection in /tools/inspect_html, and UTF-8 / RFC 5987 download headers.",
|
|
42
|
+
"",
|
|
43
|
+
"No screen was redesigned. Empty claim set on purpose. Unclaimed screens",
|
|
44
|
+
"are still measured and printed; they are not gated."
|
|
45
|
+
]
|
|
46
|
+
},
|
|
23
47
|
"12.2.1": {
|
|
24
48
|
"_why": [
|
|
25
49
|
"True Count is a backend honesty release: HNSW COUNT+delta, SkipByHash",
|
package/src-tauri/Cargo.lock
CHANGED
|
@@ -1863,7 +1863,7 @@ dependencies = [
|
|
|
1863
1863
|
|
|
1864
1864
|
[[package]]
|
|
1865
1865
|
name = "lattice-agent"
|
|
1866
|
-
version = "12.
|
|
1866
|
+
version = "12.4.0"
|
|
1867
1867
|
dependencies = [
|
|
1868
1868
|
"axum",
|
|
1869
1869
|
"base64 0.22.1",
|
|
@@ -1880,7 +1880,7 @@ dependencies = [
|
|
|
1880
1880
|
|
|
1881
1881
|
[[package]]
|
|
1882
1882
|
name = "lattice-ai-desktop"
|
|
1883
|
-
version = "12.
|
|
1883
|
+
version = "12.4.0"
|
|
1884
1884
|
dependencies = [
|
|
1885
1885
|
"lattice-host",
|
|
1886
1886
|
"lattice-jobs",
|
|
@@ -1895,7 +1895,7 @@ dependencies = [
|
|
|
1895
1895
|
|
|
1896
1896
|
[[package]]
|
|
1897
1897
|
name = "lattice-auth"
|
|
1898
|
-
version = "12.
|
|
1898
|
+
version = "12.4.0"
|
|
1899
1899
|
dependencies = [
|
|
1900
1900
|
"axum",
|
|
1901
1901
|
"base64 0.22.1",
|
|
@@ -1912,7 +1912,7 @@ dependencies = [
|
|
|
1912
1912
|
|
|
1913
1913
|
[[package]]
|
|
1914
1914
|
name = "lattice-chat"
|
|
1915
|
-
version = "12.
|
|
1915
|
+
version = "12.4.0"
|
|
1916
1916
|
dependencies = [
|
|
1917
1917
|
"axum",
|
|
1918
1918
|
"bytes",
|
|
@@ -1934,7 +1934,7 @@ dependencies = [
|
|
|
1934
1934
|
|
|
1935
1935
|
[[package]]
|
|
1936
1936
|
name = "lattice-core"
|
|
1937
|
-
version = "12.
|
|
1937
|
+
version = "12.4.0"
|
|
1938
1938
|
dependencies = [
|
|
1939
1939
|
"blake2",
|
|
1940
1940
|
"bytes",
|
|
@@ -1950,7 +1950,7 @@ dependencies = [
|
|
|
1950
1950
|
|
|
1951
1951
|
[[package]]
|
|
1952
1952
|
name = "lattice-host"
|
|
1953
|
-
version = "12.
|
|
1953
|
+
version = "12.4.0"
|
|
1954
1954
|
dependencies = [
|
|
1955
1955
|
"axum",
|
|
1956
1956
|
"lattice-agent",
|
|
@@ -1971,7 +1971,7 @@ dependencies = [
|
|
|
1971
1971
|
|
|
1972
1972
|
[[package]]
|
|
1973
1973
|
name = "lattice-ingest"
|
|
1974
|
-
version = "12.
|
|
1974
|
+
version = "12.4.0"
|
|
1975
1975
|
dependencies = [
|
|
1976
1976
|
"axum",
|
|
1977
1977
|
"lattice-auth",
|
|
@@ -1986,7 +1986,7 @@ dependencies = [
|
|
|
1986
1986
|
|
|
1987
1987
|
[[package]]
|
|
1988
1988
|
name = "lattice-jobs"
|
|
1989
|
-
version = "12.
|
|
1989
|
+
version = "12.4.0"
|
|
1990
1990
|
dependencies = [
|
|
1991
1991
|
"axum",
|
|
1992
1992
|
"lattice-auth",
|
|
@@ -2001,7 +2001,7 @@ dependencies = [
|
|
|
2001
2001
|
|
|
2002
2002
|
[[package]]
|
|
2003
2003
|
name = "lattice-platform"
|
|
2004
|
-
version = "12.
|
|
2004
|
+
version = "12.4.0"
|
|
2005
2005
|
dependencies = [
|
|
2006
2006
|
"axum",
|
|
2007
2007
|
"base64 0.22.1",
|
|
@@ -2024,7 +2024,7 @@ dependencies = [
|
|
|
2024
2024
|
|
|
2025
2025
|
[[package]]
|
|
2026
2026
|
name = "lattice-retrieval"
|
|
2027
|
-
version = "12.
|
|
2027
|
+
version = "12.4.0"
|
|
2028
2028
|
dependencies = [
|
|
2029
2029
|
"axum",
|
|
2030
2030
|
"fancy-regex",
|
package/src-tauri/Cargo.toml
CHANGED
|
@@ -1,55 +1,54 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "12.
|
|
2
|
+
"version": "12.4.0",
|
|
3
3
|
"generated_at": "vite",
|
|
4
4
|
"entrypoints": {
|
|
5
|
-
"app": "/static/app/assets/index-
|
|
5
|
+
"app": "/static/app/assets/index-CHQbWj9a.js"
|
|
6
6
|
},
|
|
7
7
|
"assets": {
|
|
8
8
|
"../node_modules/@tauri-apps/api/core.js": "/static/app/assets/core-CwxXejkd.js",
|
|
9
|
-
"_BrainSignals-
|
|
10
|
-
"_LivingBrain-
|
|
11
|
-
"_QueryClientProvider-
|
|
12
|
-
"_ReviewCard-
|
|
13
|
-
"_actHelpers-
|
|
14
|
-
"_arrow-left-
|
|
15
|
-
"_bot-
|
|
16
|
-
"_brain-
|
|
17
|
-
"_button-
|
|
18
|
-
"_circle-check-
|
|
19
|
-
"_circle-pause-
|
|
20
|
-
"_circle-play-
|
|
21
|
-
"_cpu-
|
|
22
|
-
"_download-
|
|
23
|
-
"_folder-open-
|
|
24
|
-
"_hard-drive-
|
|
25
|
-
"_input-
|
|
26
|
-
"_jsx-runtime-
|
|
27
|
-
"_link-2-
|
|
28
|
-
"_permissionCopy-
|
|
29
|
-
"_primitives-
|
|
30
|
-
"_search-
|
|
31
|
-
"_share-2-
|
|
32
|
-
"_shield-alert-
|
|
33
|
-
"
|
|
34
|
-
"
|
|
35
|
-
"
|
|
36
|
-
"
|
|
37
|
-
"
|
|
38
|
-
"index.
|
|
39
|
-
"
|
|
40
|
-
"src/
|
|
41
|
-
"src/features/act/
|
|
42
|
-
"src/features/act/
|
|
43
|
-
"src/features/
|
|
44
|
-
"src/features/
|
|
45
|
-
"src/features/
|
|
46
|
-
"src/
|
|
47
|
-
"src/pages/
|
|
48
|
-
"src/pages/
|
|
49
|
-
"src/pages/
|
|
50
|
-
"src/pages/
|
|
51
|
-
"src/pages/
|
|
52
|
-
"src/pages/
|
|
53
|
-
"src/pages/brain/DigitalBrainExplorer.tsx": "/static/app/assets/DigitalBrainExplorer-mH6ZSuvK.js"
|
|
9
|
+
"_BrainSignals-ShxKNNqr.js": "/static/app/assets/BrainSignals-ShxKNNqr.js",
|
|
10
|
+
"_LivingBrain-u9X_XGC2.js": "/static/app/assets/LivingBrain-u9X_XGC2.js",
|
|
11
|
+
"_QueryClientProvider-CTiSBeU6.js": "/static/app/assets/QueryClientProvider-CTiSBeU6.js",
|
|
12
|
+
"_ReviewCard-C64YFHOR.js": "/static/app/assets/ReviewCard-C64YFHOR.js",
|
|
13
|
+
"_actHelpers-BjMnKMCI.js": "/static/app/assets/actHelpers-BjMnKMCI.js",
|
|
14
|
+
"_arrow-left-Cbck4Ig2.js": "/static/app/assets/arrow-left-Cbck4Ig2.js",
|
|
15
|
+
"_bot-Qgvc2PGU.js": "/static/app/assets/bot-Qgvc2PGU.js",
|
|
16
|
+
"_brain-BwGnubn8.js": "/static/app/assets/brain-BwGnubn8.js",
|
|
17
|
+
"_button-DEloiIsj.js": "/static/app/assets/button-DEloiIsj.js",
|
|
18
|
+
"_circle-check-CDygnRMn.js": "/static/app/assets/circle-check-CDygnRMn.js",
|
|
19
|
+
"_circle-pause-CkkmXxA9.js": "/static/app/assets/circle-pause-CkkmXxA9.js",
|
|
20
|
+
"_circle-play-rnb6A1zq.js": "/static/app/assets/circle-play-rnb6A1zq.js",
|
|
21
|
+
"_cpu-CzcGFQQq.js": "/static/app/assets/cpu-CzcGFQQq.js",
|
|
22
|
+
"_download-BTQigJvp.js": "/static/app/assets/download-BTQigJvp.js",
|
|
23
|
+
"_folder-open-CIXPPhhm.js": "/static/app/assets/folder-open-CIXPPhhm.js",
|
|
24
|
+
"_hard-drive-CZXxdIcT.js": "/static/app/assets/hard-drive-CZXxdIcT.js",
|
|
25
|
+
"_input-CTZHuOXe.js": "/static/app/assets/input-CTZHuOXe.js",
|
|
26
|
+
"_jsx-runtime-CU_pEDDh.js": "/static/app/assets/jsx-runtime-CU_pEDDh.js",
|
|
27
|
+
"_link-2-BsG1NQUA.js": "/static/app/assets/link-2-BsG1NQUA.js",
|
|
28
|
+
"_permissionCopy-klyWL3ai.js": "/static/app/assets/permissionCopy-klyWL3ai.js",
|
|
29
|
+
"_primitives-ZmN4jzq-.js": "/static/app/assets/primitives-ZmN4jzq-.js",
|
|
30
|
+
"_search-xjKVb4Nh.js": "/static/app/assets/search-xjKVb4Nh.js",
|
|
31
|
+
"_share-2-Cuv9rj7A.js": "/static/app/assets/share-2-Cuv9rj7A.js",
|
|
32
|
+
"_shield-alert-KKySFd03.js": "/static/app/assets/shield-alert-KKySFd03.js",
|
|
33
|
+
"_textarea-CBwqgGSA.js": "/static/app/assets/textarea-CBwqgGSA.js",
|
|
34
|
+
"_useFocusTrap-D93vds_Z.js": "/static/app/assets/useFocusTrap-D93vds_Z.js",
|
|
35
|
+
"_useMutation-B9hHPD0p.js": "/static/app/assets/useMutation-B9hHPD0p.js",
|
|
36
|
+
"_workspace-JGzrc0D8.js": "/static/app/assets/workspace-JGzrc0D8.js",
|
|
37
|
+
"index.html": "/static/app/assets/index-CHQbWj9a.js",
|
|
38
|
+
"assets/index-C_dThdD6.css": "/static/app/assets/index-C_dThdD6.css",
|
|
39
|
+
"src/components/ProductFlow.tsx": "/static/app/assets/ProductFlow-CpX0BMr9.js",
|
|
40
|
+
"src/features/act/RunsListPanel.tsx": "/static/app/assets/RunsListPanel-DKZEJcxF.js",
|
|
41
|
+
"src/features/act/WorkflowGraph.tsx": "/static/app/assets/WorkflowGraph-CE6XgWjJ.js",
|
|
42
|
+
"src/features/act/WorkflowsPanel.tsx": "/static/app/assets/WorkflowsPanel-MKU05J7_.js",
|
|
43
|
+
"src/features/admin/AdminConsole.tsx": "/static/app/assets/AdminConsole-iLFwSJSg.js",
|
|
44
|
+
"src/features/brain/BrainHome.tsx": "/static/app/assets/BrainHome-CfiJ4tau.js",
|
|
45
|
+
"src/features/command/CommandPalette.tsx": "/static/app/assets/CommandPalette-Cb_GWoYC.js",
|
|
46
|
+
"src/pages/Act.tsx": "/static/app/assets/Act-inLiZfDE.js",
|
|
47
|
+
"src/pages/Brain.tsx": "/static/app/assets/Brain-Cb7noiNc.js",
|
|
48
|
+
"src/pages/Capture.tsx": "/static/app/assets/Capture-Cajj1Trf.js",
|
|
49
|
+
"src/pages/Chronicle.tsx": "/static/app/assets/Chronicle-CPd8GP_O.js",
|
|
50
|
+
"src/pages/Library.tsx": "/static/app/assets/Library-Dk5Mefl_.js",
|
|
51
|
+
"src/pages/System.tsx": "/static/app/assets/System-Dretrknf.js",
|
|
52
|
+
"src/pages/brain/DigitalBrainExplorer.tsx": "/static/app/assets/DigitalBrainExplorer-Df6KVrBz.js"
|
|
54
53
|
}
|
|
55
54
|
}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["assets/RunsListPanel-DKZEJcxF.js","assets/jsx-runtime-CU_pEDDh.js","assets/workspace-JGzrc0D8.js","assets/index-CHQbWj9a.js","assets/QueryClientProvider-CTiSBeU6.js","assets/index-C_dThdD6.css","assets/primitives-ZmN4jzq-.js","assets/useMutation-B9hHPD0p.js","assets/circle-check-CDygnRMn.js","assets/button-DEloiIsj.js","assets/actHelpers-BjMnKMCI.js","assets/circle-play-rnb6A1zq.js","assets/WorkflowsPanel-MKU05J7_.js","assets/input-CTZHuOXe.js","assets/textarea-CBwqgGSA.js","assets/folder-open-CIXPPhhm.js"])))=>i.map(i=>d[i]);
|
|
2
|
+
import{i as e,n as t,t as n}from"./jsx-runtime-CU_pEDDh.js";import"./workspace-JGzrc0D8.js";import{t as r}from"./useMutation-B9hHPD0p.js";import{D as i,H as a,R as o,S as s,b as c,i as l,k as u,o as d,v as f,z as p}from"./index-CHQbWj9a.js";import{n as m}from"./QueryClientProvider-CTiSBeU6.js";import{t as h}from"./bot-Qgvc2PGU.js";import{t as g}from"./circle-pause-CkkmXxA9.js";import{_,c as v,d as y,g as b,h as x,i as S,m as C,n as w,o as T,p as E,r as D,s as O,t as k,u as A,v as j}from"./primitives-ZmN4jzq-.js";import{t as M}from"./button-DEloiIsj.js";import{t as N}from"./input-CTZHuOXe.js";import{t as P}from"./textarea-CBwqgGSA.js";import{a as F,i as I,n as L,r as R}from"./ReviewCard-C64YFHOR.js";var z=o(`play`,[[`path`,{d:`M5 5a2 2 0 0 1 3.008-1.728l11.997 6.998a2 2 0 0 1 .003 3.458l-12 7A2 2 0 0 1 5 19z`,key:`10ikf1`}]]),B=e(t()),V=n();function H(){let e=p(e=>e.language),t=m(),[n,r]=B.useState(`pending`),[i,o]=B.useState(`all`),[c,l]=B.useState({}),u=a({queryKey:[`automationReviews`,n,i],queryFn:()=>f.automationReviews({...n===`all`?{}:{status:n},...i===`all`?{}:{source:i}})}),d=u.data?.data.items||[],h=a({queryKey:[`proposalCounts`],queryFn:f.proposalCounts}),g=Number(h.data?.data?.pending||0),_=async(n,r,i=!1,a)=>{let o=await(r===`approve`?()=>f.approveReviewItem(n.id):r===`dismiss`?n.source===`change_proposal`?()=>f.rejectProposal(n.id,a||``):()=>f.dismissReviewItem(n.id):r===`snooze`?()=>f.snoozeReviewItem(n.id,R()):r===`unsnooze`?()=>f.unsnoozeReviewItem(n.id):()=>f.runNowReviewItem(n.id))();if(!o.ok){let t=r===`approve`&&n.source===`change_proposal`&&o.status===409;return l(r=>({...r,[n.id]:t?{tone:`error`,message:s(e,`proposals.conflict.title`),conflict:!0}:{tone:`error`,message:s(e,`review.feedback.error`),...o.error?{detail:o.error}:{}}})),o}if(r===`run_now`){let t=o.data.payload||{},r=o.data.provenance||{},a=String(t.last_run_id||r.run_id||``),c=i?s(e,`review.regenerated`):s(e,`review.executed`);l(e=>({...e,[n.id]:{tone:`success`,message:a?`${c} · ${a}`:c}}))}else l(e=>{let t={...e};return delete t[n.id],t});return await Promise.all([t.invalidateQueries({queryKey:[`automationReviews`]}),t.invalidateQueries({queryKey:[`proposalCounts`]}),t.invalidateQueries({queryKey:[`pendingProposals`]})]),o};return u.isLoading?(0,V.jsx)(T,{title:s(e,`review.inbox.title`)}):(0,V.jsxs)(`div`,{className:`review-inbox`,children:[(0,V.jsxs)(`div`,{className:`review-inbox-head`,children:[(0,V.jsxs)(`div`,{children:[(0,V.jsx)(`h2`,{className:`text-xl font-bold`,children:s(e,`review.inbox.title`)}),(0,V.jsx)(`p`,{className:`text-sm text-muted-foreground`,children:s(e,`review.inbox.description`)})]}),(0,V.jsxs)(`div`,{className:`flex flex-wrap items-center gap-2`,children:[g>0?(0,V.jsx)(j,{variant:`warning`,"data-testid":`proposal-count-badge`,children:s(e,`review.proposal.badge`,{count:g})}):null,u.data?(0,V.jsx)(j,{variant:u.data.ok?`success`:`warning`,children:u.data.ok?s(e,`review.status.connected`):s(e,`review.status.unavailable`)}):null]})]}),(0,V.jsxs)(`div`,{className:`flex flex-wrap items-center gap-x-6 gap-y-2 py-1`,children:[(0,V.jsxs)(`div`,{className:`flex min-w-0 flex-wrap items-center gap-2`,children:[(0,V.jsx)(`span`,{id:`review-status-filter-label`,className:`text-xs font-semibold tracking-wide text-muted-foreground`,children:s(e,`review.status.title`)}),(0,V.jsx)(y,{tabs:F.map(t=>({id:t.id,label:s(e,t.labelKey)})),value:n,onChange:e=>r(e),ariaLabelledBy:`review-status-filter-label`})]}),(0,V.jsxs)(`div`,{className:`flex min-w-0 flex-wrap items-center gap-2`,children:[(0,V.jsx)(`span`,{id:`review-source-filter-label`,className:`text-xs font-semibold tracking-wide text-muted-foreground`,children:s(e,`review.source.title`)}),(0,V.jsx)(y,{tabs:I.map(t=>({id:t.id,label:s(e,t.labelKey)})),value:i,onChange:e=>o(e),ariaLabelledBy:`review-source-filter-label`})]})]}),(0,V.jsx)(`div`,{className:`pt-2`,children:u.isError||u.data&&!u.data.ok?(0,V.jsx)(D,{title:s(e,`review.inbox.loadError`),detail:(0,V.jsxs)(V.Fragment,{children:[s(e,`review.inbox.unavailable`),u.data?.error?(0,V.jsx)(`span`,{className:`mt-1 block text-xs opacity-75`,children:u.data.error}):null]})}):d.length?(0,V.jsx)(`div`,{className:`flex flex-col gap-3`,children:d.map(e=>(0,V.jsx)(L,{item:e,feedback:c[e.id],onAction:_},e.id))}):(0,V.jsx)(D,{title:s(e,`review.inbox.empty`),detail:n===`snoozed`?s(e,`review.inbox.emptySnoozed`):s(e,`review.inbox.emptyPending`)})})]})}var U=[{id:`review`,labelKey:`act.tab.review`},{id:`runs`,labelKey:`act.tab.runsHistory`}],W={runs:{titleKey:`act.title.runs`,copyKey:`act.copy.runs`},agents:{titleKey:`act.title.goals`,copyKey:`act.copy.goals`},workflows:{titleKey:`act.title.workflows`,copyKey:`act.copy.workflows`},hooks:{titleKey:`act.title.safeguards`,copyKey:`act.copy.safeguards`},tools:{titleKey:`act.title.permissions`,copyKey:`act.copy.permissions`}},G=[{id:`runs`,labelKey:`act.tab.runs`},{id:`agents`,labelKey:`act.tab.goals`},{id:`workflows`,labelKey:`act.tab.recipes`},{id:`hooks`,labelKey:`act.tab.safeguards`,advancedLabelKey:`act.tab.hooks`},{id:`tools`,labelKey:`act.tab.permissions`,advancedLabelKey:`act.tab.tools`}],K=B.lazy(()=>c(()=>import(`./RunsListPanel-DKZEJcxF.js`).then(e=>({default:e.RunsListPanel})),__vite__mapDeps([0,1,2,3,4,5,6,7,8,9,10,11]))),q=B.lazy(()=>c(()=>import(`./WorkflowsPanel-MKU05J7_.js`).then(e=>({default:e.WorkflowsPanel})),__vite__mapDeps([12,1,2,3,4,5,7,6,8,9,13,14,15,10,11])));function J({initialTab:e}){let t=p(e=>e.mode),n=p(e=>e.language),[r,a]=B.useState(()=>e===`agents`||e===`workflows`||e===`hooks`||e===`tools`?e:`runs`),[o,c]=B.useState(e===`runs`?`runs`:`review`);B.useEffect(()=>{e===`review`?(a(`runs`),c(`review`)):e===`runs`?(a(`runs`),c(`runs`)):G.some(t=>t.id===e)&&a(e)},[e]);let u=e=>{a(e),d(`/`+e)},f=e=>{c(e),d(e===`review`?`/review`:`/runs`)},{titleKey:m,copyKey:h}=W[r];return(0,V.jsxs)(`div`,{className:`product-page act-page space-y-5`,children:[(0,V.jsxs)(`header`,{className:`page-hero`,children:[(0,V.jsxs)(`div`,{className:`page-kicker`,children:[(0,V.jsx)(i,{className:`h-4 w-4`}),` `,s(n,`act.kicker`)]}),(0,V.jsx)(`h1`,{className:`page-title`,children:s(n,m)}),(0,V.jsx)(`p`,{className:`page-copy`,children:s(n,h)})]}),(0,V.jsx)(y,{tabs:(t===`basic`?G.filter(e=>e.id===`runs`||e.id===`agents`||e.id===`workflows`):G).map(e=>({id:e.id,label:s(n,t===`basic`||!e.advancedLabelKey?e.labelKey:e.advancedLabelKey)})),value:r,onChange:e=>u(e)}),r===`runs`?(0,V.jsx)(X,{subTab:o,onSubTabChange:f}):null,r===`agents`?(0,V.jsx)(Y,{}):null,r===`workflows`?(0,V.jsx)(l,{language:n,resetKey:`act-workflows`,children:(0,V.jsx)(q,{})}):null,r===`hooks`?(0,V.jsx)(Z,{}):null,r===`tools`?(0,V.jsx)(Q,{}):null]})}function Y(){let e=m(),t=p(e=>e.mode),n=p(e=>e.language),[i,o]=B.useState(``),c=a({queryKey:[`agentRuntime`],queryFn:f.agentRuntime}),l=a({queryKey:[`agentRegistry`],queryFn:f.agentRegistry,enabled:t!==`basic`}),d=a({queryKey:[`agentCapabilities`],queryFn:f.agentCapabilities,enabled:t!==`basic`}),g=r({mutationFn:()=>f.runAgent(i,[`planner`,`executor`,`reviewer`]),onSuccess:()=>e.invalidateQueries({queryKey:[`agentRuntime`]})}),[y,T]=B.useState(``),D=r({mutationFn:()=>f.registerAgent({name:y,type:`custom`,capabilities:[]}),onSuccess:()=>e.invalidateQueries({queryKey:[`agentRegistry`]})}),O=(c.data?.data||{}).runtime||{},k=!!O.ready,F=t===`basic`?s(n,`act.goal.modelRequired`):String(O.unavailable_reason||s(n,`act.runtime.modelUnavailable`)),I=!!i.trim()&&k&&!g.isPending;return(0,V.jsxs)(`div`,{className:`work-start-flow flex flex-col gap-4`,children:[(0,V.jsxs)(E,{className:`work-goal-card`,children:[(0,V.jsxs)(b,{children:[(0,V.jsxs)(_,{className:`flex items-center gap-2`,children:[(0,V.jsx)(h,{className:`h-4 w-4`}),` `,s(n,`act.goal.title`)]}),(0,V.jsx)(x,{children:s(n,`act.goal.description`)})]}),(0,V.jsxs)(C,{className:`space-y-3`,children:[(0,V.jsx)(P,{value:i,onChange:e=>o(e.target.value),placeholder:s(n,`act.goal.placeholder`)}),k?null:(0,V.jsx)(j,{variant:`warning`,children:F}),(0,V.jsxs)(M,{className:`w-full`,variant:k?`default`:`outline`,disabled:!I,onClick:()=>g.mutate(),children:[(0,V.jsx)(z,{className:`h-4 w-4`}),` `,k?s(n,`act.goal.start`):s(n,`act.goal.needsModel`)]}),g.data?(0,V.jsx)(v,{result:g.data,successLabel:s(n,`act.goal.completed`)}):null,g.data&&g.data?.data?(0,V.jsx)(`div`,{className:`text-xs text-emerald-600`,children:s(n,`act.goal.brainSaved`)}):null]})]}),t===`basic`?(0,V.jsxs)(`div`,{className:`work-safety-note`,children:[(0,V.jsx)(u,{className:`h-4 w-4`,"aria-hidden":`true`}),(0,V.jsx)(`span`,{children:s(n,`act.goal.safety`)})]}):(0,V.jsxs)(V.Fragment,{children:[(0,V.jsx)(w,{title:s(n,`act.panel.readiness`),result:c.data,children:e=>(0,V.jsx)(A,{value:e})}),(0,V.jsx)(w,{title:s(n,`act.panel.agentTeam`),result:l.data,children:e=>(0,V.jsxs)(`div`,{className:`space-y-3`,children:[(0,V.jsx)(S,{items:e.agents,titleKey:`name`,metaKey:`type`,labelPrefix:`act.agentRole`}),(0,V.jsxs)(`div`,{className:`flex gap-2`,children:[(0,V.jsx)(N,{value:y,onChange:e=>T(e.target.value),placeholder:s(n,`act.agent.namePlaceholder`)}),(0,V.jsx)(M,{disabled:!y.trim()||D.isPending,onClick:()=>D.mutate(),children:s(n,`act.agent.register`)})]})]})}),(0,V.jsx)(w,{title:s(n,`act.panel.capabilities`),result:d.data,children:e=>(0,V.jsx)(A,{value:e})})]})]})}function X({subTab:e,onSubTabChange:t}){let n=p(e=>e.language);return(0,V.jsxs)(`div`,{className:`space-y-4`,children:[(0,V.jsx)(y,{tabs:U.map(e=>({id:e.id,label:s(n,e.labelKey)})),value:e,onChange:e=>t(e)}),e===`runs`?(0,V.jsx)(l,{language:n,resetKey:`act-runs`,children:(0,V.jsx)(K,{})}):(0,V.jsx)(H,{})]})}function Z(){let e=p(e=>e.mode),t=p(e=>e.language),n=a({queryKey:[`hooks`],queryFn:f.hooks}),r=a({queryKey:[`hookRuns`],queryFn:f.hookRuns});return e===`basic`?(0,V.jsxs)(`div`,{className:`flex flex-col gap-4`,children:[(0,V.jsx)(w,{title:s(t,`act.panel.safeguards`),result:n.data,children:e=>(0,V.jsx)(S,{items:e.hooks,titleKey:`name`,metaKey:`kind`})}),(0,V.jsx)(O,{title:s(t,`act.hooks.detailed`),detail:s(t,`act.hooks.detailedHint`)})]}):(0,V.jsxs)(`div`,{className:`flex flex-col gap-4`,children:[(0,V.jsx)(w,{title:s(t,`act.panel.hooks`),result:n.data,children:e=>(0,V.jsx)(S,{items:e.hooks,titleKey:`name`,metaKey:`kind`})}),(0,V.jsx)(w,{title:s(t,`act.panel.hookRuns`),result:r.data,children:e=>(0,V.jsx)(S,{items:e.runs,titleKey:`hook_id`,metaKey:`status`})}),(0,V.jsxs)(E,{children:[(0,V.jsxs)(b,{children:[(0,V.jsxs)(_,{className:`flex items-center gap-2`,children:[(0,V.jsx)(g,{className:`h-4 w-4`}),` `,s(t,`act.hooks.runManual`)]}),(0,V.jsx)(x,{children:s(t,`act.hooks.runManualHint`)})]}),(0,V.jsx)(C,{children:(0,V.jsx)(k,{label:s(t,`act.hooks.runAll`),action:()=>f.hookRun({event:`manual`}),invalidate:[`hookRuns`]})})]})]})}function Q(){let e=p(e=>e.language),t=a({queryKey:[`toolPermissions`],queryFn:f.toolPermissions});return(0,V.jsx)(w,{title:s(e,`act.panel.permissions`),result:t.data,children:e=>(0,V.jsx)(S,{items:e.permissions||e,titleKey:`tool`,metaKey:`risk`})})}export{J as ActPage};
|