CaveauAI REST API — Complete Reference

3 views

CaveauAI REST API Documentation

The CaveauAI REST API lets you integrate AI-powered document search and chat into your own applications. Available on Starter plans and above (Trial plans do not have API access).

Base URL: https://ai.bluenotelogic.com/api/v2


Authentication

All API requests require an API key passed in the X-API-Key header.

X-API-Key: bnl_sk_your_api_key_here

Generating an API Key:

  1. Log in to the AI platform at ai.bluenotelogic.com
  2. Navigate to the Dashboard or API settings
  3. Click Generate API Key
  4. Copy the key immediately — it's only shown once
  5. Keys are SHA-256 hashed at rest for security

API keys are prefixed with bnl_sk_ for easy identification.


POST /api/v2/chat.php — AI Chat

Send a question and get an AI-generated answer with source citations from your knowledge base.

Request

{
  "message": "What are the GDPR requirements for DPIAs?",
  "use_corpus": true,
  "model": "qwen2.5:72b",
  "temperature": 0.3,
  "top_p": 0.9,
  "max_tokens": 2048,
  "stream": false,
  "search_packages": ["do-better-legal", "corpus_eu_ai"],
  "category": "gdpr",
  "language": "en",
  "conversation_history": [
    {"role": "user", "content": "What is a DPIA?"},
    {"role": "assistant", "content": "A Data Protection Impact Assessment..."}
  ],
  "session_id": "optional-session-id"
}

Required fields: message

Optional fields:

Field Type Default Description
use_corpus boolean true Search document corpus for context
model string plan default Specific model to use
temperature float 0.3 Creativity (0.0-1.0, lower = more focused)
top_p float 0.9 Diversity of token sampling
max_tokens integer 2048 Maximum response length (256-4096)
stream boolean false Enable SSE streaming response
search_packages array all Specific corpus packages to search
category string null Filter by document category
language string null Preferred response language
conversation_history array [] Prior messages for multi-turn chat
session_id string null Resume a previous conversation

Response

{
  "success": true,
  "query_id": "q_abc123",
  "response": "According to Article 35 of the GDPR, a Data Protection Impact Assessment is required when...",
  "model": "qwen2.5:72b",
  "sources": [
    {
      "title": "GDPR Article 35 — Data protection impact assessment",
      "document_id": 1234,
      "relevance": 0.92,
      "excerpt": "Where a type of processing... is likely to result in a high risk...",
      "package": "corpus_eu_ai"
    }
  ],
  "response_time_ms": 2340,
  "tokens_used": 1847,
  "corpus_chunks_used": 5,
  "queries_remaining": 487,
  "context_stats": {
    "system_tokens": 150,
    "rag_tokens": 3200,
    "history_tokens": 0,
    "response_tokens": 1847,
    "max_context": 32768
  }
}

Streaming Mode

Set "stream": true to receive responses via Server-Sent Events (SSE). Each event contains a token fragment:

data: {"token": "According"}
data: {"token": " to"}
data: {"token": " Article"}
...
data: {"done": true, "sources": [...], "response_time_ms": 2340}

GET /api/v2/documents.php — List Documents

Retrieve your uploaded documents with metadata.

curl -H "X-API-Key: bnl_sk_..." 
  "https://ai.bluenotelogic.com/api/v2/documents.php"

Query parameters:

Parameter Description
id Get a single document by ID
category Filter by category
status Filter by status (pending, ready, error)
limit Max results (default 50)
offset Pagination offset

Response:

{
  "success": true,
  "documents": [
    {
      "id": 42,
      "title": "Employment Contract Template",
      "source_type": "pdf",
      "category": "contracts",
      "language": "no",
      "author": "Legal Team",
      "tags": "employment, template, 2024",
      "word_count": 3200,
      "chunk_count": 8,
      "file_size_bytes": 245000,
      "status": "ready",
      "created_at": "2026-03-15T10:30:00Z"
    }
  ],
  "total": 156
}

POST /api/v2/documents.php — Upload Document

Upload and ingest a document into your private corpus.

curl -X POST 
  -H "X-API-Key: bnl_sk_..." 
  -F "file=@contract.pdf" 
  -F "title=Service Agreement 2026" 
  -F "category=contracts" 
  -F "author=Legal Department" 
  -F "tags=service,agreement,2026" 
  -F "source_url=https://example.com/contract" 
  -F "publication_date=2026-01-15" 
  https://ai.bluenotelogic.com/api/v2/documents.php

Supported file types: PDF, DOCX, TXT, HTML, MD (max 50 MB)

Response:

{
  "success": true,
  "document_id": 43,
  "chunks_created": 12,
  "word_count": 4500,
  "status": "ready"
}

DELETE /api/v2/documents.php — Delete Document

curl -X DELETE 
  -H "X-API-Key: bnl_sk_..." 
  -H "Content-Type: application/json" 
  -d '{"id": 43}' 
  https://ai.bluenotelogic.com/api/v2/documents.php

This permanently removes the document, all its chunks, and vector embeddings from Qdrant.


Rate Limits

Plan Monthly Limit
Trial No API access
Starter 500 requests/month
Professional 2,000 requests/month
Enterprise Custom

Rate limit headers are included in every response:

X-RateLimit-Limit: 2000
X-RateLimit-Remaining: 1487
X-RateLimit-Reset: 2026-05-01T00:00:00Z

What counts: Chat requests and search requests. What doesn't count: Document management (list, upload, delete), failed requests (4xx/5xx).


Error Codes

HTTP Code Meaning Example
200 Success
400 Bad Request Missing required field
401 Unauthorized Invalid or missing API key
403 Forbidden Feature not available on plan
429 Rate Limited Monthly quota exceeded
500 Server Error Internal processing failure

Error response format:

{
  "error": "Rate limit exceeded",
  "code": "RATE_LIMIT_EXCEEDED",
  "retry_after": 3600
}

Code Examples

Python

import requests

API_KEY = "bnl_sk_your_key"
BASE = "https://ai.bluenotelogic.com/api/v2"

# Ask a question
response = requests.post(
    f"{BASE}/chat.php",
    headers={"X-API-Key": API_KEY},
    json={
        "message": "What are the notice periods in Norwegian employment law?",
        "use_corpus": True,
        "temperature": 0.3
    }
)

data = response.json()
print(data["response"])
for source in data["sources"]:
    print(f"  Source: {source['title']} (relevance: {source['relevance']})")

JavaScript (Node.js)

const response = await fetch("https://ai.bluenotelogic.com/api/v2/chat.php", {
  method: "POST",
  headers: {
    "X-API-Key": "bnl_sk_your_key",
    "Content-Type": "application/json"
  },
  body: JSON.stringify({
    message: "Summarize GDPR Article 6 requirements",
    use_corpus: true
  })
});

const data = await response.json();
console.log(data.response);

PHP

$ch = curl_init("https://ai.bluenotelogic.com/api/v2/chat.php");
curl_setopt_array($ch, [
    CURLOPT_POST => true,
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_HTTPHEADER => [
        "X-API-Key: bnl_sk_your_key",
        "Content-Type: application/json"
    ],
    CURLOPT_POSTFIELDS => json_encode([
        "message" => "What is the AI Act risk classification?",
        "use_corpus" => true
    ])
]);

$response = json_decode(curl_exec($ch), true);
echo $response["response"];