Deploying a machine learning model with FastAPI plays a crucial role in facilitating effortless access for both users and applications. FastAPI, a modern Python web framework, streamlines the machine learning model deployment process, which is contributing to its growing popularity. This guide will guide you through the process of deploying a machine-learning model using FastAPI.
Prerequisites:
Before we get started, please make sure you meet the following requirements:
Python and pip are installed on your system.
A basic understanding of machine learning and Python.
In this tutorial, we will clone and setup a project from GitHub and create a FastAPI for that project.
Setting up the GitHub repository:
In this section, we'll walk through the process of cloning a repository that's dedicated to passport classification. This repository contains the necessary code and resources to determine whether an image is of a passport or not. The classification is achieved using machine learning techniques, and it's a valuable tool for various applications that require passport recognition.
By cloning this repository, you'll have access to the code and model needed to classify passport images. Simply provide an image as input, and the system will return a prediction, indicating whether the image depicts a passport.
Cloning the Repository:
Use the following command to clone the repository:
git clone https://github.com/MeharRamzan/passport-classification.git cd passport-classification
Installing Required Dependencies:
Install the necessary dependencies using the command below:
# create virtual envirnment python3 -m venv .env source .env/bin/activate # install requiremnets pip install -r requirements.txt
Downloading Model Weights:
Download the model weights by running the command:
gdown --id 1K5sWbItnEQosgVCFp2NcL57k8NqhTt0C --output passport_classifier.pth
Testing the Repository:
Execute the following command to verify whether the setup was successful or not.
python main.py sample_images/
What is FastAPI?
FastAPI is a modern web framework for building APIs with Python. It's characterized by its speed, automatic interactive documentation, and support for type hints. These features make it a compelling choice for developing web applications and APIs.
Endpoints and Methods
In the FastAPI world, endpoints are specific URLs that your API exposes, and methods define the type of operations you can perform on these endpoints. Let's explore these concepts in detail.
Endpoints
Endpoints are the URLs or paths that your API provides for accessing resources or performing actions. They play a pivotal role in defining the structure and functionality of your API. Each endpoint is associated with one or more HTTP methods, indicating what actions can be taken at that URL.
Methods
In FastAPI, methods refer to the HTTP verbs such as GET, POST, PUT, DELETE, etc. These methods define the type of operation you want to perform on a specific resource or endpoint.
The GET Method
The GET method is primarily used for retrieving data from the server. I mostly use this GET method at the root to notify me whenever I call the server whether it is up and running or not.
import uvicorn from fastapi import FastAPI APP = FastAPI() @APP.get("/") def read_root(): return {"message": "Server is up"} if __name__ == "__main__": uvicorn.run(APP, host="0.0.0.0", port=8000)
To test the endpoint using the
curl
command, you can use the following command in your terminal:curl -X GET http://localhost:8000/
You will receive this output
The POST Method
The POST method in FastAPI is used for sending data to the server to create or update a resource. It's a versatile HTTP method commonly used for various purposes, such as submitting forms, uploading files, and more.
In the context of our classification model, we can use the POST method to allow users to upload an image, which the model will then process and classify as a passport or not. Here's an example of how to create a POST endpoint that will accept an image from your local storage and return the image name:
from fastapi import FastAPI, UploadFile from PIL import Image #TODO: Import model APP = FastAPI() MODEL = None #TODO: Initialize the classification model # POST endpoint to upload and classify an image @APP.post("/classify") async def classify_image(file: UploadFile): # Read the uploaded image image = Image.open(file.file) #TODO: Classify the image using the initialized model return {"filename": file.filename}
Now let's integrate our classification model with FastAPI. Within the
model.classify
module, there is a class calledPassportClassifier
containing apredict
method. This method accepts an image as input and returns an output. You can find the code integration details in the README.md file.import uvicorn from fastapi import FastAPI, UploadFile from PIL import Image from model.classify import PassportClassifier APP = FastAPI() MODEL = PassportClassifier(model_path='passport_classifier.pth') # Endpoint for a POST request at "/classify" @APP.post("/classify") def classify_image(file: UploadFile): # Open the uploaded image image = Image.open(file.file) # Classify the image using the initialized model prediction = MODEL.classify(image) return {"results": prediction} if __name__ == "__main__": # Run the FastAPI app using Uvicorn uvicorn.run(APP, host="0.0.0.0", port=8000)
Here's the complete code, which combines both GET and POST methods. Additionally, I intend to utilize
@app.on_event('startup')
within this code. The@app.on_event('startup')
event, when used, allows us to execute specific tasks at the beginning of our FastAPI application's lifecycle. These tasks often include activities like connecting to databases, loading configuration settings, or initializing resources. This ensures that our application is properly configured and prepared before it starts handling incoming requests.import uvicorn from model.classify import PassportClassifier from PIL import Image from fastapi import FastAPI, UploadFile MODEL = None APP = FastAPI(title="Passport Classification") @APP.on_event('startup') def init_model(): global MODEL # Initialize the model when the app starts MODEL = PassportClassifier(model_path='passport_classifier.pth') # Endpoint for a GET request at the root ("/") @APP.get("/") def read_root(): return {"message": "Server is up"} # Endpoint for a POST request at "/classify" @APP.post("/classify") def classify_image(file: UploadFile): # Open the uploaded image image = Image.open(file.file) # Classify the image using the initialized model prediction = MODEL.classify(image) return {"results": prediction} if __name__ == "__main__": # Run the FastAPI app using Uvicorn uvicorn.run(APP, host="0.0.0.0", port=8000)
Execute the command below to launch your FastAPI:
python app.py
In your web browser, enter either localhost:8000/docs or http://{your_ip}:{port}/docs, This will display the SwaggerUI interface as follows.
You can easily test the API using either the SwaggerUI interface or a curl command. Below is the curl command you can use to test the API:
curl -X POST -F "file=@Image_path" http://localhost:8000/classify
Example :
curl -X POST -F "file=@sample_images/3423-0613f34b-bcee-4a06-b923-a56318f24185_12_17_2022_05_42_4912_17_2022_05_43_21.jpeg" http://localhost:8000/classify
By default, when you use a localhost address, you can only access your FastAPI application on your local system. If you want your application to be accessible from any host or system, you should use your global IP address and expose the port on your system.
In Ubuntu you can simply check your global ip using
curl -4
ifconfig.me
command on the terminal.
Conclusion :
In this tutorial, we have set up a GitHub repository for passport classification and created a FastAPI application for it. After reading this blog, you should be able to create your own FastAPI projects for different models and applications.
Happy coding :)