nubitio / platform
Platform foundation for Nubit Symfony apps: domain exceptions, tenant contracts, feature gates, quota contracts, messenger middleware, cache/file/export helpers.
Package info
pkg:composer/nubitio/platform
Requires
- php: >=8.3
- psr/cache: ^3.0
- psr/log: ^3.0
- psr/simple-cache: ^3.0
- symfony/clock: ^7.4 || ^8.0
- symfony/console: ^7.4 || ^8.0
- symfony/dependency-injection: ^7.4 || ^8.0
- symfony/http-foundation: ^7.4 || ^8.0
- symfony/http-kernel: ^7.4 || ^8.0
- symfony/lock: ^7.4 || ^8.0
- symfony/messenger: ^7.4 || ^8.0
- symfony/process: ^7.4 || ^8.0
- symfony/service-contracts: ^3.0
- symfony/string: ^7.4 || ^8.0
- symfony/validator: ^7.4 || ^8.0
Requires (Dev)
- doctrine/dbal: ^4.0
- league/flysystem: ^3.0
- monolog/monolog: ^3.0
- open-telemetry/api: ^1.0
- phpoffice/phpspreadsheet: ^5.8.1
- phpunit/phpunit: ^11.5 || ^12.0
- pontedilana/php-weasyprint: ^2.2
- symfony/cache: ^7.4 || ^8.0
Suggests
- doctrine/dbal: Required by Nubit\Platform\Observability\Doctrine tracing middleware and Nubit\Platform\Tenant\Backup\PostgresTenantBackupRunner
- league/flysystem: Required by Nubit\Platform\Filesystem\FileManager
- monolog/monolog: Required by Nubit\Platform\Observability\Logging\TenantLogProcessor
- open-telemetry/api: Trace correlation in TenantLogProcessor
- phpoffice/phpspreadsheet: Required by Nubit\Platform\Export\XlsExporter
- pontedilana/php-weasyprint: Required by Nubit\Platform\Export\PdfExporter
This package is auto-updated.
Last update: 2026-08-22 16:55:17 UTC
README
Platform foundation for Nubit Symfony apps: the framework-agnostic contracts and helpers that the rest of the stack builds on.
composer require nubitio/platform
What's inside
- Exceptions —
ServiceException,ValidationException,NotFoundException,DomainProblemException,QuotaExceededExceptionwithDomainErrorCode. Throw these from services;nubitio/api-platformmaps them to proper HTTP responses. - Tenant —
TenantContextplus contracts (TenantRegistryInterface,TenantConnectionSwitcherInterface,TenantDescriptorRegistryInterface,TenantBackupRunnerInterface). Single-tenant apps bind noop implementations; multi-tenant apps provide real ones.PostgresTenantBackupRunneris the one shipped backup implementation (pg_dump --format=custom, credentials from the Doctrine connection, password viaPGPASSWORD, dump persisted throughFileManager);nubitio/admin-bundlewires it behindnubit_admin.backup.enabled. - Feature gates —
#[RequiresFeature]attribute +FeatureCheckerInterface. - Quota contracts —
QuotaEnforcerInterface,QuotaResourceResolverInterface. - Messenger —
TenantStampMiddleware/TenantContextMiddlewarepropagate tenant + actor through async messages. - Infra helpers —
CacheManager,FileManager(Flysystem),TenantRateLimiter,XlsExporter(PhpSpreadsheet),PdfExporter(WeasyPrint),PerTenantCommandconsole base class,TenantLogProcessor(Monolog) and tenant-aware OpenTelemetry spans viaTenantTracer. - Feature flags — vendor-neutral, typed evaluation through
TenantFeatureFlags; distinct from plan entitlements exposed byFeatureCheckerInterface.StaticFeatureFlagProviderprovides deterministic local defaults and the provider port can be adapted to OpenFeature. - Privacy —
#[SensitiveData],DataRedactorand sink-specific policies protect structured logs, traces, analytics and integrations. - Analytics — typed, versioned events with explicit purpose, consent checks, deduplication and provider-neutral sanitized delivery.
- Notifications —
NotificationMessage(a scalar-only, Messenger-serializable payload) plusNotificationDispatcherInterfaceandNotificationChannelInterface. The contracts live here so domain code can raise a notification without depending on a delivery mechanism;nubitio/admin-bundlesupplies the Messenger dispatcher and the email/in-app channels. - HTTP —
ApiResponseJSON envelope (success/message/data).
Heavy integrations (Flysystem, PhpSpreadsheet, WeasyPrint, Monolog, OpenTelemetry) are suggest-ed — install them only if you use the corresponding helper.
Sensitive data
Classify the canonical DTO/entity property once:
use Nubit\Platform\Privacy\Attribute\SensitiveData; use Nubit\Platform\Privacy\DataClassification; final readonly class LoginContext { public function __construct( public string $username, #[SensitiveData(DataClassification::Confidential)] public string $email, #[SensitiveData(DataClassification::Restricted)] public string $accessToken, ) { } }
For values inserted into an untyped array, classify them explicitly:
$context = [ 'email' => new SensitiveValue($email, DataClassification::Confidential), 'token' => new SensitiveValue($token, DataClassification::Restricted), ];
SensitiveDataProcessor sanitizes structured Monolog context and extra fields.
TraceAttributeSanitizer applies the same kernel to OpenTelemetry attributes. Restricted
data is dropped by default. Confidential data is masked in logs and HMACed in traces or
analytics when a key is configured; without the key it is dropped.
The processor intentionally does not rewrite arbitrary log or exception messages. Never interpolate secrets or complete request payloads into text:
// Safe: the structured value passes through the redactor. $logger->info('Authentication failed', ['email' => new SensitiveValue( $email, DataClassification::Confidential, )]);
See the ERP SaaS platform roadmap for the classification matrix, threat model and phased rollout.
Analytics
Analytics payloads must be DTOs so the privacy metadata is applied before a provider receives them:
$result = $publisher->publish(new AnalyticsEvent( id: $commandId, // stable idempotency key name: 'invoice.paid', schemaVersion: 1, purpose: AnalyticsPurpose::Operational, payload: new InvoicePaidAnalyticsPayload($channel, $customerEmail), ));
AnalyticsProviderInterface receives only SanitizedAnalyticsEvent. Product and
marketing events are denied by the safe default consent checker. The included
InMemoryAnalyticsDeduplicator is bounded and suitable for tests or one local process;
production must bind AnalyticsDeduplicatorInterface to an atomic shared store or use
an outbox table with a unique event ID.
License
MIT