@axiom-lattice/core 6.3.1 → 6.3.2
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/dist/index.d.mts +40 -1
- package/dist/index.d.ts +40 -1
- package/dist/index.js +143 -23
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +140 -23
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -2
package/dist/index.mjs
CHANGED
|
@@ -40174,6 +40174,33 @@ function clearEncryptionKeyCache() {
|
|
|
40174
40174
|
cachedKey = null;
|
|
40175
40175
|
keyValidated = false;
|
|
40176
40176
|
}
|
|
40177
|
+
function encryptConfigFields(config, fields) {
|
|
40178
|
+
if (!fields?.length) return config;
|
|
40179
|
+
const out = { ...config };
|
|
40180
|
+
for (const field of fields) {
|
|
40181
|
+
const value = out[field];
|
|
40182
|
+
if (typeof value === "string" && value.length > 0) {
|
|
40183
|
+
out[field] = encrypt(value);
|
|
40184
|
+
}
|
|
40185
|
+
}
|
|
40186
|
+
return out;
|
|
40187
|
+
}
|
|
40188
|
+
function decryptConfigFields(config, fields) {
|
|
40189
|
+
if (!fields?.length) return config;
|
|
40190
|
+
const out = { ...config };
|
|
40191
|
+
for (const field of fields) {
|
|
40192
|
+
const value = out[field];
|
|
40193
|
+
if (typeof value === "string" && value.length > 0) {
|
|
40194
|
+
try {
|
|
40195
|
+
out[field] = decrypt(value);
|
|
40196
|
+
} catch (error) {
|
|
40197
|
+
console.error(`Failed to decrypt connection field "${field}":`, error);
|
|
40198
|
+
throw new Error("Failed to decrypt connection configuration");
|
|
40199
|
+
}
|
|
40200
|
+
}
|
|
40201
|
+
}
|
|
40202
|
+
return out;
|
|
40203
|
+
}
|
|
40177
40204
|
|
|
40178
40205
|
// src/util/safeUpstreamUrl.ts
|
|
40179
40206
|
var UnsafeUpstreamUrlError = class extends Error {
|
|
@@ -43707,7 +43734,7 @@ function createTaskMiddleware(options = {}) {
|
|
|
43707
43734
|
error: "Task changed before activity could be recorded."
|
|
43708
43735
|
});
|
|
43709
43736
|
markMutation();
|
|
43710
|
-
return JSON.stringify({ success: true, data: activity });
|
|
43737
|
+
return JSON.stringify({ success: true, data: activity, task: existing });
|
|
43711
43738
|
}
|
|
43712
43739
|
case "update": {
|
|
43713
43740
|
taskUpdateDebug("update:enter", {
|
|
@@ -46198,6 +46225,12 @@ import { createMiddleware as createMiddleware27, tool as tool67 } from "langchai
|
|
|
46198
46225
|
import { z as z73 } from "zod";
|
|
46199
46226
|
import { AgentType as AgentType10 } from "@axiom-lattice/protocols";
|
|
46200
46227
|
|
|
46228
|
+
// src/connection/connectionSecretFields.ts
|
|
46229
|
+
function connectionSecretFields(plugin) {
|
|
46230
|
+
const fields = plugin?.connection?.fields ?? [];
|
|
46231
|
+
return fields.filter((field) => field.type === "password" || field.widget === "password").map((field) => field.key);
|
|
46232
|
+
}
|
|
46233
|
+
|
|
46201
46234
|
// src/middlewares/sandboxPluginsSkills.ts
|
|
46202
46235
|
var PLUGIN_JSON_TEMPLATE = `{
|
|
46203
46236
|
"schemaVersion": 1,
|
|
@@ -46861,11 +46894,25 @@ Use the \`manage_plugin\` tool. The loop:
|
|
|
46861
46894
|
|
|
46862
46895
|
1. \`action: "validate"\` with \`{ type, manifest, handlers }\` \u2014 dry-run, no writes, returns diagnostics.
|
|
46863
46896
|
2. \`action: "create"\` or \`"update"\` \u2014 writes files, bumps version, reloads.
|
|
46864
|
-
3.
|
|
46897
|
+
3. If the plugin has \`connection.fields\` and a tool reads credentials: a **human**
|
|
46898
|
+
must configure a connection of this plugin type. You cannot create credentials.
|
|
46899
|
+
Call \`list_connections { type }\` first \u2014 if none exist, use \`ask_user_to_clarify\`
|
|
46900
|
+
to state explicitly that only the human can configure the connector, ask them to
|
|
46901
|
+
add it (Console \u2192 Connections) and to give you the connection key. Do not claim
|
|
46902
|
+
the tool works until a real \`connectionKey\` test passes.
|
|
46903
|
+
4. \`action: "test"\` to exercise a handler without an LLM:
|
|
46865
46904
|
- Tool: \`{ type, target: { kind: "tool", name, input, connectionKey? } }\`
|
|
46866
46905
|
- Connection: \`{ type, target: { kind: "connection-test" } }\` or \`{ kind: "connection-discover" }\`
|
|
46867
46906
|
Returns \`{ ok, result, exitCode, durationMs, stdout, stderr }\`.
|
|
46868
|
-
|
|
46907
|
+
For credentialed tools, pass the real \`connectionKey\`. Without one, the handler
|
|
46908
|
+
receives an empty connection \u2014 that only checks plumbing, NOT functional success.
|
|
46909
|
+
5. \`action: "reload"\` if you edited files directly.
|
|
46910
|
+
|
|
46911
|
+
## Secrets
|
|
46912
|
+
- \`list_connections\` returns identifiers only (\`key\`/\`name\`/\`description\`), never config or secrets.
|
|
46913
|
+
- \`test\` output is redacted: real connection secret values are replaced with
|
|
46914
|
+
\`[redacted]\`. Never rely on echoing credentials to verify a handler \u2014 assert on
|
|
46915
|
+
functional output instead.
|
|
46869
46916
|
|
|
46870
46917
|
## Common failures
|
|
46871
46918
|
| Symptom | Cause |
|
|
@@ -46875,9 +46922,12 @@ Use the \`manage_plugin\` tool. The loop:
|
|
|
46875
46922
|
| TOOL_SCHEMA | unsupported JSON Schema keyword |
|
|
46876
46923
|
| non-zero exit | handler threw; read stdout/stderr from \`test\` |
|
|
46877
46924
|
| old behaviour after edit | version/hash unchanged \u2014 bump \`version\` or call \`reload\` |
|
|
46925
|
+
| empty connection in handler | no \`connectionKey\` passed, or no connection configured for this type |
|
|
46878
46926
|
|
|
46879
46927
|
Fall back to \`execute_code\`/\`shell\` to run \`node handlers/x.js\` manually with
|
|
46880
|
-
\`PLUGIN_INPUT\`
|
|
46928
|
+
\`PLUGIN_INPUT\` and a synthetic \`PLUGIN_CONNECTION_FILE\` to reproduce logic bugs.
|
|
46929
|
+
A synthetic fixture only verifies plumbing \u2014 a real upstream call requires a real
|
|
46930
|
+
\`connectionKey\` configured by a human.
|
|
46881
46931
|
`,
|
|
46882
46932
|
resources: {}
|
|
46883
46933
|
}
|
|
@@ -46908,8 +46958,13 @@ implemented", "UI added", "validated/tested via manage_plugin"). As you work,
|
|
|
46908
46958
|
update each Task's status to reflect reality. Never use \`write_todos\`.
|
|
46909
46959
|
|
|
46910
46960
|
Author with the \`manage_plugin\` tool: validate, then create/update, then test.
|
|
46911
|
-
|
|
46912
|
-
\`
|
|
46961
|
+
If a tool needs credentials, a human must configure the connection \u2014 use
|
|
46962
|
+
\`list_connections\` to check, and \`ask_user_to_clarify\` to ask the human to add
|
|
46963
|
+
the connector and give you its key. Only after a real \`connectionKey\` test
|
|
46964
|
+
passes may you call the tool verified; without it, report functionality as
|
|
46965
|
+
unverified (missing credentials), not as passing. Use \`shell_exec\` (the tool
|
|
46966
|
+
provided by the \`code_eval\` middleware) to run \`node handlers/x.js\` for manual
|
|
46967
|
+
checks when reproducing a failure.`;
|
|
46913
46968
|
|
|
46914
46969
|
// src/middlewares/sandboxPluginsMiddleware.ts
|
|
46915
46970
|
var PLUGIN_BUILDER_SKILLS = [...Object.keys(SANDBOX_PLUGIN_SKILLS), "task-tracking"];
|
|
@@ -46917,6 +46972,37 @@ function tenantIdFrom(exeConfig) {
|
|
|
46917
46972
|
const c = exeConfig;
|
|
46918
46973
|
return c?.configurable?.runConfig?.tenantId ?? "default";
|
|
46919
46974
|
}
|
|
46975
|
+
function collectSecretValues(connection, fields) {
|
|
46976
|
+
if (!connection) return [];
|
|
46977
|
+
const values = [];
|
|
46978
|
+
for (const field of fields) {
|
|
46979
|
+
const value = connection[field];
|
|
46980
|
+
if (typeof value === "string" && value.length > 0) values.push(value);
|
|
46981
|
+
}
|
|
46982
|
+
return values;
|
|
46983
|
+
}
|
|
46984
|
+
function errorText(err) {
|
|
46985
|
+
return err instanceof Error ? err.message : String(err);
|
|
46986
|
+
}
|
|
46987
|
+
function redactString(value, secrets) {
|
|
46988
|
+
let out = value;
|
|
46989
|
+
for (const secret of secrets) out = out.split(secret).join("[redacted]");
|
|
46990
|
+
return out;
|
|
46991
|
+
}
|
|
46992
|
+
function redactSecretValues(payload, secrets) {
|
|
46993
|
+
if (secrets.length === 0) return payload;
|
|
46994
|
+
const walk = (node) => {
|
|
46995
|
+
if (typeof node === "string") return redactString(node, secrets);
|
|
46996
|
+
if (Array.isArray(node)) return node.map(walk);
|
|
46997
|
+
if (node !== null && typeof node === "object") {
|
|
46998
|
+
const out = {};
|
|
46999
|
+
for (const [key5, value] of Object.entries(node)) out[key5] = walk(value);
|
|
47000
|
+
return out;
|
|
47001
|
+
}
|
|
47002
|
+
return node;
|
|
47003
|
+
};
|
|
47004
|
+
return walk(payload);
|
|
47005
|
+
}
|
|
46920
47006
|
var managePluginSchema = z73.object({
|
|
46921
47007
|
action: z73.enum(["list", "get", "validate", "create", "update", "delete", "reload", "test"]),
|
|
46922
47008
|
type: z73.string().optional(),
|
|
@@ -46948,6 +47034,10 @@ var sandboxPluginsPlugin = {
|
|
|
46948
47034
|
description: "Author and manage tenant plugins in the shared sandbox: clarify goal, inputs/outputs, credentials, and whether a UI is needed; then write the manifest and JS handlers, add an optional HTML MCP App UI, and validate/test with the manage_plugin tool.",
|
|
46949
47035
|
type: AgentType10.DEEP_AGENT,
|
|
46950
47036
|
prompt: PLUGIN_BUILDER_PROMPT,
|
|
47037
|
+
// Read-only discovery of connection identifiers (metadata only — never
|
|
47038
|
+
// config/secrets) so the builder can confirm a human configured a
|
|
47039
|
+
// connector and pass its key to `manage_plugin test`.
|
|
47040
|
+
tools: ["list_connections"],
|
|
46951
47041
|
middleware: [
|
|
46952
47042
|
{
|
|
46953
47043
|
id: "sandbox-plugins",
|
|
@@ -47083,8 +47173,19 @@ var sandboxPluginsPlugin = {
|
|
|
47083
47173
|
input.target.connectionKey ? { connections: [input.target.connectionKey] } : { connectAll: true },
|
|
47084
47174
|
{ tenantId: tenantId2 }
|
|
47085
47175
|
);
|
|
47086
|
-
const
|
|
47087
|
-
|
|
47176
|
+
const secrets2 = collectSecretValues(connection, connectionSecretFields(plugin));
|
|
47177
|
+
try {
|
|
47178
|
+
const result = await plugin.connection?.test?.(connection ?? {});
|
|
47179
|
+
return JSON.stringify(redactSecretValues(
|
|
47180
|
+
result ?? { ok: false, message: "no test handler" },
|
|
47181
|
+
secrets2
|
|
47182
|
+
));
|
|
47183
|
+
} catch (err) {
|
|
47184
|
+
return JSON.stringify(redactSecretValues(
|
|
47185
|
+
{ ok: false, message: errorText(err) },
|
|
47186
|
+
secrets2
|
|
47187
|
+
));
|
|
47188
|
+
}
|
|
47088
47189
|
}
|
|
47089
47190
|
if (input.target.kind === "connection-discover") {
|
|
47090
47191
|
const { connection } = await resolveSandboxPluginConnections(
|
|
@@ -47092,8 +47193,16 @@ var sandboxPluginsPlugin = {
|
|
|
47092
47193
|
input.target.connectionKey ? { connections: [input.target.connectionKey] } : { connectAll: true },
|
|
47093
47194
|
{ tenantId: tenantId2 }
|
|
47094
47195
|
);
|
|
47095
|
-
const
|
|
47096
|
-
|
|
47196
|
+
const secrets2 = collectSecretValues(connection, connectionSecretFields(plugin));
|
|
47197
|
+
try {
|
|
47198
|
+
const result = await plugin.connection?.discover?.(connection ?? {});
|
|
47199
|
+
return JSON.stringify(redactSecretValues(result ?? [], secrets2));
|
|
47200
|
+
} catch (err) {
|
|
47201
|
+
return JSON.stringify(redactSecretValues(
|
|
47202
|
+
{ error: errorText(err) },
|
|
47203
|
+
secrets2
|
|
47204
|
+
));
|
|
47205
|
+
}
|
|
47097
47206
|
}
|
|
47098
47207
|
const executor = catalog2.getExecutor();
|
|
47099
47208
|
const manifestContent = await catalog2.readPluginFile(tenantId2, input.type, "plugin.json");
|
|
@@ -47111,19 +47220,24 @@ var sandboxPluginsPlugin = {
|
|
|
47111
47220
|
{ connections: [input.target.connectionKey] },
|
|
47112
47221
|
{ tenantId: tenantId2 }
|
|
47113
47222
|
) : {};
|
|
47114
|
-
const
|
|
47115
|
-
|
|
47116
|
-
|
|
47117
|
-
|
|
47118
|
-
|
|
47119
|
-
|
|
47120
|
-
|
|
47121
|
-
|
|
47122
|
-
tenantId: tenantId2,
|
|
47123
|
-
|
|
47124
|
-
|
|
47125
|
-
|
|
47126
|
-
|
|
47223
|
+
const secrets = collectSecretValues(resolved.connection, connectionSecretFields(plugin));
|
|
47224
|
+
try {
|
|
47225
|
+
const result = await executor.invoke({
|
|
47226
|
+
manifest: parsedManifest,
|
|
47227
|
+
handler: toolDef.handler,
|
|
47228
|
+
input: input.target.input ?? null,
|
|
47229
|
+
connection: resolved.connection,
|
|
47230
|
+
connections: resolved.connections,
|
|
47231
|
+
context: { tenantId: tenantId2, pluginType: input.type, tool: toolDef.name },
|
|
47232
|
+
runConfig: {
|
|
47233
|
+
tenantId: tenantId2,
|
|
47234
|
+
assistantId: typeof runCfg.assistant_id === "string" ? runCfg.assistant_id : void 0
|
|
47235
|
+
}
|
|
47236
|
+
});
|
|
47237
|
+
return JSON.stringify(redactSecretValues(result, secrets));
|
|
47238
|
+
} catch (err) {
|
|
47239
|
+
return JSON.stringify(redactSecretValues({ ok: false, error: errorText(err) }, secrets));
|
|
47240
|
+
}
|
|
47127
47241
|
}
|
|
47128
47242
|
default:
|
|
47129
47243
|
return `unsupported action: ${input.action}`;
|
|
@@ -47786,6 +47900,7 @@ export {
|
|
|
47786
47900
|
configurePluginCatalogSync,
|
|
47787
47901
|
configureStores,
|
|
47788
47902
|
connectAllChannels,
|
|
47903
|
+
connectionSecretFields,
|
|
47789
47904
|
convertToConnection,
|
|
47790
47905
|
createAgentNode,
|
|
47791
47906
|
createAgentTeam,
|
|
@@ -47826,11 +47941,13 @@ export {
|
|
|
47826
47941
|
createUnknownToolHandlerMiddleware,
|
|
47827
47942
|
createWidgetMiddleware,
|
|
47828
47943
|
decrypt,
|
|
47944
|
+
decryptConfigFields,
|
|
47829
47945
|
describeCronExpression,
|
|
47830
47946
|
documentLearningPlugin,
|
|
47831
47947
|
documentParserPlugin,
|
|
47832
47948
|
embeddingsLatticeManager,
|
|
47833
47949
|
encrypt,
|
|
47950
|
+
encryptConfigFields,
|
|
47834
47951
|
ensureBuiltinAgentsForTenant,
|
|
47835
47952
|
ensurePluginSkillInSandbox,
|
|
47836
47953
|
evaluateLatticeCaseWithLogs,
|