Integrations
Backend Integration
Integrate Lelu into any backend service. The Engine exposes a standard REST API, so it works with any language or framework. This guide covers Express, FastAPI, and raw Go.
Express (Node.js)
Use the TypeScript SDK as Express middleware to gate every route that performs a sensitive AI action.
npm
npm install @lelu-auth/lelu
middleware/lelu.ts
import { LeluClient } from "@lelu-auth/lelu";
import type { Request, Response, NextFunction } from "express";
const lelu = new LeluClient({
baseUrl: process.env.LELU_URL!,
apiKey: process.env.LELU_API_KEY!,
});
export function leluGate(action: string) {
return async (req: Request, res: Response, next: NextFunction) => {
const decision = await lelu.authorize({
action,
confidence: req.body.confidence ?? 1.0,
});
if (decision.requiresHumanReview) {
await decision.wait(); // long-poll for approval
}
if (!decision.allowed) {
return res.status(403).json({ error: "Action not authorized by Lelu" });
}
next();
};
}
// Usage:
// app.post("/refund", leluGate("issue_refund"), refundHandler);FastAPI (Python)
Use the Python SDK as a FastAPI dependency to authorize AI-driven actions.
pip
pip install auth-pe
dependencies/lelu.py
from fastapi import HTTPException, Depends
from auth_pe import LeluClient
import os
lelu = LeluClient(
base_url=os.environ["LELU_URL"],
api_key=os.environ["LELU_API_KEY"],
)
def require_lelu(action: str):
async def dependency(confidence: float = 1.0):
decision = lelu.authorize(action=action, confidence=confidence)
if decision.requires_human_review:
decision.wait()
if not decision.allowed:
raise HTTPException(status_code=403, detail="Action denied by Lelu")
return Depends(dependency)
# Usage:
# @app.post("/delete-user")
# async def delete_user(_=require_lelu("delete_user")):
# ...Go (Raw HTTP)
Call the Engine REST API directly from any Go service with a simple helper function.
lelu/client.go
package lelu
import (
"bytes"
"encoding/json"
"fmt"
"net/http"
)
type AuthRequest struct {
Action string `json:"action"`
Confidence float64 `json:"confidence"`
}
type AuthResponse struct {
Status string `json:"status"`
RequestID string `json:"request_id"`
}
func Authorize(action string, confidence float64) (*AuthResponse, error) {
body, _ := json.Marshal(AuthRequest{Action: action, Confidence: confidence})
req, _ := http.NewRequest("POST", engineURL+"/api/v1/authorize", bytes.NewBuffer(body))
req.Header.Set("Authorization", "Bearer "+apiKey)
req.Header.Set("Content-Type", "application/json")
resp, err := http.DefaultClient.Do(req)
if err != nil {
return nil, err
}
defer resp.Body.Close()
var result AuthResponse
json.NewDecoder(resp.Body).Decode(&result)
return &result, nil
}