# Deploying an ADK agent for Gemini Enterprise: Agent Runtime or Cloud Run? Comment: After iterating on the [API Contract](/agents/ap-api-contract/) post, I asked Codex 5.6 Sol Ultra to form an opinion about when to use Agent Runtime and when to use Cloud Run in the context of a GE app connected agent, and then write a post. I specifically instructed it to avoid the cloudpickle [deployment options](/agents/5-ways-to-deploy/) (which only work on Agent Runtime), to focus on the other trade-offs. This is the resulting post, presented unmodified. I think it captures the nuances well and presents a balanced view. –William Let's say you've built an agent with ADK and want to make it available in the Gemini Enterprise app. You don't want to pickle the agent — you want to deploy its source or a container — and both Agent Runtime and Cloud Run look like reasonable places to run it. Which should you choose? For that specific case, I would deploy the source to Agent Runtime with `adk deploy agent_engine`, then register the resulting `reasoningEngine` with Gemini Enterprise using the native ADK integration. I would choose Cloud Run and Agent2Agent (A2A) if serving clients beyond Gemini Enterprise, or keeping the endpoint portable, were actual requirements. That recommendation is more specific than saying Agent Runtime is always the right place to run an agent. It isn't. Cloud Run is a pretty capable container platform. Both paths ultimately execute a container, but Agent Runtime adds a different resource model, contract, lifecycle, and integration with Gemini Enterprise. Note: This comparison reflects the product documentation and implementation at the time of writing. In particular, several of the A2A integration pieces are still in Preview or Experimental. ## Three choices hiding in one question There are really three separate decisions here: 1. **How you package the agent:** a serialized Python object, source code, a Dockerfile, or a prebuilt container image. 2. **Where it runs:** Agent Runtime or Cloud Run. 3. **How Gemini Enterprise calls it:** the native ADK integration through a `reasoningEngine`, or the portable A2A protocol through an Agent Card and endpoint URL. These choices are related, but they aren't the same. In particular, avoiding pickle doesn't imply Cloud Run. Agent Runtime accepts source, Dockerfiles, and prebuilt containers too. I covered the packaging options in [5 ways to deploy agents on Agent Platform](/agents/5-ways-to-deploy/). The contract choice is easy to muddle as well. The [Agent Platform runtime contract](/agents/ap-api-contract/) is the plumbing between an Agent Runtime `reasoningEngine` and the container behind it. A2A is an external protocol that a client such as Gemini Enterprise uses to talk directly to an agent service. Here's the resulting matrix: | Host and Gemini Enterprise contract | Does it work? | When I would use it | |---|---|---| | **Agent Runtime with native ADK registration** | Yes | The default for an ADK agent built primarily for Gemini Enterprise. | | **Cloud Run with A2A** | Yes | When portability, other A2A clients, or Cloud Run-specific control matters. | | **Agent Runtime with A2A** | Yes, currently in Preview | When you want the Agent Platform control plane but specifically need A2A as the client contract. | | **Cloud Run with Runtime-shaped routes** | The HTTP routes can exist, but native Gemini Enterprise registration doesn't work | Don't use this as a substitute for a `reasoningEngine`; use A2A or deploy the container to Agent Runtime. | ## The path I would use The current ADK deployment command takes an agent folder: ```shell adk deploy agent_engine \ --project=PROJECT_ID \ --region=LOCATION \ --display_name="My Agent" \ AGENT_FOLDER ``` The [ADK deployment guide](https://adk.dev/deploy/agent-runtime/deploy/) describes this as packaging the code, building it into a container, and deploying that container to Agent Runtime. Looking at the [current CLI implementation](https://github.com/google/adk-python/blob/main/src/google/adk/cli/cli_deploy.py), it generates a Dockerfile, sends the source and Dockerfile using `source_packages`, selects the Dockerfile build with `image_spec`, declares the ADK class methods, and creates a `reasoningEngine` resource. So this is a source deployment from the developer's point of view and a container deployment under the hood. That current CLI path doesn't create a `.pkl` deployment artifact. Nice! You then register the full resource name with Gemini Enterprise: ``` projects/PROJECT_ID/locations/LOCATION/reasoningEngines/RESOURCE_ID ``` Gemini Enterprise stores that resource in an `adkAgentDefinition`. A turn then follows this path: ``` Gemini Enterprise app ↓ reasoningEngines/RESOURCE_ID:streamQuery ↓ Agent Runtime → /api/stream_reasoning_engine ↓ class_method: streaming_agent_run_with_events ↓ ADK Runner → root_agent ``` The [native ADK registration guide](https://docs.cloud.google.com/gemini/enterprise/docs/register-and-manage-an-adk-agent) documents the `reasoningEngine` resource binding. The rather long `streaming_agent_run_with_events` method name is the interesting part of the integration. ## What the native ADK handoff does `streaming_agent_run_with_events` isn't agent business logic. It's an adapter between Gemini Enterprise, which owns the outer conversation, and the ADK runner executing the next turn. The request can carry: - the new message; - preceding ADK events; - session artifacts; - user authorizations; - user and session identifiers; and - request labels and other context. The response streams the new ADK events, changed artifacts, and the resulting session id. If necessary, the adapter creates a session and seeds it with the supplied events and artifacts before running the agent. The [official `AdkApp` implementation](https://github.com/googleapis/python-aiplatform/blob/main/vertexai/agent_engines/templates/adk.py) contains that translation, and its [API reference](https://docs.cloud.google.com/python/docs/reference/agentplatform/latest/vertexai.agent_engines.AdkApp) describes the method as primarily intended for Agentspace — the former name of Gemini Enterprise. The current deployment command also points the ADK session and memory service URIs at the new `reasoningEngine`, so the generated server uses Agent Platform Sessions and Memory Bank rather than keeping that state in one container. There are two caveats here. Saving a conversation to Memory Bank still requires an explicit agent or application action, and durable artifact storage needs to be configured separately. The handoff can carry artifacts; that doesn't make the default artifact service durable. The [ADK agent documentation for Agent Runtime](https://docs.cloud.google.com/gemini-enterprise-agent-platform/build/runtime/create-an-adk-agent) describes these managed-service defaults. The authorization handoff is similarly deliberate. The `AdkApp` adapter puts forwarded OAuth tokens into temporary ADK state, which keeps them out of the persisted session. That's a useful bit of plumbing to get from the supported adapter rather than recreating in every agent. You don't implement this method yourself when you use the supported ADK deployment tooling. The generated server registers it, along with the normal session, memory, and streaming-query methods. If you build a serving layer from scratch, however, then your container does have to implement the ADK profile that Gemini Enterprise expects. The [runtime contract documentation](https://docs.cloud.google.com/gemini-enterprise-agent-platform/scale/runtime/runtime-contract) specifically recommends using the ADK tooling if you want these updates handled alongside ADK releases. This is Agent Runtime's strongest advantage for this particular use case. It doesn't make the agent more intelligent, and most of the individual pieces could be assembled on Cloud Run. It removes the separate A2A surface and state model you would otherwise have to operate. ## No pickle does not mean Cloud Run Agent Runtime currently offers several no-pickle deployment paths: - `adk deploy agent_engine`, which builds a generated ADK container from your source; - generic source deployment, which sends a `tar.gz` archive directly to the Agent Platform API; - Developer Connect deployment from a linked Git revision; - a source deployment containing your own Dockerfile, which Agent Runtime builds; and - a prebuilt image in Artifact Registry. Only the agent-object path — passing `agent=local_agent` to the SDK — creates a `.pkl`. The [Agent Runtime deployment guide](https://docs.cloud.google.com/gemini-enterprise-agent-platform/scale/runtime/deploy-an-agent) separates these methods explicitly. Generic source and Developer Connect deployments are Python-only; Dockerfile and image deployments can use any language that serves the Runtime contract. For a normal Python ADK agent, I would start with `adk deploy agent_engine`. It keeps the source-oriented workflow while letting the ADK project maintain the serving adapter and method declaration. The generic inline-source path is also legitimate, but it asks you to declare the entrypoint and `classMethods` yourself and currently has an 8 MB source-package limit. Tip: Use your own Dockerfile or prebuilt image when you need OS packages, an exact base image, image signing and SBOMs, private build infrastructure, or an existing container release pipeline. Where possible, keep the Google-provided ADK API server inside that image rather than writing the Runtime dispatch layer again. Source versus container changes who owns the build. It doesn't determine how Gemini Enterprise invokes the finished agent. ## What changes on Cloud Run On Cloud Run, the practical Gemini Enterprise contract is A2A. The agent may still be implemented entirely in ADK, but Gemini Enterprise registers it as an A2A agent and calls the URL from its Agent Card: ``` Gemini Enterprise app ↓ A2A v0.3 streaming request ↓ Cloud Run service → A2A request handler and TaskStore ↓ ADK A2A executor ↓ ADK Runner → root_agent ``` ADK's [`to_a2a()` helper](https://adk.dev/a2a/quickstart-exposing/) removes a fair amount of boilerplate. It can generate the Agent Card, install an A2A executor, mount the routes, and bridge requests into an ADK runner. At the time of writing this ADK integration is marked **Experimental**, though, and its defaults are designed for development: in-memory ADK services, an `InMemoryTaskStore`, and an in-memory push-notification store. For a production Cloud Run deployment, you need to make deliberate choices for all of these: - the Agent Card, skills, capabilities, and advertised endpoint URL; - the A2A protocol version and Gemini Enterprise compatibility; - persistent A2A task storage; - an explicit ADK session and artifact strategy, if the agent uses them; - service-to-service authentication; - any end-user OAuth handling; and - registration with the Gemini Enterprise app. The state detail is easy to miss. An A2A `TaskStore` tracks A2A tasks and their status. If the service also uses ADK Sessions, an ADK `SessionService` stores the conversation events and working state. They solve different problems, so persisting the TaskStore alone doesn't persist the ADK session. The [Cloud Run A2A guide](https://docs.cloud.google.com/run/docs/deploy-a2a-agents) recommends AlloyDB for production task storage, while the [ADK Cloud Run deployment guide](https://adk.dev/deploy/cloud-run/) warns that its default session and artifact services are in-memory and disappear when an instance is recycled. You can connect an ADK agent on Cloud Run to Agent Platform Sessions and Memory Bank explicitly using the documented `agentengine://` service URIs. That narrows the state-management difference, but it doesn't remove the A2A TaskStore or the protocol adapter. Cloud Run can build this service from source or deploy a prebuilt image. Both are no-pickle paths, and source deployment still produces a container behind the scenes. The packaging choice doesn't supply A2A by itself: an ordinary `adk deploy cloud_run` API server still needs A2A enabled and a usable Agent Card before Gemini Enterprise can register it through this route. Gemini Enterprise's [A2A registration guide](https://docs.cloud.google.com/gemini/enterprise/docs/register-and-manage-an-a2a-agent) currently supports the A2A v0.3 streaming mechanism. If your service uses A2A 1.x, you need the compatibility package provided by the SDK. ## Cloud Run is becoming agent-aware Cloud Run can now label a workload as an agent, assign it a system-managed Agent Identity, and register it automatically in Agent Registry. That's useful — especially if your organization wants a catalog of agents running across several platforms — but it doesn't turn an ADK `root_agent` into a serving application. Specifically, `--functional-type=agent` and `--identity-type=agent-identity` don't create an Agent Card, install an A2A executor, configure either state store, or attach the service to Gemini Enterprise. They also don't create a `reasoningEngine`. The [Cloud Run Agent Platform feature](https://docs.cloud.google.com/run/docs/ai/agent-platform-features) is currently in Preview and documents Agent Identity and Registry as the two provided integrations. So yes, the convenience features can be added to Cloud Run. Google has already started doing that. Today the native ADK handoff and managed Runtime resource are still separate. ## What about A2A on Agent Runtime? Agent Runtime can host an A2A agent too. Its A2A template exposes operations such as sending a message, fetching a task, and cancelling a task, while the deployment is still managed as a `reasoningEngine`. Both [creating an A2A agent on Agent Runtime](https://docs.cloud.google.com/gemini-enterprise-agent-platform/build/runtime/create-an-a2a-agent) and [using that agent](https://docs.cloud.google.com/gemini-enterprise-agent-platform/scale/runtime/use-an-a2a-agent) are currently marked Preview. This combination makes sense when you specifically want the Agent Platform control plane and an A2A boundary. For an ADK agent built primarily for Gemini Enterprise, however, it adds the A2A task and compatibility machinery while skipping the most useful part of the native integration. Interestingly, the current `adk deploy agent_engine` implementation also enables ADK's A2A handling in the generated server. That doesn't automatically give you a production-ready A2A service, and it doesn't change the Gemini Enterprise contract: A2A still needs an Agent Card, registration, and its own persistence decisions and testing. If I needed both, I would keep Gemini Enterprise on the native route and treat A2A as a separately configured surface for other clients. ## Can Cloud Run expose the Runtime contract? Technically, yes. A Cloud Run service can expose `/api/reasoning_engine` and `/api/stream_reasoning_engine`, accept the same request envelope, and even implement `streaming_agent_run_with_events`. That still doesn't make the service a native ADK agent from Gemini Enterprise's point of view. Native registration doesn't accept an arbitrary URL for that contract; it accepts a resource name with this shape: ``` projects/PROJECT_ID/locations/LOCATION/reasoningEngines/RESOURCE_ID ``` The public `:query` and `:streamQuery` APIs, declared `classMethods`, runtime identity, and container routing all belong to that resource. Copying the final two HTTP routes copies one layer of the wire format, not the control-plane resource Gemini Enterprise registers. On Cloud Run, use A2A. If you want the native contract, deploy the same container to Agent Runtime. ## Security and governance Both paths can be private and properly authenticated. The native registration documentation says that communication between Agent Runtime and Gemini Enterprise is compatible with VPC Service Controls, supports private cross-project connections, and supplies the user's email to the agent. For a private A2A service on Cloud Run, Gemini Enterprise generates a Google-signed OIDC token for the Discovery Engine service agent and sends it in `X-Serverless-Authorization`. Cloud Run consumes that header to enforce `roles/run.invoker`. If the agent also needs delegated access on behalf of the user, Gemini Enterprise sends the user's OAuth token separately in the normal `Authorization` header. That's a pretty clean arrangement. One difference is governance. A directly registered A2A agent does **not** send traffic through Agent Gateway, so Gateway policies don't apply. Importing the agent from Agent Registry through the governed route can add Gateway policy, but it also adds Registry and Gateway configuration and requires the regions to line up. Warning: Gemini Enterprise's console-level Model Armor configuration doesn't automatically protect custom ADK or A2A agents. The two registration guides say to integrate Model Armor in the agent application if you need it. This isn't a reason to prefer one host over the other, but it's an important production detail. ## Operations and maturity Google now lists [Agent Runtime among the generally available Agent Platform features](https://cloud.google.com/blog/products/ai-machine-learning/whats-new-in-gemini-enterprise-agent-platform), including support for containers. That doesn't mean every control is at the same launch stage: customized scaling controls and [revision traffic management](https://docs.cloud.google.com/gemini-enterprise-agent-platform/scale/runtime/manage-revisions-and-traffic) are currently Preview. Cloud Run's core revision and traffic-management features are more established, which can be a good reason to keep an existing Cloud Run release pipeline. The end-to-end A2A route has more moving parts at earlier launch stages today: - Gemini Enterprise A2A registration is Preview; - Cloud Run's A2A deployment feature is Preview; - Cloud Run's Agent Platform integration is Preview; and - ADK's A2A exposure is Experimental. By comparison, the native Gemini Enterprise ADK registration page isn't marked Preview. Its management examples still use the Discovery Engine `v1alpha` API, though, so I would pin the ADK and Agent Platform SDK versions I've tested and include a real Gemini Enterprise invocation in release verification. Testing only `async_stream_query` or the Agent Runtime playground doesn't exercise the GE-specific handoff. Agent Runtime also has an asynchronous query-job API whose jobs can run for up to seven days, whereas an individual Cloud Run request has a maximum timeout of 60 minutes. A Cloud Run application can of course run longer work through a separate asynchronous architecture. The seven-day Runtime job isn't the normal interactive Gemini Enterprise `:streamQuery` path, so I wouldn't choose a host on that feature alone. See the [Agent Runtime usage guide](https://docs.cloud.google.com/gemini-enterprise-agent-platform/scale/runtime/use-an-adk-agent) and [Cloud Run timeout documentation](https://docs.cloud.google.com/run/docs/configuring/request-timeout). Before a production rollout, check the [Agent Platform quotas](https://docs.cloud.google.com/gemini-enterprise-agent-platform/resources/agent-quotas) as well. The default `Query`/`StreamQuery` quota is 90 requests per minute per project and region, and one agent turn can append several session events. ## Cost The unit compute prices are remarkably close. As of September 2, 2026, [Agent Platform pricing](https://cloud.google.com/products/gemini-enterprise-agent-platform/pricing) lists Agent Runtime at $0.085 per vCPU-hour and $0.009 per GiB-hour, rounded to the nearest second, with idle time between turns unbilled. [Cloud Run request-based pricing](https://cloud.google.com/run/pricing) lists active compute at $0.000024 per vCPU-second and $0.0000025 per GiB-second. That's about $0.0864 per vCPU-hour and $0.009 per GiB-hour, plus the request charge. The free tiers are similarly shaped too. This compares list-price units, not the final bill. The practical bill can still differ: - Agent Runtime currently defaults to 4 vCPU and 4 GiB per instance; the controls used to right-size that allocation are currently Preview. - Agent Platform Sessions and Memory Bank have their own storage and operation charges. - A production A2A deployment may need AlloyDB or another durable TaskStore, which can cost more than the low-volume Cloud Run service itself. - Cloud Run supports instance-based billing and committed-use discounts. - Model calls, external tools, Model Armor, and Gemini Enterprise licensing are separate either way. Sessions and Memory Bank began using the current Agent Platform pricing on September 1, 2026. Storage is $0.30 per GiB-month; reads consume one $0.085 Agent Compute unit per three million operations, and writes consume one unit per million operations. Memory generation and embedding tokens are billed separately too. I wouldn't choose between these products on the tiny compute-rate difference. The useful distinction is how much of the agent integration you want the platform to own. ## When I would choose Cloud Run instead Cloud Run with A2A is the better fit when at least one of these is a real requirement: - other A2A clients are first-class consumers of the agent; - the endpoint needs to move between Cloud Run, GKE, another cloud, or on-premises infrastructure; - A2A is your organization's required interoperability boundary; - you need custom HTTP routes, middleware, sidecars, or networking in the same service; - your production process depends on Cloud Run's mature revisions, traffic splitting, billing controls, and operational tooling; or - you deliberately want to own the A2A task and persistence model. If Gemini Enterprise is the only or primary client and none of those requirements applies, the extra adapter, TaskStore, and protocol compatibility work doesn't buy much. ## What I would deploy Putting it all together, here's the path I would start with: 1. Keep the ADK `root_agent` and tools independent of the serving protocol. 2. Pin the ADK and Agent Platform SDK versions. 3. Deploy the source with `adk deploy agent_engine` — no object serialization. 4. Use Agent Identity and grant it only the downstream permissions it needs. 5. Configure durable artifact storage if the agent uses artifacts. 6. Integrate Model Armor in the application if the deployment requires it. 7. Register the resulting `reasoningEngine` with Gemini Enterprise using the native ADK integration. 8. Test the actual Gemini Enterprise path, including session continuity, artifacts, tool authorization, and user identity. 9. Right-size the container and request any quota increases before rollout. For this agent, that's where I'd start. If A2A clients appear later, the core ADK agent can stay the same while you add and test the second serving surface.