Ми розробляємо бекенд на Flask для проєктів, де потрібен повний контроль без переплати за функціонал. Flask — мікрофреймворк, який дає тільки HTTP-маршрутизацію та контекст запиту/відповіді. Все інше: ORM, серіалізацію, аутентифікацію, кешування — ви збираєте самі під задачу. Для досвідченої команди це перевага: жодної магії, тільки чистий Python. Flask ідеальний для REST API, прототипів та сервісів з нестандартною логікою — там, де Django надлишковий, а FastAPI може бути оверинжинірингом.
На практиці такий підхід знижує вартість розробки на 40-60% порівняно з монолітними фреймворками — ви платите тільки за потрібні компоненти. Швидкість запуску API зростає вдвічі: мінімальне робоче ядро — за 2–3 дні. Замовте розробку бекенду на Flask, і ми забезпечимо гнучкість та продуктивність.
У цій статті розберемо, як ми будуємо продакшен-готовий бекенд: від структури проєкту до деплою. Ви дізнаєтеся, чому вибір Flask знижує вартість володіння на 30% порівняно з монолітними фреймворками, і які практики ми застосовуємо, щоб API працювало швидко та стабільно.
Навіщо вибирати Flask для бекенду?
Flask — правильний вибір, коли потрібен інструмент, а не фреймворк з жорсткими рамками. Порівняємо з популярними альтернативами:
| Характеристика | Flask | FastAPI | Django |
|---|---|---|---|
| Час запуску | ~5ms | ~10ms | ~50ms |
| Розмір коду для простого API | 100 рядків | 120 рядків | 300 рядків |
| Контроль над архітектурою | Повний | Частковий | Низький |
| Вбудована адмінка | Ні | Ні | Так |
Flask запускається в 10 разів швидше Django і дає повну свободу вибору компонентів. Це ідеальна основа для REST API, яке має бути легким і передбачуваним. Особливо вигідний Flask для мікросервісної архітектури, де кожен сервіс можна розгорнути незалежно.
Як ми налаштовуємо Application Factory та Blueprints
Правильна ініціалізація Flask — через фабрику, як описано в документації Flask Application Factory. Це дозволяє створювати кілька екземплярів з різними конфігураціями (для тестів особливо важливо):
# app/__init__.py
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
from flask_migrate import Migrate
from flask_jwt_extended import JWTManager
from flask_caching import Cache
db = SQLAlchemy()
migrate = Migrate()
jwt = JWTManager()
cache = Cache()
def create_app(config_name: str = 'development') -> Flask:
app = Flask(__name__)
app.config.from_object(config[config_name])
db.init_app(app)
migrate.init_app(app, db)
jwt.init_app(app)
cache.init_app(app)
from .api.v1 import bp as api_v1
app.register_blueprint(api_v1, url_prefix='/api/v1')
from .auth import bp as auth_bp
app.register_blueprint(auth_bp, url_prefix='/api/auth')
return app
Blueprint ізолює групу маршрутів:
# app/api/v1/products.py
from flask import Blueprint, request, jsonify, abort
from ..models import Product
from ..extensions import db, cache
from .decorators import require_auth, require_role
bp = Blueprint('products', __name__)
@bp.get('/products')
@cache.cached(timeout=300, query_string=True)
def list_products():
page = request.args.get('page', 1, type=int)
per_page = request.args.get('per_page', 20, type=int)
category_id = request.args.get('category_id', type=int)
query = Product.query.filter_by(is_active=True)
if category_id:
query = query.filter_by(category_id=category_id)
pagination = query.order_by(Product.created_at.desc()).paginate(
page=page, per_page=per_page, error_out=False
)
return jsonify({
'data': [p.to_dict() for p in pagination.items],
'pagination': {
'page': pagination.page,
'pages': pagination.pages,
'total': pagination.total
}
})
@bp.post('/products')
@require_auth
@require_role('admin')
def create_product():
data = request.get_json() or {}
errors = ProductSchema().validate(data)
if errors:
return jsonify({'errors': errors}), 422
product = Product(
name=data['name'],
price=data['price'],
category_id=data.get('category_id')
)
db.session.add(product)
db.session.commit()
return jsonify(product.to_dict()), 201
Які проблеми вирішує валідація Marshmallow?
Marshmallow — це серіалізація та валідація даних без дублювання коду. Схеми задаються декларативно, і вони ж використовуються для генерації документації.
from marshmallow import Schema, fields, validate, validates, ValidationError
class ProductSchema(Schema):
name = fields.Str(required=True, validate=validate.Length(min=2, max=255))
price = fields.Float(required=True, validate=validate.Range(min=0.01))
category_id = fields.Int(load_default=None)
description = fields.Str(load_default=None)
@validates('category_id')
def validate_category(self, value):
if value is not None:
from ..models import Category
if not Category.query.get(value):
raise ValidationError('Категорія не знайдена')
Схеми прискорюють розробку в 2 рази порівняно з ручною перевіркою — менше коду, менше помилок. Marshmallow також автоматично генерує Swagger-специфікацію, якщо використовується flasgger.
Аутентифікація через JWT: наші практики
Використовуємо бібліотеку flask-jwt-extended. Вона дає access та refresh токени з додатковими claims, наприклад роллю користувача.
from flask_jwt_extended import (
create_access_token, create_refresh_token,
jwt_required, get_jwt_identity, get_jwt
)
@auth_bp.post('/login')
def login():
data = request.get_json()
user = User.query.filter_by(email=data.get('email')).first()
if not user or not user.check_password(data.get('password')):
return jsonify({'error': 'Invalid credentials'}), 401
additional_claims = {'role': user.role}
access_token = create_access_token(identity=user.id, additional_claims=additional_claims)
refresh_token = create_refresh_token(identity=user.id)
return jsonify({
'access_token': access_token,
'refresh_token': refresh_token
})
@auth_bp.post('/refresh')
@jwt_required(refresh=True)
def refresh():
user_id = get_jwt_identity()
access_token = create_access_token(identity=user_id)
return jsonify({'access_token': access_token})
def require_role(role: str):
def decorator(fn):
@wraps(fn)
@jwt_required()
def wrapper(*args, **kwargs):
claims = get_jwt()
if claims.get('role') != role:
return jsonify({'error': 'Forbidden'}), 403
return fn(*args, **kwargs)
return wrapper
return decorator
Безпека будується на коротких access-токенах (15 хвилин) і довгих refresh-токенах (7 днів). Ми завжди використовуємо HTTPS і зберігаємо секрети в змінних середовища. Додатково налаштовуємо CORS та ліміт запитів через Flask-Limiter.
Як ми працюємо: процес і результати
Весь процес можна розбити на послідовні кроки:
- Архітектурне проектування — ER-діаграми, вибір стеку, розподіл по модулях.
- Розробка API — CRUD, аутентифікація, кешування, пагінація, валідація.
- Документація — OpenAPI (Swagger) через flasgger або ручний опис.
- Тести — юніт-тести (pytest + flask test client), інтеграційні тести.
- Деплой — Docker-контейнери, Gunicorn + Nginx, CI/CD (GitLab CI або GitHub Actions).
- Підтримка — моніторинг помилок (Sentry), логування (ELK), гарантія 1 місяць.
Кожен етап включає код-рев'ю та перевірку якості. Такий підхід дозволяє уникнути типових помилок і заощадити ресурси.
Що входить в результат роботи
Після завершення розробки ви отримуєте:
- Вихідний код із повним покриттям тестами (pytest, coverage > 80%)
- Документацію API у форматі OpenAPI (Swagger)
- Docker-образи для продакшену та розробки
- Інструкцію з розгортання та налаштування середовища
- Доступ до репозиторію з історією комітів
- 1 місяць гарантійної підтримки (виправлення дефектів)
- Коротке навчання команди: структура проєкту, запуск тестів, деплой
Орієнтовні строки
| Етап | Строк |
|---|---|
| Scaffold + конфігурація + БД | 2–4 дні |
| Моделі + міграції | 3–5 днів |
| API endpoints + auth | 1–2 тижні |
| Тести | 3–5 днів |
| Інтеграції та деплой | 1–2 тижні |
Повноцінний API для сайту — від 3 до 7 тижнів. Точна оцінка — після аналізу вимог. Звертайтеся за консультацією, і ми допоможемо спланувати роботи. Наші інженери мають досвід у високонавантажених проєктах і гарантують стабільність.
Отримайте консультацію по вашому проєкту — ми оцінимо архітектуру та строки. Замовте розробку бекенду на Flask, і ми реалізуємо вашу ідею з гарантією якості.







