ltcai 9.0.0 → 9.1.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 +80 -46
- package/auto_setup.py +7 -853
- package/desktop/electron/README.md +9 -0
- package/desktop/electron/main.cjs +5 -3
- package/docs/CHANGELOG.md +146 -2
- package/docs/COMMUNITY_AND_PLUGINS.md +3 -2
- package/docs/DEVELOPMENT.md +53 -14
- package/docs/LEGACY_COMPATIBILITY.md +4 -4
- package/docs/ONBOARDING.md +10 -2
- package/docs/OPERATIONS.md +8 -4
- package/docs/PRODUCT_DIRECTION_REVIEW.md +4 -0
- package/docs/TRUST_MODEL.md +5 -2
- package/docs/WHY_LATTICE.md +15 -10
- package/docs/WORKFLOW_DESIGNER.md +22 -0
- package/docs/kg-schema.md +13 -2
- package/docs/mcp-tools.md +17 -6
- package/docs/privacy.md +19 -3
- package/docs/public-deploy.md +32 -3
- package/docs/security-model.md +46 -11
- package/lattice_brain/__init__.py +1 -1
- package/lattice_brain/archive.py +1 -6
- package/lattice_brain/context.py +66 -9
- package/lattice_brain/graph/_kg_fsutil.py +1 -5
- package/lattice_brain/graph/discovery_index.py +174 -20
- package/lattice_brain/graph/documents.py +44 -9
- package/lattice_brain/graph/ingest.py +47 -20
- package/lattice_brain/graph/provenance.py +13 -6
- package/lattice_brain/graph/retrieval.py +140 -39
- package/lattice_brain/graph/retrieval_docgen.py +37 -4
- package/lattice_brain/ingestion.py +4 -7
- package/lattice_brain/portability.py +28 -14
- package/lattice_brain/runtime/agent_runtime.py +5 -9
- package/lattice_brain/runtime/hooks.py +30 -13
- package/lattice_brain/runtime/multi_agent.py +27 -8
- package/lattice_brain/runtime/statuses.py +10 -0
- package/lattice_brain/utils.py +20 -2
- package/lattice_brain/workflow.py +1 -5
- package/latticeai/__init__.py +1 -1
- package/latticeai/api/admin.py +1 -1
- package/latticeai/api/agent_registry.py +10 -8
- package/latticeai/api/agents.py +22 -3
- package/latticeai/api/auth.py +78 -16
- package/latticeai/api/browser.py +303 -34
- package/latticeai/api/chat.py +320 -850
- package/latticeai/api/chat_agent_http.py +356 -0
- package/latticeai/api/chat_contracts.py +54 -0
- package/latticeai/api/chat_documents.py +256 -0
- package/latticeai/api/chat_helpers.py +24 -1
- package/latticeai/api/chat_history.py +99 -0
- package/latticeai/api/chat_intents.py +302 -0
- package/latticeai/api/chat_stream.py +115 -0
- package/latticeai/api/computer_use.py +62 -9
- package/latticeai/api/health.py +9 -3
- package/latticeai/api/hooks.py +17 -6
- package/latticeai/api/knowledge_graph.py +78 -14
- package/latticeai/api/local_files.py +7 -2
- package/latticeai/api/mcp.py +102 -23
- package/latticeai/api/models.py +72 -33
- package/latticeai/api/network.py +5 -5
- package/latticeai/api/permissions.py +67 -26
- package/latticeai/api/plugins.py +21 -7
- package/latticeai/api/portability.py +5 -5
- package/latticeai/api/realtime.py +33 -5
- package/latticeai/api/setup.py +2 -2
- package/latticeai/api/static_routes.py +123 -24
- package/latticeai/api/tools.py +96 -14
- package/latticeai/api/workflow_designer.py +37 -0
- package/latticeai/api/workspace.py +2 -1
- package/latticeai/app_factory.py +110 -52
- package/latticeai/core/agent.py +19 -9
- package/latticeai/core/agent_registry.py +1 -5
- package/latticeai/core/config.py +23 -3
- package/latticeai/core/context_builder.py +21 -3
- package/latticeai/core/invitations.py +1 -4
- package/latticeai/core/io_utils.py +9 -1
- package/latticeai/core/legacy_compatibility.py +24 -3
- package/latticeai/core/marketplace.py +1 -1
- package/latticeai/core/plugins.py +15 -0
- package/latticeai/core/policy.py +1 -1
- package/latticeai/core/realtime.py +38 -15
- package/latticeai/core/sessions.py +7 -2
- package/latticeai/core/timeutil.py +10 -0
- package/latticeai/core/tool_registry.py +90 -18
- package/latticeai/core/users.py +1 -5
- package/latticeai/core/workspace_graph_trace.py +31 -5
- package/latticeai/core/workspace_memory.py +3 -1
- package/latticeai/core/workspace_os.py +18 -7
- package/latticeai/core/workspace_os_utils.py +0 -5
- package/latticeai/core/workspace_permissions.py +2 -1
- package/latticeai/core/workspace_plugins.py +1 -1
- package/latticeai/core/workspace_runs.py +14 -5
- package/latticeai/core/workspace_skills.py +1 -1
- package/latticeai/core/workspace_snapshots.py +2 -1
- package/latticeai/core/workspace_timeline.py +2 -1
- package/latticeai/integrations/telegram_bot.py +94 -43
- package/latticeai/models/router.py +130 -36
- package/latticeai/runtime/access_runtime.py +62 -4
- package/latticeai/runtime/automation_runtime.py +13 -7
- package/latticeai/runtime/brain_runtime.py +19 -7
- package/latticeai/runtime/chat_wiring.py +2 -0
- package/latticeai/runtime/config_runtime.py +58 -26
- package/latticeai/runtime/context_runtime.py +16 -4
- package/latticeai/runtime/hooks_runtime.py +1 -1
- package/latticeai/runtime/model_wiring.py +33 -5
- package/latticeai/runtime/namespace_runtime.py +62 -72
- package/latticeai/runtime/platform_runtime_wiring.py +4 -3
- package/latticeai/runtime/review_wiring.py +1 -1
- package/latticeai/runtime/router_registration.py +34 -1
- package/latticeai/runtime/security_runtime.py +110 -13
- package/latticeai/runtime/stages.py +27 -0
- package/latticeai/server_app.py +5 -1
- package/latticeai/services/architecture_readiness.py +74 -5
- package/latticeai/services/brain_automation.py +3 -26
- package/latticeai/services/chat_service.py +205 -15
- package/latticeai/services/local_knowledge.py +423 -0
- package/latticeai/services/memory_service.py +55 -21
- package/latticeai/services/model_engines.py +48 -33
- package/latticeai/services/model_errors.py +17 -0
- package/latticeai/services/model_loading.py +28 -25
- package/latticeai/services/model_runtime.py +228 -162
- package/latticeai/services/p_reinforce.py +22 -3
- package/latticeai/services/platform_runtime.py +83 -23
- package/latticeai/services/product_readiness.py +19 -17
- package/latticeai/services/review_queue.py +12 -0
- package/latticeai/services/router_context.py +1 -0
- package/latticeai/services/run_executor.py +4 -9
- package/latticeai/services/search_service.py +203 -28
- package/latticeai/services/tool_dispatch.py +28 -5
- package/latticeai/services/triggers.py +53 -4
- package/latticeai/services/upload_service.py +13 -2
- package/latticeai/setup/__init__.py +25 -0
- package/latticeai/setup/auto_setup.py +857 -0
- package/latticeai/setup/wizard.py +1264 -0
- package/latticeai/tools/__init__.py +278 -0
- package/{tools → latticeai/tools}/commands.py +67 -7
- package/{tools → latticeai/tools}/computer.py +1 -1
- package/{tools → latticeai/tools}/documents.py +1 -1
- package/{tools → latticeai/tools}/filesystem.py +3 -3
- package/latticeai/tools/knowledge.py +178 -0
- package/{tools → latticeai/tools}/local_files.py +1 -1
- package/{tools → latticeai/tools}/network.py +0 -1
- package/local_knowledge_api.py +4 -342
- package/package.json +22 -2
- package/scripts/brain_quality_eval.py +3 -1
- package/scripts/bump_version.py +3 -0
- package/scripts/capture_release_evidence.mjs +180 -0
- package/scripts/check_current_release_docs.mjs +142 -0
- package/scripts/check_i18n_literals.mjs +107 -31
- package/scripts/check_openapi_drift.mjs +56 -0
- package/scripts/export_openapi.py +67 -7
- package/scripts/i18n_literal_allowlist.json +22 -24
- package/scripts/run_integration_tests.mjs +72 -10
- package/scripts/validate_release_artifacts.py +49 -7
- package/scripts/wheel_smoke.py +5 -0
- package/setup_wizard.py +3 -1260
- package/src-tauri/Cargo.lock +1 -1
- package/src-tauri/Cargo.toml +1 -1
- package/src-tauri/tauri.conf.json +1 -1
- package/static/app/asset-manifest.json +11 -11
- package/static/app/assets/Act-Bzz0bUyW.js +1 -0
- package/static/app/assets/Brain-Dj2J20YA.js +321 -0
- package/static/app/assets/Capture-CqlEl1Ga.js +1 -0
- package/static/app/assets/Library-B03FP1Yx.js +1 -0
- package/static/app/assets/System-80lHW0Ux.js +1 -0
- package/static/app/assets/index-BiMofBTM.js +17 -0
- package/static/app/assets/index-Bmx9rzTc.css +2 -0
- package/static/app/assets/primitives-Q1A96_7v.js +1 -0
- package/static/app/assets/textarea-D13RtnTo.js +1 -0
- package/static/app/index.html +2 -2
- package/static/sw.js +1 -1
- package/tools/__init__.py +21 -269
- package/docs/CODE_REVIEW_2026-07-06.md +0 -764
- package/latticeai/runtime/app_context_runtime.py +0 -13
- package/latticeai/runtime/tail_wiring.py +0 -21
- package/scripts/com.pts.claudecode.discord.plist +0 -31
- package/scripts/pts-claudecode-discord-bridge.mjs +0 -207
- package/scripts/start-pts-claudecode-discord.sh +0 -51
- package/static/app/assets/Act-21lIXx2E.js +0 -1
- package/static/app/assets/Brain-BqUd5UJJ.js +0 -321
- package/static/app/assets/Capture-BA7Z2Q1u.js +0 -1
- package/static/app/assets/Library-bFMtyni3.js +0 -1
- package/static/app/assets/System-K6krGCqn.js +0 -1
- package/static/app/assets/index-C4R3ws30.js +0 -17
- package/static/app/assets/index-ChSeOB02.css +0 -2
- package/static/app/assets/primitives-sQU3it5I.js +0 -1
- package/static/app/assets/textarea-DK3Fd_lR.js +0 -1
- package/tools/knowledge.py +0 -95
|
@@ -21,11 +21,21 @@ from __future__ import annotations
|
|
|
21
21
|
import argparse
|
|
22
22
|
import json
|
|
23
23
|
import re
|
|
24
|
+
import tarfile
|
|
24
25
|
import zipfile
|
|
25
26
|
from pathlib import Path
|
|
26
27
|
from typing import Dict, List, Optional
|
|
27
28
|
|
|
28
29
|
SEMVER_RE = re.compile(r"^\d+\.\d+\.\d+([.-][0-9A-Za-z.]+)?$")
|
|
30
|
+
FORBIDDEN_PERSONAL_PATHS = (
|
|
31
|
+
re.compile(r"(?:^|/)DISCORD_AGENTS\.md$", re.IGNORECASE),
|
|
32
|
+
re.compile(r"(?:^|/)scripts/[^/]*discord-bridge[^/]*\.mjs$", re.IGNORECASE),
|
|
33
|
+
re.compile(r"(?:^|/)scripts/start-[^/]*-discord\.sh$", re.IGNORECASE),
|
|
34
|
+
re.compile(r"(?:^|/)scripts/com\.[^/]*\.discord\.plist$", re.IGNORECASE),
|
|
35
|
+
re.compile(r"(?:^|/)bin/pts-grok$", re.IGNORECASE),
|
|
36
|
+
re.compile(r"(?:^|/)scripts/launch-pts-grok\.sh$", re.IGNORECASE),
|
|
37
|
+
re.compile(r"(?:^|/)(?:HEARTBEAT|IDENTITY|SOUL|TOOLS|USER)\.md$", re.IGNORECASE),
|
|
38
|
+
)
|
|
29
39
|
|
|
30
40
|
|
|
31
41
|
def _expected_names(version: str) -> Dict[str, str]:
|
|
@@ -58,6 +68,36 @@ def _vsix_version(path: Path) -> Optional[str]:
|
|
|
58
68
|
return None
|
|
59
69
|
|
|
60
70
|
|
|
71
|
+
def _forbidden_archive_entries(path: Path) -> List[str]:
|
|
72
|
+
"""Return machine-local bot/agent paths accidentally shipped in an archive."""
|
|
73
|
+
names: List[str] = []
|
|
74
|
+
try:
|
|
75
|
+
if zipfile.is_zipfile(path):
|
|
76
|
+
with zipfile.ZipFile(path) as archive:
|
|
77
|
+
names = archive.namelist()
|
|
78
|
+
elif tarfile.is_tarfile(path):
|
|
79
|
+
with tarfile.open(path, "r:*") as archive:
|
|
80
|
+
names = archive.getnames()
|
|
81
|
+
except (OSError, tarfile.TarError, zipfile.BadZipFile):
|
|
82
|
+
# Archive integrity is validated by the package-specific smoke checks;
|
|
83
|
+
# this helper is narrowly responsible for preventing personal files.
|
|
84
|
+
return []
|
|
85
|
+
|
|
86
|
+
return sorted(
|
|
87
|
+
name
|
|
88
|
+
for name in names
|
|
89
|
+
if any(pattern.search(name.replace("\\", "/")) for pattern in FORBIDDEN_PERSONAL_PATHS)
|
|
90
|
+
)
|
|
91
|
+
|
|
92
|
+
|
|
93
|
+
def _reject_personal_files(path: Path, artifact_type: str, errors: List[str]) -> None:
|
|
94
|
+
forbidden = _forbidden_archive_entries(path)
|
|
95
|
+
if forbidden:
|
|
96
|
+
errors.append(
|
|
97
|
+
f"{artifact_type} contains machine-local bot/agent files: {', '.join(forbidden)}"
|
|
98
|
+
)
|
|
99
|
+
|
|
100
|
+
|
|
61
101
|
def validate(
|
|
62
102
|
version: str,
|
|
63
103
|
dist_dir: Path,
|
|
@@ -84,6 +124,7 @@ def validate(
|
|
|
84
124
|
artifact = dist_dir / expected[key]
|
|
85
125
|
if artifact.is_file():
|
|
86
126
|
found[key] = str(artifact)
|
|
127
|
+
_reject_personal_files(artifact, key, errors)
|
|
87
128
|
else:
|
|
88
129
|
errors.append(f"missing {key}: {artifact.name}")
|
|
89
130
|
|
|
@@ -91,6 +132,7 @@ def validate(
|
|
|
91
132
|
vsix = dist_dir / expected["vsix"]
|
|
92
133
|
if vsix.is_file():
|
|
93
134
|
found["vsix"] = str(vsix)
|
|
135
|
+
_reject_personal_files(vsix, "vsix", errors)
|
|
94
136
|
if not _vsix_has_entrypoint(vsix):
|
|
95
137
|
errors.append(f"{vsix.name} is missing extension/out/extension.js (compile step skipped?)")
|
|
96
138
|
vsix_ver = _vsix_version(vsix)
|
|
@@ -100,12 +142,12 @@ def validate(
|
|
|
100
142
|
errors.append(f"missing vsix: {vsix.name}")
|
|
101
143
|
|
|
102
144
|
# npm pack tarball lives at repo root, not dist/.
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
145
|
+
tgz = dist_dir.parent / f"ltcai-{version}.tgz"
|
|
146
|
+
if tgz.is_file():
|
|
147
|
+
found["tgz"] = str(tgz)
|
|
148
|
+
_reject_personal_files(tgz, "npm tarball", errors)
|
|
149
|
+
elif require_tgz:
|
|
150
|
+
errors.append(f"missing npm tarball: {tgz.name} (run `npm pack`)")
|
|
109
151
|
|
|
110
152
|
dmg = dist_dir.parent / "src-tauri" / "target" / "release" / "bundle" / "dmg" / f"Lattice AI_{version}_aarch64.dmg"
|
|
111
153
|
if dmg.is_file():
|
|
@@ -144,7 +186,7 @@ def main(argv: Optional[List[str]] = None) -> int:
|
|
|
144
186
|
parser.add_argument("version", help="exact version to validate, e.g. 1.1.0")
|
|
145
187
|
parser.add_argument("--dist", default="dist", help="dist directory (default: dist)")
|
|
146
188
|
parser.add_argument("--require-vsix", action="store_true", help="fail if the VSIX is absent")
|
|
147
|
-
parser.add_argument("--require-tgz", action="store_true", help="
|
|
189
|
+
parser.add_argument("--require-tgz", action="store_true", help="fail if the npm pack tarball is absent")
|
|
148
190
|
parser.add_argument("--require-dmg", action="store_true", help="fail if the Tauri DMG is absent")
|
|
149
191
|
parser.add_argument("--json", action="store_true", help="emit machine-readable JSON")
|
|
150
192
|
args = parser.parse_args(argv)
|
package/scripts/wheel_smoke.py
CHANGED
|
@@ -53,6 +53,8 @@ WHEEL_MODULES = [
|
|
|
53
53
|
"latticeai.core.mcp_registry",
|
|
54
54
|
"latticeai.api.knowledge_graph",
|
|
55
55
|
"latticeai.services.p_reinforce",
|
|
56
|
+
"latticeai.tools",
|
|
57
|
+
"latticeai.tools.knowledge",
|
|
56
58
|
"ltcai_cli",
|
|
57
59
|
"auto_setup",
|
|
58
60
|
"server",
|
|
@@ -65,11 +67,14 @@ WHEEL_MODULES = [
|
|
|
65
67
|
"p_reinforce",
|
|
66
68
|
"telegram_bot",
|
|
67
69
|
"tools",
|
|
70
|
+
"tools.knowledge",
|
|
68
71
|
]
|
|
69
72
|
|
|
70
73
|
IMPORT_CHECK = (
|
|
71
74
|
"import importlib\n"
|
|
72
75
|
+ "".join(f"importlib.import_module({mod!r})\n" for mod in WHEEL_MODULES)
|
|
76
|
+
+ "assert importlib.import_module('tools') is importlib.import_module('latticeai.tools')\n"
|
|
77
|
+
+ "assert importlib.import_module('tools.knowledge') is importlib.import_module('latticeai.tools.knowledge')\n"
|
|
73
78
|
+ f"print('wheel imports ok: {len(WHEEL_MODULES)} modules')\n"
|
|
74
79
|
)
|
|
75
80
|
|