Container

The dependency injection container (DIC) registers dependencies (shared or not) and resolves registered dependencies automatically.

<?php
$app
->getContainer()
    ->
share(PDO::class, ['sqlite:db.sqlite']);

The service can then be automatically injected into your Action Models. If the PDO service wouldn't have been registered into the container, a new instance would have been created (which wouldn't have worked as PDO requires configuration).

<?php
namespace App\ActionModel;

class 
HelloActionModel
{
    public function 
__construct(\PDO)
    {
        
// ...
    
}

    
// ...
}

For more complex services, a service factory (Gobline\Container\ServiceFactoryInterface) and a service configurator (Gobline\Container\ServiceConfiguratorInterface) can be used.

Below are examples of service factories, which allow me to register Doctrine's ORM as a service as well as entity repositories.

<?php
namespace App\Provider;

use 
Gobline\Container\ServiceFactoryInterface;
use 
Doctrine\ORM\Tools\Setup;
use 
Doctrine\ORM\EntityManager;
use \
PDO;

class 
EntityManagerFactory implements ServiceFactoryInterface
{
    private 
$pdo;
    private 
$isDevMode;

    public function 
__construct(PDO $pdo$isDevMode true)
    {
        
$this->pdo $pdo;
        
$this->isDevMode $isDevMode;
    }

    public function 
create()
    {
        
$config Setup::createAnnotationMetadataConfiguration(
            [
__DIR__.'/../Model/Entity'], $this->isDevMode);

        return 
EntityManager::create(['pdo' => $this->pdo], $config);
    }
}
<?php
namespace App\Provider;

use 
Gobline\Container\ServiceFactoryInterface;
use 
Doctrine\ORM\EntityManager;

class 
EntityRepositoryFactory implements ServiceFactoryInterface
{
    private 
$entityManager;
    private 
$repositoryClassName;

    public function 
__construct(EntityManager $entityManager$repositoryClassName)
    {
        
$this->entityManager $entityManager;
        
$this->repositoryClassName $repositoryClassName;
    }

    public function 
create()
    {
        return 
$this->entityManager->getRepository($this->repositoryClassName);
    }
}