<?php
declare(strict_types=1);

namespace App\Foundation;

final class Application
{
    private static ?self $instance = null;
    private Container $container;
    private bool $booted = false;

    private function __construct(private readonly string $basePath) { $this->container = new Container(); }

    public static function instance(?string $basePath = null): self
    {
        if (self::$instance === null) {
            if ($basePath === null) throw new \RuntimeException('BASE_PATH requis au premier démarrage AXIOM.');
            self::$instance = new self($basePath);
        }
        return self::$instance;
    }

    public function boot(): self
    {
        if ($this->booted) return $this;
        $version = is_file($this->basePath . '/VERSION') ? trim((string)file_get_contents($this->basePath . '/VERSION')) : '9.3.6';
        $coreVersion = is_file($this->basePath . '/CORE_VERSION') ? trim((string)file_get_contents($this->basePath . '/CORE_VERSION')) : '0.9.6-rc1-core';

        $this->container->set('app', $this);
        $this->container->set(self::class, $this);
        $this->container->set(Container::class, $this->container);
        $this->container->set('base_path', $this->basePath);
        $this->container->set(ConfigRepository::class, new ConfigRepository(['app' => [
            'name' => 'AXIOM Platform — CDA', 'version' => $version, 'core_version' => $coreVersion,
        ]]));
        $this->container->set(EventDispatcher::class, new EventDispatcher());
        $this->container->set(ModuleRegistry::class, new ModuleRegistry());
        $this->container->set(MetadataRegistry::class, new MetadataRegistry());
        $this->container->set(HealthReport::class, new HealthReport());
        $this->container->set(CacheManager::class, new CacheManager($this->basePath . '/storage/cache/axiom'));
        $runtime = new \App\Runtime\ModuleRuntime($this, [$this->basePath . '/modules']);
        $this->container->set(\App\Runtime\ModuleRuntime::class, $runtime);

        $modules = $this->modules();
        CompatibilityBridge::registerLegacyModules($modules);
        $modules->register('axiom.foundation', [
            'name' => 'AXIOM Foundation', 'version' => $coreVersion, 'legacy' => false,
            'enabled' => true, 'dependencies' => [],
        ]);
        $modules->register('axiom.studio', [
            'name' => 'AXIOM Studio', 'version' => '1.0.0-foundation', 'legacy' => false,
            'enabled' => true, 'dependencies' => ['axiom.foundation'],
        ]);

        $metadata = $this->metadata();
        $metadata->registerEntity('core.person', ['label' => 'Personne', 'searchable' => true, 'fields' => ['last_name', 'first_name', 'birth_date']]);
        $metadata->registerEntity('core.organization', ['label' => 'Organisation', 'searchable' => true, 'fields' => ['name', 'type']]);

        $runtime->discoverAndBoot();

        $this->booted = true;
        $this->events()->dispatch('axiom.foundation.booted', $this);
        return $this;
    }

    public function container(): Container { return $this->container; }
    public function events(): EventDispatcher { return $this->container->get(EventDispatcher::class); }
    public function modules(): ModuleRegistry { return $this->container->get(ModuleRegistry::class); }
    public function metadata(): MetadataRegistry { return $this->container->get(MetadataRegistry::class); }
    public function cache(): CacheManager { return $this->container->get(CacheManager::class); }
    public function version(): string { return (string)$this->container->get(ConfigRepository::class)->get('app.version', '9.3.6'); }
}
