From 43e0710249ba011dfd669b8469f1a8f4774d526e Mon Sep 17 00:00:00 2001
From: hiroTamada <88675973+hiroTamada@users.noreply.github.com>
Date: Mon, 19 Oct 2026 17:02:36 +0000
Subject: [PATCH] Document existing-user AgentCard wallet imports
---
integrations/wallets/agentcard.mdx | 87 +++++++++++++++++++++++++++---
integrations/wallets/overview.mdx | 5 ++
2 files changed, 85 insertions(+), 7 deletions(-)
diff --git a/integrations/wallets/agentcard.mdx b/integrations/wallets/agentcard.mdx
index 81398532..007ebf05 100644
--- a/integrations/wallets/agentcard.mdx
+++ b/integrations/wallets/agentcard.mdx
@@ -164,10 +164,80 @@ kernel vault-provider-configs create \
the response exposes `test_mode` (`true` means sandbox, `false` means live).
-verify it against `AGENTCARD_MODE`. then create the wallet with the
-project-scoped `kernel` client and `vault` from
-[Before you start](#before-you-start). CLI users should restore their
-project-scoped `KERNEL_API_KEY` before running the wallet command.
+verify it against `AGENTCARD_MODE`. create the wallet with the project-scoped
+`kernel` client and `vault` from [Before you start](#before-you-start).
+CLI users must restore their project-scoped `KERNEL_API_KEY` before running
+wallet commands.
+
+#### Import an existing user
+
+complete agentcard's [enrollment or sign-in flow](https://docs.agentcard.sh/vault/adding-a-card)
+in your own application and store the resulting `usr_` user id. if you've
+already connected the user, reuse that id; don't enroll them again.
+
+pass the user id with your provider configuration. the examples read it from
+`AGENTCARD_USER_ID` on your server. in your application, resolve the id from the
+stored mapping for the authenticated end user who owns the vault, not from an
+untrusted request field. no per-user access or refresh tokens are required.
+
+
+
+```typescript TypeScript
+const wallet = await kernel.vaults.items.upsert("agentcard-wallet", {
+ id_or_name: vault.id,
+ type: "wallet",
+ spec: {
+ provider: "agentcard",
+ provider_config: { name: agentcardConfig.name },
+ user_id: process.env.AGENTCARD_USER_ID!,
+ },
+});
+```
+
+```python Python
+wallet = kernel.vaults.items.upsert(
+ "agentcard-wallet",
+ id_or_name=vault.id,
+ type="wallet",
+ spec={
+ "provider": "agentcard",
+ "provider_config": {"name": agentcard_config.name},
+ "user_id": os.environ["AGENTCARD_USER_ID"],
+ },
+)
+```
+
+```bash CLI
+kernel vaults wallets create user-12345 agentcard-wallet \
+ --provider agentcard \
+ --provider-config-name checkout-agentcard \
+ --spec "$(jq -n --arg user_id "$AGENTCARD_USER_ID" '{user_id: $user_id}')"
+```
+
+
+
+the cli example uses `jq` to build the json specification. KERNEL validates
+provider access using the selected credentials and their sandbox/live mode
+before creating the wallet. a successful import returns `state.status` set to
+`connected`, without a `card_enrollment` action. KERNEL manages the
+client-credentials access token; there's no per-user refresh-token handoff.
+
+a valid connection with no stored cards also returns `connected`. inspect the
+wallet's advertised `payment_methods` expansion before creating a purchase;
+a connected wallet alone doesn't mean a card is available. continue with
+[Create a card item](#create-a-card-item) once the user has a stored card.
+
+if agentcard rejects the user or credentials, import returns `400` without
+creating a wallet. check the user id, provider configuration, and sandbox/live
+mode, then retry with the corrected specification. after success, the user and
+configuration bindings are immutable. repeating the same key and specification
+returns the existing wallet; changing either binding returns `409`.
+
+#### Enroll through KERNEL instead
+
+if you want KERNEL to create and poll the hosted enrollment session, omit
+`user_id` while keeping your provider configuration. this is an alternative to
+importing a connected user, not a second step after import.
@@ -237,7 +307,7 @@ deadline expires. then continue with [Create a card item](#create-a-card-item).
## Lifecycle
-1. create a `wallet` item and open the returned `card_enrollment` action for the user.
+1. connect a `wallet` item: open the returned `card_enrollment` action, or import an existing user with your own provider configuration.
2. wait for the wallet to become `connected`.
3. create a reusable `card` item with the merchant, amount, and currency.
4. attach the vault to a browser and give `state.aliases` to the agent.
@@ -352,7 +422,10 @@ kernel vaults items get user-12345 agentcard-wallet --wait 60
contain the action url.
-`spec.user_id` can reuse a user who was already enrolled through another wallet in your organization. it cannot reference an arbitrary agentcard user.
+with KERNEL-managed credentials, `spec.user_id` can only reuse a user already
+connected through another wallet in your organization under the same
+configuration. to import a user connected through your own application, select
+your customer-owned configuration and follow [Import an existing user](#import-an-existing-user).
## Create a card item
@@ -745,7 +818,7 @@ wallet and card items accept these `spec` fields. fields not listed here are rej
| item | required fields | optional fields |
| --- | --- | --- |
-| wallet | `provider: 'agentcard'` | `provider_config`; `user_id` for a user already enrolled in the organization under the same configuration |
+| wallet | `provider: 'agentcard'` | `provider_config`; `user_id` to import a connected user with customer-owned credentials, or reuse an organization-local user with KERNEL-managed credentials |
| card | `provider`, `wallet`, `merchant`, `amount`, `currency` | `card_id`, `checkout_origin` |
agentcard accepts amounts from 1–9007199254740991 and a three-letter `currency`. `merchant` accepts 1–120 printable characters without control characters. `card_id` uses the provider's `vc_` identifier, and wallet `user_id` uses its `usr_` identifier.
diff --git a/integrations/wallets/overview.mdx b/integrations/wallets/overview.mdx
index f4936db9..0fcb8071 100644
--- a/integrations/wallets/overview.mdx
+++ b/integrations/wallets/overview.mdx
@@ -72,6 +72,11 @@ provider configuration stores your application's `client_id` and `client_secret`
not an end user's wallet grant. credentials are encrypted at rest; secrets are
never returned.
+with your own client, you can connect users in your backend before creating
+wallets in KERNEL. link imports the user's oauth access and refresh tokens;
+agentcard imports the connected user's `user_id` after validating provider
+access under your configuration, without another hosted enrollment action.
+
configurations are organization-scoped and shared across projects, unlike
project-scoped vaults. create, update, and delete require organization-scoped
authentication; project-scoped api keys receive `403`. names are unique within