1-how-to-build-a-restful-api-with-fastapi-and-postgresql.html

How to Build a RESTful API with FastAPI and PostgreSQL

In the modern world of web development, APIs are the backbone of application functionality. Among various frameworks available for building APIs, FastAPI stands out due to its speed and ease of use. Coupling FastAPI with PostgreSQL, a powerful relational database, can yield a robust and scalable application. In this article, we’ll walk through the steps to create a RESTful API using FastAPI and PostgreSQL, complete with code examples, actionable insights, and troubleshooting tips.

What is FastAPI?

FastAPI is a modern, high-performance web framework for building APIs with Python 3.6+ based on standard Python type hints. It is designed for speed, efficiency, and simplicity, allowing developers to create APIs quickly while ensuring code quality.

Key Features of FastAPI:

  • Fast: As the name suggests, it is one of the fastest Python frameworks available.
  • Easy to Use: The intuitive design helps developers get started quickly.
  • Automatic Documentation: FastAPI generates interactive API documentation using Swagger UI and ReDoc.
  • Type Validation: It automatically validates request and response data based on Python type hints.

What is PostgreSQL?

PostgreSQL is an advanced, open-source relational database management system known for its robustness, extensibility, and support for complex queries. It is an ideal choice for applications requiring complex data relationships and transactions.

Benefits of Using PostgreSQL:

  • ACID Compliance: Ensures reliable transactions.
  • Rich Data Types: Supports JSON, XML, and more.
  • Scalability: Handles large volumes of data without performance loss.

Setting Up Your Environment

Before diving into the coding, let's set up the environment. You’ll need:

  1. Python 3.6+: Ensure you have Python installed on your machine.
  2. PostgreSQL: Install PostgreSQL and set up a new database.
  3. FastAPI: Install FastAPI and a server (like uvicorn).
  4. SQLAlchemy: For database interactions.

You can set up your environment using pip:

pip install fastapi uvicorn sqlalchemy psycopg2

Creating a RESTful API

Step 1: Setting Up the Database

First, let's create a PostgreSQL database. You can use the following SQL commands to create a database and a sample table.

CREATE DATABASE fastapi_db;

\c fastapi_db

CREATE TABLE items (
    id SERIAL PRIMARY KEY,
    name VARCHAR(100) NOT NULL,
    description TEXT,
    price NUMERIC(10, 2) NOT NULL
);

Step 2: Setting Up FastAPI

Create a new Python file, say main.py, and set up the basic FastAPI application.

from fastapi import FastAPI
from sqlalchemy import create_engine, Column, Integer, String, Numeric
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import sessionmaker

DATABASE_URL = "postgresql://user:password@localhost/fastapi_db"
engine = create_engine(DATABASE_URL)
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
Base = declarative_base()

app = FastAPI()

Step 3: Defining the Model

Define the data model using SQLAlchemy. This represents the structure of your database items.

class Item(Base):
    __tablename__ = "items"

    id = Column(Integer, primary_key=True, index=True)
    name = Column(String, index=True)
    description = Column(String)
    price = Column(Numeric)

Step 4: Creating CRUD Operations

Next, implement the Create, Read, Update, and Delete (CRUD) operations. This will allow you to interact with the database.

from fastapi import Depends, HTTPException
from sqlalchemy.orm import Session

Base.metadata.create_all(bind=engine)

# Dependency
def get_db():
    db = SessionLocal()
    try:
        yield db
    finally:
        db.close()

# Create an item
@app.post("/items/", response_model=Item)
def create_item(item: Item, db: Session = Depends(get_db)):
    db.add(item)
    db.commit()
    db.refresh(item)
    return item

# Read all items
@app.get("/items/", response_model=list[Item])
def read_items(skip: int = 0, limit: int = 10, db: Session = Depends(get_db)):
    items = db.query(Item).offset(skip).limit(limit).all()
    return items

# Update an item
@app.put("/items/{item_id}", response_model=Item)
def update_item(item_id: int, item: Item, db: Session = Depends(get_db)):
    db_item = db.query(Item).filter(Item.id == item_id).first()
    if not db_item:
        raise HTTPException(status_code=404, detail="Item not found")
    db_item.name = item.name
    db_item.description = item.description
    db_item.price = item.price
    db.commit()
    db.refresh(db_item)
    return db_item

# Delete an item
@app.delete("/items/{item_id}")
def delete_item(item_id: int, db: Session = Depends(get_db)):
    db_item = db.query(Item).filter(Item.id == item_id).first()
    if not db_item:
        raise HTTPException(status_code=404, detail="Item not found")
    db.delete(db_item)
    db.commit()
    return {"detail": "Item deleted"}

Step 5: Running Your API

To run your FastAPI application, use the command:

uvicorn main:app --reload

You can now access the interactive API documentation at http://localhost:8000/docs.

Troubleshooting Common Issues

  • Database Connection Problems: Ensure your DATABASE_URL is correctly formatted and your PostgreSQL server is running.
  • Dependency Errors: Make sure all required packages are installed correctly.
  • 404 Errors: Check your endpoint paths and HTTP methods (GET, POST, etc.).

Conclusion

Building a RESTful API with FastAPI and PostgreSQL is not only efficient but also enjoyable thanks to FastAPI's user-friendly design. By following this guide, you can create a fully functional API capable of handling various data operations. With its automatic validation and interactive documentation, FastAPI makes API development straightforward and efficient. Start experimenting with more complex use cases and enhance your API's functionality to meet your application needs!

SR
Syed
Rizwan

About the Author

Syed Rizwan is a Machine Learning Engineer with 5 years of experience in AI, IoT, and Industrial Automation.