Creating Your Own URL Shortener using Python and FastAPI
Have you ever found yourself struggling to share long and complicated URLs with your friends or colleagues? Certainly, you are not alone.
Many people are looking for an efficient way to shorten links and make them more manageable. Luckily, with the help of Python and FastAPI, you can create your own URL shortener from scratch.
In this article, we will guide you through the process of setting up the environment, building the API, modeling an SQLite database, and optimizing the app. So, let’s get started!
Setting up the Environment
Creating the right environment for your project is crucial. First, you need to create a project folder structure that will allow you to organize all the files and resources in one place.
The primary keywords for your URL shortener project are URL shortener, Python, and FastAPI, so you can include them in the folder name to make it easier to identify. Next, you need to install the dependencies required for your project.
We recommend using FastAPI as the main tool for building the API, as well as uvicorn for running the development web server. You will also need the following dependencies: sqlalchemy for interacting with the database, python-dotenv for defining environment variables, and validators for validating URLs. Once you have installed the dependencies, create a virtual environment to ensure that your project is isolated from other Python installations on your computer.
Finally, define your environment variables. You can use a separate config.py file or an external .env file for this purpose.
It’s a good idea to include caching as one of your variables to improve performance.
Building the URL Shortener with FastAPI
Now it’s time to start building the actual URL shortener. FastAPI makes it easy to create a REST API with minimal code.
You can run the development web server with uvicorn and test the API in your browser or using an API client like Postman. One of the key components of your URL shortener is the database.
You can use SQLite, a lightweight database, and SQLAlchemy, an ORM tool, to interact with it. The ORM will map your Python classes to database tables and make it easier to perform CRUD actions (create, read, update, delete).
With FastAPI, you can also generate auto-generated API documentation to help you understand the endpoints and parameters. This will be useful when testing your API.
You can then start building the endpoints and defining the necessary parameters. Don’t forget to create the data models using Pydantic to validate data and ensure consistency.
Optimizing the App by Refactoring the Code
Optimizing your app is an ongoing process. Once you have built the basic functionality, you can start refactoring the code to make it more efficient and maintainable.
One way to do this is by using functions to encapsulate common code and make it reusable. You can also use FastAPI’s dependency injection to minimize the amount of code in your endpoints.
Another helpful technique is unit testing, which helps to catch errors before they occur and ensures that changes to the code don’t break existing functionality.
In conclusion, building a URL shortener using Python and FastAPI is a great learning experience that can teach you all the key components of building an API, including setting up the environment, modeling a database, and optimizing the app.
With these skills, you can tackle even more complex projects and create powerful APIs in no time. So, don’t be afraid to experiment and try new things!
Demo: Your Python URL Shortener
Now, it’s time to see everything in action and create a demo of your own Python URL shortener.
In this section, we will guide you through building an API to create and manage shortened URLs, and how to leverage FastAPI’s auto-generated documentation to test API endpoints.
Building an API to Create and Manage Shortened URLs
The first step in building your Python URL shortener is to create the API that will handle the shortening and management of URLs. We will use FastAPI to build the API since it is a modern and fast web framework that enables us to work with minimal setup and boilerplate code. The first endpoint that we’ll create is for shortening a URL.
We’ll receive the URL as a parameter, validate it using the validators library, and then insert it into the database. To create the endpoint, create a file named shortener.py within your project folder and add the following code:
from fastapi import FastAPI
from pydantic import BaseModel
from sqlalchemy import create_engine
from sqlalchemy.orm import declarative_base, sessionmaker
from validators import url
engine = create_engine('sqlite:///shortener.db')
SessionLocal = sessionmaker(bind=engine)
Base = declarative_base()
class URL(Base):
__tablename__ = 'urls'
id = Column(Integer, primary_key=True, index=True)
url = Column(String(2000), unique=True)
def __repr__(self):
return f'{self.url}'
Base.metadata.create_all(bind=engine)
class UrlRequest(BaseModel):
url: str
app = FastAPI()
@app.post('/shorten/')
async def create_short_url(url_request: UrlRequest):
if not url(url_request.url):
return {'message': 'Invalid URL'}
db = SessionLocal()
db_url = URL(url=url_request.url)
db.add(db_url)
db.commit()
db.refresh(db_url)
db.close()
return {'short_url': f'http://localhost:8000/{db_url.id}'}
In the code above, we defined the SQLAlchemy ORM model for our URL table with an ID and URL column. We also added code to handle the database session and bind it to our SQLite instance.
After that, we added the class UrlRequest to define the expected shape of the incoming JSON body data. Furthermore, we created the `create_short_url` function which is bound to the path “/shorten/” and listens to HTTP POST requests.
This function receives data in the `UrlRequest` schema, validates the URL, inserts it to the database, and returns a response with the shortened URL. Leveraging FastAPI’s Auto-generated Documentation to Test API Endpoints
FastAPI allows us to leverage its auto-generated documentation to test our API endpoints.
If you run your development server with the `uvicorn main:app –reload` command, you can access the automatically generated OpenAPI interactive documentation at http://localhost:8000/docs. Here you can navigate through the schema we just defined and test the API endpoints.
To try out our `/shorten/` endpoint, you can click on the POST method then click on Try it out and enter the URL you want to shorten. FastAPI’s documentation allows us to quickly test the endpoints we create, saving a lot of time and effort we’d spend on manual entry.
We recommend that you test every endpoint you create and update the documentation with the appropriate information.
Providing API Endpoints for Different HTTP Request Types
Now that you have an endpoint for shortening long URLs, it’s time to provide endpoints that allow users to retrieve and delete their shortened URLs. In FastAPI, you can use the HTTP request types GET and DELETE to provide these functionalities. The first endpoint you’ll create is for redirecting a short URL to a long URL.
The client will make a GET request to the shortened URL, and the server will look up the original URL in the database and redirect the client to it. To create the endpoint, add the following code to the `shortener.py` file:
@app.get('/{url_id}/')
async def redirect_to_url(url_id: int):
db = SessionLocal()
db_url = db.query(URL).filter(URL.id == url_id).first()
db.close()
if not db_url:
raise HTTPException(status_code=404, detail="URL not found")
return RedirectResponse(url=db_url.url)
In the code above, we defined a new route named `/{url_id}/` with an integer parameter that points to the short URL.
The server uses this ID to query the database for the corresponding long URL, and then redirects the client to it using the `RedirectResponse` class. The second endpoint that we will create is for deleting URLs. We’ll make a DELETE request to the shortened URL’s ID, and the server will remove the URL from the database.
To create the endpoint, add the following code to your `shortener.py` file:
@app.delete('/{url_id}/')
async def delete_url(url_id: int):
db = SessionLocal()
db_url = db.query(URL).filter(URL.id == url_id).first()
if not db_url:
raise HTTPException(status_code=404, detail="URL not found")
db.delete(db_url)
db.commit()
db.close()
return {'message': 'URL has been deleted'}
To use the endpoint, make sure you pass the URL ID as a parameter within the DELETE request. The function then handles the session to delete the selected URL from the database and returns a message notifying the user that the URL has been successfully deleted.
In conclusion, by leveraging the FastAPI framework, we have successfully built a Python URL shortener with API endpoints to create, retrieve, update, and delete URLs. FastAPI’s autogenerated documentation simplifies the testing process and clarifies the behavior of the API. HTTP request types and other FastAPI functionalities allowed us to extend the functionality of our URL shortener API.
We hope this article gives you enough knowledge and inspiration to build your first Python FastAPI project!
Prerequisites
Before you dive into building your Python URL shortener, there are a few concepts you should be familiar with to follow along with this tutorial. These concepts include:
- Object-Oriented Programming (OOP): FastAPI and SQLAlchemy make use of OOP, which involves organizing code into classes that hold properties and methods.
- Understanding OOP concepts will help you create models and interact with objects in the database.
- JSON: JSON is a lightweight data interchange format used to send data between clients and servers.
- FastAPI uses JSON for input and output data, so you must be comfortable with JSON data and its syntax.
- Type Checking: FastAPI uses Pydantic for validating data objects and ensuring that they are of the expected data type.
- It is essential to understand type checking to make sure your data validation is working correctly.
- HTTP requests: You will also need to be familiar with HTTP and its request types (GET, POST, PUT, DELETE) and status codes.
- FastAPI uses these request types to route traffic to the appropriate endpoint and return responses to clients.
Conclusion
In this tutorial, we have taken you through all the necessary steps to build a functioning URL shortener with FastAPI and SQLite. By setting up the environment, building the API using FastAPI and SQLAlchemy, and optimizing the code, you now have a Python-based URL shortening service that is ready to use.
FastAPI’s autogenerated documentation helps you to test endpoints easily and makes debugging simpler by clarifying API behavior. And with the help of HTTP request types, object-oriented programming, JSON, and type checking, you can build upon your URL shortener API’s functionality and make it more robust.
We hope that this tutorial has been valuable to you and has given you the basic knowledge needed to build APIs using FastAPI and SQLite. Remember, the potential to extend the functionality of an API is limitless.
We encourage you to experiment and add new features to your Python URL shortener, such as user authentication, custom URL entries, and analytics.
Thank you for taking the time to follow this tutorial, and we look forward to seeing what you create with FastAPI!
This tutorial article demonstrates how to build a Python-based URL shortener with FastAPI and SQLite.
Through step-by-step guidance, the article explains how to set up the environment, build the API, model the database, and optimize the code, ultimately enabling the reader to create a fully-functioning URL shortening service. Additionally, the article explains important concepts required for following the tutorial, such as object-oriented programming, JSON, type-checking, and HTTP requests.
The article concludes with suggestions for extending the functionality of the URL shortener API. Overall, with this tutorial, readers have the knowledge and resources needed to build APIs with FastAPI and SQLite and can apply this knowledge to develop powerful APIs that meet their unique needs.