fastapi-fullstack 0.1.7__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- fastapi_fullstack-0.1.7.dist-info/METADATA +739 -0
- fastapi_fullstack-0.1.7.dist-info/RECORD +241 -0
- fastapi_fullstack-0.1.7.dist-info/WHEEL +4 -0
- fastapi_fullstack-0.1.7.dist-info/entry_points.txt +2 -0
- fastapi_fullstack-0.1.7.dist-info/licenses/LICENSE +21 -0
- fastapi_gen/__init__.py +3 -0
- fastapi_gen/cli.py +442 -0
- fastapi_gen/config.py +356 -0
- fastapi_gen/generator.py +207 -0
- fastapi_gen/prompts.py +874 -0
- fastapi_gen/template/VARIABLES.md +276 -0
- fastapi_gen/template/cookiecutter.json +93 -0
- fastapi_gen/template/hooks/post_gen_project.py +355 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/.env.prod.example +56 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/.github/workflows/ci.yml +150 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/.gitignore +109 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/AGENTS.md +55 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/CLAUDE.md +99 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/Makefile +315 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/README.md +768 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/.dockerignore +60 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/.env.example +155 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/.pre-commit-config.yaml +32 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/Dockerfile +56 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/alembic/env.py +76 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/alembic/script.py.mako +30 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/alembic/versions/.gitkeep +0 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/alembic.ini +48 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/__init__.py +3 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/admin.py +447 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/agents/__init__.py +23 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/agents/assistant.py +226 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/agents/langchain_assistant.py +226 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/agents/prompts.py +10 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/agents/tools/__init__.py +13 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/agents/tools/datetime_tool.py +17 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/__init__.py +1 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/deps.py +541 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/exception_handlers.py +98 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/router.py +10 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/__init__.py +9 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/__init__.py +87 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/agent.py +902 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/auth.py +395 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/conversations.py +498 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/health.py +227 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/items.py +275 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/oauth.py +205 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/sessions.py +168 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/users.py +333 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/webhooks.py +477 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/routes/v1/ws.py +46 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/api/versioning.py +221 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/clients/__init__.py +14 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/clients/redis.py +88 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/commands/__init__.py +117 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/commands/cleanup.py +75 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/commands/example.py +28 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/commands/seed.py +266 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/__init__.py +5 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/cache.py +23 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/config.py +267 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/csrf.py +153 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/exceptions.py +122 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/logfire_setup.py +101 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/middleware.py +99 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/oauth.py +23 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/rate_limit.py +58 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/sanitize.py +271 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/core/security.py +102 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/__init__.py +7 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/base.py +41 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/models/__init__.py +31 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/models/conversation.py +319 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/models/item.py +96 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/models/session.py +126 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/models/user.py +218 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/models/webhook.py +244 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/db/session.py +130 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/main.py +334 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/pipelines/__init__.py +9 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/pipelines/base.py +73 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/__init__.py +49 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/base.py +154 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/conversation.py +838 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/item.py +222 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/session.py +318 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/user.py +322 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/repositories/webhook.py +358 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/__init__.py +50 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/base.py +57 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/conversation.py +192 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/item.py +52 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/session.py +42 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/token.py +31 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/user.py +64 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/schemas/webhook.py +89 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/services/__init__.py +38 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/services/conversation.py +850 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/services/item.py +246 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/services/session.py +333 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/services/user.py +432 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/services/webhook.py +561 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/__init__.py +5 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/celery_app.py +64 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/taskiq_app.py +38 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/tasks/__init__.py +25 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/tasks/examples.py +106 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/tasks/schedules.py +29 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/app/worker/tasks/taskiq_examples.py +92 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/cli/__init__.py +1 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/cli/commands.py +438 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/pyproject.toml +180 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/scripts/.gitkeep +0 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/__init__.py +1 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/api/__init__.py +1 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/api/test_auth.py +242 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/api/test_exceptions.py +151 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/api/test_health.py +113 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/api/test_items.py +310 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/api/test_users.py +253 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/conftest.py +151 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_admin.py +890 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_agents.py +261 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_clients.py +183 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_commands.py +173 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_core.py +143 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_pipelines.py +118 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_repositories.py +181 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_security.py +124 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_services.py +363 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/backend/tests/test_worker.py +85 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docker-compose.dev.yml +242 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docker-compose.frontend.yml +31 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docker-compose.prod.yml +435 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docker-compose.yml +241 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docs/adding_features.md +132 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docs/architecture.md +63 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docs/patterns.md +161 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/docs/testing.md +120 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/.dockerignore +40 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/.env.example +12 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/.gitignore +45 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/.prettierignore +19 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/.prettierrc +11 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/Dockerfile +44 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/README.md +648 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/e2e/auth.setup.ts +49 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/e2e/auth.spec.ts +134 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/e2e/chat.spec.ts +207 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/e2e/home.spec.ts +73 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/instrumentation.ts +14 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/messages/en.json +84 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/messages/pl.json +84 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/next.config.ts +76 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/package.json +69 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/playwright.config.ts +101 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/postcss.config.mjs +7 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(auth)/layout.tsx +11 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(auth)/login/page.tsx +5 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(auth)/register/page.tsx +5 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(dashboard)/chat/page.tsx +48 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(dashboard)/dashboard/page.tsx +99 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(dashboard)/layout.tsx +17 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/(dashboard)/profile/page.tsx +152 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/auth/callback/page.tsx +113 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/layout.tsx +46 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/[locale]/page.tsx +73 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/auth/login/route.ts +58 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/auth/logout/route.ts +24 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/auth/me/route.ts +39 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/auth/oauth-callback/route.ts +50 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/auth/refresh/route.ts +54 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/auth/register/route.ts +26 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/conversations/[id]/messages/route.ts +41 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/conversations/[id]/route.ts +108 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/conversations/route.ts +73 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/api/health/route.ts +21 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/globals.css +323 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/layout.tsx +22 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/app/providers.tsx +29 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/auth/index.ts +2 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/auth/login-form.tsx +120 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/auth/register-form.tsx +153 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/chat-container.tsx +234 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/chat-input.tsx +72 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/conversation-sidebar.tsx +328 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/copy-button.tsx +46 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/index.ts +11 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/local-conversation-sidebar.tsx +295 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/markdown-content.tsx +167 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/message-item.tsx +79 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/message-list.tsx +18 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/chat/tool-call-card.tsx +79 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/icons/google-icon.tsx +32 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/icons/index.ts +3 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/language-switcher.tsx +97 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/layout/header.tsx +65 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/layout/index.ts +2 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/layout/sidebar.tsx +82 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/theme/index.ts +7 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/theme/theme-provider.tsx +53 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/theme/theme-toggle.tsx +105 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/badge.tsx +35 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/button.test.tsx +75 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/button.tsx +56 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/card.tsx +82 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/index.ts +13 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/input.tsx +21 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/label.tsx +21 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/components/ui/sheet.tsx +109 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/hooks/index.ts +7 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/hooks/use-auth.ts +97 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/hooks/use-chat.ts +203 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/hooks/use-conversations.ts +181 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/hooks/use-local-chat.ts +165 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/hooks/use-websocket.ts +105 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/i18n.ts +37 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/lib/api-client.ts +90 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/lib/constants.ts +39 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/lib/server-api.ts +78 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/lib/utils.test.ts +44 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/lib/utils.ts +44 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/middleware.ts +31 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/auth-store.test.ts +72 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/auth-store.ts +64 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/chat-sidebar-store.ts +17 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/chat-store.ts +65 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/conversation-store.ts +76 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/index.ts +9 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/local-chat-store.ts +255 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/sidebar-store.ts +17 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/stores/theme-store.ts +44 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/types/api.ts +27 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/types/auth.ts +52 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/types/chat.ts +83 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/types/conversation.ts +49 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/src/types/index.ts +10 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/tsconfig.json +28 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/vitest.config.ts +36 -0
- fastapi_gen/template/{{cookiecutter.project_slug}}/frontend/vitest.setup.ts +56 -0
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
{%- if cookiecutter.enable_docker %}
|
|
2
|
+
# Git
|
|
3
|
+
.git
|
|
4
|
+
.gitignore
|
|
5
|
+
|
|
6
|
+
# Python
|
|
7
|
+
__pycache__
|
|
8
|
+
*.py[cod]
|
|
9
|
+
*$py.class
|
|
10
|
+
*.so
|
|
11
|
+
.Python
|
|
12
|
+
.venv
|
|
13
|
+
venv/
|
|
14
|
+
ENV/
|
|
15
|
+
|
|
16
|
+
# IDE
|
|
17
|
+
.idea
|
|
18
|
+
.vscode
|
|
19
|
+
*.swp
|
|
20
|
+
*.swo
|
|
21
|
+
|
|
22
|
+
# Testing
|
|
23
|
+
.pytest_cache
|
|
24
|
+
.coverage
|
|
25
|
+
htmlcov/
|
|
26
|
+
.tox
|
|
27
|
+
.nox
|
|
28
|
+
|
|
29
|
+
# Documentation
|
|
30
|
+
docs/_build/
|
|
31
|
+
*.md
|
|
32
|
+
!README.md
|
|
33
|
+
|
|
34
|
+
# Build artifacts
|
|
35
|
+
dist/
|
|
36
|
+
build/
|
|
37
|
+
*.egg-info/
|
|
38
|
+
|
|
39
|
+
# Development files
|
|
40
|
+
.env
|
|
41
|
+
.env.local
|
|
42
|
+
*.db
|
|
43
|
+
*.sqlite
|
|
44
|
+
|
|
45
|
+
# Docker
|
|
46
|
+
Dockerfile*
|
|
47
|
+
docker-compose*.yml
|
|
48
|
+
.docker
|
|
49
|
+
|
|
50
|
+
# CI/CD
|
|
51
|
+
.github/
|
|
52
|
+
.gitlab-ci.yml
|
|
53
|
+
|
|
54
|
+
# Misc
|
|
55
|
+
.DS_Store
|
|
56
|
+
Thumbs.db
|
|
57
|
+
*.log
|
|
58
|
+
{%- else %}
|
|
59
|
+
# Docker is disabled
|
|
60
|
+
{%- endif %}
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
# {{ cookiecutter.project_name }} Environment Variables
|
|
2
|
+
|
|
3
|
+
# === Project ===
|
|
4
|
+
PROJECT_NAME={{ cookiecutter.project_name }}
|
|
5
|
+
DEBUG=true
|
|
6
|
+
ENVIRONMENT=local
|
|
7
|
+
|
|
8
|
+
{%- if cookiecutter.enable_logfire %}
|
|
9
|
+
|
|
10
|
+
# === Logfire ===
|
|
11
|
+
# Get your token at https://logfire.pydantic.dev
|
|
12
|
+
LOGFIRE_TOKEN=
|
|
13
|
+
LOGFIRE_SERVICE_NAME={{ cookiecutter.project_slug }}
|
|
14
|
+
LOGFIRE_ENVIRONMENT=development
|
|
15
|
+
{%- endif %}
|
|
16
|
+
|
|
17
|
+
{%- if cookiecutter.use_postgresql %}
|
|
18
|
+
|
|
19
|
+
# === PostgreSQL ===
|
|
20
|
+
POSTGRES_HOST=localhost
|
|
21
|
+
POSTGRES_PORT=5432
|
|
22
|
+
POSTGRES_USER=postgres
|
|
23
|
+
POSTGRES_PASSWORD=postgres
|
|
24
|
+
POSTGRES_DB={{ cookiecutter.project_slug }}
|
|
25
|
+
{%- endif %}
|
|
26
|
+
|
|
27
|
+
{%- if cookiecutter.use_mongodb %}
|
|
28
|
+
|
|
29
|
+
# === MongoDB ===
|
|
30
|
+
MONGO_HOST=localhost
|
|
31
|
+
MONGO_PORT=27017
|
|
32
|
+
MONGO_DB={{ cookiecutter.project_slug }}
|
|
33
|
+
# MONGO_USER=
|
|
34
|
+
# MONGO_PASSWORD=
|
|
35
|
+
{%- endif %}
|
|
36
|
+
|
|
37
|
+
{%- if cookiecutter.use_sqlite %}
|
|
38
|
+
|
|
39
|
+
# === SQLite ===
|
|
40
|
+
SQLITE_PATH=./{{ cookiecutter.project_slug }}.db
|
|
41
|
+
{%- endif %}
|
|
42
|
+
|
|
43
|
+
{%- if cookiecutter.use_jwt %}
|
|
44
|
+
|
|
45
|
+
# === JWT Auth ===
|
|
46
|
+
# Generate with: openssl rand -hex 32
|
|
47
|
+
SECRET_KEY=change-me-in-production-use-openssl-rand-hex-32
|
|
48
|
+
ACCESS_TOKEN_EXPIRE_MINUTES=10080
|
|
49
|
+
ALGORITHM=HS256
|
|
50
|
+
{%- endif %}
|
|
51
|
+
|
|
52
|
+
{%- if cookiecutter.use_api_key %}
|
|
53
|
+
|
|
54
|
+
# === API Key Auth ===
|
|
55
|
+
API_KEY=change-me-in-production
|
|
56
|
+
API_KEY_HEADER=X-API-Key
|
|
57
|
+
{%- endif %}
|
|
58
|
+
|
|
59
|
+
{%- if cookiecutter.enable_redis %}
|
|
60
|
+
|
|
61
|
+
# === Redis ===
|
|
62
|
+
REDIS_HOST=localhost
|
|
63
|
+
REDIS_PORT=6379
|
|
64
|
+
# REDIS_PASSWORD=
|
|
65
|
+
REDIS_DB=0
|
|
66
|
+
{%- endif %}
|
|
67
|
+
|
|
68
|
+
{%- if cookiecutter.use_celery %}
|
|
69
|
+
|
|
70
|
+
# === Celery ===
|
|
71
|
+
CELERY_BROKER_URL=redis://localhost:6379/0
|
|
72
|
+
CELERY_RESULT_BACKEND=redis://localhost:6379/0
|
|
73
|
+
{%- endif %}
|
|
74
|
+
|
|
75
|
+
{%- if cookiecutter.use_taskiq %}
|
|
76
|
+
|
|
77
|
+
# === Taskiq ===
|
|
78
|
+
TASKIQ_BROKER_URL=redis://localhost:6379/1
|
|
79
|
+
TASKIQ_RESULT_BACKEND=redis://localhost:6379/1
|
|
80
|
+
{%- endif %}
|
|
81
|
+
|
|
82
|
+
{%- if cookiecutter.enable_sentry %}
|
|
83
|
+
|
|
84
|
+
# === Sentry ===
|
|
85
|
+
SENTRY_DSN=
|
|
86
|
+
{%- endif %}
|
|
87
|
+
|
|
88
|
+
{%- if cookiecutter.enable_file_storage %}
|
|
89
|
+
|
|
90
|
+
# === S3/MinIO Storage ===
|
|
91
|
+
S3_ENDPOINT=
|
|
92
|
+
S3_ACCESS_KEY=
|
|
93
|
+
S3_SECRET_KEY=
|
|
94
|
+
S3_BUCKET={{ cookiecutter.project_slug }}
|
|
95
|
+
S3_REGION=us-east-1
|
|
96
|
+
{%- endif %}
|
|
97
|
+
|
|
98
|
+
{%- if cookiecutter.enable_ai_agent %}
|
|
99
|
+
|
|
100
|
+
# === AI Agent ({{ cookiecutter.ai_framework }}, {{ cookiecutter.llm_provider }}) ===
|
|
101
|
+
{%- if cookiecutter.use_openai %}
|
|
102
|
+
OPENAI_API_KEY=
|
|
103
|
+
AI_MODEL=gpt-4o-mini
|
|
104
|
+
{%- endif %}
|
|
105
|
+
{%- if cookiecutter.use_anthropic %}
|
|
106
|
+
ANTHROPIC_API_KEY=
|
|
107
|
+
AI_MODEL=claude-sonnet-4-5-20241022
|
|
108
|
+
{%- endif %}
|
|
109
|
+
{%- if cookiecutter.use_openrouter %}
|
|
110
|
+
OPENROUTER_API_KEY=
|
|
111
|
+
AI_MODEL=anthropic/claude-3.5-sonnet
|
|
112
|
+
{%- endif %}
|
|
113
|
+
AI_TEMPERATURE=0.7
|
|
114
|
+
{%- if cookiecutter.use_langchain %}
|
|
115
|
+
|
|
116
|
+
# === LangSmith (LangChain Observability) ===
|
|
117
|
+
# Get your API key at https://smith.langchain.com
|
|
118
|
+
LANGCHAIN_TRACING_V2=true
|
|
119
|
+
LANGCHAIN_API_KEY=
|
|
120
|
+
LANGCHAIN_PROJECT={{ cookiecutter.project_slug }}
|
|
121
|
+
LANGCHAIN_ENDPOINT=https://api.smith.langchain.com
|
|
122
|
+
{%- endif %}
|
|
123
|
+
{%- endif %}
|
|
124
|
+
|
|
125
|
+
{%- if cookiecutter.enable_cors %}
|
|
126
|
+
|
|
127
|
+
# === CORS ===
|
|
128
|
+
# JSON list of allowed origins (default: localhost:3000, localhost:8080)
|
|
129
|
+
# Note: "*" is blocked in production - specify explicit origins
|
|
130
|
+
CORS_ORIGINS=["http://localhost:3000","http://localhost:8080"]
|
|
131
|
+
{%- endif %}
|
|
132
|
+
|
|
133
|
+
{%- if cookiecutter.enable_docker %}
|
|
134
|
+
|
|
135
|
+
# === Docker Production (Traefik) ===
|
|
136
|
+
# Domain for production deployment
|
|
137
|
+
DOMAIN=example.com
|
|
138
|
+
|
|
139
|
+
# Let's Encrypt email for SSL certificates
|
|
140
|
+
ACME_EMAIL=admin@example.com
|
|
141
|
+
|
|
142
|
+
# Traefik dashboard auth (generate with: htpasswd -nb admin password)
|
|
143
|
+
# TRAEFIK_DASHBOARD_AUTH=admin:$$apr1$$...
|
|
144
|
+
|
|
145
|
+
{%- if cookiecutter.enable_redis %}
|
|
146
|
+
# Redis password for production
|
|
147
|
+
REDIS_PASSWORD=change-me-in-production
|
|
148
|
+
{%- endif %}
|
|
149
|
+
|
|
150
|
+
{%- if cookiecutter.use_celery %}
|
|
151
|
+
# Flower monitoring credentials
|
|
152
|
+
FLOWER_USER=admin
|
|
153
|
+
FLOWER_PASSWORD=change-me-in-production
|
|
154
|
+
{%- endif %}
|
|
155
|
+
{%- endif %}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
{%- if cookiecutter.enable_precommit %}
|
|
2
|
+
repos:
|
|
3
|
+
- repo: https://github.com/pre-commit/pre-commit-hooks
|
|
4
|
+
rev: v5.0.0
|
|
5
|
+
hooks:
|
|
6
|
+
- id: trailing-whitespace
|
|
7
|
+
- id: end-of-file-fixer
|
|
8
|
+
- id: check-yaml
|
|
9
|
+
- id: check-toml
|
|
10
|
+
- id: check-added-large-files
|
|
11
|
+
args: ['--maxkb=1000']
|
|
12
|
+
- id: check-merge-conflict
|
|
13
|
+
- id: detect-private-key
|
|
14
|
+
|
|
15
|
+
- repo: https://github.com/astral-sh/ruff-pre-commit
|
|
16
|
+
rev: v0.8.0
|
|
17
|
+
hooks:
|
|
18
|
+
- id: ruff
|
|
19
|
+
args: [--fix]
|
|
20
|
+
- id: ruff-format
|
|
21
|
+
|
|
22
|
+
- repo: https://github.com/pre-commit/mirrors-mypy
|
|
23
|
+
rev: v1.13.0
|
|
24
|
+
hooks:
|
|
25
|
+
- id: mypy
|
|
26
|
+
additional_dependencies:
|
|
27
|
+
- pydantic>=2.0.0
|
|
28
|
+
- pydantic-settings>=2.0.0
|
|
29
|
+
args: [--ignore-missing-imports]
|
|
30
|
+
{%- else %}
|
|
31
|
+
# Pre-commit is disabled for this project
|
|
32
|
+
{%- endif %}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
{%- if cookiecutter.enable_docker %}
|
|
2
|
+
# Build stage
|
|
3
|
+
FROM python:{{ cookiecutter.python_version }}-slim AS builder
|
|
4
|
+
|
|
5
|
+
ENV PYTHONUNBUFFERED=1
|
|
6
|
+
ENV PYTHONDONTWRITEBYTECODE=1
|
|
7
|
+
WORKDIR /app
|
|
8
|
+
|
|
9
|
+
# Install uv
|
|
10
|
+
COPY --from=ghcr.io/astral-sh/uv:latest /uv /bin/uv
|
|
11
|
+
ENV UV_COMPILE_BYTECODE=1
|
|
12
|
+
ENV UV_LINK_MODE=copy
|
|
13
|
+
|
|
14
|
+
# Install dependencies
|
|
15
|
+
RUN --mount=type=cache,target=/root/.cache/uv \
|
|
16
|
+
--mount=type=bind,source=uv.lock,target=uv.lock \
|
|
17
|
+
--mount=type=bind,source=pyproject.toml,target=pyproject.toml \
|
|
18
|
+
uv sync --frozen --no-install-project --no-dev
|
|
19
|
+
|
|
20
|
+
# Copy application
|
|
21
|
+
COPY . /app
|
|
22
|
+
|
|
23
|
+
# Install project
|
|
24
|
+
RUN --mount=type=cache,target=/root/.cache/uv \
|
|
25
|
+
uv sync --frozen --no-dev
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
# Runtime stage
|
|
29
|
+
FROM python:{{ cookiecutter.python_version }}-slim
|
|
30
|
+
|
|
31
|
+
ENV PYTHONUNBUFFERED=1
|
|
32
|
+
ENV PYTHONDONTWRITEBYTECODE=1
|
|
33
|
+
WORKDIR /app
|
|
34
|
+
|
|
35
|
+
# Copy virtual environment from builder
|
|
36
|
+
COPY --from=builder /app/.venv /app/.venv
|
|
37
|
+
COPY --from=builder /app /app
|
|
38
|
+
|
|
39
|
+
# Add venv to path
|
|
40
|
+
ENV PATH="/app/.venv/bin:$PATH"
|
|
41
|
+
|
|
42
|
+
# Create non-root user
|
|
43
|
+
RUN adduser --disabled-password --gecos "" appuser && \
|
|
44
|
+
chown -R appuser:appuser /app
|
|
45
|
+
USER appuser
|
|
46
|
+
|
|
47
|
+
EXPOSE {{ cookiecutter.backend_port }}
|
|
48
|
+
|
|
49
|
+
# Health check
|
|
50
|
+
HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
|
|
51
|
+
CMD python -c "import httpx; httpx.get('http://localhost:{{ cookiecutter.backend_port }}/api/v1/health')" || exit 1
|
|
52
|
+
|
|
53
|
+
CMD ["python", "-m", "cli.commands", "server", "run", "--host", "0.0.0.0", "--port", "{{ cookiecutter.backend_port }}"]
|
|
54
|
+
{%- else %}
|
|
55
|
+
# Docker is disabled for this project
|
|
56
|
+
{%- endif %}
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
{%- if cookiecutter.use_postgresql or cookiecutter.use_sqlite %}
|
|
2
|
+
"""Alembic migration environment."""
|
|
3
|
+
# ruff: noqa: I001 - Imports structured for Jinja2 template conditionals
|
|
4
|
+
|
|
5
|
+
from logging.config import fileConfig
|
|
6
|
+
|
|
7
|
+
from alembic import context
|
|
8
|
+
from sqlalchemy import engine_from_config, pool
|
|
9
|
+
|
|
10
|
+
from app.core.config import settings
|
|
11
|
+
from app.db.base import Base
|
|
12
|
+
|
|
13
|
+
# Import all models here to ensure they are registered with Base.metadata
|
|
14
|
+
{%- if cookiecutter.use_jwt %}
|
|
15
|
+
from app.db.models.user import User # noqa: F401
|
|
16
|
+
{%- endif %}
|
|
17
|
+
|
|
18
|
+
config = context.config
|
|
19
|
+
|
|
20
|
+
if config.config_file_name is not None:
|
|
21
|
+
fileConfig(config.config_file_name)
|
|
22
|
+
|
|
23
|
+
target_metadata = Base.metadata
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
def get_url() -> str:
|
|
27
|
+
"""Get database URL from settings."""
|
|
28
|
+
{%- if cookiecutter.use_postgresql %}
|
|
29
|
+
return settings.DATABASE_URL_SYNC
|
|
30
|
+
{%- else %}
|
|
31
|
+
return settings.DATABASE_URL
|
|
32
|
+
{%- endif %}
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
def run_migrations_offline() -> None:
|
|
36
|
+
"""Run migrations in 'offline' mode."""
|
|
37
|
+
url = get_url()
|
|
38
|
+
context.configure(
|
|
39
|
+
url=url,
|
|
40
|
+
target_metadata=target_metadata,
|
|
41
|
+
literal_binds=True,
|
|
42
|
+
dialect_opts={"paramstyle": "named"},
|
|
43
|
+
)
|
|
44
|
+
|
|
45
|
+
with context.begin_transaction():
|
|
46
|
+
context.run_migrations()
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
def run_migrations_online() -> None:
|
|
50
|
+
"""Run migrations in 'online' mode."""
|
|
51
|
+
configuration = config.get_section(config.config_ini_section)
|
|
52
|
+
configuration["sqlalchemy.url"] = get_url()
|
|
53
|
+
|
|
54
|
+
connectable = engine_from_config(
|
|
55
|
+
configuration,
|
|
56
|
+
prefix="sqlalchemy.",
|
|
57
|
+
poolclass=pool.NullPool,
|
|
58
|
+
)
|
|
59
|
+
|
|
60
|
+
with connectable.connect() as connection:
|
|
61
|
+
context.configure(
|
|
62
|
+
connection=connection,
|
|
63
|
+
target_metadata=target_metadata,
|
|
64
|
+
)
|
|
65
|
+
|
|
66
|
+
with context.begin_transaction():
|
|
67
|
+
context.run_migrations()
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
if context.is_offline_mode():
|
|
71
|
+
run_migrations_offline()
|
|
72
|
+
else:
|
|
73
|
+
run_migrations_online()
|
|
74
|
+
{%- else %}
|
|
75
|
+
# Alembic - not configured (no SQL database)
|
|
76
|
+
{%- endif %}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
{%- if cookiecutter.use_postgresql or cookiecutter.use_sqlite %}
|
|
2
|
+
"""${message}
|
|
3
|
+
|
|
4
|
+
Revision ID: ${up_revision}
|
|
5
|
+
Revises: ${down_revision | comma,n}
|
|
6
|
+
Create Date: ${create_date}
|
|
7
|
+
|
|
8
|
+
"""
|
|
9
|
+
from typing import Sequence, Union
|
|
10
|
+
|
|
11
|
+
from alembic import op
|
|
12
|
+
import sqlalchemy as sa
|
|
13
|
+
${imports if imports else ""}
|
|
14
|
+
|
|
15
|
+
# revision identifiers, used by Alembic.
|
|
16
|
+
revision: str = ${repr(up_revision)}
|
|
17
|
+
down_revision: Union[str, None] = ${repr(down_revision)}
|
|
18
|
+
branch_labels: Union[str, Sequence[str], None] = ${repr(branch_labels)}
|
|
19
|
+
depends_on: Union[str, Sequence[str], None] = ${repr(depends_on)}
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def upgrade() -> None:
|
|
23
|
+
${upgrades if upgrades else "pass"}
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
def downgrade() -> None:
|
|
27
|
+
${downgrades if downgrades else "pass"}
|
|
28
|
+
{%- else %}
|
|
29
|
+
# Alembic - not configured
|
|
30
|
+
{%- endif %}
|
|
File without changes
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
{%- if cookiecutter.use_postgresql or cookiecutter.use_sqlite %}
|
|
2
|
+
# Alembic Configuration
|
|
3
|
+
|
|
4
|
+
[alembic]
|
|
5
|
+
script_location = alembic
|
|
6
|
+
prepend_sys_path = .
|
|
7
|
+
version_path_separator = os
|
|
8
|
+
# Human-readable migration file names: 2024-01-15_add_users_table.py
|
|
9
|
+
file_template = %%(year)d-%%(month).2d-%%(day).2d_%%(slug)s
|
|
10
|
+
|
|
11
|
+
[post_write_hooks]
|
|
12
|
+
|
|
13
|
+
[loggers]
|
|
14
|
+
keys = root,sqlalchemy,alembic
|
|
15
|
+
|
|
16
|
+
[handlers]
|
|
17
|
+
keys = console
|
|
18
|
+
|
|
19
|
+
[formatters]
|
|
20
|
+
keys = generic
|
|
21
|
+
|
|
22
|
+
[logger_root]
|
|
23
|
+
level = WARN
|
|
24
|
+
handlers = console
|
|
25
|
+
qualname =
|
|
26
|
+
|
|
27
|
+
[logger_sqlalchemy]
|
|
28
|
+
level = WARN
|
|
29
|
+
handlers =
|
|
30
|
+
qualname = sqlalchemy.engine
|
|
31
|
+
|
|
32
|
+
[logger_alembic]
|
|
33
|
+
level = INFO
|
|
34
|
+
handlers =
|
|
35
|
+
qualname = alembic
|
|
36
|
+
|
|
37
|
+
[handler_console]
|
|
38
|
+
class = StreamHandler
|
|
39
|
+
args = (sys.stderr,)
|
|
40
|
+
level = NOTSET
|
|
41
|
+
formatter = generic
|
|
42
|
+
|
|
43
|
+
[formatter_generic]
|
|
44
|
+
format = %(levelname)-5.5s [%(name)s] %(message)s
|
|
45
|
+
datefmt = %H:%M:%S
|
|
46
|
+
{%- else %}
|
|
47
|
+
# Alembic - not configured (no SQL database)
|
|
48
|
+
{%- endif %}
|