/api/v1/moderationSingle-Item Moderation
Moderate a single piece of content in real-time. Returns a decision with confidence score and any triggered rules.
Authentication
All requests must include a valid API key in the Authorization header:
Authorization: Bearer <your cai_live_ API key>Request Body
| Parameter | Type |
|---|---|
contentrequiredThe content to moderate. Maximum 100,000 characters. | string |
contentTypeUse "text". Image and mixed requests currently return 503 because their required evaluation is unavailable. | stringDefault: "text" |
contextOptional context to improve moderation accuracy. | object |
context.platformIdYour platform's identifier for tracking. | string |
context.communityIdYour external community/channel identifier for tracking. | string |
context.authorReputationAuthor reputation score (0-100) for context. | number |
rulesConfigConfigure which rules to apply. | object |
rulesConfig.useGlobalSafetyApply CommunitAI's global safety rules. | booleanDefault: true |
rulesConfig.customRuleIdsSpecific active rules owned by your customer. Missing, inactive, or foreign IDs return 503. | string[] |
rulesConfig.interpretationRule strictness. One of: "strict", "moderate", "permissive". | string |
optionsAdditional response options. | object |
options.explainInclude human-readable explanation in response. | booleanDefault: false |
options.suggestRewriteRequest a rewrite for eligible nonsevere violations. Returned only after it passes the same policies; it is not guaranteed. | booleanDefault: false |
options.returnConfidenceInclude confidence score in response. | booleanDefault: true |
Example Request
{
"content": "Check out this amazing offer! Click here now!!!",
"contentType": "text",
"context": {
"communityId": "tech-forum",
"authorReputation": 45
},
"rulesConfig": {
"useGlobalSafety": true,
"interpretation": "moderate"
},
"options": {
"explain": true,
"returnConfidence": true
}
}Response
| Parameter | Type |
|---|---|
successWhether the request was processed successfully. | boolean |
data.requestIdUnique identifier for this request. | string |
data.decisionModeration decision. One of: "approve", "reject", "warn", "review". | string |
data.confidenceConfidence score from 0 to 1; omitted when options.returnConfidence=false. | number |
data.rulesTriggeredList of rules that matched the content. | array |
data.rulesTriggered[].ruleIdUnique rule identifier. | string |
data.rulesTriggered[].ruleNameHuman-readable rule name. | string |
data.rulesTriggered[].severityRule severity. One of: "low", "moderate", "high", "critical". | string |
data.rulesTriggered[].matchScoreHow strongly the content matched this rule (0-1). | number |
data.explanationHuman-readable explanation (if options.explain=true). | string |
data.suggestedRewriteOptional verified rewrite when requested and available. | string |
data.processingTimeMsServer-side processing time in milliseconds. | number |
data.modelVersionActual evaluation provenance, such as a model identifier or custom-rules. | string |
Recorded Response
From an isolated HTTP test on October 9, 2026 with a customer-owned keyword rule and global safety disabled. The 12 ms value is this observation, not a latency promise.
{
"success": true,
"data": {
"requestId": "b80df991-c565-4ebe-bb5f-02ce87074b65",
"decision": "reject",
"confidence": 1,
"rulesTriggered": [
{
"ruleId": "4a539406-f9de-4068-95c6-3e8be8dc7d88",
"ruleName": "Protect private phone numbers",
"severity": "low",
"matchScore": 1
}
],
"explanation": "Custom rules triggered: Protect private phone numbers",
"processingTimeMs": 12,
"modelVersion": "custom-rules"
}
}Error Responses
VALIDATION_ERRORRequest body is invalid or missing required fields.
{ "success": false, "error": { "code": "VALIDATION_ERROR", "message": "Request validation failed" } }UNAUTHORIZEDThe Authorization header is missing or contains an invalid key.
{ "success": false, "error": { "code": "UNAUTHORIZED", "message": "Invalid or missing API key" } }FORBIDDENYour API key lacks the 'moderate:single' permission.
{ "success": false, "error": { "code": "FORBIDDEN", "message": "API key does not have required permission" } }RATE_LIMIT_EXCEEDEDYou've exceeded your plan's request limit. Retry after the indicated time.
{ "success": false, "error": { "code": "RATE_LIMIT_EXCEEDED", "message": "Rate limit exceeded" } }MODERATION_UNAVAILABLEA required provider, policy evaluation, or persistence step failed. Hold the content; this is not an approval. Disabled deployments return SERVICE_UNAVAILABLE.
{ "success": false, "error": { "code": "MODERATION_UNAVAILABLE", "message": "Required moderation is unavailable" } }INTERNAL_ERRORServer error. Contact support if this persists.
{ "success": false, "error": { "code": "INTERNAL_ERROR", "message": "An unexpected error occurred" } }Code Examples
TypeScript
import { CommunitAIModerator } from '@communitai/maas';
import { env } from '@/env';
const client = new CommunitAIModerator({
apiKey: env.COMMUNITAI_API_KEY, // Import your application's validated server configuration.
});
async function moderatePost(content: string, communityId: string) {
const result = await client.moderate({
content,
contentType: "text",
context: { communityId },
options: { explain: true },
});
switch (result.decision) {
case "approve":
return { allowed: true };
case "reject":
return { allowed: false, reason: result.explanation };
case "warn":
return { allowed: true, flagged: true };
case "review":
return { allowed: false, pending: true, requestId: result.requestId };
}
}cURL
curl -X POST https://www.communitai.org/api/v1/moderation \
-H "Authorization: Bearer $COMMUNITAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"content": "Hello world!",
"contentType": "text",
"options": {
"explain": true
}
}'