Skip to content
Open
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
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
1 change: 1 addition & 0 deletions .github/workflows/link-checker.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ jobs:
--no-progress
--root-dir "$(pwd)/docs"
'./**/*.md'
'./examples/inline/**'
fail: true
failIfEmpty: true
env:
Expand Down
17 changes: 2 additions & 15 deletions docs/2.0/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -260,14 +260,7 @@ that reads this property without handling `undefined` no longer compiles under
`strict` mode.

```typescript
// Before (ADK TypeScript 1.x)
const name = ctx.agent.name;

// After (ADK TypeScript 2.0), inside an agent's own execution
const name = requireAgent(ctx).name;

// After (ADK TypeScript 2.0), outside an agent's own execution
const name = ctx.agent?.name;
--8<-- "examples/inline/typescript/2.0/index/001-context-invocationcontext-agent-is-optio.ts"

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change is complete overkill for 6 lines of code. Remove

```

**Migration action:** Inside an agent's own execution, call `requireAgent(ctx)`,
Expand Down Expand Up @@ -347,13 +340,7 @@ logic into the execution lifecycle.
`session.NewEvent` now requires a `context.Context` as its first argument:

```go
// Before (ADK Go 1.x)
ev := session.NewEvent(ctx.InvocationID())
// or
ev := session.NewEventWithContext(ctx, ctx.InvocationID())

// After (ADK Go 2.0)
ev := session.NewEvent(ctx, ctx.InvocationID())
--8<-- "examples/inline/go/2.0/index/002-event-construction-session-newevent-sign.go.txt"

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

similar comment here. too much for no appreciable gain, and added maintenance cost.

```

The event ID and timestamp are now obtained through the `platform` package,
Expand Down
8 changes: 1 addition & 7 deletions docs/a2a/a2a-extension.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,13 +31,7 @@ To activate the extension, the client can instantiate the `RemoteA2aAgent` with
Activating this extension implies that the server will use the new agent executor implementation.

```python
from google.adk.agents.remote_a2a_agent import RemoteA2aAgent

remote_agent = RemoteA2aAgent(
name="remote_agent",
agent_card="http://localhost:8000/a2a/remote_agent/.well-known/agent-card.json",
use_legacy=False,
)
--8<-- "examples/inline/python/a2a/a2a-extension/001-client-side-extension-activation.py"

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

GLOBAL: Inclusions are not specific (global fix): In order to not bloat pages unnecessarily, the inclusions need to be targeted and not include the entirety of the source code file. You do this by inserting tags in the source code file to mark the beginning and ending of the code you want to include (and skip all the boilerplate stuff).

Not doing this will bloat the documentation pages with lines and lines boilerplate code and wind up frustrating users

```

The `A2aAgentExecutor` uses by default the new implementation, if the a2a extension is detected in the request.
Expand Down
3 changes: 1 addition & 2 deletions docs/a2a/quickstart-consuming-kotlin.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,7 @@ compile classpath as well, because `A2AAgent`'s `httpClient` parameter defaults
to `JdkA2AHttpClient()`:

```kotlin title="build.gradle.kts"
implementation("com.google.adk:google-adk-kotlin-a2a:0.8.0")
implementation("org.a2aproject.sdk:a2a-java-sdk-client:1.0.0.Final")
--8<-- "examples/inline/kotlin/a2a/quickstart-consuming-kotlin/001-add-the-a2a-dependency.kt"
```

## Start a remote agent server
Expand Down
66 changes: 3 additions & 63 deletions docs/a2a/quickstart-consuming.md
Original file line number Diff line number Diff line change
Expand Up @@ -158,20 +158,7 @@ In the sample, the `check_prime_agent` already has an agent card provided:
The main agent uses the `RemoteA2aAgent` class to consume the remote agent (`prime_agent` in our example). As you can see below, `RemoteA2aAgent` requires the `name` and an `agent_card`, which can be an `AgentCard` object, a URL (as in the example below), or a path to a local agent card file; the `description` field is optional and defaults to an empty string.

```python title="a2a_basic/agent.py"
<...code truncated...>

from google.adk.agents.remote_a2a_agent import AGENT_CARD_WELL_KNOWN_PATH
from google.adk.agents.remote_a2a_agent import RemoteA2aAgent

prime_agent = RemoteA2aAgent(
name="prime_agent",
description="Agent that handles checking if numbers are prime.",
agent_card=(
f"http://localhost:8001/a2a/check_prime_agent{AGENT_CARD_WELL_KNOWN_PATH}"
),
)

<...code truncated>
--8<-- "examples/inline/python/a2a/quickstart-consuming/001-how-it-works.py"
```

!!! note "Using the new A2A integration"
Expand All @@ -180,35 +167,7 @@ prime_agent = RemoteA2aAgent(
Then, you can simply use the `RemoteA2aAgent` in your agent. In this case, `prime_agent` is used as one of the sub-agents in the `root_agent` below:

```python title="a2a_basic/agent.py"
from google.adk.agents.llm_agent import Agent
from google.genai import types

root_agent = Agent(
model="gemini-flash-latest",
name="root_agent",
instruction="""
<You are a helpful assistant that can roll dice and check if numbers are prime.
You delegate rolling dice tasks to the roll_agent and prime checking tasks to the prime_agent.
Follow these steps:
1. If the user asks to roll a die, delegate to the roll_agent.
2. If the user asks to check primes, delegate to the prime_agent.
3. If the user asks to roll a die and then check if the result is prime, call roll_agent first, then pass the result to prime_agent.
Always clarify the results before proceeding.>
""",
global_instruction=(
"You are DicePrimeBot, ready to roll dice and check prime numbers."
),
sub_agents=[roll_agent, prime_agent],
tools=[example_tool],
generate_content_config=types.GenerateContentConfig(
safety_settings=[
types.SafetySetting( # avoid false alarm about rolling dice.
category=types.HarmCategory.HARM_CATEGORY_DANGEROUS_CONTENT,
threshold=types.HarmBlockThreshold.OFF,
),
]
),
)
--8<-- "examples/inline/python/a2a/quickstart-consuming/002-how-it-works.py"
```

### Advanced Configuration: Custom Converters and Interceptors
Expand Down Expand Up @@ -245,26 +204,7 @@ Through interceptors, you can also modify the `ParametersConfig` for the A2A req
* **`client_call_context`**: Inject specific client call contexts for the underlying transport.

```python
<...code truncated...>

from google.adk.a2a.agent import A2aRemoteAgentConfig
from google.adk.agents.remote_a2a_agent import AGENT_CARD_WELL_KNOWN_PATH
from google.adk.agents.remote_a2a_agent import RemoteA2aAgent

prime_agent = RemoteA2aAgent(
name="prime_agent",
description="Agent that handles checking if numbers are prime.",
agent_card=(
f"http://localhost:8001/a2a/check_prime_agent{AGENT_CARD_WELL_KNOWN_PATH}"
),
use_legacy=False,
config=A2aRemoteAgentConfig(
a2a_message_converter=my_a2a_message_converter,
request_interceptors=[my_request_interceptor],
),
)

<...code truncated>
--8<-- "examples/inline/python/a2a/quickstart-consuming/003-request-parameters-configuration.py"
```


Expand Down
42 changes: 5 additions & 37 deletions docs/a2a/quickstart-exposing.md
Original file line number Diff line number Diff line change
Expand Up @@ -60,22 +60,13 @@ The sample consists of :
You can take an existing agent built using ADK and make it A2A-compatible by simply wrapping it using the `to_a2a()` function. For example, if you have an agent like the following defined in `root_agent`:

```python
# Your agent code here
root_agent = Agent(
model='gemini-flash-latest',
name='hello_world_agent',

<...your agent code...>
)
--8<-- "examples/inline/python/a2a/quickstart-exposing/001-exposing-the-remote-agent-with-the-toa2a.py"
```

Then you can make it A2A-compatible simply by using `to_a2a(root_agent)`:

```python
from google.adk.a2a.utils.agent_to_a2a import to_a2a

# Make your agent A2A-compatible
a2a_app = to_a2a(root_agent, port=8001)
--8<-- "examples/inline/python/a2a/quickstart-exposing/002-your-agent-code-here.py"
```

The `to_a2a()` function will even auto-generate an agent card in-memory behind-the-scenes by [extracting skills, capabilities, and metadata from ADK agent](https://github.com/google/adk-python/blob/main/src/google/adk/a2a/utils/agent_card_builder.py), so that the well-known agent card is made available when the agent endpoint is served using `uvicorn`.
Expand All @@ -84,30 +75,12 @@ You can also provide your own agent card by using the `agent_card` parameter. Th

**Example with an `AgentCard` object:**
```python
from google.adk.a2a.utils.agent_to_a2a import to_a2a
from a2a.types import AgentCard

# Define A2A agent card
my_agent_card = AgentCard(
name="file_agent",
url="http://example.com",
description="Test agent from file",
version="1.0.0",
capabilities={},
skills=[],
default_input_modes=["text/plain"],
default_output_modes=["text/plain"],
supports_authenticated_extended_card=False,
)
a2a_app = to_a2a(root_agent, port=8001, agent_card=my_agent_card)
--8<-- "examples/inline/python/a2a/quickstart-exposing/003-make-your-agent-a2a-compatible.py"
```

**Example with a path to a JSON file:**
```python
from google.adk.a2a.utils.agent_to_a2a import to_a2a

# Load A2A agent card from a file
a2a_app = to_a2a(root_agent, port=8001, agent_card="/path/to/your/agent-card.json")
--8<-- "examples/inline/python/a2a/quickstart-exposing/004-define-a2a-agent-card.py"
```

### Under the hood: to_a2a() method
Expand Down Expand Up @@ -279,12 +252,7 @@ The new version of the [agent executor](https://github.com/google/adk-python/blo
However, you can also bypass the extension and force the server to use the new executor version by setting the `force_new_version=True` flag when instantiating the `A2aAgentExecutor`. This allows you to use the new executor logic without needing to modify existing clients to send the extension.

```python
from google.adk.a2a.executor.a2a_agent_executor import A2aAgentExecutor

executor = A2aAgentExecutor(
...,
force_new_version=True
)
--8<-- "examples/inline/python/a2a/quickstart-exposing/005-agent-executor-v2.py"
```

## Next Steps
Expand Down
23 changes: 2 additions & 21 deletions docs/agents/config.md
Original file line number Diff line number Diff line change
Expand Up @@ -151,32 +151,13 @@ You can also bypass the CLI and dynamically load and execute a configuration-bas
=== "Python"

```python
import asyncio
from google.adk.agents import config_agent_utils
from google.adk.runners import Runner

async def main():
# Load the agent directly from the YAML config file
agent = config_agent_utils.from_config("my_agent/root_agent.yaml")
# ...

if __name__ == "__main__":
asyncio.run(main())
--8<-- "examples/inline/python/agents/config/001-run-programmatically.py"
```

=== "Java"

```java
import com.google.adk.agents.BaseAgent;
import com.google.adk.agents.ConfigAgentUtils;

public class AgentApp {
public static void main(String[] args) throws Exception {
// Load the agent directly from the YAML config file
BaseAgent agent = ConfigAgentUtils.fromConfig("my_agent/root_agent.yaml");
// ...
}
}
--8<-- "examples/inline/java/agents/config/002-run-programmatically.java"
```

## Example configs
Expand Down
Loading
Loading