Hello! Welcome back to your course on becoming a Full Stack AI Developer.
In our previous lesson, we covered the theoretical foundations of RESTful APIs, including resources, HTTP verbs, and status codes. You learned why APIs are designed this way. Now, it's time to put that theory into practice.
Today's learning outcome is to build a RESTful API supporting CRUD operations using Flask-RESTful. This is a critical skill. When you build an AI model, you'll need an API to make its predictions available to other applications, like a web front-end or a mobile app. This lesson is your first major step in learning how to do that.

We'll be using Flask-RESTful, an extension for Flask that simplifies API development by providing tools that align perfectly with the REST principles we discussed.
1. Project Setup and Database Model
Before we can manage data through an API, we need a place to store that data. We will use Flask-SQLAlchemy to set up a simple SQLite database and define a data model for our "users" resource. We will then set up our basic Flask application and initialize the Flask-RESTful extension.
A well-structured API starts with a clear plan. The diagram below shows the high-level design of the kind of application we are building. An API client (like a browser or testing tool) will send HTTP requests to our Flask backend, which will then use SQLAlchemy to interact with a database.

To get started with the practical setup, we'll watch a video that guides us through the initial steps.
Python REST API Tutorial for Beginners | How to Build a Flask REST API
This video by Dave Gray provides a clear, step-by-step guide to setting up a Flask project for a REST API. We'll start by setting up the environment and creating our database model.
Watch the video from the beginning until 10:01 to understand the project setup. Then, watch from 12:33 to 17:02 to see how the database model is defined and the database is created. Pay close attention to: Creating a virtual environment and installing Flask, Flask-RESTful, and Flask-SQLAlchemy. Setting up the basic app.py file. Defining the UserModel class using db.Model. Creating the database using a separate script.
To summarize the key code from the video, your initial api.py (or app.py) file will look something like this:
# api.py
from flask import Flask
from flask_restful import Api
from flask_sqlalchemy import SQLAlchemy
app = Flask(__name__)
api = Api(app)
# Configure the SQLite database
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///database.db'
db = SQLAlchemy(app)
# Define the User model
class UserModel(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(80), unique=True, nullable=False)
email = db.Column(db.String(80), unique=True, nullable=False)
def __repr__(self):
return f"<User {self.name}>"
# This block is important for creating the database tables
# It should be run once. After the first run, you can comment it out.
# with app.app_context():
# db.create_all()
if __name__ == '__main__':
app.run(debug=True)
Note: The video uses a separate create_db.py script. An alternative, shown above, is to use with app.app_context(): db.create_all() directly in your main file. Both achieve the same result: creating the database.db file based on your models.
2. Building Resources for CRUD Operations
In Flask-RESTful, the core building blocks are Resources. A resource is a Python class that maps to one or more API endpoints and contains methods for each supported HTTP verb (get, post, put, etc.).
We will build two types of resources for our users entity:
- A collection resource (
Users): To handle requests on the collection of all users (e.g.,GET /api/usersto list all users,POST /api/usersto create a new user). - An individual resource (
User): To handle requests for a single, specific user (e.g.,GET /api/users/1to get user 1,PATCH /api/users/1to update them).
Implementing GET (All) and POST (Create)
Let's start with the collection resource. We'll implement the GET method to read all users and the POST method to create a new user.
To do this effectively, we'll use two powerful features of Flask-RESTful:
reqparse: To parse and validate incoming request data (for ourPOSTmethod).marshal_with: A decorator to format and serialize the data we send back in our response.
Python REST API Tutorial for Beginners | How to Build a Flask REST API
Continuing with the same video, let's see how to implement our first resource to handle GET and POST requests.
Watch the video from 19:56 to 26:22. This segment covers: Creating the Users resource class. Implementing the get method to retrieve all users. Defining the user_fields for serialization with @marshal_with. Setting up reqparse (called user_args) for input validation. Implementing the post method to create a new user and add it to the database.
After following the video, your api.py will be expanded with the resource for handling the collection of users:
# ... (imports and app setup from before) ...
from flask_restful import Resource, reqparse, fields, marshal_with
# ... (db and UserModel definition) ...
# Define the structure of the data to be rendered as JSON
user_fields = {
'id': fields.Integer,
'name': fields.String,
'email': fields.String
}
# Setup the request parser for POST requests
parser = reqparse.RequestParser()
parser.add_argument('name', type=str, required=True, help='Name cannot be blank!')
parser.add_argument('email', type=str, required=True, help='Email cannot be blank!')
# Resource for a collection of users (GET all, POST new)
class UserListResource(Resource):
@marshal_with(user_fields)
def get(self):
users = UserModel.query.all()
return users, 200
@marshal_with(user_fields)
def post(self):
args = parser.parse_args()
user = UserModel(name=args['name'], email=args['email'])
db.session.add(user)
db.session.commit()
# The created user object is returned and marshalled
return user, 201
# Add the resource to the API at the '/api/users' endpoint
api.add_resource(UserListResource, '/api/users')
At this point, you have functional GET and POST endpoints. You can test them using a tool like Postman or the Thunder Client extension for VS Code, as demonstrated in the next part of the video (26:22 to 30:29).
3. Implementing GET (One), Update, and Delete
Now let's create the second resource to manage individual users. This resource will handle endpoints that include a user's ID in the URL, like /api/users/1.
We will implement:
GET /api/users/<id>: To retrieve a single user.PATCH /api/users/<id>: To update a user's details.PATCHis used for partial updates, whilePUTis typically for a full replacement.DELETE /api/users/<id>: To remove a user.
Python REST API Tutorial for Beginners | How to Build a Flask REST API
Let's complete our CRUD functionality by building the resource for individual user operations.
Watch the video from 30:29 to 38:48. This final practical part demonstrates: Creating a new User resource class for single items. Passing the user_id from the URL to the resource methods. Implementing the get, patch, and delete methods. Using abort to handle cases where a user is not found (404 error). Testing the new PATCH and DELETE endpoints.
By adding this final piece, your API becomes fully-featured for user management. Here's the code for the individual user resource:
# ... (at the end of your api.py file) ...
# Setup a separate parser for PATCH requests, where fields are not required
update_parser = reqparse.RequestParser()
update_parser.add_argument('name', type=str, help='Name to update')
update_parser.add_argument('email', type=str, help='Email to update')
# Resource for a single user (GET one, PATCH, DELETE)
class UserResource(Resource):
@marshal_with(user_fields)
def get(self, user_id):
user = UserModel.query.get_or_404(user_id)
return user, 200
@marshal_with(user_fields)
def patch(self, user_id):
user = UserModel.query.get_or_404(user_id)
args = update_parser.parse_args()
if args['name']:
user.name = args['name']
if args['email']:
user.email = args['email']
db.session.commit()
return user, 200
def delete(self, user_id):
user = UserModel.query.get_or_404(user_id)
db.session.delete(user)
db.session.commit()
return {'message': 'User deleted'}, 204 # 204 No Content
# Add the second resource to the API
# Note the URL now includes an integer parameter for the user_id
api.add_resource(UserResource, '/api/users/<int:user_id>')
A quick note: The video uses .query.filter_by(id=id).first() and then checks if the result is None before aborting. A convenient Flask-SQLAlchemy shortcut is query.get_or_404(id), which automatically finds the user by primary key or triggers a 404 Not Found response.
Conclusion
Congratulations! You have successfully built a complete RESTful API with full CRUD functionality using Flask-RESTful. You've gone from the theory of REST to a practical, working implementation.
Key Takeaways:
- Flask-RESTful provides a structured way to build APIs using Resource classes.
- It's common practice to have separate resources for handling collections (e.g.,
/users) and individual items (e.g.,/users/<id>). reqparseis a powerful tool for validating incoming request data, ensuring your API is robust.- The
@marshal_withdecorator simplifies output formatting, guaranteeing your API returns consistent, well-structured JSON responses. - HTTP verbs (
GET,POST,PATCH,DELETE) map directly to methods within your resource classes.
You now have a solid foundation for exposing services and data over the web. In our next lesson, we will build upon this API. We'll address a crucial real-world problem: security. You will learn how to configure CORS and implement JWT-based API authentication to protect your endpoints and control who can access them.