Examples

export VERUSCITE_API_KEY='vc_your_key_here'

Check account

curl -sS "https://veruscite-data.com/api/v1/me" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" | jq .

Submit a file

The form field name must be file, and the path needs @ so curl uploads the file contents (not a plain string).

curl -sS -X POST "https://veruscite-data.com/api/v1/documents" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" \
  -F "file=@./paper.pdf" | jq .

Poll until finished, then get results

DOC_ID=123

while true; do
  RESP=$(curl -sS "https://veruscite-data.com/api/v1/documents/$DOC_ID" \
    -H "Authorization: Bearer $VERUSCITE_API_KEY")
  echo "$RESP" | jq '{status, finished, total_citations}'
  echo "$RESP" | jq -e '.finished == true' >/dev/null && break
  sleep 5
done

curl -sS "https://veruscite-data.com/api/v1/documents/$DOC_ID/results" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" | jq .

List active jobs

curl -sS "https://veruscite-data.com/api/v1/jobs" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" | jq .

List all your documents

# Newest first: id, filename, status, created_at, citation counts
curl -sS "https://veruscite-data.com/api/v1/documents?limit=50" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" | jq .

# Only completed
curl -sS "https://veruscite-data.com/api/v1/documents?status=completed&limit=20" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" | jq .

Rename a document and set owner notes

DOC_ID=123
curl -sS -X PATCH "https://veruscite-data.com/api/v1/documents/$DOC_ID" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"filename":"references.bib","notes":"Smoke test bibliography"}' | jq .

Edit or delete a citation

DOC_ID=123

# Get a citation id from results (stable id, not list index)
CITE_ID=$(curl -sS "https://veruscite-data.com/api/v1/documents/$DOC_ID/results" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" | jq '.citations[0].id')
echo "CITE_ID=$CITE_ID"

# Edit fields (partial patch; only send keys you want to change)
curl -sS -X POST "https://veruscite-data.com/api/v1/documents/$DOC_ID/citations/$CITE_ID" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"action":"edit","fields":{"title":"Corrected title","year":2024,"notes":"Fixed OCR"}}' | jq .

# Delete the row
curl -sS -X POST "https://veruscite-data.com/api/v1/documents/$DOC_ID/citations/$CITE_ID" \
  -H "Authorization: Bearer $VERUSCITE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"action":"delete"}' | jq .

Python

import os
import time
import requests

API_KEY = os.environ["VERUSCITE_API_KEY"]
HEADERS = {"Authorization": f"Bearer {API_KEY}"}
paper_path = "paper.pdf"

# File-like object or raw bytes both work (multipart field name must be "file"):
with open(paper_path, "rb") as f:
    r = requests.post(
        "https://veruscite-data.com/api/v1/documents",
        headers=HEADERS,
        files={"file": (paper_path, f, "application/pdf")},
    )
# Equivalent with bytes already in memory:
# pdf_bytes = open(paper_path, "rb").read()
# files={"file": ("paper.pdf", pdf_bytes, "application/pdf")}
r.raise_for_status()
doc_id = r.json()["document"]["id"]

while True:
    st = requests.get(
        f"https://veruscite-data.com/api/v1/documents/{doc_id}",
        headers=HEADERS,
    ).json()
    print(st["status"], st.get("total_citations"))
    if st.get("finished"):
        break
    time.sleep(5)

results = requests.get(
    f"https://veruscite-data.com/api/v1/documents/{doc_id}/results",
    headers=HEADERS,
).json()
print(results["citation_count"], "citations")

# Document display name + owner notes
requests.patch(
    f"https://veruscite-data.com/api/v1/documents/{doc_id}",
    headers=HEADERS,
    json={"filename": "references.bib", "notes": "Smoke test bibliography"},
).raise_for_status()

# Edit one citation by stable id from results
cite_id = results["citations"][0]["id"]
requests.post(
    f"https://veruscite-data.com/api/v1/documents/{doc_id}/citations/{cite_id}",
    headers=HEADERS,
    json={"action": "edit", "fields": {"title": "Corrected title", "notes": "Fixed"}},
).raise_for_status()

# Delete a citation
# requests.post(
#     f"https://veruscite-data.com/api/v1/documents/{doc_id}/citations/{cite_id}",
#     headers=HEADERS,
#     json={"action": "delete"},
# ).raise_for_status()