Skip to main content

Enforcing an Ecosystem as a Wallet

This page explains how ecosystem constraints — such as those required by EUDI — are enforced by the wallet.

For an overview of how ecosystems operate, see Ecosystem Enforcement Overview.

Prerequisites​

A wallet must have ecosystems available before it can enforce them on interactions. See Determining available ecosystems below for how a wallet instance determines this.

Determining available ecosystems​

A wallet instance checks two sources, in order:

  1. Registration — if the wallet instance is registered with a Wallet Provider, the ecosystems selected by that Provider apply. See Enforcing an Ecosystem as a Provider.

  2. Own configuration — if the wallet instance is not registered with a Provider, it falls back to its own organization's configuration. See Enabling Ecosystems for instructions on selecting ecosystems for a standalone wallet organization.

How enforcement works​

Ecosystem constraints can be checked at up to two points in a flow. See the Ecosystem Enforcement Reference for the complete list of validations per ecosystem.

First gateway: handle-invitation​

Every credential offer or proof request starts with:

POST /api/interaction/v1/handle-invitation

{
"ecosystem": "EUDI",
{{...}}
}

You can name an ecosystem explicitly, as shown, or omit it.

If you name an ecosystem during handle-invitation, that single ecosystem is enforced on the interaction. If that ecosystem fails to validate the interaction, the call fails — this is true even if the wallet is not set to require enforcement globally.

If you omit ecosystem, the system falls back to auto-detection: every ecosystem available to the wallet checks the interaction. If no ecosystem returns TRUSTED, the call fails only if enforcement is required.

In both cases, the response includes ecosystemErrors, giving the result of every ecosystem checked — just the one named, or all of them if auto-detection ran.

Second gateway: issuance-accept or submit-presentation​

Depending on ecosystem, other trust checks may occur in the next call of the interaction:

  • Issuance: POST /api/interaction/v1/issuance-accept
  • Presentation: POST /api/interaction/v1/submit-presentation

If you named an ecosystem above and it validated the interaction, the same ecosystem will continue its checks at this stage.

If you omitted ecosystem above, any ecosystems which validated the interaction in the first step are used again to check at this stage.

Issuance and presentation both follow the same success/failure/ecosystemErrors shape as the first gateway. A credential offer, for example, can pass handle-invitation and still fail issuance-accept if it does not pass these further checks.

If more than one ecosystem validates an interaction at this final step, the first ecosystem — as determined by the order in which you passed them when enabling them — is chosen as the final ecosystem, and is used for filling trustInformation. See Looking up interaction partner details.

Requiring ecosystem enforcement​

Any ecosystem available to a wallet organization is available for use, either passed in handle-invitation or found through auto-detection. To require that every interaction pass at least one ecosystem's constraints, update the wallet organization:

PATCH /api/organisations/v1/{id}

{
"configuration": {
"enforceEcosystemAsHolder": true
}
}

If enforcement is required, handle-invitation only succeeds when at least one ecosystem returns TRUSTED; otherwise it fails.

Looking up interaction partner details​

Once issuance-accept or submit-presentation succeeds, the credential or proof request exists in the wallet, and its detail response includes a trustInformation object summarizing how it was resolved:

GET /api/credential/v1/{id} GET /api/proof-request/v1/{id}

"trustInformation": {
"result": "TRUSTED",
"name": "EUDI",
"receivedAt": "2026-09-11T12:25:06.715Z",
"ecosystemErrors": {
"EUDI": { "result": "TRUSTED" },
"OTHER": {
"result": "NOT_TRUSTED",
"error": {
"code": "BR_0486",
"message": "..."
}
}
}
}
  • result is TRUSTED or UNTRUSTED. If ecosystem enforcement is required, either because it was passed with handle-invitation or because it is required by the configuration, the top-level result must be TRUSTED.
  • ecosystemErrors repeats the same per-provider detail from the two gateways, for whichever ecosystems were actually checked. A TRUSTED overall result can still show a rejected entry here if a different provider failed. Note the naming: entries here use NOT_TRUSTED, while trustInformation.result itself uses UNTRUSTED.
  • Resolution is also recorded as an ECOSYSTEMS_RESOLVED history event, using the same per-provider shape.

For the full resolved detail about the interaction partner — not just the verdict — call:

  • GET /api/credential/v1/{id}/trust-detail
  • GET /api/proof-request/v1/{id}/trust-detail

The responses to these calls return issuer and verifier blocks which include details from that entity's registration, including privacy policy and support URLs, service descriptions, intermediaries, and more.