Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 13 additions & 3 deletions frontend/src/create/CustomCreate.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ import {
A2A_REGISTRY_DEFAULTS,
A2A_REGISTRY_ENV,
BUILTIN_TOOLS,
CREATE_BUILTIN_TOOLS,
createBuiltinToolsForProvider,
STM_BACKENDS,
LTM_BACKENDS,
KB_BACKENDS,
Expand Down Expand Up @@ -2928,14 +2928,24 @@ export function CustomCreate({

// Root-only rich sections read these off the root draft directly.
const builtinTools = node.builtinTools ?? [];
const createBuiltinTools = useMemo(
() => createBuiltinToolsForProvider(cloudProvider),
[cloudProvider],
);
const createBuiltinToolIds = useMemo(
() => new Set(createBuiltinTools.map((tool) => tool.id)),
[createBuiltinTools],
);
const mcpTools = node.mcpTools ?? [];
const selectedSkills = node.selectedSkills ?? [];
const toggleBuiltin = (id: string) =>
const toggleBuiltin = (id: string) => {
if (!createBuiltinToolIds.has(id)) return;
patch({
builtinTools: builtinTools.includes(id)
? builtinTools.filter((x) => x !== id)
: [...builtinTools, id],
});
};

// Detail-pane branching is driven by the SELECTED node's type.
const orchestrator = isOrchestratorType(node.agentType);
Expand Down Expand Up @@ -3923,7 +3933,7 @@ export function CustomCreate({
</span>
<div className="cw-tools-list-shell">
<Checklist
items={CREATE_BUILTIN_TOOLS}
items={createBuiltinTools}
selected={builtinTools}
onToggle={toggleBuiltin}
scrollRows={6}
Expand Down
19 changes: 14 additions & 5 deletions frontend/src/create/normalizeDraft.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,8 @@ import {
type CustomTool,
type SelectedSkill,
} from "./types";
import { CREATE_BUILTIN_TOOLS, DEFAULT_KB_BACKEND } from "./veadkCatalog";
import { createBuiltinToolsForProvider, DEFAULT_KB_BACKEND } from "./veadkCatalog";
import type { CloudProvider } from "../adk/cloudProvider";

const STM_IDS = new Set(["local", "sqlite", "mysql", "postgresql"]);
const LTM_IDS = new Set([
Expand All @@ -30,7 +31,6 @@ const TOOL_IDS = new Set([
"run_code",
"vesearch",
]);
const GENERATED_TOOL_IDS = new Set(CREATE_BUILTIN_TOOLS.map((tool) => tool.id));
const AGENT_TYPES = new Set(["llm", "sequential", "parallel", "loop", "a2a"]);

function asString(v: unknown, fallback = ""): string {
Expand Down Expand Up @@ -283,11 +283,18 @@ export function normalizeDraft(raw: unknown): AgentDraft {
};
}

export function sanitizeGeneratedDraftCapabilities(draft: AgentDraft): AgentDraft {
export function sanitizeGeneratedDraftCapabilities(
draft: AgentDraft,
inheritedCloudProvider: CloudProvider = draft.cloudProvider ?? "volcengine",
): AgentDraft {
const cloudProvider = draft.cloudProvider ?? inheritedCloudProvider;
const generatedToolIds = new Set(
createBuiltinToolsForProvider(cloudProvider).map((tool) => tool.id),
);
return {
...draft,
builtinTools: (draft.builtinTools ?? []).filter((toolId) =>
GENERATED_TOOL_IDS.has(toolId),
generatedToolIds.has(toolId),
),
tracing: false,
tracingExporters: [],
Expand All @@ -298,6 +305,8 @@ export function sanitizeGeneratedDraftCapabilities(draft: AgentDraft): AgentDraf
knowledgebase: false,
knowledgebaseBackend: DEFAULT_KB_BACKEND,
knowledgebaseIndex: "",
subAgents: draft.subAgents.map(sanitizeGeneratedDraftCapabilities),
subAgents: draft.subAgents.map((child) =>
sanitizeGeneratedDraftCapabilities(child, cloudProvider),
),
};
}
18 changes: 18 additions & 0 deletions frontend/src/create/veadkCatalog.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@
// Each option carries enough metadata to (a) render a picker and (b) emit
// runnable Python + a complete .env.example.

import type { CloudProvider } from "../adk/cloudProvider";

export interface EnvVar {
key: string;
/** Whether the feature is non-functional without it (still emitted, but flagged). */
Expand Down Expand Up @@ -250,10 +252,26 @@ const HIDDEN_CREATE_TOOL_IDS = new Set([
"text_to_speech",
"vesearch",
]);

const BYTEPLUS_HIDDEN_CREATE_TOOL_IDS = new Set([
"web_search",
"parallel_web_search",
]);

export const CREATE_BUILTIN_TOOLS = BUILTIN_TOOLS.filter(
(tool) => !HIDDEN_CREATE_TOOL_IDS.has(tool.id),
);

export function createBuiltinToolsForProvider(
cloudProvider: CloudProvider = "volcengine",
): ToolOption[] {
const hidden =
cloudProvider === "byteplus"
? BYTEPLUS_HIDDEN_CREATE_TOOL_IDS
: new Set<string>();
return CREATE_BUILTIN_TOOLS.filter((tool) => !hidden.has(tool.id));
}

/* ------------------------------------------------------------------ *
* Short-term memory backends.
* ------------------------------------------------------------------ */
Expand Down
18 changes: 14 additions & 4 deletions frontend/tests/generatedAgentPlanner.test.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,11 @@ test("removes hidden capabilities from every generated Agent", () => {
);
const sanitizer = normalizeSource.slice(start);

assert.match(sanitizer, /GENERATED_TOOL_IDS\.has\(toolId\)/);
assert.match(
sanitizer,
/createBuiltinToolsForProvider\(cloudProvider\)\.map\(\(tool\) => tool\.id\)/,
);
assert.match(sanitizer, /generatedToolIds\.has\(toolId\)/);
assert.match(sanitizer, /tracing: false/);
assert.match(sanitizer, /tracingExporters: \[\]/);
assert.match(sanitizer, /memory: \{ shortTerm: false, longTerm: false \}/);
Expand All @@ -37,7 +41,7 @@ test("removes hidden capabilities from every generated Agent", () => {
assert.match(sanitizer, /knowledgebaseIndex: ""/);
assert.match(
sanitizer,
/subAgents: draft\.subAgents\.map\(sanitizeGeneratedDraftCapabilities\)/,
/subAgents: draft\.subAgents\.map\(\(child\) =>[\s\S]*?sanitizeGeneratedDraftCapabilities\(child, cloudProvider\)/,
);
assert.match(
createSource,
Expand All @@ -49,8 +53,14 @@ test("keeps OpenViking long-term memory when normalizing imported drafts", () =>
assert.match(normalizeSource, /"openviking"/);
});

test("feeds supported generated tool ids into the checklist selection", () => {
assert.match(createSource, /items=\{CREATE_BUILTIN_TOOLS\}/);
test("feeds provider-supported generated tool ids into the checklist selection", () => {
assert.match(
createSource,
/createBuiltinToolsForProvider\(cloudProvider\)/,
);
assert.match(createSource, /new Set\(createBuiltinTools\.map\(\(tool\) => tool\.id\)\)/);
assert.match(createSource, /if \(!createBuiltinToolIds\.has\(id\)\) return/);
assert.match(createSource, /items=\{createBuiltinTools\}/);
assert.match(createSource, /selected=\{builtinTools\}/);
});

Expand Down
10 changes: 9 additions & 1 deletion frontend/tests/markdownPromptEditor.test.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -581,11 +581,19 @@ test("advanced model connection settings use an accessible disclosure", () => {
});

test("built-in tools adapt columns and scroll after six rows", () => {
assert.match(createSource, /items=\{CREATE_BUILTIN_TOOLS\}[\s\S]*?scrollRows=\{6\}/);
assert.match(createSource, /items=\{createBuiltinTools\}[\s\S]*?scrollRows=\{6\}/);
assert.match(
catalogSource,
/HIDDEN_CREATE_TOOL_IDS = new Set\(\[[\s\S]*?"web_scraper"[\s\S]*?"text_to_speech"[\s\S]*?"vesearch"/,
);
assert.match(
catalogSource,
/BYTEPLUS_HIDDEN_CREATE_TOOL_IDS = new Set\(\[[\s\S]*?"web_search"[\s\S]*?"parallel_web_search"/,
);
assert.match(
catalogSource,
/cloudProvider === "byteplus"[\s\S]*?BYTEPLUS_HIDDEN_CREATE_TOOL_IDS[\s\S]*?return CREATE_BUILTIN_TOOLS\.filter\(\(tool\) => !hidden\.has\(tool\.id\)\)/,
);
assert.match(
createStyles,
/\.cw-tools-list-shell\s*\{[\s\S]*?container-type:\s*inline-size;/,
Expand Down
2 changes: 1 addition & 1 deletion tests/cli/test_studio_rbac.py
Original file line number Diff line number Diff line change
Expand Up @@ -436,7 +436,7 @@ async def initialize_evaluation_sets(**_kwargs: Any) -> list[str]:
runtime_envs = cloud["runtime_envs"]
assert runtime_envs["CLOUD_PROVIDER"] == "byteplus"
assert runtime_envs["AGENTKIT_CLOUD_PROVIDER"] == "byteplus"
assert runtime_envs["DATABASE_VIKING_REGION"] == "ap-southeast-1"
assert runtime_envs["DATABASE_VIKING_REGION"] == "cn-hongkong"
assert "BYTEPLUS_ACCESS_KEY" not in runtime_envs
assert "BYTEPLUS_SECRET_KEY" not in runtime_envs
assert "BYTEPLUS_SESSION_TOKEN" not in runtime_envs
Expand Down
2 changes: 1 addition & 1 deletion tests/cli/test_studio_update.py
Original file line number Diff line number Diff line change
Expand Up @@ -451,7 +451,7 @@ def update_application_code_bundle(self, **kwargs: object) -> str:
"CLOUD_PROVIDER": "byteplus",
"AGENTKIT_CLOUD_PROVIDER": "byteplus",
"BYTEPLUS_REGION": "ap-southeast-1",
"DATABASE_VIKING_REGION": "ap-southeast-1",
"DATABASE_VIKING_REGION": "cn-hongkong",
}


Expand Down
36 changes: 31 additions & 5 deletions tests/test_vikingdb_knowledge_backend.py
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ def test_viking_knowledgebase_reads_byteplus_credentials(
assert backend.session_token == "bp-token"


def test_byteplus_viking_knowledgebase_uses_byteplus_region(
def test_byteplus_viking_knowledgebase_uses_hong_kong_fallback(
monkeypatch: pytest.MonkeyPatch,
) -> None:
from veadk.knowledgebase.backends.vikingdb_knowledge_backend import (
Expand All @@ -107,9 +107,35 @@ def test_byteplus_viking_knowledgebase_uses_byteplus_region(

backend = VikingDBKnowledgeBackend(index="vikingkl_we4191n")

assert backend.region == "ap-southeast-1"
assert backend.host == "api-knowledgebase.mlp.ap-southeast-1.bytepluses.com"
assert backend.region == "cn-hongkong"
assert backend.host == "api-knowledgebase.mlp.cn-hongkong.bytepluses.com"
assert (
backend.base_url
== "https://api-knowledgebase.mlp.ap-southeast-1.bytepluses.com"
backend.base_url == "https://api-knowledgebase.mlp.cn-hongkong.bytepluses.com"
)


def test_byteplus_viking_knowledgebase_keeps_hong_kong_region(
monkeypatch: pytest.MonkeyPatch,
) -> None:
from veadk.knowledgebase.backends.vikingdb_knowledge_backend import (
VikingDBKnowledgeBackend,
)

monkeypatch.setenv("CLOUD_PROVIDER", "byteplus")
monkeypatch.setenv("AGENTKIT_CLOUD_PROVIDER", "byteplus")
monkeypatch.setenv("DATABASE_VIKING_REGION", "cn-hongkong")
monkeypatch.setenv("BYTEPLUS_ACCESS_KEY", "bp-ak")
monkeypatch.setenv("BYTEPLUS_SECRET_KEY", "bp-sk")
monkeypatch.setattr(
VikingDBKnowledgeBackend,
"collection_status",
lambda self: {"existed": True},
)

backend = VikingDBKnowledgeBackend(index="vikingkl_we4191n")

assert backend.region == "cn-hongkong"
assert backend.host == "api-knowledgebase.mlp.cn-hongkong.bytepluses.com"
assert (
backend.base_url == "https://api-knowledgebase.mlp.cn-hongkong.bytepluses.com"
)
Loading
Loading