feat(database): Database Connection Module and Seed Data (#11) - #20
Conversation
Implements production-ready database connection management with connection pooling, retry logic, health checks, and an idempotent seed data script for development environments. **Database Connection Module (app/db/session.py):** - Connection pooling with QueuePool (pool_size=5, max_overflow=10) - Session factory with autocommit=False, autoflush=False - Context manager (get_db_session) for safe session handling - Health check function (check_database_health) - Retry logic with exponential backoff using tenacity **Seed Data Script (migrations/seed_data.py):** - Creates development user (dev@noosphere.local) - Creates classification prompt v1 - Creates sample items across 4 categories (Admin, Ideas, People, Projects) - Fully idempotent - safe to run multiple times - Accepts optional session parameter for testing **Testing:** - 10 tests for session module (connection, context manager, health check, retry) - 9 tests for seed data script (creation, idempotency, data validation) - All tests passing with transaction isolation - 74 total tests passing (19 new + 55 existing) **Dependencies:** - Added tenacity>=8.2.3,<9.0.0 for retry logic **Files Added:** - api-service/app/db/session.py - api-service/migrations/seed_data.py - api-service/tests/db/__init__.py - api-service/tests/db/test_session.py - api-service/tests/test_seed_data.py **Files Modified:** - api-service/requirements.txt (added tenacity) - api-service/app/db/__init__.py (exported session functions) **Quality Checks:** ✅ ruff format - all files formatted ✅ ruff check - no violations ✅ pyright - no type errors ✅ pytest - all 74 tests passing Closes #11 Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Summary of ChangesHello @deserat, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed! This pull request significantly enhances the Highlights
🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console. Using Gemini Code AssistThe full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips. Invoking Gemini You can request assistance from Gemini at any point by creating a comment using either
Customization To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a Limitations & Feedback Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here. You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension. Footnotes
|
There was a problem hiding this comment.
Code Review
This pull request introduces a robust database connection module and a helpful seed data script. The implementation is solid, with good use of connection pooling, retry logic with tenacity, and a well-structured, idempotent seeder. The accompanying tests are thorough and cover success, failure, and edge cases effectively.
My review includes a few suggestions to improve maintainability and correctness:
- Refining the public API of the
dbmodule. - Using more specific exception handling.
- Correcting a docstring for accuracy.
- Removing a magic number for the embedding dimension.
- Fixing a couple of minor issues in the tests related to imports.
Overall, this is a high-quality contribution that sets a strong foundation for database interactions in the application.
| # Session should be closed after exiting context | ||
| # Verify by trying to execute a query, which should fail | ||
| with pytest.raises((InvalidRequestError, Exception)): | ||
| db_session_obj.execute(text("SELECT 1")) |
| __all__ = [ | ||
| "_import_models", | ||
| "engine", | ||
| "SessionLocal", | ||
| "get_db_session", | ||
| "check_database_health", | ||
| "connect_with_retry", | ||
| ] |
There was a problem hiding this comment.
The function _import_models is prefixed with an underscore, indicating it's intended for internal use (specifically by Alembic, as noted in app/db/base.py). Exporting it in __all__ makes it part of the public API of the app.db package, which is misleading. It should be removed from __all__ to maintain a clean public interface.
__all__ = [
"engine",
"SessionLocal",
"get_db_session",
"check_database_health",
"connect_with_retry",
]|
/gemini review |
There was a problem hiding this comment.
Code Review
This pull request introduces a robust database connection module and a seed data script, which are great additions. The implementation is solid, with connection pooling, retry logic, and comprehensive tests.
My review focuses on a few areas for improvement:
- Configuration Management: Moving
load_dotenv()out of the session module to the application entry point for better control. - Code Maintainability: Refactoring magic numbers into constants and improving module-level exports (
__all__). - Test Quality: Making tests more specific and removing redundancy.
- Clarity: Improving docstrings and logging for better developer experience and debuggability.
Overall, this is a high-quality contribution. The suggested changes are mostly aimed at improving long-term maintainability and adhering to best practices.
| from unittest.mock import Mock, patch | ||
|
|
||
| import pytest | ||
| from sqlalchemy.exc import OperationalError |
There was a problem hiding this comment.
| Usage: | ||
| from app.db.session import get_db_session, check_database_health | ||
|
|
||
| with get_db_session() as session: | ||
| users = session.query(User).all() | ||
|
|
There was a problem hiding this comment.
The usage example in the docstring is a bit misleading. It shows importing from app.db.session, but since this is the app.db package's __init__.py, the example should demonstrate usage by importing from app.db. Also, the User model is used without being imported, which could be confusing. It would be clearer to either show the import or use a more generic example that doesn't require a model.
| Usage: | |
| from app.db.session import get_db_session, check_database_health | |
| with get_db_session() as session: | |
| users = session.query(User).all() | |
| Usage: | |
| from app.db import get_db_session | |
| from app.models.user import User | |
| with get_db_session() as session: | |
| users = session.query(User).all() |
| __all__ = [ | ||
| "_import_models", | ||
| "engine", | ||
| "SessionLocal", | ||
| "get_db_session", | ||
| "check_database_health", | ||
| "connect_with_retry", | ||
| ] |
There was a problem hiding this comment.
The __all__ list exports _import_models, which is prefixed with an underscore, suggesting it's for internal use. Typically, such internal functions shouldn't be part of a module's public API. It's also good practice to keep the __all__ list sorted alphabetically for better readability and maintenance.
I suggest removing _import_models and sorting the list.
__all__ = [
"SessionLocal",
"check_database_health",
"connect_with_retry",
"engine",
"get_db_session",
]Addresses all feedback from Gemini Code Assist code review: **Critical/High Priority:** - Add missing text import in test_session.py (NameError fix) - Remove load_dotenv() from session.py (better architecture) Environment should be loaded at application entry point - Move uuid import to top of file (PEP 8) **Exception Handling:** - Use specific OperationalError instead of generic Exception - Add logging to check_database_health() for debugging - Improve test_get_db_session_always_closes to verify close() is called **Documentation:** - Fix connect_with_retry docstring (accurate wait times: 1s, 2s) - Fix __init__.py docstring example (correct import path and User import) **API Design:** - Remove _import_models from public API (__all__) - Sort __all__ alphabetically for maintainability **Code Quality:** - Extract embedding dimension to named constant (EMBEDDING_DIMENSION = 1536) - Use constant in Item model, seed_data.py, and tests - Remove sys.path manipulation from seed_data.py - Remove redundant test (test_seed_data_handles_errors_gracefully) **Testing:** - 73 tests passing (removed 1 redundant test) - All quality checks passing (ruff, pyright) - Seed script verified working Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Summary
Implements production-ready database connection management with connection pooling, retry logic, and health checks, along with an idempotent seed data script for development environments.
Resolves: #11
Parent Epic: EPIC-2 - PostgreSQL Database with pgvector
Changes
Database Connection Module (
app/db/session.py)get_db_session) for safe transaction handlingcheck_database_health)Seed Data Script (
migrations/seed_data.py)Testing
✅ 10 tests for session module covering:
✅ 9 tests for seed data script covering:
✅ 74 total tests passing (19 new + 55 existing)
✅ Transaction isolation working correctly
Dependencies
tenacity>=8.2.3,<9.0.0for retry logic with exponential backoffQuality Checks
Files Changed
Added:
api-service/app/db/session.py(108 lines)api-service/migrations/seed_data.py(142 lines)api-service/tests/db/__init__.pyapi-service/tests/db/test_session.py(112 lines)api-service/tests/test_seed_data.py(142 lines)Modified:
api-service/requirements.txt(added tenacity)api-service/app/db/__init__.py(exported session functions)Usage
Running Seed Data
# From api-service directory python -m migrations.seed_dataUsing Connection Module
Test Plan
Related Issues
🤖 Generated with Claude Code