mirror of
https://github.com/Vateron-Media/XC_VM.git
synced 2026-10-04 04:02:30 +02:00
Verify every dev-doc claim against src/ and fix factual drift: wrong method signatures/return types, wrong enum casing (BootContext cases are PascalCase), stale paths (M3u parsers are Composer deps under vendor/, MobileDetect is mobiledetect/mobiledetectlib v4.9.0 \Detection\MobileDetect, NotFoundException lives in XcVm\Core\Container\Psr), a fictional `stream:check` command/class, reversed migration-failure semantics ([FAIL] = not recorded, retried), inverted isStreamRunning/isStreamAlive descriptions, findProcessPIDs ANY-not-ALL, acquireCronLock has no shutdown callback, and nonexistent make targets. Split oversized pages and fix nav + cross-links: - modules.md -> module-authoring / module-lifecycle / module-extension-points - cli-tools.md -> cli-tools + database-migrations - streaming-subsystem.md -> + streaming-diagnostics - geoip-and-device-detection.md -> geoip-isp-and-geo-routing + device-detection-and-stb-locking Add development/core-wiring.md: how the core assembles itself at boot (container population, ServiceContainer reference, bootAll orchestration, CLI command auto-discovery, end-to-end Admin/CLI boot walkthroughs). Only docs/en + mkdocs.yml touched; docs/ru is regenerated before release.
135 lines
4.5 KiB
Markdown
135 lines
4.5 KiB
Markdown
# Exception Hierarchy
|
|
|
|
XC_VM's framework exceptions extend `XcVmException` — an empty **marker** base
|
|
(`class XcVmException extends \RuntimeException {}`, it adds no extra data) — so callers can
|
|
catch the whole family with one `catch (XcVmException)` or target a specific subsystem.
|
|
|
|
> **Scope.** This typed hierarchy covers the **DI container** and **module system** only.
|
|
> It is not the whole panel: streaming/auth endpoints report failures through
|
|
> `generateError()` (not exceptions), and much domain/CLI code throws plain
|
|
> `\RuntimeException` or SPL exceptions — those still match `catch (XcVmException)` only when
|
|
> the class actually extends it.
|
|
|
|
---
|
|
|
|
## Tree
|
|
|
|
```
|
|
\Exception
|
|
└── \RuntimeException
|
|
└── XcVmException
|
|
├── Container
|
|
│ └── ContainerException (PSR-11 ContainerExceptionInterface)
|
|
│ ├── CircularDependencyException
|
|
│ ├── ServiceCreationException
|
|
│ └── NotFoundException (PSR-11 NotFoundExceptionInterface) *
|
|
└── Module
|
|
└── ModuleException
|
|
├── ModuleNotFoundException
|
|
├── ModuleLoadException
|
|
├── ModuleManifestException
|
|
└── ModuleCycleException
|
|
```
|
|
|
|
> \* `NotFoundException` extends `ContainerException` (so it belongs in this tree), but it
|
|
> physically lives at `src/Core/Container/Psr/NotFoundException.php` under the namespace
|
|
> `XcVm\Core\Container\Psr` — **not** in `Core/Exception/Container/`.
|
|
|
|
---
|
|
|
|
## Container exceptions
|
|
|
|
| Class | When thrown |
|
|
| ----- | ----------- |
|
|
| `ContainerException` | Base for all container failures |
|
|
| `CircularDependencyException` | A service's factory graph contains a cycle |
|
|
| `ServiceCreationException` | Factory callable threw while creating a service |
|
|
| `NotFoundException` | `get($id)` called for an unregistered service |
|
|
|
|
`NotFoundException` implements both PSR-11 interfaces so the container is compliant:
|
|
|
|
```php
|
|
try {
|
|
$service = $container->get('unknown');
|
|
} catch (NotFoundException $e) {
|
|
// PSR-11 NotFoundExceptionInterface
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Module exceptions
|
|
|
|
| Class | When thrown |
|
|
| ----- | ----------- |
|
|
| `ModuleException` | Base for all module failures |
|
|
| `ModuleNotFoundException` | Required dependency module is missing |
|
|
| `ModuleLoadException` | Module file cannot be loaded or class not found |
|
|
| `ModuleManifestException` | `module.json` is missing, malformed, or fails validation |
|
|
| `ModuleCycleException` | Dependency graph has a cycle — thrown by `ModuleLoader`'s topological sort with the cycle path (`a -> b -> a`) in the message. (Some `@throws` docblocks say `\RuntimeException`; that's just the base type — `ModuleCycleException` extends it via `XcVmException`.) |
|
|
|
|
---
|
|
|
|
## Catching by subsystem
|
|
|
|
```php
|
|
// Catch any XC_VM exception
|
|
try {
|
|
$loader->loadAll();
|
|
} catch (XcVmException $e) {
|
|
logger()->error($e->getMessage());
|
|
}
|
|
|
|
// Catch only module-related failures
|
|
try {
|
|
$loader->loadAll();
|
|
} catch (ModuleException $e) {
|
|
// ModuleNotFoundException | ModuleLoadException | ...
|
|
}
|
|
|
|
// Catch container-specific failures
|
|
try {
|
|
$container->get('missing');
|
|
} catch (ContainerException $e) {
|
|
// CircularDependencyException | NotFoundException | ...
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## Adding or choosing an exception
|
|
|
|
- **Which to throw:** use the most specific existing type (e.g. `ModuleManifestException`
|
|
for a bad `module.json`). If nothing fits and it's a framework-level failure, throw
|
|
`XcVmException` (or a new subclass) so it stays catchable as one family. Domain/business
|
|
errors that aren't framework concerns may throw a plain `\RuntimeException` /
|
|
`\InvalidArgumentException`.
|
|
- **Adding a category:** create the class under `src/Core/Exception/<Subsystem>/`, extend the
|
|
subsystem base (`ContainerException` / `ModuleException`) — or `XcVmException` for a new
|
|
subsystem — and add it to the tree above. No registration is needed; it's plain PHP.
|
|
|
|
---
|
|
|
|
## Location
|
|
|
|
```
|
|
src/Core/Exception/
|
|
├── XcVmException.php
|
|
├── Container/
|
|
│ ├── ContainerException.php
|
|
│ ├── CircularDependencyException.php
|
|
│ └── ServiceCreationException.php
|
|
└── Module/
|
|
├── ModuleException.php
|
|
├── ModuleNotFoundException.php
|
|
├── ModuleLoadException.php
|
|
├── ModuleManifestException.php
|
|
└── ModuleCycleException.php
|
|
```
|
|
|
|
## Related files
|
|
|
|
| File | Role |
|
|
| --- | --- |
|
|
| `src/Core/Exception/` | Exception base classes and the project hierarchy |
|