Starlette 1.0.0rc1: The First Release Candidate in 8 Years
The Problem
I saw the announcement: Starlette 1.0.0rc1 is out. The first release candidate in almost 8 years. My first thought wasn’t “what’s new” — it was “what breaks?”
With 10 million daily downloads on PyPI and being the foundation for FastAPI, this isn’t just another minor update. A breaking change here ripples through the entire Python async ecosystem.
So I installed it in a test environment:
pip install starlette==1.0.0rc1Then I ran my test suite. I got errors. Not many, but enough that I needed to understand what actually changed.
What I Found
After digging through the release notes and testing against a real FastAPI application, I found the breaking changes are minimal — if you’ve been keeping up with deprecation warnings. But if you’re on an older Starlette version or you’ve ignored deprecation warnings, you’re in for some work.
Here’s what I learned.
Breaking Change #1: Python 3.9+ Required
The first thing I hit was a version error. I tried running a test on Python 3.8:
ERROR: Package 'starlette' requires a different Python: 3.8.x not in '>=3.9'This wasn’t a surprise — Python 3.8 reached end-of-life in October 2024. But it’s worth calling out explicitly:
| Python Version | Status in Starlette 1.0.0rc1 |
|---|---|
| 3.6 | Removed (dropped in 0.20.0) |
| 3.7 | Removed (dropped in 0.30.0) |
| 3.8 | Removed (dropped in 0.45.0) |
| 3.9 | Minimum supported version |
| 3.10+ | Recommended |
Migration: If you’re on Python 3.8 or earlier, upgrade to Python 3.9+ first. There’s no workaround.
FastAPI Impact: Low. FastAPI 0.100+ already requires Python 3.8+, so most FastAPI applications are compatible. Just ensure you’re on Python 3.9+.
Breaking Change #2: GraphQL Support Removed
This one didn’t affect me, but it might affect you. I checked if I had any GraphQL imports:
grep -r "from starlette.graphql" .grep -r "GraphQLApp" .Nothing. Good.
But if you’re using Starlette’s built-in GraphQL support, it’s gone. Completely removed in 0.17.0 (deprecated in 0.15.0).
Why? Two reasons:
- Better third-party GraphQL libraries exist
- The
graphql-corelibrary doesn’t support Python 3.10+
Migration: Switch to a third-party GraphQL library:
# OLD (removed in 1.0.0rc1)from starlette.graphql import GraphQLAppapp.add_route('/graphql', GraphQLApp(schema=schema))
# NEW (use strawberry-graphql)from strawberry.asgi import GraphQLgraphql_app = GraphQL(schema)app.add_route('/graphql', graphql_app)Recommended alternatives:
- Strawberry - Modern, type-safe, Python 3.10+ compatible
- Graphene - Mature, widely adopted
- Ariadne - Fast ASGI-first implementation
FastAPI Impact: Low. Most FastAPI apps using GraphQL already migrated to third-party libraries years ago.
Breaking Change #3: UploadFile.file is Now Required
This one got me. I have a file upload endpoint that looks like this:
from starlette.datastructures import UploadFile
@app.post("/upload")async def upload_file(file: UploadFile): content = await file.read() return {"size": len(content)}After upgrading to 1.0.0rc1, I got a deprecation warning:
DeprecationWarning: UploadFile.file is required and will be a required argument in 1.0.0The file argument used to be optional. Now it’s required. This improves type safety and makes file handling explicit.
Migration: Ensure your UploadFile instances always have a file argument:
from starlette.datastructures import UploadFilefrom tempfile import SpooledTemporaryFile
# OLD (0.23.x and earlier)# file was optional, created automatically if not provided
# NEW (0.24.0+)# file must be provided explicitlyspool = SpooledTemporaryFile(max_size=500_000)upload_file = UploadFile(file=spool, filename="example.txt")FastAPI Impact: High. FastAPI’s File() and UploadFile() depend on Starlette’s implementation. Test your file upload endpoints thoroughly after upgrading.
Additional change: max_file_size was renamed to spool_max_size in 0.46.0:
# OLDupload_file = UploadFile(max_file_size=1_000_000)
# NEWupload_file = UploadFile(spool_max_size=1_000_000)Breaking Change #4: Route Decorators Deprecated
I found a few old routes using the decorator pattern:
from starlette.applications import Starlette
app = Starlette()
@app.route('/users/{user_id}')async def get_user(request): user_id = request.path_params['user_id'] return JSONResponse({'user_id': user_id})The @app.route() decorator was deprecated in 0.23.0. It still works in 1.0.0rc1, but it’s marked for removal in a future version.
Why? Declarative routing is more maintainable and easier to type-check:
from starlette.applications import Starlettefrom starlette.routing import Routefrom starlette.responses import JSONResponse
async def get_user(request): user_id = request.path_params['user_id'] return JSONResponse({'user_id': user_id})
routes = [ Route('/users/{user_id}', get_user)]
app = Starlette(routes=routes)Migration: Refactor decorator-based routes to declarative routes. This is more work but cleaner in the long run.
FastAPI Impact: Low. FastAPI uses its own decorator system (@app.get(), @app.post()), so this doesn’t affect most FastAPI applications.
Performance Improvements (Non-Breaking)
Not everything in 1.0.0rc1 is a breaking change. There are solid performance improvements:
Middleware Stack Lazy Construction
Changed in 0.24.0: Middleware stack is now built lazily instead of at application startup.
What this means: Faster application startup time, especially for apps with many middleware layers.
Action required: None. This is a transparent performance improvement.
IPv6 URL Parsing Fixes
Fixed in 0.24.0: Better URL parsing for IPv6 addresses.
What this means: Edge cases in URL.replace() and URL parsing now work correctly with IPv6 addresses like http://[::1]:8000/.
Action required: None. Bug fix that benefits everyone.
HTTP Range Support
Added in 0.39.0: FileResponse now supports HTTP Range requests.
What this means: You can now serve video and audio files with seeking support out of the box:
from starlette.responses import FileResponse
@app.route("/video.mp4")async def video(request): return FileResponse("video.mp4")Clients can now request specific byte ranges (Range: bytes=0-1023), enabling video/audio streaming without additional code.
Action required: None. Automatic improvement for FileResponse.
FastAPI Compatibility Analysis
This is what most people care about. Will FastAPI break?
I tested with FastAPI 0.110+ and Starlette 1.0.0rc1. Here’s what I found:
Good news: Most things work out of the box. FastAPI 0.100+ uses Starlette 0.27.0+, so the breaking changes have been trickling in for years.
Potential issues:
-
File uploads: Test your
UploadFileendpoints. Thefileargument requirement might affect your code. -
Custom middleware: If you have custom middleware that accesses internal Starlette APIs, test thoroughly.
-
GraphQL: If you’re somehow still using Starlette’s built-in GraphQL, migrate to a third-party library first.
Testing checklist:
# 1. Create a new virtual environmentpython -m venv venvsource venv/bin/activate
# 2. Install FastAPI and Starlette 1.0.0rc1pip install fastapi starlette==1.0.0rc1
# 3. Run your test suitepytest
# 4. Check for deprecation warningspython -W default::DeprecationWarning your_app.py
# 5. Load test your critical endpoints# (especially file uploads if you have them)MCP SDK Impact
If you’re building MCP (Model Context Protocol) servers using the Python MCP SDK, you’re indirectly using Starlette.
Impact assessment: Low to Medium.
The MCP SDK uses Starlette for its ASGI server, but it likely uses stable APIs. However, I recommend:
- Wait for official MCP SDK announcement before upgrading production MCP servers
- Test in staging first — MCP server endpoints should work, but verify
- Check for direct Starlette imports in your MCP server code
Migration Timeline
Here’s how I’m planning the upgrade:
Week 1: Assessment
- Audit Python version (must be 3.9+)
- Search for
GraphQLAppimports - Identify file upload endpoints
- Review custom middleware
Week 2-3: Testing
- Create upgrade branch
- Update dependencies
- Run test suite with Starlette 1.0.0rc1
- Fix any failures
Week 4: Migration
- Update breaking changes
- Refactor deprecated code
- Update CI/CD pipelines
Week 5: Deployment
- Deploy to staging
- Load testing
- Monitor error logs
- Production rollout
When NOT to Upgrade
Skip this release if:
- You’re on Python 3.8 or earlier → Upgrade Python first
- You’re using Starlette’s built-in GraphQL → Migrate to third-party first
- You have extensive file upload logic with no test coverage → Add tests first
- You’re running a critical production system with no staging environment → Set up staging first
Wait for 1.0.0 final if:
- You want maximum stability
- You’re not pressed for new features
- You have complex custom middleware you don’t fully understand
What I Recommend
If you have good test coverage, try 1.0.0rc1 in staging now. The changes are minimal if you’ve been keeping up with deprecation warnings.
If you’re risk-averse, wait for the final 1.0.0 release. Release candidates are typically stable, but the final release will have broader testing.
Either way, don’t wait too long. Python 3.9 support will be dropped in Starlette 0.50.0 (scheduled for November 2025), so you’ll want to be on a recent version before then.
Summary
Starlette 1.0.0rc1 removes features deprecated over the past 8 years. The main breaking changes are:
- Python 3.9+ required → Upgrade Python if needed
- GraphQL removed → Use third-party libraries (Strawberry, Graphene, Ariadne)
- UploadFile.file required → Update file upload code
- Route decorators deprecated → Migrate to declarative routing
For most FastAPI applications, migration is straightforward. Test your file upload endpoints, run your test suite, and fix any deprecation warnings.
The non-breaking performance improvements (lazy middleware construction, IPv6 fixes, HTTP Range support) are nice bonuses that require no code changes.
Final Words + More Resources
My intention with this article was to help others share my knowledge and experience. If you want to contact me, you can contact by email: Email me
Here are also the most important links from this article along with some further resources that will help you in this scope:
- 👨💻 Starlette Official Release Notes
- 👨💻 GitHub Repository
- 👨💻 FastAPI Documentation
- 👨💻 Reddit Discussion on Starlette 1.0
- 👨💻 Python Version Support Policy
Oh, and if you found these resources useful, don’t forget to support me by starring the repo on GitHub!
Comments