- Add comprehensive health check system with multiple endpoints - Add Prometheus metrics endpoint - Add production logging configurations (5 strategies) - Add complete deployment documentation suite: * QUICKSTART.md - 30-minute deployment guide * DEPLOYMENT_CHECKLIST.md - Printable verification checklist * DEPLOYMENT_WORKFLOW.md - Complete deployment lifecycle * PRODUCTION_DEPLOYMENT.md - Comprehensive technical reference * production-logging.md - Logging configuration guide * ANSIBLE_DEPLOYMENT.md - Infrastructure as Code automation * README.md - Navigation hub * DEPLOYMENT_SUMMARY.md - Executive summary - Add deployment scripts and automation - Add DEPLOYMENT_PLAN.md - Concrete plan for immediate deployment - Update README with production-ready features All production infrastructure is now complete and ready for deployment.
414 lines
13 KiB
Markdown
414 lines
13 KiB
Markdown
# Database Module Migration Analysis
|
|
|
|
Complete analysis of Database module exception migration requirements.
|
|
|
|
## Module Statistics
|
|
|
|
- **Total PHP Files**: 292
|
|
- **Total Exceptions**: 111 exceptions to analyze
|
|
- RuntimeException: 24 instances
|
|
- InvalidArgumentException: 79 instances
|
|
- DatabaseException: 8 instances (already using framework exception)
|
|
- PDOException: 0 (caught and re-thrown)
|
|
|
|
## Exception Categories
|
|
|
|
### Category 1: PDO/Connection Errors (HIGH PRIORITY)
|
|
**Files**: PdoConnection.php, ConnectionPool.php, DatabaseFactory.php
|
|
**Count**: 8 existing + need SQLSTATE integration
|
|
**Pattern**: Catch PDOException → Re-throw as specific exception
|
|
|
|
**Examples**:
|
|
```php
|
|
// PdoConnection.php:31
|
|
throw DatabaseException::simple("Failed to execute query: {$e->getMessage()}", $e);
|
|
|
|
// ConnectionPool.php:72
|
|
throw DatabaseException::create(...)
|
|
```
|
|
|
|
**Migration Strategy**:
|
|
- Implement SQLSTATE integration FIRST
|
|
- Create QueryExecutionException, ConnectionFailedException, etc.
|
|
- Extract SQLSTATE from PDOException
|
|
- Map to specific DatabaseErrorCode
|
|
|
|
### Category 2: Unsupported Driver/Feature (MEDIUM PRIORITY)
|
|
**Count**: 14 instances
|
|
**Pattern**: `throw new \RuntimeException("Unsupported database driver: {$driver}")`
|
|
|
|
**Files**:
|
|
- QueryHistoryLogger.php:259
|
|
- Schema.php:107, 126, 143, 217
|
|
- SchemaBuilderFactory.php:43
|
|
- DatabasePlatformInitializer.php:28, 29
|
|
- DatabaseOptimizeCommand.php:196
|
|
- MigrationDatabaseManager.php:113
|
|
- StoredProcedureDefinition.php:213
|
|
|
|
**Migration Target**: `UnsupportedDriverException` or `FeatureNotSupportedException`
|
|
|
|
**ErrorCode**: `DatabaseErrorCode::UNSUPPORTED_DRIVER` (new)
|
|
|
|
**Examples**:
|
|
```php
|
|
// Before
|
|
default => throw new \RuntimeException("Unsupported database driver: {$driver}")
|
|
|
|
// After
|
|
default => throw UnsupportedDriverException::forDriver($driver)
|
|
```
|
|
|
|
### Category 3: Invalid Schema/Compiler Arguments (MEDIUM PRIORITY)
|
|
**Count**: 35 instances (mostly InvalidArgumentException)
|
|
**Pattern**: Schema compiler validation, column type validation, index validation
|
|
|
|
**Files**:
|
|
- PostgreSQLSchemaCompiler.php: 7 instances
|
|
- MySQLSchemaCompiler.php: 7 instances
|
|
- SQLiteSchemaCompiler.php: 6 instances
|
|
- Index/AdvancedIndexDefinition.php: 8 instances
|
|
- Index/AdvancedIndexType.php: 4 instances
|
|
|
|
**Decision**: **KEEP as InvalidArgumentException**
|
|
- These are configuration/schema definition errors (developer errors)
|
|
- Not runtime business logic exceptions
|
|
- Similar to constructor validation
|
|
|
|
**Examples to KEEP**:
|
|
```php
|
|
// KEEP - Schema definition validation
|
|
throw new \InvalidArgumentException("Unknown column type: {$column->type}")
|
|
throw new \InvalidArgumentException("FULLTEXT index not supported by {$driver}")
|
|
throw new \InvalidArgumentException('Fill factor must be between 10 and 100')
|
|
```
|
|
|
|
### Category 4: Missing Required Configuration (MEDIUM PRIORITY)
|
|
**Count**: 6 instances
|
|
**Pattern**: Missing required data for operation
|
|
|
|
**Files**:
|
|
- SelectQueryBuilder.php:422, 497, 531
|
|
- SchemaBuilder.php:229
|
|
- StoredProcedureDefinition.php:164, 188, 217
|
|
|
|
**Migration Target**: `InvalidQueryStateException` or `MissingRequirementException`
|
|
|
|
**ErrorCode**: `DatabaseErrorCode::INVALID_STATE` or `MISSING_REQUIREMENT`
|
|
|
|
**Examples**:
|
|
```php
|
|
// SelectQueryBuilder.php:422
|
|
throw new \RuntimeException('FROM clause is required');
|
|
|
|
// After
|
|
throw InvalidQueryStateException::missingFromClause();
|
|
|
|
// SchemaBuilder.php:229
|
|
throw new \RuntimeException("Cannot create table '{$this->tableName}' without columns");
|
|
|
|
// After
|
|
throw InvalidSchemaException::tableWithoutColumns($this->tableName);
|
|
```
|
|
|
|
### Category 5: Missing Dependencies/Configuration (LOW PRIORITY)
|
|
**Count**: 5 instances
|
|
**Pattern**: Logger not configured, entity manager missing, etc.
|
|
|
|
**Files**:
|
|
- DatabaseManager.php:111
|
|
- ProfilingConnection.php:302
|
|
- LazyLoader.php:323, 332
|
|
|
|
**Migration Target**: `MissingDependencyException`
|
|
|
|
**ErrorCode**: `DatabaseErrorCode::DEPENDENCY_MISSING` (new)
|
|
|
|
**Examples**:
|
|
```php
|
|
// DatabaseManager.php:111
|
|
throw new \RuntimeException('Clock is required for database profiling');
|
|
|
|
// After
|
|
throw MissingDependencyException::forComponent('Clock', 'Database profiling');
|
|
```
|
|
|
|
### Category 6: Repository/Query Errors (LOW PRIORITY)
|
|
**Count**: 12 instances (InvalidArgumentException)
|
|
**Pattern**: Validation in repository methods, pagination, profiling
|
|
|
|
**Files**:
|
|
- PaginatedResult.php: 4 instances
|
|
- Restrictions.php: 2 instances
|
|
- QueryProfiler.php: 2 instances
|
|
- SlowQueryDetector.php: 1 instance
|
|
- Various export/format errors
|
|
|
|
**Decision**: **MIXED - Analyze case by case**
|
|
|
|
**Keep (Constructor Validation)**:
|
|
```php
|
|
// PaginatedResult.php:20 - KEEP
|
|
throw new \InvalidArgumentException('Current page must be at least 1');
|
|
```
|
|
|
|
**Migrate (Business Logic)**:
|
|
```php
|
|
// Restrictions.php:159 - MIGRATE
|
|
throw new \InvalidArgumentException('At least one criterion is required');
|
|
// Should be: InvalidCriteriaException::empty()
|
|
```
|
|
|
|
### Category 7: Profiling/Monitoring Errors (LOW PRIORITY)
|
|
**Count**: 8 instances
|
|
**Pattern**: Configuration errors in profiling/monitoring
|
|
|
|
**Files**:
|
|
- ProfilingDashboard.php: 4 instances
|
|
- QueryProfiler.php, QueryLogger.php, SlowQueryDetector.php
|
|
|
|
**Decision**: **KEEP most, MIGRATE connection-not-found**
|
|
|
|
**Migrate**:
|
|
```php
|
|
// ProfilingDashboard.php:91
|
|
throw new \InvalidArgumentException("Connection '$connectionName' not registered");
|
|
// Should be: ConnectionNotFoundException::byName($connectionName)
|
|
```
|
|
|
|
## Recommended Exception Classes
|
|
|
|
### 1. SQLSTATE-Aware Exceptions (HIGH PRIORITY)
|
|
```php
|
|
QueryExecutionException // General query failures with SQLSTATE
|
|
ConnectionFailedException // Connection errors (SQLSTATE 08xxx)
|
|
ConstraintViolationException // Constraint violations (SQLSTATE 23xxx)
|
|
DeadlockException // Deadlocks (SQLSTATE 40001)
|
|
TransactionException // Transaction errors
|
|
```
|
|
|
|
### 2. Configuration/Schema Exceptions (MEDIUM PRIORITY)
|
|
```php
|
|
UnsupportedDriverException // Unsupported database driver
|
|
UnsupportedFeatureException // Feature not supported by driver
|
|
InvalidQueryStateException // Missing FROM clause, etc.
|
|
InvalidSchemaException // Schema definition errors
|
|
MigrationException // Migration-specific errors
|
|
```
|
|
|
|
### 3. Dependency Exceptions (LOW PRIORITY)
|
|
```php
|
|
MissingDependencyException // Missing required components
|
|
ConnectionNotFoundException // Connection not found in pool/registry
|
|
```
|
|
|
|
### 4. Query Builder Exceptions (LOW PRIORITY)
|
|
```php
|
|
InvalidCriteriaException // Criteria/Restrictions errors
|
|
```
|
|
|
|
## Migration Phases
|
|
|
|
### Phase 1: SQLSTATE Foundation (CRITICAL PATH)
|
|
**Time**: 2-3 hours
|
|
**Priority**: HIGH
|
|
|
|
1. Create `SqlState` value object
|
|
2. Create `SqlStateErrorMapper` service
|
|
3. Extend `DatabaseErrorCode` enum with all codes
|
|
4. Write comprehensive tests
|
|
|
|
**Deliverables**:
|
|
- `/src/Framework/Database/ValueObjects/SqlState.php`
|
|
- `/src/Framework/Database/Services/SqlStateErrorMapper.php`
|
|
- `/src/Framework/Exception/Core/DatabaseErrorCode.php` (extended)
|
|
- `/tests/Unit/Framework/Database/SqlStateTest.php`
|
|
|
|
### Phase 2: SQLSTATE Exception Classes (CRITICAL PATH)
|
|
**Time**: 3-4 hours
|
|
**Priority**: HIGH
|
|
|
|
1. Create `QueryExecutionException` with SQLSTATE
|
|
2. Create `ConnectionFailedException` with SQLSTATE
|
|
3. Create `ConstraintViolationException` with SQLSTATE
|
|
4. Create `DeadlockException` with SQLSTATE
|
|
5. Create `TransactionException`
|
|
|
|
**Deliverables**:
|
|
- 5 exception classes in `/src/Framework/Database/Exception/`
|
|
- Factory methods with rich context
|
|
- Integration tests with mock PDOExceptions
|
|
|
|
### Phase 3: Core Connection Migration (CRITICAL PATH)
|
|
**Time**: 2-3 hours
|
|
**Priority**: HIGH
|
|
|
|
1. Update `PdoConnection` with `handlePdoException()`
|
|
2. Update `ConnectionPool` exception handling
|
|
3. Update `DatabaseFactory` connection errors
|
|
4. Integration tests with real database
|
|
|
|
**Files**:
|
|
- `PdoConnection.php` (5 exceptions)
|
|
- `ConnectionPool.php` (3 exceptions)
|
|
- `DatabaseFactory.php`
|
|
|
|
### Phase 4: Configuration Exceptions (MEDIUM PRIORITY)
|
|
**Time**: 2-3 hours
|
|
**Priority**: MEDIUM
|
|
|
|
1. Create `UnsupportedDriverException`
|
|
2. Create `UnsupportedFeatureException`
|
|
3. Create `InvalidQueryStateException`
|
|
4. Create `InvalidSchemaException`
|
|
5. Migrate 14 unsupported driver errors
|
|
6. Migrate 6 missing requirement errors
|
|
|
|
**Files**:
|
|
- Schema.php, SchemaBuilderFactory.php, etc. (14 files)
|
|
- SelectQueryBuilder.php, SchemaBuilder.php, etc. (6 files)
|
|
|
|
### Phase 5: Dependency Exceptions (LOW PRIORITY)
|
|
**Time**: 1-2 hours
|
|
**Priority**: LOW
|
|
|
|
1. Create `MissingDependencyException`
|
|
2. Create `ConnectionNotFoundException`
|
|
3. Migrate 5 missing dependency errors
|
|
4. Migrate 4 connection-not-found errors
|
|
|
|
**Files**:
|
|
- DatabaseManager.php, ProfilingConnection.php, LazyLoader.php
|
|
- ProfilingDashboard.php
|
|
|
|
### Phase 6: Query Builder Exceptions (LOW PRIORITY)
|
|
**Time**: 1 hour
|
|
**Priority**: LOW
|
|
|
|
1. Create `InvalidCriteriaException`
|
|
2. Migrate Restrictions.php errors (2 instances)
|
|
|
|
## Total Effort Estimate
|
|
|
|
**High Priority (Phases 1-3)**: 7-10 hours
|
|
- SQLSTATE Foundation: 2-3h
|
|
- SQLSTATE Exceptions: 3-4h
|
|
- Core Connection Migration: 2-3h
|
|
|
|
**Medium Priority (Phase 4)**: 2-3 hours
|
|
**Low Priority (Phases 5-6)**: 2-3 hours
|
|
|
|
**Total**: 11-16 hours
|
|
|
|
## Success Criteria
|
|
|
|
### Must Have (Phase 1-3)
|
|
- [x] SQLSTATE integration complete
|
|
- [x] All PDOException catches handled
|
|
- [x] Connection errors user-friendly
|
|
- [x] Constraint violations descriptive
|
|
- [x] Deadlocks with automatic retry
|
|
- [x] Integration tests passing
|
|
|
|
### Should Have (Phase 4)
|
|
- [ ] Unsupported driver errors clear
|
|
- [ ] Query state errors descriptive
|
|
- [ ] Schema errors actionable
|
|
|
|
### Nice to Have (Phase 5-6)
|
|
- [ ] All dependency errors migrated
|
|
- [ ] Query builder exceptions complete
|
|
|
|
## Risk Assessment
|
|
|
|
**High Risk**:
|
|
- SQLSTATE mapping completeness - Mitigate: Comprehensive test coverage
|
|
- Breaking changes to existing code - Mitigate: Maintain backward compatibility via DatabaseException::simple()
|
|
- Performance impact - Mitigate: Benchmark critical paths
|
|
|
|
**Medium Risk**:
|
|
- Test database setup complexity - Mitigate: Use SQLite for tests
|
|
- Migration effort underestimation - Mitigate: Phased approach
|
|
|
|
**Low Risk**:
|
|
- Documentation completeness - Mitigate: Update docs incrementally
|
|
|
|
## Decision Matrix
|
|
|
|
### What to Migrate
|
|
|
|
**YES - Migrate to specific exceptions**:
|
|
- ✅ PDOException catches → SQLSTATE-aware exceptions
|
|
- ✅ Unsupported driver errors → UnsupportedDriverException
|
|
- ✅ Missing FROM clause → InvalidQueryStateException
|
|
- ✅ Connection not found → ConnectionNotFoundException
|
|
- ✅ Missing dependencies (Clock, etc.) → MissingDependencyException
|
|
- ✅ Empty criteria → InvalidCriteriaException
|
|
|
|
**NO - Keep as InvalidArgumentException**:
|
|
- ❌ Constructor parameter validation
|
|
- ❌ Schema compiler column type validation
|
|
- ❌ Index type validation
|
|
- ❌ Fill factor range validation
|
|
- ❌ Page number validation (PaginatedResult constructor)
|
|
- ❌ Export format validation (in __construct or similar)
|
|
|
|
**MAYBE - Analyze context**:
|
|
- ⚠️ Profile ID not found → Consider ProfileNotFoundException
|
|
- ⚠️ Slow query threshold validation → Keep as InvalidArgumentException
|
|
|
|
## Files Requiring Changes
|
|
|
|
### Critical Path (Phase 1-3) - 8 files
|
|
```
|
|
src/Framework/Database/PdoConnection.php
|
|
src/Framework/Database/ConnectionPool.php
|
|
src/Framework/Database/DatabaseFactory.php
|
|
src/Framework/Database/Middleware/RetryMiddleware.php
|
|
src/Framework/Database/ValueObjects/SqlState.php (NEW)
|
|
src/Framework/Database/Services/SqlStateErrorMapper.php (NEW)
|
|
src/Framework/Database/Exception/QueryExecutionException.php (NEW)
|
|
src/Framework/Database/Exception/ConnectionFailedException.php (NEW)
|
|
src/Framework/Database/Exception/ConstraintViolationException.php (NEW)
|
|
src/Framework/Database/Exception/DeadlockException.php (NEW)
|
|
src/Framework/Database/Exception/TransactionException.php (NEW)
|
|
src/Framework/Exception/Core/DatabaseErrorCode.php (EXTEND)
|
|
```
|
|
|
|
### Medium Priority (Phase 4) - 20 files
|
|
```
|
|
src/Framework/Database/Schema/Schema.php
|
|
src/Framework/Database/Platform/SchemaBuilderFactory.php
|
|
src/Framework/Database/Platform/DatabasePlatformInitializer.php
|
|
src/Framework/Database/QueryBuilder/SelectQueryBuilder.php
|
|
src/Framework/Database/Schema/SchemaBuilder.php
|
|
src/Framework/Database/StoredProcedure/StoredProcedureDefinition.php
|
|
... (14 more schema/driver files)
|
|
```
|
|
|
|
### Low Priority (Phase 5-6) - 10 files
|
|
```
|
|
src/Framework/Database/DatabaseManager.php
|
|
src/Framework/Database/Profiling/ProfilingConnection.php
|
|
src/Framework/Database/LazyLoader.php
|
|
src/Framework/Database/Profiling/ProfilingDashboard.php
|
|
src/Framework/Database/Criteria/Restrictions.php
|
|
... (5 more profiling/query files)
|
|
```
|
|
|
|
## Next Steps
|
|
|
|
1. **Start with Phase 1**: SQLSTATE Foundation
|
|
2. **Validate design** with tests before Phase 2
|
|
3. **Incremental migration**: Complete one phase before next
|
|
4. **Test coverage**: ≥80% for new exception classes
|
|
5. **Documentation**: Update database-patterns.md incrementally
|
|
|
|
## Questions to Resolve
|
|
|
|
1. Should `ProfileNotFoundException` be created or keep as InvalidArgumentException?
|
|
2. Should migration-specific errors get their own exception class or reuse InvalidSchemaException?
|
|
3. Should export format errors be migrated or kept as InvalidArgumentException?
|
|
|
|
**Recommendation**: Start simple, migrate obvious cases first, defer edge cases to later phases.
|