Skip to content

Ramane-Vision/swara-agent-capstone

Repository files navigation

Swara Agent — Multi-Agent River Pollution Monitoring

Track: Agents for Good Capstone for: 5-Day AI Agents: Intensive Vibe Coding Course with Google (Kaggle x Google)

A multi-agent system that turns raw river-monitoring sensor data (camera-based garbage detection + ultrasonic water-level sensing) into decision-ready alerts and plain-language reports for local environmental officers — without anyone having to watch a live camera feed all day.

The problem

Rivers running through dense urban areas (e.g. Kalimas in Surabaya) accumulate floating garbage that clogs flow and worsens flooding. Low-cost embedded sensor rigs (ESP32-S3 camera + ultrasonic sensors) can now detect this automatically and cheaply — but raw sensor telemetry is not something a busy kelurahan officer or volunteer cleanup coordinator can act on directly. Someone (or something) still has to watch the stream, decide what's significant, and turn it into a message a human will actually read and act on.

Why agents

This is a perception -> decision -> communication pipeline with different skills at each stage, which is exactly where a small team of specialist agents beats one giant prompt:

  • A Perception Agent doesn't need any language ability — it just needs to validate and classify.
  • An Alert Agent needs to draft clear, calm, non-alarmist human communication, and must never independently trigger a physical-world action.
  • A Report Agent needs to synthesize a trend, not just a single reading.
  • A Coordinator ties them together with explicit, auditable routing logic instead of one opaque mega-prompt deciding everything.

Splitting these concerns means each agent can be tested, replaced, or scaled independently — e.g. swapping in a stronger LLM just for report-writing without touching the perception/validation code path at all.

Architecture

flowchart LR
    subgraph Hardware["Field hardware (ESP32-S3 + OV2640 + dual JSN-SR04T)"]
        S[Sensor packet: coverage_camera + height_ratio_sensor]
    end

    S --> P[Perception Agent\nvalidate + fuse + classify]
    P -->|severity=normal/watch| C[Coordinator Agent\nADK-style orchestrator]
    P -->|severity=alert| C

    C -->|route: alert| A[Alert Agent\nloads river-report-skill\nrate-limited + human-in-the-loop]
    C -->|route: periodic| R[Report Agent\nloads river-report-skill\nsynthesizes trend]

    A --> H{{Human operator\nconfirms physical action}}
    R --> O[Plain-language summary]

    C -.exposed via.-> M[MCP Server\nget_latest_reading\nget_detection_log\nget_river_health_summary\nrequest_action]
    M -.queried by.-> Ext[Any MCP client:\nAntigravity / Claude / Gemini CLI / dashboard]
Loading

Repository layout

swara-agent-capstone/
├── main.py                        # CLI demo: streams sample data through the agents
├── agents/
│   ├── store.py                   # shared in-memory state (readings/alerts/reports)
│   ├── llm_client.py               # Gemini wrapper w/ offline-safe fallback
│   ├── perception_agent.py         # validates + classifies sensor packets
│   ├── alert_agent.py              # drafts alerts, rate-limited, human-in-the-loop
│   ├── report_agent.py             # synthesizes periodic plain-language reports
│   └── coordinator.py              # ADK-style orchestrator / routing logic
├── mcp_server/
│   └── server.py                   # exposes the system as MCP tools
├── skills/
│   └── river-report-skill/
│       └── SKILL.md                # progressive-disclosure drafting style guide
├── security/
│   └── guardrails.py               # input validation, rate limiting, human approval gate
├── data/
│   └── sample_sensor_stream.json   # synthetic demo data (30 readings, 2 locations)
├── requirements.txt
└── .env.example

Key course concepts demonstrated

Concept (rubric) Where
Multi-agent system (ADK-style) agents/coordinator.py orchestrates perception_agent.py, alert_agent.py, report_agent.py as independent specialists
MCP Server mcp_server/server.py — exposes get_latest_reading, get_detection_log, get_river_health_summary, request_action as MCP tools
Agent skills skills/river-report-skill/SKILL.md, loaded on-demand (progressive disclosure) only when drafting an alert or report
Security features security/guardrails.py — input validation against malformed/spoofed sensor packets, alert rate-limiting, mandatory human-in-the-loop approval before any physical-world action
Deployability Stateless agent modules + MCP server designed to run as separate Cloud Run services in production (see "Deploying" below)

Running it

Quick demo (no API key needed)

pip install -r requirements.txt
python main.py

This streams 30 synthetic sensor readings through the full agent pipeline and prints every agent's reasoning and decisions to the console, ending with a health summary. It runs in offline mode by default (template-based drafting) so it works immediately with zero setup.

Running with real Gemini calls

cp .env.example .env
# edit .env and paste a free key from https://aistudio.google.com/app/apikey
export $(cat .env | xargs)
python main.py

Running the MCP server

python -m mcp_server.server

Then point any MCP-compatible client (Antigravity, Claude Desktop, Gemini CLI) at this script over stdio to query get_river_health_summary, get_detection_log, etc. directly.

Deploying (production path)

Each agent module is stateless and takes its dependencies (store, LLM client) as constructor arguments, so in production:

  1. mcp_server/server.py deploys as its own Cloud Run service (swap the in-memory Store for Firestore).
  2. coordinator.py runs as a Cloud Run job/service triggered by each new sensor packet arriving from the ESP32-S3 devices (e.g. via Pub/Sub).
  3. Alerts route to a real channel (WhatsApp Business API / Telegram) instead of stdout, but the pending_human_approval gate stays in place before any dispatch of a physical crew or (future) skimmer robot.

Real-world grounding

The sensor-fusion formula and hardware (OV2640 camera + dual JSN-SR04T ultrasonic sensors on an ESP32-S3, Score = α·Coverage_camera + (1−α)·Height_ratio_sensor) mirrors an actual river-garbage-monitoring hardware project (Swara, PKM-KI 2026) currently in development. This capstone builds the agentic decision and communication layer on top of that kind of sensor stream — the part that turns raw detections into something a human can actually act on.

License

Submission and source code licensed under CC-BY 4.0, per competition rules.

About

No description, website, or topics provided.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages