Enable Discovery debug logging for production troubleshooting

- Add DISCOVERY_LOG_LEVEL=debug
- Add DISCOVERY_SHOW_PROGRESS=true
- Temporary changes for debugging InitializerProcessor fixes on production
This commit is contained in:
2025-08-11 20:13:26 +02:00
parent 59fd3dd3b1
commit 55a330b223
3683 changed files with 2956207 additions and 16948 deletions

View File

@@ -0,0 +1,334 @@
# Byte Value Object
The `Byte` value object provides a type-safe way to work with byte sizes in your application. It offers convenient conversions, arithmetic operations, and human-readable formatting for file sizes, memory usage, and other byte-based measurements.
## Basic Usage
### Creating Byte Instances
```php
use App\Framework\Core\ValueObjects\Byte;
use App\Framework\Core\ValueObjects\ByteUnit;
// From raw bytes
$size = Byte::fromBytes(1048576); // 1 MB
// From specific units
$fileSize = Byte::fromMegabytes(5.5);
$memoryLimit = Byte::fromGigabytes(2);
$smallFile = Byte::fromKilobytes(256);
// From human-readable strings
$uploadLimit = Byte::parse('10MB');
$cacheSize = Byte::parse('500 KB');
$logSize = Byte::parse('1.5GB');
// Using enum for flexibility
$customSize = Byte::fromUnit(100, ByteUnit::MEGABYTE);
```
### Converting Between Units
```php
$size = Byte::fromMegabytes(5.5);
echo $size->toBytes(); // 5767168
echo $size->toKilobytes(); // 5632.0
echo $size->toMegabytes(); // 5.5
echo $size->toGigabytes(); // 0.01
// Custom precision
echo $size->toGigabytes(4); // 0.0054
// Using enum for dynamic conversion
$unit = ByteUnit::KILOBYTE;
echo $size->toUnit($unit); // 5632.0
```
### Human-Readable Formatting
```php
$size = Byte::fromBytes(1536000);
echo $size->toHumanReadable(); // "1.46 MB"
echo $size->toHumanReadable(0); // "1 MB"
echo (string) $size; // "1.46 MB" (same as toHumanReadable())
// Get the best unit for display
$unit = $size->getBestUnit(); // ByteUnit::MEGABYTE
echo $unit->value; // "MB"
echo $unit->getName(); // "Megabyte"
```
## Arithmetic Operations
```php
$file1 = Byte::fromMegabytes(5);
$file2 = Byte::fromMegabytes(3);
// Addition
$total = $file1->add($file2); // 8 MB
// Subtraction
$difference = $file1->subtract($file2); // 2 MB
// Multiplication
$doubled = $file1->multiply(2); // 10 MB
// Division
$half = $file1->divide(2); // 2.5 MB
// Percentage calculation
$percentage = $file1->percentOf($total); // 62.5
```
## Comparisons
```php
$file1 = Byte::fromMegabytes(5);
$file2 = Byte::fromMegabytes(3);
$limit = Byte::fromMegabytes(10);
// Equality
if ($file1->equals($file2)) {
echo "Files are the same size";
}
// Size comparisons
if ($file1->greaterThan($file2)) {
echo "File 1 is larger";
}
if ($file1->lessThan($limit)) {
echo "File is under the limit";
}
// Utility checks
if ($file1->isEmpty()) {
echo "File is empty";
}
```
## Framework Integration Examples
### File Upload Validation
```php
class FileUploadMiddleware
{
public function validate(UploadedFile $file): void
{
$maxSize = Byte::parse($_ENV['MAX_UPLOAD_SIZE'] ?? '10MB');
$fileSize = Byte::fromBytes($file->getSize());
if ($fileSize->greaterThan($maxSize)) {
throw new ValidationException(
"File size {$fileSize} exceeds limit of {$maxSize}"
);
}
}
}
```
### Memory Usage Monitoring
```php
class PerformanceMonitor
{
public function checkMemoryUsage(): array
{
$current = Byte::fromBytes(memory_get_usage(true));
$peak = Byte::fromBytes(memory_get_peak_usage(true));
$limit = Byte::parse(ini_get('memory_limit'));
return [
'current' => $current->toHumanReadable(),
'peak' => $peak->toHumanReadable(),
'limit' => $limit->toHumanReadable(),
'usage_percentage' => $current->percentOf($limit),
];
}
}
```
### Database Entity
```php
use App\Framework\Database\Attributes\Column;
use App\Framework\Database\Attributes\Entity;
#[Entity(tableName: 'files')]
final readonly class File
{
public function __construct(
#[Column(name: 'id', primary: true)]
public int $id,
#[Column(name: 'filename')]
public string $filename,
#[Column(name: 'file_size')]
public int $fileSizeBytes,
) {}
public function getFileSize(): Byte
{
return Byte::fromBytes($this->fileSizeBytes);
}
public function isLargeFile(): bool
{
return $this->getFileSize()->greaterThan(Byte::fromMegabytes(50));
}
}
```
### Cache Size Management
```php
class CacheManager
{
public function cleanupIfNeeded(): void
{
$cacheSize = $this->getCurrentCacheSize();
$maxSize = Byte::parse($_ENV['CACHE_MAX_SIZE'] ?? '1GB');
if ($cacheSize->greaterThan($maxSize)) {
$this->clearOldEntries();
$newSize = $this->getCurrentCacheSize();
$freed = $cacheSize->subtract($newSize);
$this->logger->info("Cache cleanup freed {$freed}");
}
}
private function getCurrentCacheSize(): Byte
{
$totalBytes = 0;
foreach ($this->getCacheFiles() as $file) {
$totalBytes += filesize($file);
}
return Byte::fromBytes($totalBytes);
}
}
```
## ByteUnit Enum
The `ByteUnit` enum provides type-safe unit definitions:
```php
// Available units
ByteUnit::BYTE // 'B'
ByteUnit::KILOBYTE // 'KB'
ByteUnit::MEGABYTE // 'MB'
ByteUnit::GIGABYTE // 'GB'
ByteUnit::TERABYTE // 'TB'
// Get multiplier
$multiplier = ByteUnit::MEGABYTE->getMultiplier(); // 1048576
// Get human name
$name = ByteUnit::GIGABYTE->getName(); // "Gigabyte"
// Find best unit for a size
$unit = ByteUnit::bestUnitFor(1048576); // ByteUnit::MEGABYTE
// Parse from string
$unit = ByteUnit::fromString('MB'); // ByteUnit::MEGABYTE
$unit = ByteUnit::fromString('megabytes'); // ByteUnit::MEGABYTE
```
## Constants
```php
// Common sizes
$empty = Byte::zero(); // 0 B
$kb = Byte::oneKilobyte(); // 1 KB
$mb = Byte::oneMegabyte(); // 1 MB
$gb = Byte::oneGigabyte(); // 1 GB
```
## Configuration Examples
### Environment Variables
```bash
# .env file
MAX_UPLOAD_SIZE=10MB
CACHE_MAX_SIZE=1GB
LOG_MAX_SIZE=100MB
MEMORY_LIMIT_WARNING=512MB
```
### Application Usage
```php
// Configuration class
class AppConfig
{
public static function getMaxUploadSize(): Byte
{
return Byte::parse($_ENV['MAX_UPLOAD_SIZE'] ?? '5MB');
}
public static function getCacheLimit(): Byte
{
return Byte::parse($_ENV['CACHE_MAX_SIZE'] ?? '500MB');
}
}
// Usage in controllers
class FileController
{
public function upload(Request $request): Response
{
$maxSize = AppConfig::getMaxUploadSize();
foreach ($request->files as $file) {
$fileSize = Byte::fromBytes($file->getSize());
if ($fileSize->greaterThan($maxSize)) {
return new JsonResponse([
'error' => "File {$file->getName()} ({$fileSize}) exceeds maximum size of {$maxSize}"
], 413);
}
}
// Process upload...
}
}
```
## Error Handling
```php
try {
// Invalid format
$size = Byte::parse('invalid');
} catch (InvalidArgumentException $e) {
echo $e->getMessage(); // "Invalid byte format: invalid"
}
try {
// Negative bytes
$size = Byte::fromBytes(-100);
} catch (InvalidArgumentException $e) {
echo $e->getMessage(); // "Bytes cannot be negative"
}
try {
// Subtraction resulting in negative
$result = Byte::fromBytes(100)->subtract(Byte::fromBytes(200));
} catch (InvalidArgumentException $e) {
echo $e->getMessage(); // "Subtraction would result in negative bytes"
}
```
## Best Practices
1. **Use in Configuration**: Store all size limits as `Byte` objects for type safety
2. **Database Storage**: Store raw bytes as integers, convert to `Byte` objects in getters
3. **Validation**: Use `Byte` objects for all size-related validation logic
4. **Logging**: Use `toHumanReadable()` for user-friendly log messages
5. **APIs**: Accept string formats and parse them into `Byte` objects
6. **Performance**: Create `Byte` objects lazily when needed, store raw bytes when possible