Content moderation API

Moderation with your policy, not ours

A kids’ app, a gaming community and a marketplace draw the line in different places. Our open moderation pack, on par with dedicated moderation models, gives a calibrated score for each of 17 categories, with thresholds you set, and runs your own rules in the same call.

Read the paper (PDF)
Cost at scale

About $0.16 per 1,000 posts

1M posts for about $162. On spinf-12b, our optimized Gemma 4 12B, only input is billed, at $0.09 per million tokens: the content once per call, each question's own tokens, and one empty floor per question. The scores are free.

Combine use cases in the same call

The pack is open: a readable JSON file you can download, with every question and threshold. Run it with your own rules and any other classification (topic, intent, prompt injection) on the same post, in one call: the post is read and billed once, and each extra question adds only its own tokens.

posts1,000,000× tokens each (about)1,800= tokens1.8B× $0.09 / 1M$162.00

Assumes 100-token posts, the full moderation prompt-pack (22 categories and a safe / unsafe decision) and two policy questions of your own in the same call. The first 50M tokens are free. Gemma is a trademark of Google LLC.

Pricing details
Tested on public data · spinf/moderation 0.1.1 · 14,504 posts

Results you can trust

Tested on 14,504 real, labelled posts and messages from public test sets, none of which were used to build the pack. Everything is public: rerun the test yourself with your own API key.

The full paper

spinf/moderation: calibrated content moderation from plain-language questions

How the pack works, every category and test set, the safe / unsafe results, cost, what did not work, and the limits.

Used for the safe / unsafe decision
CategoryRanks harmful above harmless
CategoryRanks harmful above harmless
Public test setPostsRanks harmful aboveCaught out of the box
OpenAI moderation · SH5199.1%100%
BeaverTails · self_harm1995.9%84%
Aegis 2.0 · Suicide and Self Harm18992.4%46%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Guns and Illegal Weapons15594.2%40%
Public test setPostsRanks harmful aboveCaught out of the box
OpenAI moderation · S23798.7%96%
BeaverTails · sexually_explicit,adult_content10097.4%78%
Civil Comments · sexual_explicit25386.6%38%
Aegis 2.0 · Sexual25186.4%37%
Public test setPostsRanks harmful aboveCaught out of the box
BeaverTails · animal_abuse4494.0%43%
OpenAI moderation · V22490.3%62%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Sexual (minor)12393.0%66%
BeaverTails · child_abuse2788.6%52%
OpenAI moderation · S38585.9%38%
Public test setPostsRanks harmful aboveCaught out of the box
OpenAI moderation · H16292.2%69%
BeaverTails · discrimination,stereotype,injustice16391.5%53%
Aegis 2.0 · Hate/Identity Hate27989.6%32%
Civil Comments · identity_attack33184.8%52%
BeaverTails · hate_speech,offensive_language17478.3%33%
Public test setPostsRanks harmful aboveCaught out of the box
Civil Comments · threat33593.7%52%
OpenAI moderation · V9492.0%47%
OpenAI moderation · H24191.2%51%
Aegis 2.0 · Threat6284.8%66%
Aegis 2.0 · Violence37180.6%47%
BeaverTails · violence,aiding_and_abetting,incitement36873.7%40%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Malware8885.8%64%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Controlled/Regulated Substances18690.4%36%
BeaverTails · drug_abuse,weapons,banned_substance11380.9%43%
Public test setPostsRanks harmful aboveCaught out of the box
BeaverTails · privacy_violation10391.2%69%
Aegis 2.0 · PII/Privacy14376.9%53%
Public test setPostsRanks harmful aboveCaught out of the box
OpenAI moderation · HR7694.9%46%
Aegis 2.0 · Harassment23686.1%8%
Civil Comments · insult1,02266.2%10%
Public test setPostsRanks harmful aboveCaught out of the box
BeaverTails · terrorism,organized_crime4382.0%7%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Profanity32381.8%48%
Civil Comments · obscene21179.9%44%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Fraud/Deception13780.8%40%
Public test setPostsRanks harmful aboveCaught out of the box
Aegis 2.0 · Criminal Planning/Confessions82789.5%73%
BeaverTails · financial_crime,property_crime,theft14084.2%81%
Aegis 2.0 · Illegal Activity17452.1%13%
Scored and reported, not used for the decision unless you turn them on
CategoryRanks harmful above harmless
CategoryRanks harmful above harmless
Public test setPostsRanks harmful aboveCaught out of the box
Deysi spam detection · spam49899.6%–
YouTube comment spam · spam1,00593.6%–
SMS Spam Collection · spam74791.9%–

Ranks harmful above harmless: show the pack two posts, one that belongs to the category and one that does not. This is how often it gives the first one the higher score (50% would be a coin flip). Out of the box, each category flags only 0.5% of everyday content, and you can make it stricter or looser. Click a category to see its public test sets.

Data, method, the safe / unsafe results and every number on this page: see the paper.

Test sets, questions and code on GitHub: reproduce it with your own key

The questions matter: iterate on yours

As with any language model, the wording of the questions and a few labelled examples change the results a lot. With spinf that is cheap to get right: try a few wordings and example sets on a few hundred of your own items for cents, and keep the best. How to write questions

Live example

See it on a real post

One call: every moderation category, the decision, and a rule of your own.

The post
Guaranteed 300% returns in 7 days! DM me your wallet seed phrase and I'll set up the trading bot for you for free. Only 5 spots left.
Unsafe

The pack’s decision, with its default settings

YOUR RULE, SAME CALL

Does the post promise guaranteed investment returns?

0.92

Probability of “yes”. On a harmless bike-sale post: 0.09.
The moderation pack · all 22 categories

Fraud and scamsflagged

0.98

Hacking and malwareflagged

0.96

Spam and advertisingreported only

0.88

General (overall harmfulness)flagged

0.68

Other crime

0.48

Private personal information

0.42

Illegal drugs

0.36

Weapons

0.32

Child sexual exploitation and grooming

0.32

Extremism and terrorism

0.29

Gore and graphic violence

0.29

Sexual content

0.28

Self-harm and suicide

0.26

Gambling (topic)reported only

0.13

Harassment and bullying

0.13

Profanity

0.10

Violence and threats

0.06

Hate against protected groups

0.04

Medication (topic)reported only

0.01

Tobacco and vaping (topic)reported only

0.01

Alcohol (topic)reported only

0.00

Gibberishreported only

0.00

Each score is 0 to 1, comparable across categories. Flagged: over the category’s threshold. Reported only: scored, not used for the decision unless you turn it on.
import os
import requests

resp = requests.post(
    "https://api.spinf.com/v1/score",
    headers={"Authorization": f"Bearer {os.environ['SPINF_API_KEY']}"},
    json={
      "model": "spinf-12b",
      "inputs": [
        {
          "id": "post-1",
          "messages": [
            {
              "role": "user",
              "content": [
                {
                  "type": "text",
                  "text": "Guaranteed 300% returns in 7 days! DM me your wallet seed phrase and I'll set up the trading bot for you for free. Only 5 spots left."
                }
              ]
            }
          ]
        }
      ],
      "scoring": {
        "packs": [
          {
            "id": "spinf/moderation",
            "context": "forum",
            "decision": {
              "mode": "micro_layer"
            }
          }
        ],
        "queries": [
          {
            "id": "guaranteed_returns",
            "template": "\n\nQuestion: Does the post promise guaranteed investment returns?\nAnswer:{?}",
            "options": [
              " Yes",
              " No"
            ]
          }
        ]
      }
    },
)
result = resp.json()["results"][0]
pack = result["packs"][0]
print("unsafe:", pack["decision"]["unsafe"])
for name, c in sorted(pack["categories"].items(), key=lambda x: -x[1]["score"]):
    print(name, round(c["score"], 2), c["flagged"])
print("your rule:", result["queries"][0]["combinations"][0]["options"])

A live call: the moderation pack (spinf/moderation 0.1.1, forum context) and one rule of your own, 1,708 billed tokens in total. The same rule on a harmless bike-sale post answers Yes 0.09.

The API call behind this example, the docs and the benchmark code are easier to read on a larger screen. Start free now, and pick it up on your laptop.

How it works

Calibrate in bulk, then decide live

The on-demand API is built for throughput: use it to measure spinf on your own history and set your thresholds. Real-time decisions then run on an endpoint reserved for you.

1

Turn on the pack

Add the moderation pack to your calls and moderate right away, with the default decision and thresholds. Try it first on your own posts in the playground.

2

Make it yours, in the same pass

Add your platform’s own rules and any other classification as questions in the same call, score your backlog, and set each threshold on your past decisions.

3

Moderate new posts

Score new posts in batches every few minutes on demand, or as they are published on a reserved endpoint.

FAQ

Content moderation: questions, answered

More in the docs and the guides: custom content moderation policies and zero-shot and few-shot classification, or .

Because moderation has no single right answer. Profanity may be fine where harassment is not; drug discussion may be welcome in a harm-reduction forum and blocked in a teen app. A fixed verdict tuned to one benchmark fits none of them exactly, so the pack gives a calibrated score per category, comparable across categories, and you set each threshold to your policy. The safe / unsafe decision is there too, when you want one.

Yes: the content moderation prompt-pack (spinf/moderation) scores 22 categories, from sexual content and violence to fraud, hacking and private information, each with a calibrated 0–1 score, plus a safe / unsafe decision. It works from the first call, with no training. Try it in the playground, or see the prompt-pack docs.

Yes, the pack is open. Download it (GET /v1/packs/spinf/moderation) to read every question, its calibration and the decision layer, or view it in the playground. Self-harm and child-safety content is always marked unsafe; you can change that list. In each call you choose the decision mode and the threshold of each category, and you add your own questions next to the pack: they read the same post in the same pass, so moderation and your other classifications cost one read of the content.

Text is available to everyone today. Images and audio are in preview, on request.

No. Content sent for scoring is processed in memory and not stored by default, and it is never used to train models.
Try it on your data

The first 50M tokens are on us

Score a sample of your history today, and talk to us when you are ready to go live.