Skip to main content
Documentation

Documents

documents.library_stats

Count what is in the document library and the tags in use
Read-onlyRead budget

REST

Shipping
POST /api/v1/documents/library_stats

MCP tool

Live
documents.library_stats

Exposed on: REST API · Shop MCP server · Claude connector · Dash (in-app copilot) · Zapier. Part of the Documents domain.

Operating contract

The shape of the shop's filing: how many documents, how much storage they take, how many are photos against PDFs, how many landed this month, and every tag actually in use.

tags IS THE VOCABULARY documents.list FILTERS ON, most-used first. Read it before filtering — a tag invented from a shop's own words matches nothing and returns an empty list that looks exactly like a shop with no such documents.

PHOTOS OUTNUMBERING PDFS BY A WIDE MARGIN IS NORMAL for this trade. Install evidence is the bulk of a shop's library and is not a filing problem.

total_bytes is what the library is holding. It is computed over the newest thousand rows, so on a large library treat it as a floor rather than a total.

This is a set of counts and a capped tag list, entirely returned, so nothing is truncated beyond that scan.

Who may call it

Permission
NoneThe header of the document library at /documents, which guards dashboard membership and nothing narrower — a document can hang off any record in the product, so gating the library on one section would hide a customer's waiver from the person holding their job.
Plan
Every planNo plan gate. Available on every Service VIN plan.
Retries
naturalNaturally idempotent — running it twice leaves the same world as running it once. A retrying integration needs no key.
Rate class
readCounted against the read budget — the widest of the four.

Input

This capability takes no arguments.

Output

FieldTypeDescription
total_countnumber

total_bytesnumber

photo_countnumber

pdf_countnumber

uploaded_this_monthnumber

tagsstring[]

Examples

Built from this capability's own schema — required fields and the ones carrying a default, and nothing invented. Paste one and it validates.

curl
export SERVICEVIN_API_KEY=svk_live_…

curl -X POST https://www.servicevin.com/api/v1/documents/library_stats \
  -H "Authorization: Bearer $SERVICEVIN_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{}'

TypeScript (fetch)
const res = await fetch("https://www.servicevin.com/api/v1/documents/library_stats", {
  method: "POST",
  headers: {
    Authorization: `Bearer ${process.env.SERVICEVIN_API_KEY}`,
    "Content-Type": "application/json",
  },
  body: JSON.stringify({}),
});

// Success and failure are both envelopes. Switch on error.code, never
// on error.message — the codes are stable, the messages are for people.
const payload = await res.json();
if (!res.ok) throw new Error(payload.error.code);
const data = payload.data;

Python (requests)
import os, requests

res = requests.post(
    "https://www.servicevin.com/api/v1/documents/library_stats",
    headers={"Authorization": f"Bearer {os.environ['SERVICEVIN_API_KEY']}"},
    json={},
    timeout=30,
)
payload = res.json()
if not res.ok:
    raise RuntimeError(payload["error"]["code"])
data = payload["data"]

MCP tools/call — https://www.servicevin.com/api/mcp
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "documents.library_stats",
    "arguments": {}
  }
}

Refusals

The four gates run in this order on every surface, and the order is not arbitrary — see Authentication.

StatusCodeWhen
404not_foundThe id is unknown, or the feature is not enabled for this account. Deliberately the same answer for both.
422validation_errorAn argument was wrong. The message names the field.
429rate_limitedToo many read calls. Back off and retry.
500internal_errorSomething failed on our side. Nothing was changed.