Connecting
QR Inventory speaks the Model Context Protocol over HTTP. Point the client at the server URL. The client posts JSON-RPC messages. A GET request to the same URL is rejected.
https://qr-inventory.com/mcp/inventory
This is not the REST API. A Sanctum API key from User Management will not authenticate an MCP client. The connector signs the user in with OAuth, and every tool is limited to that user's organisation. Requests are limited to 120 a minute for that user.
In a client such as Claude, add a custom connector and paste the server URL. The client discovers the OAuth endpoints, registers itself, and sends the user to QR Inventory to approve access. After approval, the client can call tools. The register tools are read-only. picture-board-tool is the exception: it creates a PDF and returns a download link.
A tool call looks like this:
POST https://qr-inventory.com/mcp/inventory
Authorization: Bearer {oauth-access-token}
Accept: application/json
Content-Type: application/json
{
"jsonrpc": "2.0",
"id": 1,
"method": "tools/call",
"params": {
"name": "search-assets-tool",
"arguments": { "query": "hairdryer" }
}
}
OAuth
The server uses OAuth 2.1 with the authorisation-code grant and PKCE (S256). The only scope is mcp:use. Clients are public: they register without a client secret.
| Step |
Endpoint |
What it returns |
| Protected resource |
GET /.well-known/oauth-protected-resource |
The resource URL, the authorisation server, and the mcp:use scope. |
| Authorisation server |
GET /.well-known/oauth-authorization-server |
The authorise, token, and registration endpoints, and the S256 challenge method. |
| Register a client |
POST /oauth/register |
A client_id for the redirect URI. Send JSON. redirect_uris is required. |
| Authorise |
GET /oauth/authorize |
The QR Inventory sign-in and approval screen. The user must already have an account. |
| Token |
POST /oauth/token |
An access token and a refresh token. Send the access token as Authorization: Bearer. |
POST https://qr-inventory.com/oauth/register
Content-Type: application/json
{
"client_name": "Claude",
"redirect_uris": ["https://claude.ai/api/mcp/auth_callback"],
"grant_types": ["authorization_code", "refresh_token"],
"token_endpoint_auth_method": "none"
}
A machine-readable copy of the tool list is at https://qr-inventory.com/mcp/docs.json.
Call list-filter-options-tool before filtering if you do not know the exact category, location, or group name. Names are matched exactly, ignoring letter case. Locations and groups include what sits beneath them unless you turn that off. Items packed in a container are listed in that container's notes: search for the item, then answer with the container and its location.
TOOL
list-assets-tool
List assets and return register counts.
Returns totals by status, category, subcategory and location, plus inspection and warranty rollups. The asset list is included unless include_assets is false. Read-only, and limited to the signed-in organisation.
| Argument |
Required |
Description |
category |
No |
Category name or numeric id. |
subcategory |
No |
Subcategory name or numeric id. If the name matches more than one row, also pass category or use the id. |
location |
No |
Location name or numeric id. Locations beneath it are included unless include_sublocations is false. |
include_sublocations |
No |
Include locations beneath the location filter. Defaults to true. |
group |
No |
Group name or numeric id. Groups beneath it are included unless include_subgroups is false. |
include_subgroups |
No |
Include groups beneath the group filter. Defaults to true. |
status |
No |
active, retired, or any. Defaults to any. |
include_assets |
No |
Include the asset list as well as the counts. Defaults to true. |
limit |
No |
Assets to return in the list. 1 to 200. Defaults to 100. |
offset |
No |
Assets to skip. Defaults to 0. |
TOOL
search-assets-tool
Find assets by words.
Every word must match the label, notes, sub-location, QR sticker code, serial, manufacturer, or manufacturer code. Container contents are stored in the container notes, so a match there means the item is inside that container. Read-only.
| Argument |
Required |
Description |
query |
Yes |
The words to search for. |
limit |
No |
Maximum matches. 1 to 50. Defaults to 20. |
category |
No |
Category name or numeric id. |
subcategory |
No |
Subcategory name or numeric id. If the name matches more than one row, also pass category or use the id. |
location |
No |
Location name or numeric id. Locations beneath it are included unless include_sublocations is false. |
include_sublocations |
No |
Include locations beneath the location filter. Defaults to true. |
group |
No |
Group name or numeric id. Groups beneath it are included unless include_subgroups is false. |
include_subgroups |
No |
Include groups beneath the group filter. Defaults to true. |
status |
No |
active, retired, or any. Defaults to any. |
TOOL
get-asset-tool
Fetch one asset.
Looks up a single asset by QR sticker code, serial number, or numeric id. Includes location, supplier, maintainer, and inspection dates. Use this for a container when you need its full contents. Read-only.
| Argument |
Required |
Description |
identifier |
Yes |
QR sticker code, serial number, or numeric id. |
TOOL
upcoming-inspections-tool
List inspections that are due or overdue.
Overdue assets are always included. The window looks ahead the given number of days. Read-only.
| Argument |
Required |
Description |
within_days |
No |
How far ahead to look, in days. 1 to 365. Defaults to 30. |
limit |
No |
Maximum assets to return. 1 to 100. Defaults to 50. |
TOOL
list-filter-options-tool
List the names you can filter by.
Returns the organisation's categories, subcategories, locations, and groups, each with a direct asset count. Call this before filtering when the exact name is unknown. Read-only.
This tool takes no arguments.
TOOL
picture-board-tool
Build a PDF picture board.
One card per asset, with photo, label, QR code, and location. Retired assets are excluded. The result is a download link that anyone with the link can open for 24 hours. The board is refused when the filter matches more than 250 assets.
| Argument |
Required |
Description |
category |
No |
Category name or numeric id. |
subcategory |
No |
Subcategory name or numeric id. If the name matches more than one row, also pass category or use the id. |
location |
No |
Location name or numeric id. Locations beneath it are included unless include_sublocations is false. |
include_sublocations |
No |
Include locations beneath the location filter. Defaults to true. |
group |
No |
Group name or numeric id. Groups beneath it are included unless include_subgroups is false. |
include_subgroups |
No |
Include groups beneath the group filter. Defaults to true. |
per_page |
No |
Cards per page: 4, 8, or 12. Defaults to 8. |
include_contents |
No |
Add an appendix of notes for assets that have them. Defaults to true. |
title |
No |
Title shown instead of the filter label. Maximum 80 characters. |