mirror of
https://github.com/torrentpier/torrentpier
synced 2025-08-22 06:13:58 -07:00
feat(architecture): implement hexagonal architecture foundation with DDD structure (#1991)
* feat(architecture): implement hexagonal architecture foundation with DDD structure - Add comprehensive hexagonal architecture directory structure for TorrentPier 3.0 - Create Domain, Application, Infrastructure, and Presentation layers - Establish bounded contexts for Forum, Tracker, and User domains - Add detailed README.md files for each layer and subdirectory with implementation guidance - Include hexagonal architecture specification document with migration strategy - Update composer dependencies to support new architecture - Set up foundation for CQRS, event-driven design, and clean separation of concerns This establishes the structural foundation for migrating TorrentPier to Domain-Driven Design principles using ports and adapters pattern. Future features will be built using this architecture while existing code remains functional during gradual migration. BREAKING CHANGE: New directory structure changes development workflow for new features * docs: update README files across layers to enhance clarity and consistency - Added detailed guidelines for Markdown file formatting in CLAUDE.md. - Improved README files in the Application, Domain, and Infrastructure layers to include additional context and examples. - Ensured all README files follow a consistent structure and style for better readability. - Updated documentation for Forum, Tracker, and User domains to reflect recent architectural changes. These updates aim to provide clearer guidance for developers and maintainers, aligning with the project's focus on modern architecture and clean code practices.
This commit is contained in:
parent
3637325c53
commit
39bc5977e3
50 changed files with 1118 additions and 0 deletions
20
CLAUDE.md
20
CLAUDE.md
|
@ -137,3 +137,23 @@ The TorrentPier 3.0 release represents a major architectural shift focused on:
|
|||
- **Language system**: Update global $lang usage to new Language singleton methods
|
||||
|
||||
When working with this codebase, prioritize modern architecture patterns and clean code practices. Focus on the new systems in `/src/` directory rather than maintaining legacy compatibility.
|
||||
|
||||
## Markdown File Guidelines
|
||||
|
||||
When creating or editing `.md` files in this project, follow these linting rules:
|
||||
|
||||
### MD032 - Lists surrounded by blank lines
|
||||
Always add blank lines before and after lists:
|
||||
|
||||
```markdown
|
||||
Some text here.
|
||||
|
||||
- First item
|
||||
- Second item
|
||||
- Third item
|
||||
|
||||
More text here.
|
||||
```
|
||||
|
||||
### MD047 - Files should end with a single newline
|
||||
Ensure every markdown file ends with exactly one newline character at the end of the file.
|
||||
|
|
53
config/README.md
Normal file
53
config/README.md
Normal file
|
@ -0,0 +1,53 @@
|
|||
# Application Configuration
|
||||
|
||||
System configuration files using PHP arrays for type safety and IDE support:
|
||||
|
||||
- **app.php**: Core application settings
|
||||
- Site name, URL, timezone
|
||||
- Debug mode, environment
|
||||
- Feature flags and toggles
|
||||
|
||||
- **database.php**: Database connection settings
|
||||
- Multiple connection definitions
|
||||
- Read/write splitting configuration
|
||||
- Connection pooling settings
|
||||
|
||||
- **cache.php**: Cache driver configurations
|
||||
- Redis, Memcached, file-based settings
|
||||
- TTL defaults per cache type
|
||||
- Cache key prefixes
|
||||
|
||||
- **tracker.php**: BitTorrent tracker settings
|
||||
- Announce intervals
|
||||
- Peer limits
|
||||
- Ratio requirements
|
||||
|
||||
- **environments/**: Environment-specific overrides
|
||||
- Development, staging, production settings
|
||||
- Local developer configurations
|
||||
|
||||
Example database configuration:
|
||||
```php
|
||||
<?php
|
||||
return [
|
||||
'default' => env('DB_CONNECTION', 'mysql'),
|
||||
|
||||
'connections' => [
|
||||
'mysql' => [
|
||||
'driver' => 'mysql',
|
||||
'host' => env('DB_HOST', '127.0.0.1'),
|
||||
'port' => env('DB_PORT', 3306),
|
||||
'database' => env('DB_DATABASE', 'tp'),
|
||||
'username' => env('DB_USERNAME', 'root'),
|
||||
'password' => env('DB_PASSWORD', ''),
|
||||
'charset' => 'utf8mb4',
|
||||
'collation' => 'utf8mb4_unicode_ci',
|
||||
'options' => [
|
||||
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
|
||||
PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
|
||||
PDO::ATTR_EMULATE_PREPARES => false,
|
||||
],
|
||||
],
|
||||
],
|
||||
];
|
||||
```
|
436
docs/specs/hexagonal-architecture-spec.md
Normal file
436
docs/specs/hexagonal-architecture-spec.md
Normal file
|
@ -0,0 +1,436 @@
|
|||
# Hexagonal Architecture Directory Structure Specification
|
||||
|
||||
## Overview
|
||||
|
||||
This document specifies the new hexagonal architecture directory structure for TorrentPier 3.0. The structure follows Domain-Driven Design (DDD) principles and implements a clean separation of concerns through hexagonal architecture (ports and adapters pattern).
|
||||
|
||||
## Directory Structure
|
||||
|
||||
```
|
||||
/src/
|
||||
├── Domain/ # Core business logic - no framework dependencies
|
||||
│ ├── Forum/ # Forum bounded context
|
||||
│ │ ├── Model/ # Aggregates and entities
|
||||
│ │ ├── ValueObject/ # Value objects (PostId, ThreadTitle, etc.)
|
||||
│ │ ├── Repository/ # Repository interfaces
|
||||
│ │ └── Exception/ # Domain-specific exceptions
|
||||
│ ├── Tracker/ # BitTorrent tracker bounded context
|
||||
│ │ ├── Model/ # Torrent, Peer aggregates
|
||||
│ │ ├── ValueObject/ # InfoHash, PeerId, etc.
|
||||
│ │ ├── Repository/ # Repository interfaces
|
||||
│ │ └── Exception/ # Tracker-specific exceptions
|
||||
│ ├── User/ # User management bounded context
|
||||
│ │ ├── Model/ # User aggregate
|
||||
│ │ ├── ValueObject/ # UserId, Email, Username
|
||||
│ │ ├── Repository/ # User repository interface
|
||||
│ │ └── Exception/ # Authentication/authorization exceptions
|
||||
│ └── Shared/ # Shared kernel - minimal shared concepts
|
||||
│ ├── Model/ # Base classes (AggregateRoot, Entity)
|
||||
│ ├── ValueObject/ # Common value objects (Id, DateTime)
|
||||
│ └── Event/ # Domain events base classes
|
||||
│
|
||||
├── Application/ # Application services - orchestration layer
|
||||
│ ├── Forum/
|
||||
│ │ ├── Command/ # Commands (CreatePost, LockThread)
|
||||
│ │ ├── Query/ # Queries (GetThreadList, SearchPosts)
|
||||
│ │ └── Handler/ # Command and query handlers
|
||||
│ ├── Tracker/
|
||||
│ │ ├── Command/ # Commands (RegisterTorrent, ProcessAnnounce)
|
||||
│ │ ├── Query/ # Queries (GetPeerList, GetTorrentStats)
|
||||
│ │ └── Handler/ # Command and query handlers
|
||||
│ └── User/
|
||||
│ ├── Command/ # Commands (RegisterUser, ChangePassword)
|
||||
│ ├── Query/ # Queries (GetUserProfile, SearchUsers)
|
||||
│ └── Handler/ # Command and query handlers
|
||||
│
|
||||
├── Infrastructure/ # External concerns and implementations
|
||||
│ ├── Persistence/ # Data persistence layer
|
||||
│ │ ├── Database/ # Database adapter and connection management
|
||||
│ │ ├── Migration/ # Database migrations
|
||||
│ │ └── Repository/ # Repository implementations
|
||||
│ ├── Cache/ # Caching implementations
|
||||
│ │ ├── Redis/ # Redis adapter
|
||||
│ │ ├── Memcached/ # Memcached adapter
|
||||
│ │ └── File/ # File-based cache adapter
|
||||
│ ├── Email/ # Email service implementations
|
||||
│ │ ├── Template/ # Email templates
|
||||
│ │ └── Transport/ # SMTP, API transports
|
||||
│ └── FileStorage/ # File storage abstractions
|
||||
│ ├── Local/ # Local filesystem storage
|
||||
│ └── S3/ # AWS S3 storage adapter
|
||||
│
|
||||
└── Presentation/ # User interface layer
|
||||
├── Http/ # Web interface
|
||||
│ ├── Controllers/ # HTTP controllers
|
||||
│ │ ├── Admin/ # Admin panel controllers
|
||||
│ │ ├── Api/ # REST API controllers
|
||||
│ │ └── Web/ # Web UI controllers
|
||||
│ ├── Middleware/ # HTTP middleware (auth, CORS, etc.)
|
||||
│ ├── Requests/ # Request DTOs and validation
|
||||
│ └── Responses/ # Response transformers
|
||||
└── Cli/ # Command line interface
|
||||
└── Commands/ # Console commands
|
||||
|
||||
# Additional directories (outside /src/)
|
||||
/config/ # Application configuration
|
||||
├── app.php # Main application settings
|
||||
├── database.php # Database connections
|
||||
├── cache.php # Cache drivers configuration
|
||||
├── tracker.php # BitTorrent tracker settings
|
||||
└── environments/ # Environment-specific overrides
|
||||
|
||||
/tests/ # Test suites (Pest)
|
||||
├── Unit/ # Unit tests (mirrors src/ structure)
|
||||
├── Feature/ # Feature/Integration tests
|
||||
├── Pest.php # Pest configuration
|
||||
└── TestCase.php # Base test case
|
||||
```
|
||||
|
||||
## Directory README.md Templates
|
||||
|
||||
### Domain Layer READMEs
|
||||
|
||||
#### `/src/Domain/README.md`
|
||||
```markdown
|
||||
# Domain Layer
|
||||
|
||||
This directory contains the core business logic of TorrentPier. Code here should:
|
||||
- Have no dependencies on frameworks or infrastructure
|
||||
- Represent pure business rules and domain models
|
||||
- Be testable in isolation
|
||||
- Use only PHP language features and domain concepts
|
||||
|
||||
## Bounded Contexts
|
||||
- **Forum**: Discussion forums, posts, threads
|
||||
- **Tracker**: BitTorrent tracking, peers, torrents
|
||||
- **User**: User management, authentication, profiles
|
||||
- **Shared**: Minimal shared concepts between contexts
|
||||
```
|
||||
|
||||
#### `/src/Domain/Tracker/Model/README.md`
|
||||
```markdown
|
||||
# Tracker Domain Models
|
||||
|
||||
Contains aggregate roots and entities for the BitTorrent tracker:
|
||||
- `Torrent`: Aggregate root for torrent management
|
||||
- `Peer`: Entity representing a BitTorrent peer
|
||||
- `TorrentStatistics`: Value object for torrent stats
|
||||
|
||||
Example:
|
||||
```php
|
||||
class Torrent extends AggregateRoot
|
||||
{
|
||||
public function announce(Peer $peer, AnnounceEvent $event): void
|
||||
{
|
||||
// Business logic for handling announces
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### `/src/Domain/Tracker/ValueObject/README.md`
|
||||
```markdown
|
||||
# Tracker Value Objects
|
||||
|
||||
Immutable objects representing domain concepts:
|
||||
- `InfoHash`: 20-byte torrent identifier
|
||||
- `PeerId`: Peer client identifier
|
||||
- `Port`: Network port (1-65535)
|
||||
- `BytesTransferred`: Upload/download bytes
|
||||
|
||||
Example:
|
||||
```php
|
||||
final class InfoHash
|
||||
{
|
||||
private string $hash;
|
||||
|
||||
public function __construct(string $hash)
|
||||
{
|
||||
$this->guardAgainstInvalidHash($hash);
|
||||
$this->hash = $hash;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Application Layer READMEs
|
||||
|
||||
#### `/src/Application/README.md`
|
||||
```markdown
|
||||
# Application Layer
|
||||
|
||||
Contains application services that orchestrate domain objects to fulfill use cases.
|
||||
- Commands: Write operations that change state
|
||||
- Queries: Read operations for data retrieval
|
||||
- Handlers: Process commands and queries
|
||||
|
||||
This layer should:
|
||||
- Coordinate domain objects
|
||||
- Handle transactions
|
||||
- Dispatch domain events
|
||||
- Not contain business logic
|
||||
```
|
||||
|
||||
#### `/src/Application/Tracker/Command/README.md`
|
||||
```markdown
|
||||
# Tracker Commands
|
||||
|
||||
Commands representing write operations:
|
||||
- `RegisterTorrentCommand`: Register new torrent
|
||||
- `UpdateTorrentCommand`: Modify torrent details
|
||||
- `DeleteTorrentCommand`: Remove torrent from tracker
|
||||
|
||||
Example:
|
||||
```php
|
||||
final class RegisterTorrentCommand
|
||||
{
|
||||
public function __construct(
|
||||
public readonly string $infoHash,
|
||||
public readonly int $uploaderId,
|
||||
public readonly string $name,
|
||||
public readonly int $size
|
||||
) {}
|
||||
}
|
||||
```
|
||||
|
||||
### Infrastructure Layer READMEs
|
||||
|
||||
#### `/src/Infrastructure/README.md`
|
||||
```markdown
|
||||
# Infrastructure Layer
|
||||
|
||||
Technical implementations and external service adapters:
|
||||
- Database persistence
|
||||
- Caching mechanisms
|
||||
- Email services
|
||||
- File storage
|
||||
- Third-party integrations
|
||||
|
||||
Infrastructure depends on domain, not vice versa.
|
||||
```
|
||||
|
||||
#### `/src/Infrastructure/Persistence/Repository/README.md`
|
||||
```markdown
|
||||
# Repository Implementations
|
||||
|
||||
Concrete implementations of domain repository interfaces:
|
||||
- Uses database adapter for persistence
|
||||
- Implements caching strategies
|
||||
- Handles query optimization
|
||||
- Supports multiple database backends
|
||||
|
||||
Example:
|
||||
```php
|
||||
class TorrentRepository implements TorrentRepositoryInterface
|
||||
{
|
||||
public function __construct(
|
||||
private DatabaseAdapterInterface $db
|
||||
) {}
|
||||
|
||||
public function findByInfoHash(InfoHash $infoHash): ?Torrent
|
||||
{
|
||||
// Database adapter implementation
|
||||
$row = $this->db->select('torrents')
|
||||
->where('info_hash', $infoHash->toString())
|
||||
->first();
|
||||
|
||||
return $row ? $this->hydrateFromRow($row) : null;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Presentation Layer READMEs
|
||||
|
||||
#### `/src/Presentation/README.md`
|
||||
```markdown
|
||||
# Presentation Layer
|
||||
|
||||
User interface implementations:
|
||||
- HTTP controllers for web and API
|
||||
- CLI commands for console operations
|
||||
- Request/response handling
|
||||
- Input validation
|
||||
- Output formatting
|
||||
|
||||
This layer translates between external format and application format.
|
||||
```
|
||||
|
||||
#### `/src/Presentation/Http/Controllers/Api/README.md`
|
||||
```markdown
|
||||
# API Controllers
|
||||
|
||||
RESTful API endpoints following OpenAPI specification:
|
||||
- JSON request/response format
|
||||
- Proper HTTP status codes
|
||||
- HATEOAS where applicable
|
||||
- Rate limiting aware
|
||||
|
||||
Example:
|
||||
```php
|
||||
class UserController
|
||||
{
|
||||
public function register(RegisterRequest $request): JsonResponse
|
||||
{
|
||||
$command = new RegisterUserCommand(
|
||||
$request->getUsername(),
|
||||
$request->getEmail(),
|
||||
$request->getPassword()
|
||||
);
|
||||
|
||||
$userId = $this->commandBus->handle($command);
|
||||
|
||||
return new JsonResponse([
|
||||
'id' => $userId,
|
||||
'username' => $request->getUsername()
|
||||
], Response::HTTP_CREATED);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### `/src/Presentation/Http/Controllers/Admin/README.md`
|
||||
```markdown
|
||||
# Admin Panel Controllers
|
||||
|
||||
Administrative interface controllers with enhanced security:
|
||||
- Role-based access control (RBAC)
|
||||
- Audit logging for all actions
|
||||
- Additional authentication checks
|
||||
- Administrative dashboards and reports
|
||||
|
||||
Example:
|
||||
```php
|
||||
class AdminUserController
|
||||
{
|
||||
public function index(Request $request): Response
|
||||
{
|
||||
$query = new GetUsersQuery(
|
||||
page: $request->getPage(),
|
||||
filters: $request->getFilters()
|
||||
);
|
||||
|
||||
$users = $this->queryBus->handle($query);
|
||||
|
||||
return $this->render('admin/users/index', [
|
||||
'users' => $users,
|
||||
'filters' => $request->getFilters()
|
||||
]);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### `/config/README.md`
|
||||
```markdown
|
||||
# Application Configuration
|
||||
|
||||
System configuration files using PHP arrays for type safety and IDE support:
|
||||
|
||||
- **app.php**: Core application settings
|
||||
- Site name, URL, timezone
|
||||
- Debug mode, environment
|
||||
- Feature flags and toggles
|
||||
|
||||
- **database.php**: Database connection settings
|
||||
- Multiple connection definitions
|
||||
- Read/write splitting configuration
|
||||
- Connection pooling settings
|
||||
|
||||
- **cache.php**: Cache driver configurations
|
||||
- Redis, Memcached, file-based settings
|
||||
- TTL defaults per cache type
|
||||
- Cache key prefixes
|
||||
|
||||
- **tracker.php**: BitTorrent tracker settings
|
||||
- Announce intervals
|
||||
- Peer limits
|
||||
- Ratio requirements
|
||||
|
||||
- **environments/**: Environment-specific overrides
|
||||
- Development, staging, production settings
|
||||
- Local developer configurations
|
||||
|
||||
Example database configuration:
|
||||
```php
|
||||
<?php
|
||||
return [
|
||||
'default' => env('DB_CONNECTION', 'mysql'),
|
||||
|
||||
'connections' => [
|
||||
'mysql' => [
|
||||
'driver' => 'mysql',
|
||||
'host' => env('DB_HOST', '127.0.0.1'),
|
||||
'port' => env('DB_PORT', 3306),
|
||||
'database' => env('DB_DATABASE', 'tp'),
|
||||
'username' => env('DB_USERNAME', 'root'),
|
||||
'password' => env('DB_PASSWORD', ''),
|
||||
'charset' => 'utf8mb4',
|
||||
'collation' => 'utf8mb4_unicode_ci',
|
||||
'options' => [
|
||||
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
|
||||
PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
|
||||
PDO::ATTR_EMULATE_PREPARES => false,
|
||||
],
|
||||
],
|
||||
],
|
||||
];
|
||||
```
|
||||
|
||||
## Implementation Order
|
||||
|
||||
1. **Phase 1: Foundation**
|
||||
|
||||
- Create directory structure
|
||||
- Set up base classes in Domain/Shared
|
||||
- Configure dependency injection
|
||||
|
||||
2. **Phase 2: Domain Modeling**
|
||||
|
||||
- Implement core aggregates
|
||||
- Create value objects
|
||||
- Define repository interfaces
|
||||
|
||||
3. **Phase 3: Application Services**
|
||||
|
||||
- Create commands and queries
|
||||
- Implement handlers
|
||||
- Set up event dispatching
|
||||
|
||||
4. **Phase 4: Infrastructure**
|
||||
|
||||
- Implement repositories
|
||||
- Configure database adapter
|
||||
- Set up caching
|
||||
|
||||
5. **Phase 5: Presentation**
|
||||
|
||||
- Create controllers
|
||||
- Implement middleware
|
||||
- Build CLI commands
|
||||
|
||||
## Migration Strategy
|
||||
|
||||
- Existing code remains in current locations
|
||||
- New features built in hexagonal architecture
|
||||
- Gradual migration using strangler fig pattern
|
||||
- Legacy adapters bridge old and new code
|
||||
- Feature flags control rollout
|
||||
|
||||
## Key Principles
|
||||
|
||||
1. **Dependency Rule**: Dependencies point inward (Presentation → Application → Domain)
|
||||
2. **Domain Isolation**: Business logic has no framework dependencies
|
||||
3. **Interface Segregation**: Small, focused interfaces
|
||||
4. **CQRS**: Separate read and write models
|
||||
5. **Event-Driven**: Domain events for cross-context communication
|
||||
|
||||
## Testing Strategy
|
||||
|
||||
- **Domain**: Pure unit tests, no mocks needed
|
||||
- **Application**: Unit tests with mocked repositories
|
||||
- **Infrastructure**: Integration tests with real services
|
||||
- **Presentation**: E2E tests for user journeys
|
||||
|
||||
## Notes for Developers
|
||||
|
||||
- Start reading code from the Domain layer
|
||||
- Business rules live in aggregates, not services
|
||||
- Use value objects for type safety
|
||||
- Prefer composition over inheritance
|
||||
- Keep bounded contexts loosely coupled
|
11
src/Application/Forum/Command/README.md
Normal file
11
src/Application/Forum/Command/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# Forum Commands
|
||||
|
||||
Commands representing write operations:
|
||||
|
||||
- `CreateThreadCommand`: Start new discussion
|
||||
- `CreatePostCommand`: Reply to thread
|
||||
- `EditPostCommand`: Modify existing post
|
||||
- `LockThreadCommand`: Lock thread from replies
|
||||
- `DeletePostCommand`: Remove post
|
||||
|
||||
Commands are simple DTOs containing operation data.
|
9
src/Application/Forum/Handler/README.md
Normal file
9
src/Application/Forum/Handler/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Forum Handlers
|
||||
|
||||
Command and query handlers for forum operations:
|
||||
|
||||
- `CreateThreadHandler`: Handles thread creation
|
||||
- `CreatePostHandler`: Handles post creation
|
||||
- `GetThreadListHandler`: Retrieves thread listings
|
||||
|
||||
Handlers coordinate between domain and infrastructure layers.
|
10
src/Application/Forum/Query/README.md
Normal file
10
src/Application/Forum/Query/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Forum Queries
|
||||
|
||||
Read-only queries for forum data:
|
||||
|
||||
- `GetThreadListQuery`: Paginated thread listing
|
||||
- `GetPostsByThreadQuery`: Thread posts with pagination
|
||||
- `SearchPostsQuery`: Full-text post search
|
||||
- `GetForumStatsQuery`: Forum statistics
|
||||
|
||||
Queries return DTOs optimized for presentation.
|
14
src/Application/README.md
Normal file
14
src/Application/README.md
Normal file
|
@ -0,0 +1,14 @@
|
|||
# Application Layer
|
||||
|
||||
Contains application services that orchestrate domain objects to fulfill use cases.
|
||||
|
||||
- Commands: Write operations that change state
|
||||
- Queries: Read operations for data retrieval
|
||||
- Handlers: Process commands and queries
|
||||
|
||||
This layer should:
|
||||
|
||||
- Coordinate domain objects
|
||||
- Handle transactions
|
||||
- Dispatch domain events
|
||||
- Not contain business logic
|
21
src/Application/Tracker/Command/README.md
Normal file
21
src/Application/Tracker/Command/README.md
Normal file
|
@ -0,0 +1,21 @@
|
|||
# Tracker Commands
|
||||
|
||||
Commands representing write operations:
|
||||
|
||||
- `RegisterTorrentCommand`: Register new torrent
|
||||
- `UpdateTorrentCommand`: Modify torrent details
|
||||
- `DeleteTorrentCommand`: Remove torrent from tracker
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
final class RegisterTorrentCommand
|
||||
{
|
||||
public function __construct(
|
||||
public readonly string $infoHash,
|
||||
public readonly int $uploaderId,
|
||||
public readonly string $name,
|
||||
public readonly int $size
|
||||
) {}
|
||||
}
|
||||
```
|
9
src/Application/Tracker/Handler/README.md
Normal file
9
src/Application/Tracker/Handler/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Tracker Handlers
|
||||
|
||||
Command and query handlers for tracker operations:
|
||||
|
||||
- `RegisterTorrentHandler`: Processes torrent registration
|
||||
- `GetTorrentDetailsHandler`: Retrieves torrent information
|
||||
- `UpdateTorrentHandler`: Handles torrent updates
|
||||
|
||||
Note: High-performance announce operations bypass this layer.
|
10
src/Application/Tracker/Query/README.md
Normal file
10
src/Application/Tracker/Query/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Tracker Queries
|
||||
|
||||
Read-only queries for tracker data:
|
||||
|
||||
- `GetTorrentDetailsQuery`: Single torrent information
|
||||
- `GetPeerListQuery`: Active peers for torrent
|
||||
- `GetTorrentStatsQuery`: Download/upload statistics
|
||||
- `SearchTorrentsQuery`: Browse and filter torrents
|
||||
|
||||
Optimized for high-performance read operations.
|
11
src/Application/User/Command/README.md
Normal file
11
src/Application/User/Command/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# User Commands
|
||||
|
||||
Commands for user management operations:
|
||||
|
||||
- `RegisterUserCommand`: New user registration
|
||||
- `ChangePasswordCommand`: Password update
|
||||
- `UpdateProfileCommand`: Profile modifications
|
||||
- `ActivateUserCommand`: Account activation
|
||||
- `BanUserCommand`: User suspension
|
||||
|
||||
These commands trigger domain events for cross-context synchronization.
|
9
src/Application/User/Handler/README.md
Normal file
9
src/Application/User/Handler/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# User Handlers
|
||||
|
||||
Command and query handlers for user operations:
|
||||
|
||||
- `RegisterUserHandler`: Processes user registration
|
||||
- `ChangePasswordHandler`: Handles password changes
|
||||
- `GetUserProfileHandler`: Retrieves user profiles
|
||||
|
||||
Handlers manage transactions and event dispatching.
|
10
src/Application/User/Query/README.md
Normal file
10
src/Application/User/Query/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# User Queries
|
||||
|
||||
Read operations for user data:
|
||||
|
||||
- `GetUserProfileQuery`: User profile details
|
||||
- `SearchUsersQuery`: User search with filters
|
||||
- `GetUserStatisticsQuery`: Upload/download stats
|
||||
- `GetUserPermissionsQuery`: Authorization data
|
||||
|
||||
Returns DTOs suitable for presentation layer.
|
8
src/Domain/Forum/Exception/README.md
Normal file
8
src/Domain/Forum/Exception/README.md
Normal file
|
@ -0,0 +1,8 @@
|
|||
# Forum Domain Exceptions
|
||||
|
||||
Domain-specific exceptions for forum operations:
|
||||
|
||||
- `ThreadLockedException`: Attempt to post in locked thread
|
||||
- `PostEditTimeExpiredException`: Edit time limit exceeded
|
||||
- `ForumAccessDeniedException`: Insufficient permissions
|
||||
- `InvalidPostContentException`: Post validation failed
|
15
src/Domain/Forum/Model/README.md
Normal file
15
src/Domain/Forum/Model/README.md
Normal file
|
@ -0,0 +1,15 @@
|
|||
# Forum Domain Models
|
||||
|
||||
Contains aggregate roots and entities for the forum system:
|
||||
|
||||
- `Forum`: Forum category aggregate
|
||||
- `Thread`: Discussion thread aggregate root
|
||||
- `Post`: Individual post entity
|
||||
- `Attachment`: File attachment entity
|
||||
|
||||
Business rules enforced at this level:
|
||||
|
||||
- Post editing time limits
|
||||
- Thread locking rules
|
||||
- Forum access permissions
|
||||
- Post moderation workflow
|
9
src/Domain/Forum/Repository/README.md
Normal file
9
src/Domain/Forum/Repository/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Forum Repository Interfaces
|
||||
|
||||
Repository interfaces for forum aggregates:
|
||||
|
||||
- `ForumRepositoryInterface`: Forum aggregate persistence
|
||||
- `ThreadRepositoryInterface`: Thread aggregate persistence
|
||||
- `PostRepositoryInterface`: Post queries (read-only)
|
||||
|
||||
These interfaces define contracts that infrastructure must implement.
|
10
src/Domain/Forum/ValueObject/README.md
Normal file
10
src/Domain/Forum/ValueObject/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Forum Value Objects
|
||||
|
||||
Immutable objects representing forum concepts:
|
||||
|
||||
- `PostId`: Unique post identifier
|
||||
- `ThreadTitle`: Thread title with validation
|
||||
- `PostContent`: Formatted post content
|
||||
- `ForumSlug`: URL-friendly forum identifier
|
||||
|
||||
These objects ensure type safety and encapsulate validation rules.
|
15
src/Domain/README.md
Normal file
15
src/Domain/README.md
Normal file
|
@ -0,0 +1,15 @@
|
|||
# Domain Layer
|
||||
|
||||
This directory contains the core business logic of TorrentPier. Code here should:
|
||||
|
||||
- Have no dependencies on frameworks or infrastructure
|
||||
- Represent pure business rules and domain models
|
||||
- Be testable in isolation
|
||||
- Use only PHP language features and domain concepts
|
||||
|
||||
## Bounded Contexts
|
||||
|
||||
- **Forum**: Discussion forums, posts, threads
|
||||
- **Tracker**: BitTorrent tracking, peers, torrents
|
||||
- **User**: User management, authentication, profiles
|
||||
- **Shared**: Minimal shared concepts between contexts
|
15
src/Domain/Shared/Event/README.md
Normal file
15
src/Domain/Shared/Event/README.md
Normal file
|
@ -0,0 +1,15 @@
|
|||
# Domain Events
|
||||
|
||||
Base classes and interfaces for domain event system:
|
||||
|
||||
- `DomainEvent`: Base event interface
|
||||
- `EventRecording`: Trait for aggregate event recording
|
||||
- `AggregateHistory`: Event sourcing support
|
||||
|
||||
Example events:
|
||||
|
||||
- `UserRegisteredEvent`
|
||||
- `TorrentUploadedEvent`
|
||||
- `ThreadCreatedEvent`
|
||||
|
||||
Events enable loose coupling between bounded contexts.
|
10
src/Domain/Shared/Exception/README.md
Normal file
10
src/Domain/Shared/Exception/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Shared Domain Exceptions
|
||||
|
||||
Base exception classes used across all bounded contexts:
|
||||
|
||||
- `DomainException`: Base domain exception
|
||||
- `InvalidArgumentException`: Invalid input validation
|
||||
- `EntityNotFoundException`: Generic entity not found
|
||||
- `BusinessRuleViolationException`: Business rule violations
|
||||
|
||||
These provide common exception handling patterns without coupling contexts.
|
10
src/Domain/Shared/Model/README.md
Normal file
10
src/Domain/Shared/Model/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Shared Domain Models
|
||||
|
||||
Base classes and interfaces used across bounded contexts:
|
||||
|
||||
- `AggregateRoot`: Base class for all aggregates
|
||||
- `Entity`: Base class for entities
|
||||
- `DomainEvent`: Interface for domain events
|
||||
- `ValueObject`: Base value object interface
|
||||
|
||||
These provide common functionality while maintaining context boundaries.
|
9
src/Domain/Shared/Repository/README.md
Normal file
9
src/Domain/Shared/Repository/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Shared Repository Interfaces
|
||||
|
||||
Common repository patterns and base interfaces:
|
||||
|
||||
- `RepositoryInterface`: Base repository contract
|
||||
- `ReadOnlyRepositoryInterface`: Query-only operations
|
||||
- `AggregateRepositoryInterface`: Aggregate-specific methods
|
||||
|
||||
These define common persistence patterns without implementation details.
|
10
src/Domain/Shared/ValueObject/README.md
Normal file
10
src/Domain/Shared/ValueObject/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Shared Value Objects
|
||||
|
||||
Common value objects used across contexts:
|
||||
|
||||
- `Id`: Generic identifier base class
|
||||
- `DateTime`: Immutable datetime wrapper
|
||||
- `Money`: Monetary value representation
|
||||
- `Percentage`: Percentage value (0-100)
|
||||
|
||||
These are minimal shared concepts that don't violate bounded context principles.
|
8
src/Domain/Tracker/Exception/README.md
Normal file
8
src/Domain/Tracker/Exception/README.md
Normal file
|
@ -0,0 +1,8 @@
|
|||
# Tracker Domain Exceptions
|
||||
|
||||
Domain-specific exceptions for tracker operations:
|
||||
|
||||
- `InvalidInfoHashException`: Malformed info hash
|
||||
- `InactiveTorrentException`: Torrent not active
|
||||
- `PeerLimitExceededException`: Too many peers
|
||||
- `InvalidAnnounceException`: Protocol violation
|
19
src/Domain/Tracker/Model/README.md
Normal file
19
src/Domain/Tracker/Model/README.md
Normal file
|
@ -0,0 +1,19 @@
|
|||
# Tracker Domain Models
|
||||
|
||||
Contains aggregate roots and entities for the BitTorrent tracker:
|
||||
|
||||
- `Torrent`: Aggregate root for torrent management
|
||||
- `Peer`: Entity representing a BitTorrent peer
|
||||
- `TorrentStatistics`: Value object for torrent stats
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
class Torrent extends AggregateRoot
|
||||
{
|
||||
public function announce(Peer $peer, AnnounceEvent $event): void
|
||||
{
|
||||
// Business logic for handling announces
|
||||
}
|
||||
}
|
||||
```
|
9
src/Domain/Tracker/Repository/README.md
Normal file
9
src/Domain/Tracker/Repository/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Tracker Repository Interfaces
|
||||
|
||||
Repository interfaces for tracker aggregates:
|
||||
|
||||
- `TorrentRepositoryInterface`: Torrent aggregate persistence
|
||||
- `PeerRepositoryInterface`: Peer data access
|
||||
- `TrackerStatsRepositoryInterface`: Statistics queries
|
||||
|
||||
These define persistence contracts without implementation details.
|
23
src/Domain/Tracker/ValueObject/README.md
Normal file
23
src/Domain/Tracker/ValueObject/README.md
Normal file
|
@ -0,0 +1,23 @@
|
|||
# Tracker Value Objects
|
||||
|
||||
Immutable objects representing domain concepts:
|
||||
|
||||
- `InfoHash`: 20-byte torrent identifier
|
||||
- `PeerId`: Peer client identifier
|
||||
- `Port`: Network port (1-65535)
|
||||
- `BytesTransferred`: Upload/download bytes
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
final class InfoHash
|
||||
{
|
||||
private string $hash;
|
||||
|
||||
public function __construct(string $hash)
|
||||
{
|
||||
$this->guardAgainstInvalidHash($hash);
|
||||
$this->hash = $hash;
|
||||
}
|
||||
}
|
||||
```
|
9
src/Domain/User/Exception/README.md
Normal file
9
src/Domain/User/Exception/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# User Domain Exceptions
|
||||
|
||||
Domain-specific exceptions for user operations:
|
||||
|
||||
- `UserNotFoundException`: User not found
|
||||
- `DuplicateUsernameException`: Username already taken
|
||||
- `InvalidCredentialsException`: Authentication failed
|
||||
- `UserNotActivatedException`: Account not activated
|
||||
- `PasswordComplexityException`: Weak password
|
15
src/Domain/User/Model/README.md
Normal file
15
src/Domain/User/Model/README.md
Normal file
|
@ -0,0 +1,15 @@
|
|||
# User Domain Models
|
||||
|
||||
Contains user management aggregates and entities:
|
||||
|
||||
- `User`: User aggregate root
|
||||
- `UserProfile`: User profile information
|
||||
- `UserCredentials`: Authentication credentials
|
||||
- `UserPermissions`: Authorization rules
|
||||
|
||||
Business rules:
|
||||
|
||||
- Password complexity requirements
|
||||
- Username uniqueness
|
||||
- Email verification workflow
|
||||
- Account activation/deactivation
|
10
src/Domain/User/Repository/README.md
Normal file
10
src/Domain/User/Repository/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# User Repository Interface
|
||||
|
||||
Repository interface for user aggregate:
|
||||
|
||||
- `UserRepositoryInterface`: User persistence and retrieval
|
||||
- `findById(UserId $id): ?User`
|
||||
- `findByUsername(Username $username): ?User`
|
||||
- `findByEmail(Email $email): ?User`
|
||||
- `save(User $user): void`
|
||||
- `delete(User $user): void`
|
11
src/Domain/User/ValueObject/README.md
Normal file
11
src/Domain/User/ValueObject/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# User Value Objects
|
||||
|
||||
Immutable objects for user domain:
|
||||
|
||||
- `UserId`: Unique user identifier
|
||||
- `Username`: Username with validation
|
||||
- `Email`: Email address with format validation
|
||||
- `HashedPassword`: Secure password representation
|
||||
- `UserRole`: User role enumeration
|
||||
|
||||
These ensure data integrity and type safety.
|
9
src/Infrastructure/Cache/File/README.md
Normal file
9
src/Infrastructure/Cache/File/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# File Cache Adapter
|
||||
|
||||
File system-based caching implementation:
|
||||
|
||||
- Simple file-based storage
|
||||
- Suitable for single-server deployments
|
||||
- Directory structure optimization
|
||||
- Lock file support for concurrency
|
||||
- Automatic garbage collection
|
9
src/Infrastructure/Cache/Memcached/README.md
Normal file
9
src/Infrastructure/Cache/Memcached/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Memcached Cache Adapter
|
||||
|
||||
Memcached-based caching implementation:
|
||||
|
||||
- Simple key-value caching
|
||||
- Distributed cache support
|
||||
- Automatic key expiration
|
||||
- Connection pooling
|
||||
- Consistent hashing for distribution
|
9
src/Infrastructure/Cache/Redis/README.md
Normal file
9
src/Infrastructure/Cache/Redis/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Redis Cache Adapter
|
||||
|
||||
Redis-based caching implementation:
|
||||
|
||||
- High-performance key-value storage
|
||||
- Support for data structures (lists, sets, hashes)
|
||||
- TTL management
|
||||
- Pub/sub for cache invalidation
|
||||
- Cluster support for scalability
|
16
src/Infrastructure/Email/Template/README.md
Normal file
16
src/Infrastructure/Email/Template/README.md
Normal file
|
@ -0,0 +1,16 @@
|
|||
# Email Templates
|
||||
|
||||
Email template management:
|
||||
|
||||
- HTML and plain text templates
|
||||
- Template variables and placeholders
|
||||
- Multi-language support
|
||||
- Template caching
|
||||
- Preview functionality
|
||||
|
||||
Common templates:
|
||||
|
||||
- User registration confirmation
|
||||
- Password reset
|
||||
- Torrent notifications
|
||||
- Forum post notifications
|
10
src/Infrastructure/Email/Transport/README.md
Normal file
10
src/Infrastructure/Email/Transport/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Email Transport
|
||||
|
||||
Email delivery mechanisms:
|
||||
|
||||
- `SmtpTransport`: Traditional SMTP delivery
|
||||
- `SendgridTransport`: SendGrid API integration
|
||||
- `MailgunTransport`: Mailgun API integration
|
||||
- `NullTransport`: Testing/development transport
|
||||
|
||||
Supports queuing and retry mechanisms.
|
11
src/Infrastructure/FileStorage/Local/README.md
Normal file
11
src/Infrastructure/FileStorage/Local/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# Local File Storage
|
||||
|
||||
Local filesystem storage implementation:
|
||||
|
||||
- Direct disk storage
|
||||
- Directory structure management
|
||||
- File permissions handling
|
||||
- Atomic file operations
|
||||
- Cleanup and maintenance
|
||||
|
||||
Used for torrent files, avatars, and attachments.
|
11
src/Infrastructure/FileStorage/S3/README.md
Normal file
11
src/Infrastructure/FileStorage/S3/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# S3 File Storage
|
||||
|
||||
Amazon S3 (or compatible) storage implementation:
|
||||
|
||||
- Cloud object storage
|
||||
- Pre-signed URLs for direct uploads
|
||||
- CDN integration support
|
||||
- Lifecycle policies
|
||||
- Multi-region support
|
||||
|
||||
Provides scalable storage for large deployments.
|
9
src/Infrastructure/Persistence/Database/README.md
Normal file
9
src/Infrastructure/Persistence/Database/README.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
# Database Adapter
|
||||
|
||||
Database connection and query building layer:
|
||||
|
||||
- `DatabaseAdapterInterface`: Common database operations
|
||||
- `QueryBuilder`: Fluent query construction
|
||||
- `ConnectionPool`: Connection management
|
||||
|
||||
Provides abstraction over raw database access.
|
10
src/Infrastructure/Persistence/Migration/README.md
Normal file
10
src/Infrastructure/Persistence/Migration/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# Database Migrations
|
||||
|
||||
Schema version control and migration management:
|
||||
|
||||
- Migration files for schema changes
|
||||
- Seed data for initial setup
|
||||
- Rollback support
|
||||
- Migration history tracking
|
||||
|
||||
Uses Phinx or similar migration tool.
|
29
src/Infrastructure/Persistence/Repository/README.md
Normal file
29
src/Infrastructure/Persistence/Repository/README.md
Normal file
|
@ -0,0 +1,29 @@
|
|||
# Repository Implementations
|
||||
|
||||
Concrete implementations of domain repository interfaces:
|
||||
|
||||
- Uses database adapter for persistence
|
||||
- Implements caching strategies
|
||||
- Handles query optimization
|
||||
- Supports multiple database backends
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
class TorrentRepository implements TorrentRepositoryInterface
|
||||
{
|
||||
public function __construct(
|
||||
private DatabaseAdapterInterface $db
|
||||
) {}
|
||||
|
||||
public function findByInfoHash(InfoHash $infoHash): ?Torrent
|
||||
{
|
||||
// Database adapter implementation
|
||||
$row = $this->db->select('torrents')
|
||||
->where('info_hash', $infoHash->toString())
|
||||
->first();
|
||||
|
||||
return $row ? $this->hydrateFromRow($row) : null;
|
||||
}
|
||||
}
|
||||
```
|
11
src/Infrastructure/README.md
Normal file
11
src/Infrastructure/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# Infrastructure Layer
|
||||
|
||||
Technical implementations and external service adapters:
|
||||
|
||||
- Database persistence
|
||||
- Caching mechanisms
|
||||
- Email services
|
||||
- File storage
|
||||
- Third-party integrations
|
||||
|
||||
Infrastructure depends on domain, not vice versa.
|
10
src/Presentation/Cli/Commands/README.md
Normal file
10
src/Presentation/Cli/Commands/README.md
Normal file
|
@ -0,0 +1,10 @@
|
|||
# CLI Commands
|
||||
|
||||
Console commands for administrative tasks:
|
||||
|
||||
- `UserCreateCommand`: Create users from CLI
|
||||
- `CacheClearCommand`: Clear cache stores
|
||||
- `MigrateCommand`: Run database migrations
|
||||
- `CronCommand`: Execute scheduled tasks
|
||||
|
||||
Built using Symfony Console component.
|
30
src/Presentation/Http/Controllers/Admin/README.md
Normal file
30
src/Presentation/Http/Controllers/Admin/README.md
Normal file
|
@ -0,0 +1,30 @@
|
|||
# Admin Panel Controllers
|
||||
|
||||
Administrative interface controllers with enhanced security:
|
||||
|
||||
- Role-based access control (RBAC)
|
||||
- Audit logging for all actions
|
||||
- Additional authentication checks
|
||||
- Administrative dashboards and reports
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
class AdminUserController
|
||||
{
|
||||
public function index(Request $request): Response
|
||||
{
|
||||
$query = new GetUsersQuery(
|
||||
page: $request->getPage(),
|
||||
filters: $request->getFilters()
|
||||
);
|
||||
|
||||
$users = $this->queryBus->handle($query);
|
||||
|
||||
return $this->render('admin/users/index', [
|
||||
'users' => $users,
|
||||
'filters' => $request->getFilters()
|
||||
]);
|
||||
}
|
||||
}
|
||||
```
|
31
src/Presentation/Http/Controllers/Api/README.md
Normal file
31
src/Presentation/Http/Controllers/Api/README.md
Normal file
|
@ -0,0 +1,31 @@
|
|||
# API Controllers
|
||||
|
||||
RESTful API endpoints following OpenAPI specification:
|
||||
|
||||
- JSON request/response format
|
||||
- Proper HTTP status codes
|
||||
- HATEOAS where applicable
|
||||
- Rate limiting aware
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
class UserController
|
||||
{
|
||||
public function register(RegisterRequest $request): JsonResponse
|
||||
{
|
||||
$command = new RegisterUserCommand(
|
||||
$request->getUsername(),
|
||||
$request->getEmail(),
|
||||
$request->getPassword()
|
||||
);
|
||||
|
||||
$userId = $this->commandBus->handle($command);
|
||||
|
||||
return new JsonResponse([
|
||||
'id' => $userId,
|
||||
'username' => $request->getUsername()
|
||||
], Response::HTTP_CREATED);
|
||||
}
|
||||
}
|
||||
```
|
16
src/Presentation/Http/Controllers/Web/README.md
Normal file
16
src/Presentation/Http/Controllers/Web/README.md
Normal file
|
@ -0,0 +1,16 @@
|
|||
# Web Controllers
|
||||
|
||||
Traditional web interface controllers:
|
||||
|
||||
- HTML response generation
|
||||
- Template rendering
|
||||
- Form handling
|
||||
- Session management
|
||||
- CSRF protection
|
||||
|
||||
Controllers for:
|
||||
|
||||
- Forum browsing and posting
|
||||
- Torrent browsing and downloading
|
||||
- User profiles and settings
|
||||
- Search functionality
|
12
src/Presentation/Http/Middleware/README.md
Normal file
12
src/Presentation/Http/Middleware/README.md
Normal file
|
@ -0,0 +1,12 @@
|
|||
# HTTP Middleware
|
||||
|
||||
Request/response pipeline middleware:
|
||||
|
||||
- `AuthenticationMiddleware`: User authentication
|
||||
- `AuthorizationMiddleware`: Permission checks
|
||||
- `CsrfProtectionMiddleware`: CSRF token validation
|
||||
- `RateLimitMiddleware`: Request throttling
|
||||
- `LocalizationMiddleware`: Language detection
|
||||
- `CorsMiddleware`: Cross-origin resource sharing
|
||||
|
||||
Middleware follows PSR-15 standard.
|
25
src/Presentation/Http/Requests/README.md
Normal file
25
src/Presentation/Http/Requests/README.md
Normal file
|
@ -0,0 +1,25 @@
|
|||
# HTTP Requests
|
||||
|
||||
Request objects and validation:
|
||||
|
||||
- Request DTOs with validation rules
|
||||
- Type-safe access to request data
|
||||
- File upload handling
|
||||
- Input sanitization
|
||||
- Custom validation rules
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
class RegisterRequest extends FormRequest
|
||||
{
|
||||
public function rules(): array
|
||||
{
|
||||
return [
|
||||
'username' => ['required', 'string', 'min:3', 'max:20', 'unique:users'],
|
||||
'email' => ['required', 'email', 'unique:users'],
|
||||
'password' => ['required', 'string', 'min:8', 'confirmed'],
|
||||
];
|
||||
}
|
||||
}
|
||||
```
|
11
src/Presentation/Http/Responses/README.md
Normal file
11
src/Presentation/Http/Responses/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# HTTP Responses
|
||||
|
||||
Response transformation and formatting:
|
||||
|
||||
- Response factories
|
||||
- JSON transformers
|
||||
- View presenters
|
||||
- Error response formatting
|
||||
- Content negotiation
|
||||
|
||||
Ensures consistent API responses and proper HTTP semantics.
|
11
src/Presentation/README.md
Normal file
11
src/Presentation/README.md
Normal file
|
@ -0,0 +1,11 @@
|
|||
# Presentation Layer
|
||||
|
||||
User interface implementations:
|
||||
|
||||
- HTTP controllers for web and API
|
||||
- CLI commands for console operations
|
||||
- Request/response handling
|
||||
- Input validation
|
||||
- Output formatting
|
||||
|
||||
This layer translates between external format and application format.
|
Loading…
Add table
Add a link
Reference in a new issue