Skip to main content
Glama
bensonaddo

FastAPI Todo MCP Server

by bensonaddo

Todo Manager — FastAPI + MCP

A full-stack todo list application built with FastAPI, SQLite, and fastapi-mcp. It provides a REST API for CRUD operations, an interactive web UI, auto-generated OpenAPI documentation, and MCP tool exposure for AI assistants (e.g. Cursor).

Live demo: https://fastapi-mcp-todo-ykjl.onrender.com


Table of Contents


Related MCP server: Todoist MCP Server

Features

  • REST API — Full CRUD for todo items with typed request/response schemas

  • Web frontend — Responsive grid UI with add, edit, complete, delete, and filter actions

  • SQLite persistence — Local file-based database (todos.db)

  • OpenAPI docs — Interactive Swagger UI and ReDoc generated automatically by FastAPI

  • MCP server — Exposes API operations as tools for AI clients via fastapi-mcp

  • Production-ready — Deployable to Render with a single render.yaml blueprint


Tech Stack

Layer

Technology

Backend

FastAPI, Uvicorn

ORM / DB

SQLAlchemy, SQLite

Validation

Pydantic v2

Frontend

HTML, CSS, vanilla JavaScript

AI Tools

fastapi-mcp, MCP

Deployment

Render (Python web service)


Project Structure

fastapi-mcp-todo/
├── main.py              # FastAPI app, routes, MCP mount
├── database.py          # SQLite engine, session, init
├── models.py            # SQLAlchemy Todo ORM model
├── schemas.py           # Pydantic request/response schemas
├── static/
│   ├── index.html       # Frontend shell
│   ├── css/style.css    # UI styles
│   └── js/app.js        # Client-side CRUD logic
├── requirements.txt     # Python dependencies
├── render.yaml          # Render deployment config
├── todos.db             # SQLite database (created at runtime, gitignored)
└── readme.md

Getting Started

Prerequisites

  • Python 3.9+

  • pip (or uv)

Installation

# Clone the repository and enter the project directory
cd fastapi-mcp-todo

# Create and activate a virtual environment
python -m venv .venv
source .venv/bin/activate        # macOS / Linux
# .venv\Scripts\activate         # Windows

# Install dependencies
pip install -r requirements.txt

Running the Application

Development (with auto-reload)

# Option A — FastAPI CLI
fastapi dev main.py

# Option B — Uvicorn directly
uvicorn main:app --reload

Production

uvicorn main:app --host 0.0.0.0 --port 8000

The app starts on http://127.0.0.1:8000 by default. The SQLite database and tables are created automatically on first startup.


Web UI

URL (local)

Description

http://127.0.0.1:8000/

Todo Manager web interface

http://127.0.0.1:8000/static/

Static assets (CSS, JS)

The frontend communicates with the /todos API and supports:

  • Adding todos (instant grid update)

  • Marking todos complete / incomplete

  • Editing todo content (modal)

  • Deleting todos (with confirmation)

  • Filtering by All / Active / Completed

  • Live stats (total, active, completed)


API Reference

Base URL (local): http://127.0.0.1:8000
Base URL (production): https://fastapi-mcp-todo-ykjl.onrender.com

All todo endpoints are tagged Todos in OpenAPI. Responses use application/json.

Endpoints Summary

Method

Path

Operation ID

Description

Success

GET

/todos

get_all_todos

List all todos

200

GET

/todos/{todo_id}

get_todo

Get one todo by ID

200

POST

/todos

create_todo

Create a new todo

201

PUT

/todos/{todo_id}

update_todo

Update a todo

200

DELETE

/todos/{todo_id}

delete_todo

Delete a todo

204


GET /todos — List all todos

Returns every todo ordered by todo_id.

Response 200

[
  {
    "todo_id": 1,
    "content": "Buy groceries",
    "completed": false
  },
  {
    "todo_id": 2,
    "content": "Schedule dentist appointment",
    "completed": true
  }
]

Example

curl http://127.0.0.1:8000/todos

GET /todos/{todo_id} — Get a single todo

Path parameters

Name

Type

Description

todo_id

integer

Unique todo ID

Response 200

{
  "todo_id": 1,
  "content": "Buy groceries",
  "completed": false
}

Response 404 — Todo not found

{
  "detail": "Todo with id 99 not found"
}

Example

curl http://127.0.0.1:8000/todos/1

POST /todos — Create a todo

Request body

{
  "content": "Finish reading chapter 5"
}

Field

Type

Required

Description

content

string

yes

Task description (min length: 1)

completed defaults to false and cannot be set on create.

Response 201

{
  "todo_id": 3,
  "content": "Finish reading chapter 5",
  "completed": false
}

Example

curl -X POST http://127.0.0.1:8000/todos \
  -H "Content-Type: application/json" \
  -d '{"content": "Finish reading chapter 5"}'

PUT /todos/{todo_id} — Update a todo

Partial updates are supported — include only the fields you want to change.

Request body (all fields optional)

{
  "content": "Updated task text",
  "completed": true
}

Field

Type

Required

Description

content

string

no

Updated description

completed

boolean

no

Updated completion state

Response 200

{
  "todo_id": 1,
  "content": "Updated task text",
  "completed": true
}

Response 404 — Todo not found

Example

curl -X PUT http://127.0.0.1:8000/todos/1 \
  -H "Content-Type: application/json" \
  -d '{"completed": true}'

DELETE /todos/{todo_id} — Delete a todo

Response 204 — No content (success)

Response 404 — Todo not found

Example

curl -X DELETE http://127.0.0.1:8000/todos/1

OpenAPI / Swagger Documentation

FastAPI auto-generates interactive API documentation from route decorators, type hints, and Pydantic schemas.

Local

Production

Use Swagger UI (/docs) to explore endpoints, view schemas, and send test requests directly from the browser.


Data Models

Todo (database)

Column

Type

Constraints

todo_id

integer

Primary key, auto-increment

content

string

Not null

completed

boolean

Not null, default false

Pydantic schemas

Schema

Purpose

TodoCreate

Request body for POST /todos

TodoUpdate

Request body for PUT /todos/{todo_id}

TodoResponse

Response body for all todo read/write ops


MCP Integration

This app exposes selected API operations as MCP tools using fastapi-mcp, allowing AI assistants to manage todos programmatically.

Exposed tools

MCP Tool

Maps to API endpoint

get_all_todos

GET /todos

get_todo

GET /todos/{todo_id}

create_todo

POST /todos

update_todo

PUT /todos/{todo_id}

delete_todo

DELETE /todos/{todo_id}

Tools are registered via operation_id on each route and mounted at /mcp.

Setup in main.py

from fastapi_mcp import FastApiMCP

mcp = FastApiMCP(
    app,
    include_operations=[
        "get_all_todos",
        "get_todo",
        "create_todo",
        "update_todo",
        "delete_todo",
    ],
)
mcp.mount()

Connect from Cursor

  1. Open Cursor Settings → Tools & MCP → Add MCP Server

  2. Add the following to your MCP configuration:

{
  "fastapi-mcp-todo": {
    "url": "http://127.0.0.1:8000/mcp"
  }
}

For the deployed app, replace the URL with:

{
  "fastapi-mcp-todo": {
    "url": "https://fastapi-mcp-todo-ykjl.onrender.com/mcp"
  }
}
  1. Restart Cursor if needed, then use natural language prompts such as:

    • "List all todos"

    • "Add a todo to call mum today"

    • "Mark todo 2 as completed"


Deployment

The project includes a Render blueprint (render.yaml):

services:
  - type: web
    name: fastapi-mcp-todo
    env: python
    buildCommand: uv pip install -r requirements.txt
    startCommand: uvicorn main:app --host 0.0.0.0 --port 8000
    plan: free

Note: On Render's free tier, the filesystem is ephemeral. SQLite data may reset on redeploy or spin-down. For persistent production storage, consider an external database (e.g. PostgreSQL).


External Resources


License

This project is for learning and demonstration purposes.

F
license - not found
-
quality - not tested
B
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/bensonaddo/fastapi-mcp-todo'

If you have feedback or need assistance with the MCP directory API, please join our Discord server