FastAPI is a modern Python web framework used to build high-performance RESTful APIs with minimal code. It provides automatic data validation, interactive API documentation, and excellent support for asynchronous programming. Because of its speed, simplicity and production-ready features, FastAPI has become one of the most frequently discussed frameworks in Python developer interviews.
1. What is FastAPI?
FastAPI is a modern, high-performance Python web framework for building APIs. It is built on Starlette for web handling and Pydantic for data validation.

Key features:
- Easy to learn and use.
- Supports asynchronous programming.
- Automatically validates request data.
- Generates interactive API documentation.
- Suitable for both small and enterprise-level applications.
2. Why is FastAPI becoming popular for API development?
FastAPI has gained popularity because it combines high performance with a simple development experience. Reasons for its popularity:
- Very fast due to ASGI and asynchronous support.
- Automatic request validation using Pydantic.
- Interactive API documentation with Swagger UI and ReDoc.
- Reduces boilerplate code.
- Provides Python type hints for better readability and IDE support.
3. What are the main features of FastAPI?
FastAPI provides several features that simplify API development. Some important features are:
- High performance comparable to Node.js and Go.
- Automatic request validation.
- Interactive API documentation.
- Dependency Injection support.
- Asynchronous programming using async and await.
- Built-in support for authentication and security.
- Easy integration with SQL and NoSQL databases.
4. How do you install FastAPI and run a FastAPI application?
FastAPI can be installed using pip, and the application is commonly run using Uvicorn, an ASGI server. Install FastAPI and Uvicorn using below command in cmd or terminal:
pip install fastapi uvicorn
from fastapi import FastAPI
app = FastAPI()
@app.get("/")
def home():
return {"message": "Hello, FastAPI!"}
Output
uvicorn main:app --reload

Here:
- main is the Python filename.
- app is the FastAPI application object.
- --reload automatically restarts the server whenever code changes.
5. Explain the structure of a basic FastAPI application.
A basic FastAPI application consists of a FastAPI instance and one or more path operation functions.
from fastapi import FastAPI
app = FastAPI()
@app.get("/")
def home():
return {"message": "Welcome"}
Structure explanation:
- Import the FastAPI class.
- Create an application instance.
- Define API endpoints using decorators like @app.get().
- Return Python objects such as dictionaries or lists, which FastAPI automatically converts to JSON.
6. What are path operations in FastAPI?
Path operations are functions that handle requests for specific URLs and HTTP methods. Each path operation consists of:
- A URL path.
- An HTTP method (GET, POST, PUT, DELETE, etc.).
- A Python function that processes the request.
Example: In this example, a GET request to /users executes the get_users() function.
from fastapi import FastAPI
app = FastAPI()
@app.get("/users")
def get_users():
return ["Alice", "John"]
7. What is the difference between Path Parameters and Query Parameters?
Both are used to send data to an API, but they serve different purposes.
Path Parameters
- Included as part of the URL.
- Usually identify a specific resource.
- Are required.
@app.get("/users/{id}")
def get_user(id: int):
return {"id": id}
Request:
/users/5
Query Parameters
- Passed after the ? symbol in the URL.
- Used for filtering, searching, sorting, or pagination.
- Usually optional.
@app.get("/users")
def get_users(page: int = 1):
return {"page": page}
Request:
/users?page=2
In general, use Path Parameters to identify resources and use Query Parameters to filter or customize the response.
8. How do you handle request bodies in FastAPI?
FastAPI uses Pydantic models to receive and validate request body data automatically.
from fastapi import FastAPI
from pydantic import BaseModel
app = FastAPI()
class Student(BaseModel):
name: str
age: int
@app.post("/students")
def create_student(student: Student):
return student
Request Body
{
"name": "Emma",
"age": 22
}
Response
{
"name": "Emma",
"age": 22
}
Using Pydantic ensures that:
- Incoming data is automatically validated.
- Invalid requests return meaningful error messages.
- The code remains clean and easy to maintain.
9. What is Pydantic and why is it used in FastAPI?
Pydantic is a Python library used for data validation and serialization. FastAPI uses Pydantic models to validate incoming request data based on Python type hints.
from pydantic import BaseModel
class User(BaseModel):
name: str
age: int
If an invalid data type is sent, FastAPI automatically returns a validation error.
Benefits of Pydantic:
- Automatic request validation.
- Clear error messages.
- Data conversion when possible.
- Cleaner and more maintainable code.
10. What are Response Models?
A Response Model defines the structure of data returned by an API. FastAPI validates and filters the response before sending it to the client.
from fastapi import FastAPI
from pydantic import BaseModel
app = FastAPI()
class User(BaseModel):
id: int
name: str
@app.get("/user", response_model=User)
def get_user():
return {"id": 1, "name": "Emma", "password": "secret"}
Response
{
"id": 1,
"name": "Emma"
}
Here, the password field is automatically excluded because it is not part of the response model.
Benefits:
- Ensures consistent API responses.
- Filters unnecessary fields.
- Improves API documentation.
- Increases security by hiding sensitive data.
11. How do you return custom HTTP status codes?
FastAPI allows custom HTTP status codes using the status_code parameter in path operation decorators.
from fastapi import FastAPI, status
app = FastAPI()
@app.post("/users", status_code=status.HTTP_201_CREATED)
def create_user():
return {"message": "User created"}
Response Status
201 Created
Common status codes include:
- 200: OK
- 201: Created
- 204: No Content
- 400: Bad Request
- 401: Unauthorized
- 404: Not Found
- 500: Internal Server Error
12. What is automatic API documentation in FastAPI?
FastAPI automatically generates interactive API documentation based on your routes, request models, and response models. Two documentation interfaces are available:
- Swagger UI -> /docs
- ReDoc -> /redoc
from fastapi import FastAPI
app = FastAPI()
@app.get("/")
def home():
return {"message": "Hello"}
Running the application automatically provides:
http://127.0.0.1:8000/docs
and
http://127.0.0.1:8000/redoc
Benefits:
- No manual documentation required.
- Interactive API testing.
- Automatically updated when endpoints change.
13. How do you validate request data in FastAPI?
FastAPI validates request data using Pydantic models and Python type hints. If invalid data is received, FastAPI automatically returns a validation error.
from pydantic import BaseModel
class Product(BaseModel):
name: str
price: float
If the client sends:
{
"name": "Laptop",
"price": "abc"
}
Response
{
"detail": [
{
"msg": "Input should be a valid number"
}
]
}
Advantages:
- Automatic validation.
- Detailed error messages.
- No need to write validation logic manually.
14. How do you organize routes in large FastAPI projects?
Large FastAPI applications organize routes into separate modules using APIRouter. This keeps the project modular and easier to maintain.
Example Project Structure:
app/
│── main.py
│── routers/
│ ├── users.py
│ ├── products.py
│ └── orders.py
from fastapi import APIRouter
router = APIRouter()
@router.get("/users")
def get_users():
return ["Emma", "John"]
Then include it in main.py:
app.include_router(router)
Benefits:
- Better code organization.
- Easier maintenance.
- Supports large applications with multiple modules.
15. What is the APIRouter class?
APIRouter is used to group related API routes together. It works similarly to Flask Blueprints or Django URL modules.
from fastapi import APIRouter
router = APIRouter(prefix="/users")
@router.get("/")
def get_users():
return ["Emma", "John"]
Register the router:
from fastapi import FastAPI
app = FastAPI()
app.include_router(router)
Now the endpoint becomes:
/users/
Benefits of APIRouter:
- Organizes related endpoints.
- Reduces code duplication.
- Supports route prefixes and tags.
- Makes large FastAPI applications easier to manage.
16. How do you handle file uploads in FastAPI?
FastAPI provides the UploadFile class to receive uploaded files efficiently. It is recommended over reading the entire file into memory because it supports streaming.
from fastapi import FastAPI, File, UploadFile
app = FastAPI()
@app.post("/upload")
async def upload_file(file: UploadFile = File(...)):
return {
"filename": file.filename,
"content_type": file.content_type
}
You can upload files using the interactive Swagger UI or any HTTP client.
Benefits of UploadFile:
- Efficient for large files.
- Provides file metadata.
- Supports asynchronous file operations.
17. How do you serve static files in FastAPI?
Static files such as CSS, JavaScript and images can be served using the StaticFiles class.
from fastapi import FastAPI
from fastapi.staticfiles import StaticFiles
app = FastAPI()
app.mount("/static", StaticFiles(directory="static"), name="static")
If the project contains:
static/
logo.png
It can be accessed at:
http://127.0.0.1:8000/static/logo.png
Common static files include:
- CSS files
- JavaScript files
- Images
- Fonts
18. How do you render HTML templates in FastAPI?
FastAPI uses Jinja2Templates to render dynamic HTML pages.
from fastapi import FastAPI, Request
from fastapi.templating import Jinja2Templates
app = FastAPI()
templates = Jinja2Templates(directory="templates")
@app.get("/")
def home(request: Request):
return templates.TemplateResponse(
"index.html",
{"request": request}
)
The HTML file should be placed inside the templates folder.
Benefits:
- Generates dynamic HTML pages.
- Passes data from Python to HTML.
- Commonly used for web applications built with FastAPI.
19. How do you handle form data in FastAPI?
Form data is handled using the Form class. It is commonly used for login forms and HTML form submissions.
from fastapi import FastAPI, Form
app = FastAPI()
@app.post("/login")
def login(
username: str = Form(...),
password: str = Form(...)
):
return {"username": username}
When submitting the form:
Username: Emma
Password: 12345
The API receives both values as form fields.
Common uses of form data:
- Login forms
- Registration forms
- Contact forms
20. What are tags in FastAPI?
Tags are used to group related endpoints in the automatically generated API documentation. They improve the organization and readability of large APIs.
from fastapi import FastAPI
app = FastAPI()
@app.get("/users", tags=["Users"])
def get_users():
return ["Emma", "John"]
In Swagger UI, this endpoint appears under the Users section.
Benefits of tags:
- Organize related endpoints.
- Improve API documentation.
- Make large APIs easier to navigate.
21. What are dependencies in FastAPI?
Dependencies are reusable functions or classes that provide common functionality to multiple API endpoints. They are typically used for authentication, database connections, configuration, and validation.
from fastapi import Depends, FastAPI
app = FastAPI()
def get_message():
return "Hello"
@app.get("/")
def home(message: str = Depends(get_message)):
return {"message": message}
Here, get_message() is automatically executed before the endpoint.
Common uses of dependencies:
- Authentication and authorization.
- Database sessions.
- Configuration settings.
- Shared validation logic.
22. Explain FastAPI's asynchronous programming model.
FastAPI supports asynchronous programming using Python's async and await keywords. This allows the server to handle multiple requests efficiently without blocking while waiting for slow operations such as database queries or API calls.
from fastapi import FastAPI
import asyncio
app = FastAPI()
@app.get("/")
async def home():
await asyncio.sleep(2)
return {"message": "Completed"}
In this example, the server can continue processing other requests while waiting for the two-second delay.
Benefits of asynchronous programming:
- Handles many concurrent requests efficiently.
- Improves application performance.
- Prevents blocking during I/O operations.
- Ideal for APIs that interact with databases, files, or external services.
23. What is Dependency Injection in FastAPI?
Dependency Injection (DI) is a design pattern where FastAPI automatically provides required objects or functions to an API endpoint instead of creating them manually. It helps make the code modular, reusable and easier to test.
from fastapi import FastAPI, Depends
app = FastAPI()
def get_message():
return "Hello FastAPI"
@app.get("/")
def home(message: str = Depends(get_message)):
return {"message": message}
Here, FastAPI automatically calls get_message() and injects its return value into the home() function.
Benefits:
- Promotes code reuse.
- Reduces code duplication.
- Simplifies testing.
- Makes applications easier to maintain.
24. What is the Depends() function?
Depends() is FastAPI's built-in mechanism for dependency injection. It tells FastAPI to execute another function before the endpoint and pass its result as an argument.
from fastapi import FastAPI, Depends
app = FastAPI()
def verify_user():
return {"username": "Emma"}
@app.get("/profile")
def profile(user = Depends(verify_user)):
return user
Here, verify_user() executes before profile().
Common uses of Depends():
- Authentication.
- Database sessions.
- Configuration.
- Shared validation logic.
25. How do you connect FastAPI to a SQL database?
FastAPI can connect to SQL databases using SQLAlchemy together with a database driver such as SQLite, PostgreSQL, or MySQL.
from sqlalchemy import create_engine
DATABASE_URL = "sqlite:///students.db"
engine = create_engine(DATABASE_URL)
The engine is then used to create database sessions and execute queries.
Common SQL databases used with FastAPI:
- SQLite
- PostgreSQL
- MySQL
- Microsoft SQL Server
26. How do you connect FastAPI with MongoDB?
FastAPI commonly connects to MongoDB using the PyMongo or Motor library. Motor is preferred for asynchronous applications.
from pymongo import MongoClient
client = MongoClient("mongodb://localhost:27017")
db = client["school"]
collection = db["students"]
You can then insert, update, retrieve, and delete documents from the collection.
Common MongoDB libraries:
- PyMongo (Synchronous)
- Motor (Asynchronous)
27. What ORM libraries are commonly used with FastAPI?
An ORM (Object Relational Mapper) allows developers to interact with databases using Python objects instead of writing raw SQL queries.
Popular ORM libraries include:
- SQLAlchemy
- SQLModel
- Tortoise ORM
- Peewee
from sqlalchemy.orm import Session
users = session.query(User).all()
Benefits of ORMs:
- Reduces SQL code.
- Improves readability.
- Simplifies database operations.
- Supports multiple database systems.
28. How do you perform CRUD operations in FastAPI?
CRUD stands for Create, Read, Update, and Delete, which are the basic operations performed on database records.
from fastapi import FastAPI
app = FastAPI()
students = []
@app.post("/students")
def create_student(student: dict):
students.append(student)
return student
@app.get("/students")
def get_students():
return students
In a real application, these operations are usually performed using a database and an ORM such as SQLAlchemy.
CRUD operations include:
- Create: Add new data.
- Read: Retrieve existing data.
- Update: Modify existing data.
- Delete: Remove data.
29. How do you implement authentication in FastAPI?
Authentication verifies the identity of a user before allowing access to protected resources. FastAPI commonly implements authentication using OAuth2 and JWT (JSON Web Tokens).
from fastapi.security import OAuth2PasswordBearer
oauth2_scheme = OAuth2PasswordBearer(tokenUrl="login")
After a user logs in successfully:
- A JWT token is generated.
- The client stores the token.
- The token is sent with future requests.
- FastAPI validates the token before granting access.
Common authentication methods:
- JWT Authentication
- OAuth2
- API Keys
- Session-based Authentication
30. What is OAuth2 in FastAPI?
OAuth2 is an industry-standard authentication framework that allows users to securely access protected APIs using access tokens instead of sending usernames and passwords with every request. FastAPI provides built-in support for OAuth2 through the fastapi.security module.
from fastapi.security import OAuth2PasswordBearer
oauth2_scheme = OAuth2PasswordBearer(tokenUrl="login")
Here, users first authenticate through the /login endpoint. After successful authentication, an access token is issued and included in future requests.
Benefits of OAuth2:
- Secure authentication.
- Token-based access.
- Reduces password exposure.
- Widely used in REST APIs and modern web applications.
31. How do JWT tokens work in FastAPI?
JWT (JSON Web Token) is a secure, token-based authentication mechanism. After a user successfully logs in, the server generates a token and sends it to the client. The client includes this token in future requests to access protected endpoints.
Authorization: Bearer <JWT_TOKEN>
FastAPI verifies the token before processing the request.
Benefits of JWT:
- Stateless authentication.
- Improves API security.
- Eliminates the need for server-side sessions.
- Widely used with REST APIs.
32. What is the difference between Authentication and Authorization?
Although both are related to security, they serve different purposes.
Authentication
- Verifies the identity of a user.
- Answers the question "Who are you?"
- Usually performed using usernames, passwords, or tokens.
Authorization
- Determines what an authenticated user is allowed to access.
- Answers the question "What are you allowed to do?"
- Usually based on user roles or permissions.
Example: A user logs in using a username and password (Authentication). After logging in, only administrators can access the admin dashboard (Authorization).
33. How do you hash passwords in FastAPI?
Passwords should never be stored as plain text. FastAPI applications commonly use the Passlib library with the bcrypt algorithm to securely hash passwords before storing them in the database.
from passlib.context import CryptContext
pwd_context = CryptContext(
schemes=["bcrypt"],
deprecated="auto"
)
hashed_password = pwd_context.hash("mypassword")
To verify a password:
pwd_context.verify("mypassword", hashed_password)
Benefits of password hashing:
- Protects user passwords.
- Prevents plain-text password storage.
- Improves application security.
34. What are Middleware in FastAPI?
Middleware is code that executes before and after every request and response. It is commonly used to process requests globally without modifying individual endpoints.
from fastapi import FastAPI, Request
app = FastAPI()
@app.middleware("http")
async def middleware(request: Request, call_next):
response = await call_next(request)
return response
Common uses of middleware:
- Logging requests.
- Authentication.
- CORS handling.
- Measuring request processing time.
- Adding custom headers.
35. How do you create a custom middleware?
A custom middleware is created using the @app.middleware("http") decorator. Inside the middleware, you can execute code before forwarding the request and after receiving the response.
import time
from fastapi import FastAPI, Request
app = FastAPI()
@app.middleware("http")
async def process_time(request: Request, call_next):
start = time.time()
response = await call_next(request)
response.headers["X-Process-Time"] = str(time.time() - start)
return response
Here, the middleware measures the request processing time and adds it to the response header.
Common uses:
- Logging.
- Performance monitoring.
- Request validation.
- Adding response headers.
36. How do you handle exceptions in FastAPI?
FastAPI handles exceptions by raising exception objects. When an exception occurs, FastAPI automatically returns an appropriate HTTP response instead of crashing the application.
from fastapi import FastAPI, HTTPException
app = FastAPI()
@app.get("/students/{id}")
def get_student(id: int):
if id != 1:
raise HTTPException(
status_code=404,
detail="Student not found"
)
return {"id": 1, "name": "Emma"}
If the student does not exist, FastAPI returns a 404 Not Found response.
Benefits of exception handling:
- Prevents application crashes.
- Returns meaningful error messages.
- Improves API reliability.
37. What is HTTPException?
HTTPException is FastAPI's built-in exception class used to return custom HTTP error responses. It allows you to specify both the HTTP status code and an error message.
from fastapi import HTTPException
raise HTTPException(
status_code=400,
detail="Invalid request"
)
Common status codes used with HTTPException:
- 400: Bad Request
- 401: Unauthorized
- 403: Forbidden
- 404: Not Found
- 500: Internal Server Error
Using HTTPException makes API error responses clear and consistent for clients.
38. How do you create custom exception handlers?
FastAPI allows you to define custom exception handlers to return consistent error responses for specific exception types across the application.
from fastapi import FastAPI, Request
from fastapi.responses import JSONResponse
app = FastAPI()
class InvalidAge(Exception):
pass
@app.exception_handler(InvalidAge)
async def invalid_age_handler(
request: Request,
exc: InvalidAge
):
return JSONResponse(
status_code=400,
content={"message": "Invalid age"}
)
If an InvalidAge exception is raised anywhere in the application, FastAPI automatically uses this handler.
Benefits:
- Centralized error handling.
- Consistent error responses.
- Cleaner endpoint code.
- Easier application maintenance.
39. How do you validate query parameters?
FastAPI validates query parameters using Python type hints and the Query class. You can specify validation rules such as minimum length, maximum length, default values, and numeric limits.
from fastapi import FastAPI, Query
app = FastAPI()
@app.get("/search")
def search(
keyword: str = Query(..., min_length=3)
):
return {"keyword": keyword}
If the query parameter does not satisfy the validation rules, FastAPI automatically returns a validation error.
Common validations include:
- Minimum and maximum length.
- Minimum and maximum values.
- Default values.
- Required parameters.
- Regular expression patterns.
40. What are Background Tasks?
Background Tasks allow FastAPI to execute tasks after sending the response to the client. This improves response time by moving non-critical work to the background.
from fastapi import FastAPI, BackgroundTasks
app = FastAPI()
def send_email():
print("Email Sent")
@app.post("/register")
def register(background_tasks: BackgroundTasks):
background_tasks.add_task(send_email)
return {"message": "User Registered"}
Here, the API immediately returns the response while the email is sent in the background.
Common uses:
- Sending emails.
- Writing log files.
- Processing reports.
- Sending notifications.
41. How do you upload multiple files?
FastAPI allows multiple file uploads by accepting a list of UploadFile objects.
from fastapi import FastAPI, UploadFile, File
app = FastAPI()
@app.post("/upload")
async def upload_files(
files: list[UploadFile] = File(...)
):
return {
"files": [file.filename for file in files]
}
The client can upload multiple files in a single request.
Benefits:
- Supports batch uploads.
- Efficient for handling large files.
- Provides metadata such as filename and content type.
42. How do you implement pagination in FastAPI?
Pagination limits the number of records returned in a single request. It improves performance and reduces the amount of data transferred. A common approach is to use the skip and limit query parameters.
from fastapi import FastAPI
app = FastAPI()
students = [
"Alice",
"Bob",
"Emma",
"John"
]
@app.get("/students")
def get_students(
skip: int = 0,
limit: int = 2
):
return students[skip: skip + limit]
Request:
/students?skip=0&limit=2
Response:
[
"Alice",
"Bob"
]
Benefits:
- Improves API performance.
- Reduces bandwidth usage.
- Makes APIs scalable for large datasets.
43. What are CORS and how do you enable them?
CORS (Cross-Origin Resource Sharing) is a browser security feature that controls whether a web application can access resources hosted on another domain. FastAPI enables CORS using the CORSMiddleware.
from fastapi import FastAPI
from fastapi.middleware.cors import CORSMiddleware
app = FastAPI()
app.add_middleware(
CORSMiddleware,
allow_origins=["*"],
allow_methods=["*"],
allow_headers=["*"],
)
Common CORS settings:
- allow_origins: Allowed websites.
- allow_methods: Allowed HTTP methods.
- allow_headers: Allowed request headers.
- allow_credentials: Allows cookies and authentication.
44. How do you configure environment variables in FastAPI?
Environment variables store configuration values such as database URLs, API keys, and secret keys outside the source code. FastAPI commonly uses python-dotenv together with a .env file to manage these settings.
Example: .env
DATABASE_URL=sqlite:///students.db
SECRET_KEY=mysecretkey
from dotenv import load_dotenv
import os
load_dotenv()
database_url = os.getenv("DATABASE_URL")
Benefits of environment variables:
- Keeps sensitive information out of the source code.
- Makes applications easier to configure across environments.
- Simplifies deployment and maintenance.
- Improves application security.
45. How does async/await improve FastAPI performance?
FastAPI uses Python's async and await keywords to perform non-blocking operations. While one request is waiting for an operation such as a database query or API call to complete, the server can process other incoming requests.
from fastapi import FastAPI
import asyncio
app = FastAPI()
@app.get("/")
async def home():
await asyncio.sleep(2)
return {"message": "Completed"}
Here, the server can continue handling other requests during the two-second wait.
Benefits:
- Handles many concurrent requests efficiently.
- Improves application responsiveness.
- Reduces idle waiting time.
- Ideal for I/O-bound operations.
46. What is the difference between synchronous and asynchronous endpoints?
FastAPI supports both synchronous (def) and asynchronous (async def) endpoints, depending on the type of work being performed.
Synchronous Endpoint
- Declared using def.
- Executes one request at a time.
- Suitable for CPU-intensive operations or libraries that do not support async.
@app.get("/sync")
def sync_endpoint():
return {"message": "Sync Endpoint"}
Asynchronous Endpoint
- Declared using async def.
- Supports non-blocking execution.
- Suitable for database queries, API calls, and file operations.
@app.get("/async")
async def async_endpoint():
return {"message": "Async Endpoint"}
In general, use async endpoints when working with asynchronous libraries and I/O operations, and use synchronous endpoints for simple or CPU-bound tasks.
47. What are WebSockets in FastAPI?
WebSockets provide full-duplex communication between the client and the server. Unlike HTTP, the connection remains open, allowing both sides to send and receive data in real time.
Common uses of WebSockets:
- Chat applications.
- Live notifications.
- Online gaming.
- Real-time dashboards.
- Stock market updates.
FastAPI provides built-in support for WebSocket communication through the WebSocket class.
48. How do you implement WebSocket communication?
A WebSocket endpoint is created using the @app.websocket() decorator. After accepting the connection, the server can continuously exchange messages with the client.
from fastapi import FastAPI, WebSocket
app = FastAPI()
@app.websocket("/ws")
async def websocket_endpoint(websocket: WebSocket):
await websocket.accept()
while True:
message = await websocket.receive_text()
await websocket.send_text(f"Received: {message}")
In this example, the server echoes every message received from the client.
Benefits:
- Real-time communication.
- Persistent connection.
- Lower latency than repeated HTTP requests.
49. How do you test FastAPI applications?
FastAPI applications are commonly tested using pytest together with FastAPI's built-in TestClient. This allows API endpoints to be tested without starting a real server.
from fastapi.testclient import TestClient
client = TestClient(app)
def test_home():
response = client.get("/")
assert response.status_code == 200
Common tests include:
- Status code validation.
- Response data validation.
- Authentication tests.
- Error handling tests.
- Database operation tests.
50. What is TestClient in FastAPI?
TestClient is a utility provided by FastAPI for testing API endpoints. It simulates HTTP requests directly within the application, making testing simple and efficient.
from fastapi.testclient import TestClient
client = TestClient(app)
response = client.get("/")
print(response.status_code)
print(response.json())
Benefits of TestClient:
- No need to run a live server.
- Supports GET, POST, PUT, DELETE, and other HTTP methods.
- Makes automated testing easy.
- Integrates well with pytest.
51. How do you mock dependencies during testing?
FastAPI allows dependencies to be replaced with mock implementations during testing using app.dependency_overrides. This helps isolate the code being tested without connecting to real databases or external services.
from fastapi.testclient import TestClient
def fake_user():
return {"username": "TestUser"}
app.dependency_overrides[get_current_user] = fake_user
client = TestClient(app)
Here, fake_user() replaces the original dependency during testing.
Benefits of mocking dependencies:
- Tests run faster.
- Avoids using real databases or APIs.
- Makes tests more reliable.
- Simplifies unit testing.
52. How do you secure a FastAPI application?
Securing a FastAPI application involves protecting APIs from unauthorized access and common security threats. FastAPI provides several built-in features that help implement secure APIs.
Common security measures include:
- Using JWT or OAuth2 for authentication.
- Hashing passwords before storing them.
- Enabling HTTPS.
- Validating all user input.
- Restricting CORS origins.
- Protecting sensitive data using environment variables.
Implementing these practices helps prevent unauthorized access and improves application security.
53. What are common security best practices in FastAPI?
Following security best practices helps build secure and reliable FastAPI applications.
Common best practices include:
- Use HTTPS for all communication.
- Store passwords using strong hashing algorithms such as bcrypt.
- Store API keys and secrets in environment variables.
- Validate all user input using Pydantic.
- Implement authentication and authorization.
- Restrict CORS to trusted domains.
- Keep dependencies updated.
- Return only necessary information in API responses.
Following these practices reduces security vulnerabilities and protects application data.
54. How do you implement rate limiting in FastAPI?
Rate limiting restricts the number of requests a client can make within a specific time period. It helps prevent abuse, brute-force attacks, and denial-of-service (DoS) attacks. FastAPI commonly implements rate limiting using third-party libraries such as SlowAPI.
from slowapi import Limiter
from slowapi.util import get_remote_address
limiter = Limiter(key_func=get_remote_address)
An endpoint can then be limited as follows:
@limiter.limit("5/minute")
This example allows a client to make only 5 requests per minute.
Benefits:
- Prevents API abuse.
- Reduces server load.
- Improves application security.
- Protects against brute-force attacks.
55. How do you optimize FastAPI performance?
FastAPI is already highly performant, but additional optimizations can further improve response times and scalability.
Common optimization techniques include:
- Use async endpoints for I/O-bound tasks.
- Optimize database queries.
- Cache frequently requested data.
- Use pagination for large datasets.
- Minimize unnecessary middleware.
- Use connection pooling for databases.
- Compress responses when appropriate.
These techniques help improve throughput and reduce response times.
56. How do you deploy a FastAPI application?
A FastAPI application is commonly deployed using an ASGI server such as Uvicorn or Gunicorn with Uvicorn workers. It can be hosted on cloud platforms or virtual servers.
Example:
uvicorn main:app --host 0.0.0.0 --port 8000
Common deployment platforms:
- Render
- Railway
- AWS
- Azure
- Google Cloud
- DigitalOcean
For production deployments, applications are often placed behind a reverse proxy such as Nginx.
57. How do you deploy FastAPI on Render?
Render is a cloud platform that supports direct deployment of FastAPI applications from a Git repository.
Basic deployment steps:
- Push the FastAPI project to GitHub.
- Create a new Web Service on Render.
- Connect the GitHub repository.
- Set the build command:
pip install -r requirements.txt
- Set the start command:
uvicorn main:app --host 0.0.0.0 --port $PORT
- Deploy the application.
Render automatically builds, deploys, and hosts the FastAPI application.
58. What ASGI server is commonly used with FastAPI and why?
Uvicorn is the most commonly used ASGI server for FastAPI because it is lightweight, fast, and fully supports asynchronous programming.
Example:
uvicorn main:app --reload
Why Uvicorn is commonly used:
- High performance.
- Supports asynchronous requests.
- Easy to configure.
- Fast startup time.
- Recommended by the FastAPI documentation.
For production environments, Uvicorn is often combined with Gunicorn to handle multiple worker processes.
59. What is the difference between ASGI and WSGI?
Both ASGI and WSGI are specifications that define how Python web applications communicate with web servers, but they are designed for different use cases.
WSGI
- Supports only synchronous applications.
- Processes one request at a time.
- Suitable for traditional web frameworks like Flask and Django (without async support).
- Does not support WebSockets.
ASGI
- Supports both synchronous and asynchronous applications.
- Handles multiple concurrent requests efficiently.
- Supports WebSockets, background tasks and long-lived connections.
- Used by FastAPI and modern asynchronous frameworks.
In general, ASGI is preferred for modern, high-performance applications that require asynchronous features.
60. How do you structure a production-ready FastAPI project?
A production-ready FastAPI project is typically organized into separate modules so that the code is easier to maintain, test, and scale.
A common project structure is:
app/
│── main.py
│── routers/
│── models/
│── schemas/
│── database/
│── services/
│── dependencies/
│── middleware/
│── utils/
│── config/
│── tests/
Benefits of this structure:
- Better separation of concerns.
- Easier code maintenance.
- Improved scalability.
- Simplifies testing and debugging.
61. How do you manage database sessions efficiently in FastAPI?
Database sessions are typically managed using Dependency Injection. A new session is created for each request and automatically closed after the request is completed.
from database import SessionLocal
def get_db():
db = SessionLocal()
try:
yield db
finally:
db.close()
The dependency is then used in an endpoint:
@app.get("/students")
def get_students(db = Depends(get_db)):
...
Benefits:
- Prevents database connection leaks.
- Automatically cleans up resources.
- Improves application reliability.
62. What are lifespan events in FastAPI?
Lifespan events allow you to execute code when the application starts and shuts down. They are commonly used to initialize shared resources during startup and release them during shutdown.
from contextlib import asynccontextmanager
from fastapi import FastAPI
@asynccontextmanager
async def lifespan(app: FastAPI):
print("Application Started")
yield
print("Application Stopped")
app = FastAPI(lifespan=lifespan)
Common uses:
- Opening database connections.
- Loading machine learning models.
- Initializing caches.
- Releasing resources during shutdown.
63. What are common FastAPI performance bottlenecks?
Although FastAPI is highly optimized, poor application design can still reduce performance.
Common bottlenecks include:
- Slow database queries.
- Blocking operations inside async endpoints.
- Returning excessively large responses.
- Too many middleware components.
- Inefficient database session management.
- Excessive external API calls.
- Missing caching for frequently requested data.
Optimizing these areas helps improve response times and application scalability.
64. What are common FastAPI interview coding tasks?
Technical interviews often include practical FastAPI coding exercises to evaluate API development skills.
Common coding tasks include:
- Create CRUD APIs.
- Build authentication using JWT.
- Validate request data using Pydantic.
- Upload one or more files.
- Connect to SQL or MongoDB.
- Implement pagination and filtering.
- Create custom middleware.
- Handle exceptions properly.
- Build protected API endpoints.
- Write unit tests using TestClient.
These tasks assess both FastAPI fundamentals and real-world development skills.
65. Describe a challenging FastAPI issue you solved and how you approached it.
This is a behavioral interview question that evaluates your problem-solving approach and practical experience. A good answer should describe the problem, the steps taken to investigate it, and the final solution.
Example Answer:
"While developing a FastAPI application, I noticed that some endpoints were responding slowly. After investigating, I found that synchronous database operations were blocking asynchronous endpoints. I replaced the blocking operations with asynchronous database calls, optimized a few SQL queries, and added pagination for large responses. This significantly reduced response time and improved the application's overall performance."
When answering this question in an interview:
- Clearly describe the problem.
- Explain how you identified the root cause.
- Describe the solution you implemented.
- Mention the improvement or outcome achieved.
This demonstrates analytical thinking, debugging skills, and practical FastAPI experience.