3.4 KiB
CLAUDE.md
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
Project Overview
This is lthn/service, a Composer package for the Core PHP Framework (Laravel-based). It provides SaaS service discovery, dependency resolution, versioning, health checks, and generic landing pages for services. It is a library package — not a standalone application.
License: EUPL-1.2
PHP: ^8.2
Dependency: lthn/php (the Core PHP Framework)
Commands
There is no standalone build, lint, or test runner in this repo. This package is consumed by a host Laravel application. To run tests:
# From the host application that requires this package:
./vendor/bin/phpunit vendor/lthn/service/src/Core/Service/Tests/
# Single test file:
./vendor/bin/phpunit vendor/lthn/service/src/Core/Service/Tests/Unit/ServiceVersionTest.php
Tests use PHPUnit with #[Test] attributes (not @test annotations or test_ prefixes).
Architecture
The package has two distinct layers with separate PSR-4 namespaces:
Core Layer (Core\Service\ → src/Core/Service/)
Framework-level service infrastructure:
- ServiceDiscovery — Scans module paths for
ServiceDefinitionimplementations, validates dependencies, resolves initialization order via topological sort, caches results for 1 hour (configurable viacore.services.cache_discovery) - Contracts/ —
ServiceDefinition(extendsAdminMenuProviderfromCore\Front\Admin),ServiceDependency(required/optional with semver constraints),HealthCheckable - ServiceVersion — Immutable readonly value object following semver with deprecation/sunset lifecycle
- HealthCheckResult — Immutable readonly result with factory methods (
healthy(),degraded(),unhealthy(),fromException()) - Enums/ServiceStatus — Backed enum: healthy, degraded, unhealthy, unknown
- Concerns/HasServiceVersion — Trait providing default
version()(1.0.0) anddependencies()(empty) for ServiceDefinition implementations - ServiceDependencyException — Named constructors:
circular(),missing(),versionMismatch()
Website Layer (Core\Website\Service\ → src/Website/Service/)
Public marketing/landing pages served as Livewire components:
- Boot — Laravel ServiceProvider that registers Blade views (
service::namespace) and web routes - View/Landing — Livewire component for service landing page, resolves workspace via subdomain (e.g.,
social.host.test→social) - View/Features — Livewire component with per-service feature lists (matched by workspace slug)
- Routes/web.php — Two routes:
/(Landing) and/features(Features) - View/Blade/ — Blade templates using
service::namespace with layout and components
Key Patterns
- All PHP files use
declare(strict_types=1) - Value objects are
final readonly class - Factory methods preferred over constructor calls for result types
- Service definitions use static methods (
definition(),version(),dependencies()) ServiceDefinition::definition()must return array with required keys:code,module,name- Service codes must match pattern:
/^[a-z][a-z0-9_-]*$/i - Subdomain routing:
{slug}.host.{tld}pattern for workspace resolution - Config keys prefixed with
core.(e.g.,core.services.cache_discovery,core.module_paths,core.app.name)