Intune Insights: Warranty Integration Implementation Guide

This is a developer guide for partners who want to turn on HP and Lenovo warranty lookups for a deployment through the REST API, instead of using the Nerdio Manager Intune Insights UI.

What this controls

Warranty lookups for HP and Lenovo devices already run on a schedule once a valid key exists for the deployment. This API is how you set (or remove) that key.

Integration type

Credential fields (inside credentialsJson)

Notes

HpWarranty

apiKey, apiSecret

Both are required for the sync job to call HP.

LenovoWarranty

clientId

Required for the sync job to call Lenovo.

DellWarranty

none

Fully managed by Nerdio. It is read-only in the admin screen and has no credential fields. Do not call this API for DellWarranty; there is nothing to set.

The two type strings are part of the contract and must be spelled exactly as shown.

Important

These strings are case-sensitive - see the table below for examples.

Correct

Incorrect

HpWarranty

HPWarranty, HpWaranty, hp-warranty

LenovoWarranty

LenovoWaranty, lenovo-warranty

See Two exact type strings, no allow-list below for further information on why it's important to match these exact strings.

Authentication

All calls use Authorization: Bearer <jwt>, where the JWT comes from the same admin token issuance Nerdio already uses for every other partner-facing feature:

POST /api/nerdio/issue-jwt/admin
ApiSecret: <shared secret>
Content-Type: application/json
 
{ "userEmail": "you@example.com", "userName": "Your Name" }

Response: 200 OK

{ "jwt": "<admin JWT>" }

The integrations endpoints below require an Instance Admin user, which is what the admin JWT already carries. No further permission grant is required.

1. Get current status

GET /api/admin/integrations/{type}

Response: 200 OK

{
  "integrationId": 1,
  "integrationType": "HpWarranty",
  "isEnabled": true,
  "isConfigured": true,
  "configJson": null,
  "createdAt": "2026-09-01T19:13:09.6863181Z",
  "updatedAt": "2026-09-01T19:13:09.6863565Z"
}

isConfigured tells you whether a credential is on file. The credential itself is never returned by this or any other endpoint.

Unknown or never-created {type} returns 404 Not Found.

To list everything configured for the deployment:

GET /api/admin/integrations

Response: 200 OK, an array of the same shape, one entry per integration type that has ever been saved (soft-deleted ones are excluded).

2. Turn on and set (or replace) the credential

PUT /api/admin/integrations/{type}
Content-Type: application/json
 
{
  "integrationType": "HpWarranty",
  "isEnabled": true,
  "credentialsJson": "{\"apiKey\":\"...\",\"apiSecret\":\"...\"}"
}
PUT /api/admin/integrations/{type}
Content-Type: application/json
 
{
  "integrationType": "LenovoWarranty",
  "isEnabled": true,
  "credentialsJson": "{\"clientId\":\"...\"}"
}

Response: 200 OK, the resulting IntegrationResponseDto (same shape as section 1).

Important

Three things about this body are easy to get wrong:

  • integrationType is required in the body, in addition to being in the route. Leaving it out returns 400 with {"errors":{"IntegrationType":["The IntegrationType field is required."]}}. Its value does not need to match the route (Nerdio Manager always stores/looks up by the route value), but omitting it entirely fails validation, so send it every time.

  • credentialsJson is a string containing JSON, not a nested JSON object. Nerdio Manager's own admin screen builds it with JSON.stringify(...) before sending. If you send it as a real nested object instead of a string, you get 400 with "The JSON value could not be converted to System.String". There is no silent failure mode here for a raw HTTP client: a wrongly-shaped credentialsJson is rejected outright.

  • Omitting credentialsJson on an existing integration keeps the previously saved credential. This is how you flip isEnabled via PUT without having the secret on hand to resend. Only send credentialsJson when you actually want to replace the stored value.

This call is an upsert: the first PUT for a {type} creates it, every subsequent PUT updates the same row.

3. Turn off (or back on) without touching the credential

PATCH /api/admin/integrations/{type}/toggle
Content-Type: application/json
 
{ "isEnabled": false }

Response: 204 No Content. Unknown {type} returns 404 Not Found.

4. Remove entirely

DELETE /api/admin/integrations/{type}

Response: 204 No Content on success, 404 Not Found if nothing is on file for that type. This is a soft delete: calling PUT again afterwards for the same {type} creates a brand new record (a new integrationId), it does not revive the deleted one.

What "it's not working" looks like

Nerdio Manager has no way to check an HP or Lenovo key against the vendor before storing it. Saving a mistyped or expired key succeeds immediately with 200 OK and isConfigured: true, exactly the same response you'd get for a correct key.

The mistake surfaces later and quietly: the next scheduled sync tries the vendor call, it fails, and a warning is written to the background sync log. Nothing is returned to whoever called this API, and no visible error message appears. From the administrator's perspective, the only visible symptom is that warranty dates for that vendor simply never populate on devices. If that happens, double-check the credential value itself; the API call having returned 200 does not mean the key is good.

Two exact type strings, no allow-list

PUT does not validate {type} against a known list. PUT /api/admin/integrations/HPWaranty (typo'd) returns 200 OK and creates a row exactly like a correctly-spelled one; there is no 404 to catch the mistake.

That row is then invisible to the sync job forever. The read path (GET/PUT/DELETE) matches {type} case-insensitively against the database, so GET /api/admin/integrations/hpwarranty happily returns the HpWarranty row and makes a typo'd or wrongly-cased save look fine on inspection. The sync job, however, loads enabled integrations and then matches the type in memory with an exact, case-sensitive string comparison against the literals "HpWarranty" and "LenovoWarranty". A row stored as HPWaranty, hpwarranty, or any other variant passes every read-side check but is silently skipped by every sync run.

Important

There is no error anywhere in this path: not from the PUT that created the row, not from a later GET, and not from the sync job (which simply finds nothing to match and moves on). Getting the two type strings exactly right the first time is the only guard that exists today. More robust and explicit error reporting is planned for a future release.

Errors

Status

When

400 Bad Request

Malformed JSON body, credentialsJson sent as a nested object instead of a string, isEnabled sent as a non-boolean, or integrationType missing from the PUT body.

401 Unauthorized

Missing or invalid bearer token on any /api/admin/integrations/* call. Also returned by /api/nerdio/issue-jwt/admin itself if the ApiSecret header is present but does not match.

403 Forbidden

Token is valid but the user is not an Instance Admin.

404 Not Found

GET, PATCH .../toggle, or DELETE against a {type} with no row on file. Not returned by PUT for an unrecognised {type}; see Two exact type strings, no allow-list.

500 Internal Server Error

POST /api/nerdio/issue-jwt/admin with an ApiSecret header present but wrong. Missing the header entirely returns 400 instead (a required-header validation failure), but a present-but-incorrect value is an unhandled exception today, not a clean 401.

Quick reference

Action

Method

Path

Body

Get an admin JWT

POST

/api/nerdio/issue-jwt/admin

{ "userEmail": "...", "userName": "..." }, ApiSecret header

List all integrations

GET

/api/admin/integrations

none

Get one integration's status

GET

/api/admin/integrations/{type}

none

Turn on / set credential

PUT

/api/admin/integrations/{type}

{ "integrationType": "...", "isEnabled": true, "credentialsJson": "..." }

Turn off / on, keep credential

PATCH

/api/admin/integrations/{type}/toggle

{ "isEnabled": false }

Remove entirely

DELETE

/api/admin/integrations/{type}

none

{type} is HpWarranty or LenovoWarranty. Do not call this API for DellWarranty.

Was this article helpful?

0 out of 0 found this helpful
Have more questions? Submit a request

Comments (0 comments)

Article is closed for comments.