diff --git a/README.md b/README.md index 8255049..7c74258 100644 --- a/README.md +++ b/README.md @@ -6,31 +6,31 @@ we have been making good and bad decisions that impacted our developer experienc Some of them are worth sharing. ### Contents -1. [Project Structure. Consistent & predictable.](https://github.com/zhanymkanov/fastapi-best-practices#1-project-structure-consistent--predictable) -2. [Excessively use Pydantic for data validation.](https://github.com/zhanymkanov/fastapi-best-practices#2-excessively-use-pydantic-for-data-validation) -3. [Use dependencies for data validation vs DB.](https://github.com/zhanymkanov/fastapi-best-practices#3-use-dependencies-for-data-validation-vs-db) -4. [Chain dependencies.](https://github.com/zhanymkanov/fastapi-best-practices#4-chain-dependencies) -5. [Decouple & Reuse dependencies. Dependency calls are cached.](https://github.com/zhanymkanov/fastapi-best-practices#5-decouple--reuse-dependencies-dependency-calls-are-cached) -6. [Follow the REST.](https://github.com/zhanymkanov/fastapi-best-practices#6-follow-the-rest) -7. [Don't make your routes async, if you have only blocking I/O operations.](https://github.com/zhanymkanov/fastapi-best-practices#7-dont-make-your-routes-async-if-you-have-only-blocking-io-operations) -8. [Custom base model from day 0.](https://github.com/zhanymkanov/fastapi-best-practices#8-custom-base-model-from-day-0) -9. [Docs.](https://github.com/zhanymkanov/fastapi-best-practices#9-docs) -10. [Use Pydantic's BaseSettings for configs.](https://github.com/zhanymkanov/fastapi-best-practices#10-use-pydantics-basesettings-for-configs) -11. [SQLAlchemy: Set DB keys naming convention.](https://github.com/zhanymkanov/fastapi-best-practices#11-sqlalchemy-set-db-keys-naming-convention) -12. [Migrations. Alembic.](https://github.com/zhanymkanov/fastapi-best-practices#12-migrations-alembic) -13. [Set DB naming convention.](https://github.com/zhanymkanov/fastapi-best-practices#13-set-db-naming-convention) -14. [Set tests client async from day 0.](https://github.com/zhanymkanov/fastapi-best-practices#14-set-tests-client-async-from-day-0) -15. [BackgroundTasks > asyncio.create_task.](https://github.com/zhanymkanov/fastapi-best-practices#15-backgroundtasks--asynciocreate_task) -16. [Typing is important.](https://github.com/zhanymkanov/fastapi-best-practices#16-typing-is-important) -17. [Save files in chunks.](https://github.com/zhanymkanov/fastapi-best-practices#17-save-files-in-chunks) -18. [Be careful with dynamic pydantic fields.](https://github.com/zhanymkanov/fastapi-best-practices#18-be-careful-with-dynamic-pydantic-fields) -19. [SQL-first, Pydantic-second.](https://github.com/zhanymkanov/fastapi-best-practices#19-sql-first-pydantic-second) -20. [Validate hosts, if users can send publicly available URLs.](https://github.com/zhanymkanov/fastapi-best-practices#20-validate-hosts-if-users-can-send-publicly-available-urls) -21. [Raise a ValueError in custom pydantic validators, if schema directly faces the client.](https://github.com/zhanymkanov/fastapi-best-practices#21-raise-a-valueerror-in-custom-pydantic-validators-if-schema-directly-faces-the-client) -22. [FastAPI converts Pydantic objects to dict, then to Pydantic object, then to JSON](https://github.com/zhanymkanov/fastapi-best-practices#22-fastapi-converts-pydantic-objects-to-dict-then-to-pydantic-object-then-to-json) -23. [If you must use sync SDK, then run it in a thread pool.](https://github.com/zhanymkanov/fastapi-best-practices#23-if-you-must-use-sync-sdk-then-run-it-in-a-thread-pool) -24. [Use linters (black, ruff).](https://github.com/zhanymkanov/fastapi-best-practices#24-use-linters-black-ruff) -25. [Bonus Section.](https://github.com/zhanymkanov/fastapi-best-practices#bonus-section) +1. [Project Structure. Consistent & predictable.](#1-project-structure-consistent--predictable) +2. [Excessively use Pydantic for data validation.](#2-excessively-use-pydantic-for-data-validation) +3. [Use dependencies for data validation vs DB.](#3-use-dependencies-for-data-validation-vs-db) +4. [Chain dependencies.](#4-chain-dependencies) +5. [Decouple & Reuse dependencies. Dependency calls are cached.](#5-decouple--reuse-dependencies-dependency-calls-are-cached) +6. [Follow the REST.](#6-follow-the-rest) +7. [Don't make your routes async, if you have only blocking I/O operations.](#7-dont-make-your-routes-async-if-you-have-only-blocking-io-operations) +8. [Custom base model from day 0.](#8-custom-base-model-from-day-0) +9. [Docs.](#9-docs) +10. [Use Pydantic's BaseSettings for configs.](#10-use-pydantics-basesettings-for-configs) +11. [SQLAlchemy: Set DB keys naming convention.](#11-sqlalchemy-set-db-keys-naming-convention) +12. [Migrations. Alembic.](#12-migrations-alembic) +13. [Set DB naming convention.](#13-set-db-naming-convention) +14. [Set tests client async from day 0.](#14-set-tests-client-async-from-day-0) +15. [BackgroundTasks > asyncio.create_task.](#15-backgroundtasks--asynciocreate_task) +16. [Typing is important.](#16-typing-is-important) +17. [Save files in chunks.](#17-save-files-in-chunks) +18. [Be careful with dynamic pydantic fields.](#18-be-careful-with-dynamic-pydantic-fields-pydantic-v1) +19. [SQL-first, Pydantic-second.](#19-sql-first-pydantic-second) +20. [Validate hosts, if users can send publicly available URLs.](#20-validate-hosts-if-users-can-send-publicly-available-urls) +21. [Raise a ValueError in custom pydantic validators, if schema directly faces the client.](#21-raise-a-valueerror-in-custom-pydantic-validators-if-schema-directly-faces-the-client) +22. [FastAPI converts Pydantic objects to dict, then to Pydantic object, then to JSON](#22-fastapi-converts-pydantic-objects-to-dict-then-to-pydantic-object-then-to-json) +23. [If you must use sync SDK, then run it in a thread pool.](#23-if-you-must-use-sync-sdk-then-run-it-in-a-thread-pool) +24. [Use linters (black, ruff).](#24-use-linters-black-ruff) +25. [Bonus Section.](#bonus-section)

Project sample built with these best-practices in mind.

### 1. Project Structure. Consistent & predictable