# Access tiers

> Which passport data is public, which is restricted, and how BatteryPass keeps restricted data out of public responses.

The Battery Regulation splits passport data by audience (Art. 77(2), Annex XIII). BatteryPass gives every
field of the registry one access tier and filters by tier on the server: a response never contains data above
the tier it is meant for.

## The tiers

`Tier` names the tier of a field or document; `PassportTier` names the tier a passport document is projected
to. A projection contains its tier and the ones before it: `legitimate_interest` includes `public`,
`authority` includes both.

| Tier                  | Audience                                                                                                     | Examples                                                                                                             |
| --------------------- | ------------------------------------------------------------------------------------------------------------ | -------------------------------------------------------------------------------------------------------------------- |
| `public`              | Everyone who scans the QR code                                                                               | Manufacturer, category, chemistry, capacity, voltages, hazardous substances, declaration of conformity               |
| `legitimate_interest` | Persons with a legitimate interest, plus notified bodies, market surveillance authorities and the Commission | Detailed composition, dismantling information, battery status, condition data such as capacity fade and cycle counts |
| `authority`           | Notified bodies, market surveillance authorities and the Commission                                          | Results of test reports                                                                                              |
| `internal`            | Your organisation only                                                                                       | Never part of a passport projection                                                                                  |

The registry decides the tier of each field: [`getRegistrySchema`](https://passport.kabin.sh/docs/en/api-reference/registry/get-registry-schema)
returns `tier` for every field. In the current registry all condition data fields are `legitimate_interest`.

## The public projection

At publication BatteryPass projects the version's snapshot to the `public` tier, stores the result as the
version's public document and [signs it](https://passport.kabin.sh/docs/en/concepts/signatures). Public operations serve this stored
document; they never project old versions again with newer code or a newer registry. A later registry change
can therefore neither reveal nor hide data in a version that is already published.

The public document lists fields of the `public` tier only. For the fields above it that have a value, it gives
the keys in `restricted_fields_present`, never the values. Documents of a restricted tier are left out
entirely, not even with their title.

```bash title="cURL"
curl -s "$BATTERYPASS_URL/api/v1/public/passports/$PASSPORT_UUID" \
  | jq '{tier: .document.tier, restricted: .document.restricted_fields_present}'
```

```json title="Response"
{
  "tier": "public",
  "restricted": ["identification.battery_status", "condition.capacity_fade"]
}
```

## Public operations return the public tier only

These operations need no key and only ever return `public` data:

| Operation                                                                                                                      | Returns                                                               |
| ------------------------------------------------------------------------------------------------------------------------------ | --------------------------------------------------------------------- |
| [`getPublicPassport`](https://passport.kabin.sh/docs/en/api-reference/public/get-public-passport)                            | The current version's public document                                 |
| [`getPublicPassportByProductId`](https://passport.kabin.sh/docs/en/api-reference/public/get-public-passport-by-product-id)   | The same, looked up by GTIN and serial number                         |
| [`getPublicPassportVersion`](https://passport.kabin.sh/docs/en/api-reference/public/get-public-passport-version)             | The public document valid at a point in time                          |
| [`downloadPublicPassportDocument`](https://passport.kabin.sh/docs/en/api-reference/public/download-public-passport-document) | A `public` document that a public field names; anything else is `404` |
| [`verifyPassport`](https://passport.kabin.sh/docs/en/api-reference/public/verify-passport)                                   | The result of the signature check, without data                       |

The [resolver](https://passport.kabin.sh/docs/en/concepts/digital-link) behind the QR code links to the same public page and JSON.

## What an API key reads

An API key reads your own organisation's passports with a viewer's rights, and that includes the restricted
tiers of your own data: the `snapshot` of [`getPassportVersion`](https://passport.kabin.sh/docs/en/api-reference/passports/get-passport-version),
[`exportPassportJson`](https://passport.kabin.sh/docs/en/api-reference/passports/export-passport-json) and
[`exportPassportPdf`](https://passport.kabin.sh/docs/en/api-reference/passports/export-passport-pdf) carry every tier. One exception:
files of the `authority` and `internal` tiers can only be downloaded by editors and above, so
[`downloadEvidence`](https://passport.kabin.sh/docs/en/api-reference/evidence/download-evidence) answers `403 forbidden` to a key for
them.

> [!WARNING]
> Data your integration reads with a key is not automatically public. Keep restricted values out of anything you
> show to end customers, and publish only what the public JSON contains.

## Restricted tiers for third parties

Third parties, such as a repair shop or an authority, do not read restricted tiers through the API. BatteryPass
has a separate, portal-based access for them:

- It is off unless the operator of the installation enables it (`TIER_PORTAL_ENABLED`, off by default). While
  it is off, the public JSON carries no `links.restricted` and nothing points to it.
- When it is on, an owner or admin of the economic operator grants `legitimate_interest` or `authority` to a
  reader's email address, with a purpose and an expiry of at most one year, and can revoke the grant at any
  time.
- The reader signs in to the portal with that verified address and sees the current version projected to the
  granted tier. Restricted documents are listed by title only.
- Every restricted read is recorded in the audit log of the passport's organisation.

This access is not an API key feature and not part of the published contract.

> [!NOTE]
> The implementing act under Art. 77(9) that defines who has a legitimate interest, and how they prove it, is
> still pending. Until then the economic operator decides whom to grant access; BatteryPass does not present
> these grants as the regulation's access mechanism.
