---
title: Testing & Deployment
slug: frameworks/kmi-testing-and-deployment
createdAt: 2026-11-03T06:49:31.314Z
---

# Integration Configuration

This guide covers testing and deployment of a **KMI version 1.0** integration. Implement the contract in the [Implementation Guide](docId\:Yhwc63UQsxJo8sMgylSvB) before running the lifecycle tests.

## What You Need

| Item                               | Purpose                                                                                 |
| ---------------------------------- | --------------------------------------------------------------------------------------- |
| Key cabinet API documentation      | Define inventory, user, permission and custody operations                               |
| Non-production cabinet environment | Test without affecting production users or keys                                         |
| Cabinet API credentials            | Let your service access the cabinet with the required permissions                       |
| Seven HTTPS endpoints              | Receive KMI operations from Sine                                                        |
| KMI API key                        | Authenticate Sine requests to your service; use a separate key per customer integration |
| Customer `externalId`              | Select the correct cabinet configuration for each request                               |
| Test key groups and keys           | Exercise inventory sync, access and returns                                             |
| Synthetic visitor data             | Exercise lifecycle operations without real personal data                                |
| Sine test site                     | Configure and test the integration                                                      |

Store real credentials in a secret manager or another approved secret store. Use synthetic values in fixtures, and do not include API keys, visitor PINs or unredacted personal data in shared logs.

Generate the KMI API key in your service and provide it, the seven endpoint URLs and the customer `externalId` to the Sine administrator through an approved secure channel. Keep cabinet API credentials in your service; they are not part of the Sine configuration.

## Sine Configuration

A Sine administrator configures the following:

| Setting               | Value                                                                   |
| --------------------- | ----------------------------------------------------------------------- |
| Verify endpoint       | HTTPS URL of your Verify operation                                      |
| Resources endpoint    | HTTPS URL of your Resources operation                                   |
| Keys endpoint         | HTTPS URL of your Keys operation                                        |
| Provision endpoint    | HTTPS URL of your Provision operation                                   |
| Activate endpoint     | HTTPS URL of your Activate operation                                    |
| Check-return endpoint | HTTPS URL of your Check-return operation                                |
| Deprovision endpoint  | HTTPS URL of your Deprovision operation                                 |
| KMI API key           | Customer-specific secret your service uses to authenticate Sine         |
| External ID           | Customer or cabinet configuration identifier understood by your service |
| Key groups            | Groups returned by your Resources endpoint                              |
| Dynamic asset type    | Sine's destination for the synchronised key options                     |

For example, the URLs can be paths under `https://integration.example.com/kmi/`, but each address is configured separately.

Your service, not Sine, stores and uses the cabinet API credentials. Protect the endpoint URLs and API key according to your organisation's security requirements.

# Testing Your Integration

## Sending Mock Requests Directly

Test request parsing, authentication and response shapes directly before testing the Sine lifecycle. Use your API client's secret storage for the KMI API key.

For example, send the following request to your test service. The hostname and API key are placeholders, not live connection details.

```http
POST /kmi/verify HTTP/1.1
Host: integration.example.com
Authorization: <REPLACE_ME>
Content-Type: application/json
Accept: application/json

{
  "config": {
    "externalId": "site-123"
  }
}
```

Expect HTTP `200` and this JSON body:

```json
{ "code": "SUCCESS" }
```

Repeat with the endpoint-specific payloads in the [Implementation Guide](docId\:Yhwc63UQsxJo8sMgylSvB). Run Provision before testing Activate, Check-return or Deprovision, and use the returned `keyUserId`. Use the same synthetic customer and key IDs throughout.

Send another request without `Authorization` and confirm HTTP `401`. Then test a valid API key with an unauthorised `externalId` and confirm HTTP `403`.

## Authentication and Validation

For every operation:

1. Send a valid `POST` request with the configured KMI API key and a JSON body.
2. Confirm that missing or invalid API keys are rejected.
3. Confirm that invalid JSON, missing required fields and unsupported field types are rejected.
4. Fuzz field types, lengths and encodings, and confirm malformed input fails safely.
5. Send a valid customer key with another customer's `externalId` and confirm your service returns `403` without accessing that cabinet.
6. Confirm that errors and logs do not expose secrets, visitor PINs or unnecessary personal data. The successful Provision response must include the visitor's cabinet credentials; handle that response securely.

The [Implementation Guide](#) contains request and response examples. The configured API key is sent as the `Authorization` header value.

## Operation Contract Tests

| Operation    | Cases to cover                                                                                                         | Successful result                                       |
| ------------ | ---------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------- |
| Verify       | Valid configuration, invalid credentials, unavailable cabinet                                                          | `200`, `SUCCESS`                                        |
| Resources    | Available groups, no groups, failed lookup                                                                             | `200`, top-level `keyGroups`                            |
| Keys         | Selected groups, overlapping groups, multiple cabinet pages, genuinely empty inventory, failed or incomplete retrieval | `200`, `SUCCESS` and complete `data` array              |
| Provision    | Valid visit, missing contact, invalid key, duplicate request, uncertain creation                                       | `201`, `PROVISIONED` and non-empty user ID and password |
| Activate     | Correct user and keys, missing user, permission failure, repeated request                                              | `200`, `ACTIVATED`                                      |
| Check-return | All returned, outstanding keys, empty request array, missing or ambiguous custody data                                 | `200`, `SUCCESS` and top-level `unreturnedKeyIds`       |
| Deprovision  | Existing access, empty key array, already-removed access, cabinet failure, repeated request                            | `200`, `DEPROVISIONED`                                  |

Check exact field names and types, not only the HTTP status. For failures, return a non-success status and a safe error response. Do not return an empty successful inventory or custody result when your service could not determine the real state.

## Inventory Safety Tests

1. Return keys from each selected group and confirm IDs remain strings, including leading zeroes.
2. Return one key in multiple groups and confirm your service returns it only once.
3. Make the cabinet API return multiple pages and confirm your service includes all of them.
4. Fail a later page and confirm your service returns an error, not a partial success.
5. Return a genuinely empty inventory and confirm the receiving environment treats it as an empty snapshot.
6. Test key IDs at and beyond the site's expected identifier-length limit, including any stable ID mapping your service uses.

Sine reconciles the successful snapshot and can remove keys that are absent from it. Test this only with dedicated non-production data.

## Testing with a Sine Test Site

Run end-to-end tests using a Sine test site, a test cabinet and synthetic visitor details.

1. Have the administrator configure your test endpoints, KMI API key and `externalId`.
2. Verify connectivity and retrieve the available key groups.
3. Select test groups and synchronise their keys into the configured dynamic asset type.
4. Confirm the check-in form presents those keys for selection.
5. Check in a test visitor, confirm the Provision and Activate requests, and inspect cabinet permissions.
6. Check out the visitor, confirm Check-return, and observe the follow-up check and Deprovision after the grace period.

Use the scenarios below to test variations and failures.

| Scenario                                        | Behaviour to verify                                                                                                   |
| ----------------------------------------------- | --------------------------------------------------------------------------------------------------------------------- |
| Key groups are selected                         | Sine calls your [Keys endpoint](#) and exposes the returned keys as form options                                      |
| Visitor selects no keys                         | Provision is not requested                                                                                            |
| Visitor supplies neither email nor mobile       | Provision is not requested                                                                                            |
| Visitor supplies mobile but no email            | Provision can be requested; no credential email is sent                                                               |
| Pass awaits approval                            | Provision prepares the user; Activate waits for acceptance                                                            |
| Pass is accepted or checked in                  | Activate is called and credential email is attempted when an email address is available                               |
| Provisioned pass is rejected                    | Deprovision is requested without waiting for the check-out grace period                                               |
| Provision fails                                 | A cabinet failure handled by Sine does not, by itself, reject check-in; no successful cabinet provisioning is assumed |
| Activation or email fails                       | A completed check-in is not rolled back                                                                               |
| Check-out reports outstanding keys              | A reminder may be sent if the visitor has an email address                                                            |
| Check-out reports no outstanding keys           | No reminder is expected; delayed deprovision is still scheduled                                                       |
| A return check fails or keys remain outstanding | Deprovision is still attempted after the grace period                                                                 |

The grace period is 15 minutes; the follow-up return check and deprovision attempt can occur later. Do not rely on deprovision happening at an exact second.

Check both the Sine activity and cabinet state. A completed check-in is not proof that the cabinet user was provisioned, activated or sent credentials.

## Failure and Recovery Tests

- Simulate cabinet authentication failures, permission errors, timeouts and unavailable services.
- Simulate a timeout after a cabinet user was created. Reconcile the outcome before retrying Provision.
- Confirm that the stored `externalId`/`visitId` to `keyUserId` mapping supports later operations, which do not include `visitId`.
- Repeat Activate and Deprovision and verify that they are safe to repeat.
- Return ambiguous custody data and confirm it is not presented as a confirmed physical return.
- Verify that the site has a process for recovering keys that remain outstanding after cabinet access ends.
- Confirm that support staff can identify the customer, operation, visit and failure using redacted diagnostics.

Do not assume exactly-once delivery or automatic retries. If a timeout leaves a cabinet write uncertain, inspect the cabinet state before repeating the operation.

# Deployment Checklist

- [ ] All seven endpoints are reachable over HTTPS with a valid certificate.
- [ ] Every endpoint authenticates the KMI API key and validates its request.
- [ ] Each customer API key is explicitly authorised for its `externalId`; a mismatch is rejected.
- [ ] Cabinet credentials are stored securely and have only the required permissions.
- [ ] Inventory responses are complete, deduplicated and use stable key IDs.
- [ ] Provisioned users cannot access requested keys before activation.
- [ ] Credential, validity and permission mappings are tested against the cabinet.
- [ ] Return classification and handling of unknown custody state are tested.
- [ ] Deprovision and already-removed-user handling are tested.
- [ ] Duplicate requests and uncertain cabinet writes have a documented recovery process.
- [ ] Test-site configuration and lifecycle tests pass.
- [ ] Support and physical-key recovery contacts are documented.

