Skip to content

Commit 980c528

Browse files
Merge branch 'main' into main
2 parents 2b85933 + 740557c commit 980c528

9 files changed

Lines changed: 95 additions & 299 deletions

File tree

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
{
2-
".": "1.31.0"
2+
".": "1.32.0"
33
}

.github/release-please-config.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"$schema": "https://raw.githubusercontent.com/googleapis/release-please/main/schemas/config.json",
3-
"last-release-sha": "d69477f6ff348311e1d53e3f2c389dcf037fb049",
3+
"last-release-sha": "5e49cfa6567a09e06409b0f380434f12f85a17c9",
44
"packages": {
55
".": {
66
"release-type": "python",

CHANGELOG.md

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,90 @@
11
# Changelog
22

3+
## [1.32.0](https://github.com/google/adk-python/compare/v1.31.0...v1.32.0) (2026-04-30)
4+
5+
6+
### Features
7+
8+
* Add an option to prevent the SaveFilesAsArtifactsPlugin from attaching reference file parts to the message ([987c809](https://github.com/google/adk-python/commit/987c809bfc816a9804c905bd5c02397e396e72d3))
9+
* add credentials parameter to BigQueryAgentAnalyticsPlugin ([34713fb](https://github.com/google/adk-python/commit/34713fb4cccae9fe066587459862f8d4c4aa166f))
10+
* Add express mode onboarding support to adk deploy cli ([2b04996](https://github.com/google/adk-python/commit/2b04996f7ac342c9e7600e4bb596a666108f8b65))
11+
* add native OpenTelemetry agentic metrics ([6942aac](https://github.com/google/adk-python/commit/6942aac5d7b1f465c20febe2a48bac90da32c4eb))
12+
* Add OpenTelemetry tracing for event compaction ([c65dd55](https://github.com/google/adk-python/commit/c65dd5580f42ed330bf4c57cd040f22748ba1444))
13+
* Add sample agent demonstrating 2LO, 3LO, and API Key auth via GcpAuthProvider ([909a8c2](https://github.com/google/adk-python/commit/909a8c2ad4d06ad485173f40f278c503cd66a063))
14+
* Add support for Anthropic's thinking blocks ([16952bd](https://github.com/google/adk-python/commit/16952bd397f871df3e5a1b035261ded3b7c226a5))
15+
* Add support for excluding predefined functions in ComputerUseToolset ([d760037](https://github.com/google/adk-python/commit/d760037f9500a9187bf835ce62eebf21e818f322))
16+
* Add support for refusal messages in ApigeeLlm ([d6594a1](https://github.com/google/adk-python/commit/d6594a1a2c11fe3f5ac94fd37a9ae4b327fa1a0c))
17+
* Added indication of user message in history event list ([662354a](https://github.com/google/adk-python/commit/662354ae55c244d79955935f2243ba3deba272e9))
18+
* Allow user to define credential_key for McpToolset ([282db87](https://github.com/google/adk-python/commit/282db876fdf8e2f0133cfc386b4b4dd1dc9bdd09)), closes [#5103](https://github.com/google/adk-python/issues/5103)
19+
* **analytics:** add support for logging LLM cache metadata to BigQuery ([02deeb9](https://github.com/google/adk-python/commit/02deeb98a08611733949fa2912f433f2ed55681a))
20+
* **eval:** add evaluate_full_response option to rubric-based evaluation ([#5316](https://github.com/google/adk-python/issues/5316)) ([7623ff1](https://github.com/google/adk-python/commit/7623ff1a27c412ff9b758bb76701e2daff570741))
21+
* **live:** Add save_live_blob query parameter to /run_live endpoint ([36ab8f1](https://github.com/google/adk-python/commit/36ab8f128c0281e44c2120a17de91e081f2232b1))
22+
* **mcp:** gracefully handle tool execution errors and transport crashes ([7744cfe](https://github.com/google/adk-python/commit/7744cfe0f36a74f50abb53ec0d42566c439257b3))
23+
24+
25+
### Bug Fixes
26+
27+
* accumulate list values when merging parallel tool call state_delta ([b0b8b31](https://github.com/google/adk-python/commit/b0b8b310af5cb1184ef3ef57f1bb551e2a9add9a)), closes [#5190](https://github.com/google/adk-python/issues/5190)
28+
* Add support for overriding the API version in GoogleLLM ([1cdd1e7](https://github.com/google/adk-python/commit/1cdd1e74ba3e59e5ef5ebb654184630c1462454e))
29+
* **auth:** isolate resolved credentials in context to prevent race conditions and data leakage ([5578772](https://github.com/google/adk-python/commit/55787721541fe0a9b5df15b980be87623e57eba8))
30+
* avoid double-execution of sync FunctionTools returning None ([78a8851](https://github.com/google/adk-python/commit/78a8851809f2be7b9e20158beee8c39cdd3fe2f8)), closes [#5284](https://github.com/google/adk-python/issues/5284)
31+
* block RCE vulnerability via nested YAML configurations in ADK ([74f235b](https://github.com/google/adk-python/commit/74f235b1195805f2316f90533d4d297038448f0a))
32+
* bump Vertex SDK version ([6380f6a](https://github.com/google/adk-python/commit/6380f6ac767a6e13faf15b7e8ac3bc48acbd5f1b))
33+
* cancel siblings in parallel function calling on failure ([49985c9](https://github.com/google/adk-python/commit/49985c91ca08e36801e72164cb6314aa9190d144))
34+
* Capture and include LLM usage metadata in summarized events ([5ce33b9](https://github.com/google/adk-python/commit/5ce33b9c1e7606cb9b84ab925f8ff47ee0347943)), closes [#4014](https://github.com/google/adk-python/issues/4014)
35+
* catch ValueError in safe-JSON serializers for circular refs ([70a7add](https://github.com/google/adk-python/commit/70a7add2bd8ddca12b5fdd63e2052f291817d5be)), closes [#5412](https://github.com/google/adk-python/issues/5412)
36+
* **deps:** bump litellm cap to >=1.83.7 to admit CVE patches ([6d2ada8](https://github.com/google/adk-python/commit/6d2ada8bbc5a08bee3ca76d3e44628b194562212))
37+
* Disable bound token for mcp_tool ([4c0c6db](https://github.com/google/adk-python/commit/4c0c6db87cd531d932c135a27e69682ed08c6f75))
38+
* fix dataset location handling in BigQueryAgentAnalyticsPlugin ([c263426](https://github.com/google/adk-python/commit/c263426fe1a8620ebebef4b7efaed1eb5b99c03f))
39+
* Fix exception handling and argument order in ReflectRetryToolPlugin ([1deab6d](https://github.com/google/adk-python/commit/1deab6d0bf32a0344ab033a1ae61cc7cddf706fd))
40+
* Fix GcpAuthProvider to return capitalized Bearer scheme ([ad937fe](https://github.com/google/adk-python/commit/ad937fe1b827309787a177a99c42df2679f9286e))
41+
* fix lifecycle issues with credentials in BigQuery Agent Analytics Plugin ([a69f861](https://github.com/google/adk-python/commit/a69f8612fa4b69273b1bb7c90c4efa53b04440e6))
42+
* Fix malformated skill.md ([9a0d2f7](https://github.com/google/adk-python/commit/9a0d2f70ba957b8fc2cae8ed3f4aa1f4885a689c))
43+
* Fix misplaced pytest decorator on helper dataclass in 2LO integration tests ([2343973](https://github.com/google/adk-python/commit/234397353189005b5641df832f8ed45018021ef7))
44+
* Fix RecursionError in ADK framework by adding circular reference detection to schema resolution ([7de5bc5](https://github.com/google/adk-python/commit/7de5bc54e11986f70a48a9dd83ea39be58ebce40))
45+
* fix rewind to preserve initial session state ([af1b00a](https://github.com/google/adk-python/commit/af1b00a12b8dd6eee844cc28df7bcd4838e22c1a)), closes [#4933](https://github.com/google/adk-python/issues/4933)
46+
* Fix SSRF and local-file access in load_web_page ([0447e93](https://github.com/google/adk-python/commit/0447e939483c1c6bc8d6df7f96b372d5f8bee7bb))
47+
* handle None state values in skill_toolset after session rewind ([a977aa3](https://github.com/google/adk-python/commit/a977aa307d56ed1efa89a3ffe4b3d96650a984d6))
48+
* **litellm:** emit input_audio for audio inline_data parts ([4073238](https://github.com/google/adk-python/commit/4073238151ee35488b50a321482db500b705234b)), closes [#5406](https://github.com/google/adk-python/issues/5406)
49+
* **live:** mark all agents' Event as from other agents ([48b7a64](https://github.com/google/adk-python/commit/48b7a64bcf5ff402d10187d269f41e6bd4b8d74a))
50+
* **live:** treat input transcription as user message ([ae1f2e6](https://github.com/google/adk-python/commit/ae1f2e6094935c972af3f6682e5c2f79a5ac70d5))
51+
* **optimization:** handle None metric scores in LocalEvalSampler ([#5415](https://github.com/google/adk-python/issues/5415)) ([684a6e7](https://github.com/google/adk-python/commit/684a6e781adf7e769c8f7f572382ceb61f26a038))
52+
* **otel:** change `gen_ai.tool_definitions` to `gen_ai.tool.definitions` ([029b87d](https://github.com/google/adk-python/commit/029b87d582bdde98be3532f26adb6e1d851c44d6))
53+
* preserve cache fingerprint stability on creation failure ([4d5438c](https://github.com/google/adk-python/commit/4d5438cfc89d69d88ba4c324c292fc23e3047f3d))
54+
* preserve empty-string text parts in A2A converter ([2d61cb6](https://github.com/google/adk-python/commit/2d61cb69704f063f66b5d83b716674f6f94b5903))
55+
* preserve function call IDs for Anthropic models ([f0c787f](https://github.com/google/adk-python/commit/f0c787fbc9c4a66b0d0eccddc6d6d03b844cfd0b))
56+
* Prevent LoopAgent from resetting sub-agent state on pause ([8846be5](https://github.com/google/adk-python/commit/8846be585dd3ac585a75aed03d9c6623a5eaa41b))
57+
* Quote user_id literals in VertexAiSessionService list filters ([bdece00](https://github.com/google/adk-python/commit/bdece003b82959d7d7649cc5c94e26306019299f))
58+
* read_file/write_file path type mismatch in BaseEnvironment and LocalEnvironment ([782796f](https://github.com/google/adk-python/commit/782796f97eb10d09d8dccb51b93868e1c07b475e))
59+
* relax EventActions.state_delta value type to Any ([dbec8e9](https://github.com/google/adk-python/commit/dbec8e937adeb608b01f43409033c1de70a86b92))
60+
* remove exclude_unset=True to correctly serialize pydantic types ([f95ac48](https://github.com/google/adk-python/commit/f95ac48e07daa0934a784c1701a124add0513297))
61+
* **samples:** Upgrade google-adk to 1.28.1 to fix vulnerability ([b848390](https://github.com/google/adk-python/commit/b8483909049d4a9bad94f6cb44cf6a26fd9faa9d))
62+
* Sanitize user_id derived from PubSub subscription and Eventarc source ([0c4f157](https://github.com/google/adk-python/commit/0c4f1570388c8361ce6ab072f5ef19a3d92dbdc2)), closes [#5324](https://github.com/google/adk-python/issues/5324)
63+
* Scope Vertex RAG memory display names ([784350d](https://github.com/google/adk-python/commit/784350dba60245ce02ad96994e7ced2b567a4dec))
64+
* Use correct camelCase functionCallId ([c87ee1e](https://github.com/google/adk-python/commit/c87ee1ee9697b4f5f2b88e45a08eeeabf9a0ad13))
65+
* web oauth flow and trace view ([87cd310](https://github.com/google/adk-python/commit/87cd310bccb33d7faae7d505a4629a2e1d77fadb))
66+
* yield tool_call_parts immediately in live mode to unblock Gemini 3.1 tool calls ([f57b05d](https://github.com/google/adk-python/commit/f57b05dac147eb72f54c9053a4a0ba7023ee55dc))
67+
68+
69+
### Performance Improvements
70+
71+
* lazy-load optional providers and auth chain to cut cold start ~25% ([66bfedc](https://github.com/google/adk-python/commit/66bfedcf8ddc7c5c518c8c7d7a967e1c488e9852))
72+
73+
74+
### Code Refactoring
75+
76+
* move exception handling from metric emission into instrumentation handlers ([62d7ee0](https://github.com/google/adk-python/commit/62d7ee024aa1e50197722d2c5914192a7f322d60))
77+
* **tests:** Refactor tests to explicitly handle JSON_SCHEMA_FOR_FUNC_DECL feature flag ([b580891](https://github.com/google/adk-python/commit/b580891adcc2c7afe110dbef394ffd7b3de67629))
78+
* Use artifact_service.load_artifact during rewind ([c3d50db](https://github.com/google/adk-python/commit/c3d50db9387f7cd76a955299e40a23925dedbc22)), closes [#4932](https://github.com/google/adk-python/issues/4932)
79+
80+
81+
### Documentation
82+
83+
* **gemini:** show subclass pattern for custom Client config ([34c7505](https://github.com/google/adk-python/commit/34c7505cc437578567008c0c8b160de083eae0d1)), closes [#3628](https://github.com/google/adk-python/issues/3628)
84+
* update `output_schema` docstring to reflect support for `tools` and `output_schema` together ([e1e652d](https://github.com/google/adk-python/commit/e1e652d73a3d41f42c517189164f740cb907896d))
85+
* Update README with instructions for installing ADK extensions ([f2a1179](https://github.com/google/adk-python/commit/f2a117972e40dd3d4299f3ff437b4382600d224e))
86+
* use sphinx-click to generate docs for google.adk.cli ([f455974](https://github.com/google/adk-python/commit/f4559743febfa91fdde6e5e2e41acf54e20396fe))
87+
388
## [1.31.0](https://github.com/google/adk-python/compare/v1.30.0...v1.31.0) (2026-04-16)
489

590

src/google/adk/cli/adk_web_server.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1889,6 +1889,7 @@ def _set_telemetry_context_if_needed(runner: Runner):
18891889

18901890
@app.post("/run", response_model_exclude_none=True)
18911891
async def run_agent(req: RunAgentRequest) -> list[Event]:
1892+
self.current_app_name_ref.value = req.app_name
18921893
runner = await self.get_runner_async(req.app_name)
18931894
_set_telemetry_context_if_needed(runner)
18941895
try:
@@ -1910,6 +1911,7 @@ async def run_agent(req: RunAgentRequest) -> list[Event]:
19101911

19111912
@app.post("/run_sse")
19121913
async def run_agent_sse(req: RunAgentRequest) -> StreamingResponse:
1914+
self.current_app_name_ref.value = req.app_name
19131915
stream_mode = StreamingMode.SSE if req.streaming else StreamingMode.NONE
19141916
runner = await self.get_runner_async(req.app_name)
19151917
_set_telemetry_context_if_needed(runner)
@@ -2089,6 +2091,7 @@ async def run_agent_live(
20892091
return
20902092

20912093
await websocket.accept()
2094+
self.current_app_name_ref.value = req.app_name
20922095
runner_for_context = await self.get_runner_async(app_name)
20932096
_set_telemetry_context_if_needed(runner_for_context)
20942097

src/google/adk/events/event_actions.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ class EventActions(BaseModel):
6464
Only used for function_response event.
6565
"""
6666

67-
state_delta: dict[str, object] = Field(default_factory=dict)
67+
state_delta: dict[str, Any] = Field(default_factory=dict)
6868
"""Indicates that the event is updating the state with the given delta."""
6969

7070
artifact_delta: dict[str, int] = Field(default_factory=dict)

src/google/adk/skills/skill_registry.py

Lines changed: 0 additions & 83 deletions
This file was deleted.

src/google/adk/tools/skill_toolset.py

Lines changed: 3 additions & 89 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,6 @@
3737
from ..features import FeatureName
3838
from ..skills import models
3939
from ..skills import prompt
40-
from ..skills.skill_registry import SkillRegistry
4140
from .base_tool import BaseTool
4241
from .base_toolset import BaseToolset
4342
from .function_tool import FunctionTool
@@ -156,20 +155,6 @@ async def run_async(
156155
}
157156

158157
skill = self._toolset._get_skill(skill_name)
159-
if not skill and self._toolset._registry:
160-
try:
161-
skill = await self._toolset._registry.get_skill(name=skill_name)
162-
if skill:
163-
self._toolset._skills[skill_name] = skill
164-
except Exception as e:
165-
logger.exception(
166-
"Failed to fetch skill '%s' from registry.", skill_name
167-
)
168-
return {
169-
"error": f"Failed to fetch skill '{skill_name}' from registry: {e}",
170-
"error_code": "REGISTRY_ERROR",
171-
}
172-
173158
if not skill:
174159
return {
175160
"error": f"Skill '{skill_name}' not found.",
@@ -786,75 +771,14 @@ async def run_async(
786771
)
787772

788773

789-
@experimental(FeatureName.SKILL_TOOLSET)
790-
class SearchSkillsTool(BaseTool):
791-
"""Tool to search for relevant skills in the registry."""
792-
793-
def __init__(self, toolset: "SkillToolset"):
794-
super().__init__(
795-
name="search_skills",
796-
description=toolset._registry.get_search_description(),
797-
)
798-
self._toolset = toolset
799-
800-
def _get_declaration(self) -> types.FunctionDeclaration | None:
801-
properties = {
802-
"query": {
803-
"type": "string",
804-
"description": "Semantic or keyword search query.",
805-
},
806-
}
807-
filter_schema = self._toolset._registry.get_filter_schema()
808-
if filter_schema:
809-
properties["filters"] = filter_schema
810-
return types.FunctionDeclaration(
811-
name=self.name,
812-
description=self.description,
813-
parameters_json_schema={
814-
"type": "object",
815-
"properties": properties,
816-
"required": ["query"],
817-
},
818-
)
819-
820-
async def run_async(
821-
self, *, args: dict[str, Any], tool_context: ToolContext
822-
) -> Any:
823-
query = args.get("query")
824-
filters = args.get("filters")
825-
826-
if not query:
827-
return {
828-
"error": "Argument 'query' is required.",
829-
"error_code": "INVALID_ARGUMENTS",
830-
}
831-
832-
results = await self._toolset._registry.search_skills(
833-
query=query, filters=filters
834-
)
835-
836-
formatted_results = []
837-
for r in results:
838-
if r.name in self._toolset._skills:
839-
logger.warning(
840-
"Naming conflict detected: Skill '%s' exists both locally and in"
841-
" the registry. Filtering out the registry skill.",
842-
r.name,
843-
)
844-
continue
845-
formatted_results.append(r.model_dump())
846-
return formatted_results
847-
848-
849774
@experimental(FeatureName.SKILL_TOOLSET)
850775
class SkillToolset(BaseToolset):
851776
"""A toolset for managing and interacting with agent skills."""
852777

853778
def __init__(
854779
self,
855-
skills: list[models.Skill] | None = None,
780+
skills: list[models.Skill],
856781
*,
857-
registry: Optional[SkillRegistry] = None,
858782
code_executor: Optional[BaseCodeExecutor] = None,
859783
script_timeout: int = _DEFAULT_SCRIPT_TIMEOUT,
860784
additional_tools: list[ToolUnion] | None = None,
@@ -863,7 +787,6 @@ def __init__(
863787
864788
Args:
865789
skills: List of skills to register.
866-
registry: Optional skill registry for dynamic discovery.
867790
code_executor: Optional code executor for script execution.
868791
script_timeout: Timeout in seconds for shell script execution via
869792
subprocess.run. Defaults to 300 seconds. Does not apply to Python
@@ -873,13 +796,12 @@ def __init__(
873796

874797
# Check for duplicate skill names
875798
seen: set[str] = set()
876-
for skill in skills or []:
799+
for skill in skills:
877800
if skill.name in seen:
878801
raise ValueError(f"Duplicate skill name '{skill.name}'.")
879802
seen.add(skill.name)
880803

881-
self._skills = {skill.name: skill for skill in skills or []}
882-
self._registry = registry
804+
self._skills = {skill.name: skill for skill in skills}
883805
self._code_executor = code_executor
884806
self._script_timeout = script_timeout
885807
self._use_invocation_cache = False
@@ -902,8 +824,6 @@ def __init__(
902824
LoadSkillResourceTool(self),
903825
RunSkillScriptTool(self),
904826
]
905-
if self._registry:
906-
self._tools.append(SearchSkillsTool(self))
907827

908828
async def get_tools(
909829
self, readonly_context: ReadonlyContext | None = None
@@ -984,12 +904,6 @@ async def process_llm_request(
984904
skills_xml = prompt.format_skills_as_xml(skills)
985905
instructions = []
986906
instructions.append(_DEFAULT_SKILL_SYSTEM_INSTRUCTION)
987-
if self._registry:
988-
instructions.append(
989-
"\nYou can also use the `search_skills` tool to discover additional"
990-
" skills in the registry if the available skills listed below are"
991-
" not sufficient.\n"
992-
)
993907
instructions.append(skills_xml)
994908
llm_request.append_instructions(instructions)
995909

0 commit comments

Comments
 (0)