DEV Community

shashank ms
shashank ms

Posted on

Using LLM for Social Media Monitoring and Analysis

What we are building

Community managers and product teams need to catch negative sentiment and bugs before they spread. We are building a lightweight social media monitoring agent that ingests raw posts, classifies sentiment, extracts topics, and flags urgent items in a single LLM pass. Because Oxlo.ai charges one flat rate per request, scanning a lengthy rant costs the same as scanning a single word.

What you'll need

Step 1: Prepare mock social data

Real APIs require auth tokens and rate-limit handling, so we will start with a hardcoded list of posts. Each dict holds a username and text.

SOCIAL_POSTS = [
    {
        "user": "@dev_frustrated",
        "text": "The new login flow is completely broken on Safari. I have tried resetting my password three times and still get a 403. This is unacceptable."
    },
    {
        "user": "@happy_customer",
        "text": "Just shipped my first project using the new API docs. The examples were super clear. Great work team!"
    },
    {
        "user": "@curious_dev",
        "text": "Does anyone know if webhook retries are configurable? I could not find it in the settings panel."
    },
    {
        "user": "@angry_user",
        "text": "Your billing page charged me twice this month. I need a refund immediately or I am disputing the charge with my bank."
    }
]

Step 2: Define the analysis prompt

We want structured JSON back. The system prompt tells the model exactly what fields to return and how to score urgency.

SYSTEM_PROMPT = """You are a social media monitoring agent. Analyze each post provided by the user.

Return a JSON object with this exact structure:
{
  "analyses": [
    {
      "user": "string",
      "sentiment": "positive" | "neutral" | "negative",
      "topics": ["topic1", "topic2"],
      "urgency": "low" | "medium" | "high",
      "summary": "one-line summary"
    }
  ]
}

Rules:
- urgency is high if the post mentions security, billing errors, broken core features, or legal threats.
- urgency is medium if the post asks a support question or reports a non-critical bug.
- urgency is low for praise or general feedback.
- Be concise. Output only valid JSON."""

Step 3: Wire up the Oxlo.ai client

We use the OpenAI SDK as a drop-in client. Point the base URL at Oxlo.ai and use your project API key.

from openai import OpenAI

client = OpenAI(base_url="https://api.oxlo.ai/v1", api_key="YOUR_OXLO_API_KEY")

Step 4: Build the analysis pipeline

This function formats the posts into a numbered list, sends them to Llama 3.3 70B, and parses the JSON response. Running the whole batch in one request keeps latency low and takes advantage of Oxlo.ai flat pricing.

import json

def analyze_posts(posts):
    lines = []
    for i, post in enumerate(posts, 1):
        lines.append(f"{i}. @{post['user']}: {post['text']}")
    user_message = "Analyze these posts:\n" + "\n".join(lines)

    response = client.chat.completions.create(
        model="llama-3.3-70b",
        messages=[
            {"role": "system", "content": SYSTEM_PROMPT},
            {"role": "user", "content": user_message},
        ],
    )

    raw = response.choices[0].message.content
    raw = raw.replace("

```json", "").replace("```

", "").strip()
    return json.loads(raw)

Step 5: Add alerting and trend logic

Now we surface anything urgent and print a quick tally of sentiment distribution.

def print_report(result):
    analyses = result.get("analyses", [])
    urgent = [a for a in analyses if a.get("urgency") == "high"]

    print(f"Analyzed {len(analyses)} posts")
    print("-" * 40)

    if urgent:
        print(f"ALERT: {len(urgent)} urgent post(s) detected")
        for item in urgent:
            print(f"  - @{item['user']}: {item['summary']}")
    else:
        print("No urgent items.")

    counts = {"positive": 0, "neutral": 0, "negative": 0}
    for a in analyses:
        s = a.get("sentiment", "neutral")
        if s in counts:
            counts[s] += 1

    print(f"Sentiment -> positive: {counts['positive']}, neutral: {counts['neutral']}, negative: {counts['negative']}")
    print("-" * 40)

Run it

Combine the pieces and execute. The first time you run this, you will see the JSON response printed and any high-urgency items flagged.

if __name__ == "__main__":
    result = analyze_posts(SOCIAL_POSTS)
    print(json.dumps(result, indent=2))
    print()
    print_report(result)

Example output:

{
  "analyses": [
    {
      "user": "@dev_frustrated",
      "sentiment": "negative",
      "topics": ["login", "Safari", "403 error"],
      "urgency": "high",
      "summary": "User reports broken login flow on Safari with repeated 403 errors."
    },
    {
      "user": "@happy_customer",
      "sentiment": "positive",
      "topics": ["API docs", "examples"],
      "urgency": "low",
      "summary": "User praises clarity of new API documentation examples."
    },
    {
      "user": "@curious_dev",
      "sentiment": "neutral",
      "topics": ["webhooks", "configuration"],
      "urgency": "medium",
      "summary": "User asks whether webhook retry settings are configurable."
    },
    {
      "user": "@angry_user",
      "sentiment": "negative",
      "topics": ["billing", "double charge", "refund"],
      "urgency": "high",
      "summary": "User reports duplicate billing charge and threatens dispute."
    }
  ]
}

Analyzed 4 posts
----------------------------------------
ALERT: 2 urgent post(s) detected
  - @dev_frustrated: User reports broken login flow on Safari with repeated 403 errors.
  - @angry_user: User reports duplicate billing charge and threatens dispute.
Sentiment -> positive: 1, neutral: 1, negative: 2
----------------------------------------

Wrap-up and next steps

You now have a working monitor that turns unstructured posts into structured alerts. To productionize it, wire the analyze_posts function to a real data source such as the Reddit API or a Mastodon firehose, and add a webhook to post urgent items into Slack.

If you expand to multilingual communities, swap the model string to qwen-3-32b without changing any other code. Because Oxlo.ai uses flat per-request pricing, long posts and threaded conversations do not inflate your bill the way token-based providers do. See the exact plans at https://oxlo.ai/pricing.

Top comments (0)