Back to Examples
TypeScript / JavaScript
Integrate GuardCrow into your TypeScript or JavaScript applications using native fetch or popular HTTP libraries.
Basic Example
A simple example using the native fetch API:
analyze.tstypescript
interface AnalysisResult {passed: boolean;score: number;sentiment: "positive" | "negative" | "neutral" | "toxic";description: string;categories: string[];processingTimeMs: number;}async function analyzeContent(content: string): Promise<AnalysisResult> {const response = await fetch("https://api.guardcrow.com/v1/analyze", {method: "POST",headers: {"X-API-Key": process.env.GUARDCROW_API_KEY!,"Content-Type": "application/json",},body: JSON.stringify({ content }),});if (!response.ok) {const error = await response.json();throw new Error(error.error?.message || "Analysis failed");}return response.json();}// Usageconst result = await analyzeContent("Hello, this is a test message");console.log(result.passed ? "Content is safe" : "Content flagged");
With Error Handling
A more robust implementation with proper error handling and retry logic:
guardcrow-client.tstypescript
interface AnalysisResult {passed: boolean;score: number;sentiment: string;description: string;categories: string[];processingTimeMs: number;}interface AnalysisError {error: {code: string;message: string;status: number;};}class GuardCrowClient {private apiKey: string;private baseUrl = "https://api.guardcrow.com/v1";private maxRetries = 3;constructor(apiKey: string) {this.apiKey = apiKey;}async analyze(content: string,metadata?: Record<string, string>): Promise<AnalysisResult> {let lastError: Error | null = null;for (let attempt = 0; attempt < this.maxRetries; attempt++) {try {const response = await fetch(`${this.baseUrl}/analyze`, {method: "POST",headers: {"X-API-Key": this.apiKey,"Content-Type": "application/json",},body: JSON.stringify({ content, metadata }),});if (response.status === 429) {// Rate limited - wait and retryconst resetTime = response.headers.get("X-RateLimit-Reset");const waitMs = resetTime? parseInt(resetTime) * 1000 - Date.now(): Math.pow(2, attempt) * 1000;await this.sleep(Math.max(waitMs, 1000));continue;}if (!response.ok) {const errorData: AnalysisError = await response.json();throw new Error(errorData.error.message);}return response.json();} catch (error) {lastError = error as Error;if (attempt < this.maxRetries - 1) {await this.sleep(Math.pow(2, attempt) * 1000);}}}throw lastError || new Error("Analysis failed after retries");}private sleep(ms: number): Promise<void> {return new Promise((resolve) => setTimeout(resolve, ms));}}// Usageconst client = new GuardCrowClient(process.env.GUARDCROW_API_KEY!);try {const result = await client.analyze("Check this content", {source: "user-comments",user_id: "user_123",});console.log("Analysis result:", result);} catch (error) {console.error("Analysis failed:", error);}
Next.js API Route
Proxy requests through your Next.js API to keep your API key secure:
app/api/moderate/route.tstypescript
import { NextRequest, NextResponse } from "next/server";export async function POST(request: NextRequest) {const { content } = await request.json();if (!content) {return NextResponse.json({ error: "Content is required" },{ status: 400 });}const response = await fetch("https://api.guardcrow.com/v1/analyze", {method: "POST",headers: {"X-API-Key": process.env.GUARDCROW_API_KEY!,"Content-Type": "application/json",},body: JSON.stringify({ content }),});const data = await response.json();return NextResponse.json(data, { status: response.status });}
Express.js Middleware
Create middleware to automatically moderate incoming content:
middleware/moderate.tstypescript
import { Request, Response, NextFunction } from "express";interface ModerationOptions {contentField?: string;blockOnFail?: boolean;minScore?: number;}export function moderateContent(options: ModerationOptions = {}) {const {contentField = "content",blockOnFail = true,minScore = 7,} = options;return async (req: Request, res: Response, next: NextFunction) => {const content = req.body[contentField];if (!content) {return next();}try {const response = await fetch("https://api.guardcrow.com/v1/analyze",{method: "POST",headers: {"X-API-Key": process.env.GUARDCROW_API_KEY!,"Content-Type": "application/json",},body: JSON.stringify({ content }),});const result = await response.json();// Attach result to request for downstream usereq.moderation = result;if (blockOnFail && result.score >= minScore) {return res.status(400).json({error: "Content blocked by moderation",reason: result.description,});}next();} catch (error) {// Don't block on API errors - let content throughconsole.error("Moderation error:", error);next();}};}// Usageapp.post("/comments", moderateContent(), (req, res) => {// Content passed moderationconsole.log("Moderation result:", req.moderation);// Save comment...});
React Hook
A custom React hook for content moderation (calls your backend API):
hooks/useModeration.tstypescript
import { useState, useCallback } from "react";interface ModerationResult {passed: boolean;score: number;sentiment: string;description: string;}interface UseModerationReturn {moderate: (content: string) => Promise<ModerationResult>;isLoading: boolean;error: string | null;result: ModerationResult | null;}export function useModeration(): UseModerationReturn {const [isLoading, setIsLoading] = useState(false);const [error, setError] = useState<string | null>(null);const [result, setResult] = useState<ModerationResult | null>(null);const moderate = useCallback(async (content: string) => {setIsLoading(true);setError(null);try {// Call your backend API (not GuardCrow directly!)const response = await fetch("/api/moderate", {method: "POST",headers: { "Content-Type": "application/json" },body: JSON.stringify({ content }),});if (!response.ok) {throw new Error("Moderation request failed");}const data = await response.json();setResult(data);return data;} catch (err) {const message = err instanceof Error ? err.message : "Unknown error";setError(message);throw err;} finally {setIsLoading(false);}}, []);return { moderate, isLoading, error, result };}// Usage in a componentfunction CommentForm() {const { moderate, isLoading, error } = useModeration();const [content, setContent] = useState("");const handleSubmit = async (e: React.FormEvent) => {e.preventDefault();try {const result = await moderate(content);if (result.passed) {// Submit the comment} else {alert("Your comment was flagged: " + result.description);}} catch {// Handle error}};return (<form onSubmit={handleSubmit}><textareavalue={content}onChange={(e) => setContent(e.target.value)}/><button disabled={isLoading}>{isLoading ? "Checking..." : "Submit"}</button>{error && <p className="error">{error}</p>}</form>);}
Type Definitions
Complete TypeScript type definitions for the API:
types/guardcrow.d.tstypescript
// Request typesexport interface AnalyzeRequest {content: string;metadata?: {source?: string;user_id?: string;[key: string]: string | undefined;};}// Response typesexport interface AnalyzeResponse {passed: boolean;score: number;sentiment: Sentiment;description: string;categories: Category[];processingTimeMs: number;}export type Sentiment = "positive" | "negative" | "neutral" | "toxic";export type Category =| "insult"| "threat"| "spam"| "hate_speech"| "harassment"| "self_harm"| "violence"| "sexual";// Error typesexport interface APIError {error: {code: ErrorCode;message: string;status: number;};}export type ErrorCode =| "MISSING_API_KEY"| "INVALID_API_KEY"| "MISSING_CONTENT"| "CONTENT_TOO_LONG"| "INVALID_JSON"| "RATE_LIMIT_EXCEEDED"| "INTERNAL_ERROR";// Health checkexport interface HealthResponse {status: "healthy" | "degraded" | "unhealthy";timestamp: string;}
Environment Setup
Add your API key to your environment variables:
.env.localbash
GUARDCROW_API_KEY=sk_live_your_api_key_here