Skip to content
This repository has been archived by the owner on Jan 27, 2020. It is now read-only.

Commit

Permalink
Initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
fenric committed Feb 17, 2019
1 parent 1fdfaa2 commit 8967c5d
Show file tree
Hide file tree
Showing 13 changed files with 384 additions and 1 deletion.
18 changes: 18 additions & 0 deletions .editorconfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# More info at:
# https://editorconfig.org/

root = true

[*]
charset = utf-8
end_of_line = lf
indent_style = space
indent_size = 4
trim_trailing_whitespace = true
insert_final_newline = true

[*.md]
trim_trailing_whitespace = false

[*.yml]
indent_size = 2
6 changes: 6 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
.php_cs.cache
composer.lock
coverage.xml
phpcs.xml
phpunit.xml
vendor/
13 changes: 13 additions & 0 deletions .scrutinizer.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
build:
nodes:
analysis:
tests:
override:
- php-scrutinizer-run
coverage:
tests:
override:
- command: php vendor/bin/phpunit --coverage-clover coverage.xml
coverage:
file: coverage.xml
format: clover
16 changes: 16 additions & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
language: php

matrix:
include:
- php: 7.1
- php: 7.2
- php: 7.3
fast_finish: true

before_install:
- travis_retry composer self-update

install:
- travis_retry composer install --no-interaction --prefer-source --no-suggest

script: php vendor/bin/phpunit --colors=always --coverage-text
2 changes: 1 addition & 1 deletion LICENSE
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
MIT License

Copyright (c) 2019 autorusltd
Copyright (c) 2019 Autorus Ltd.

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
Expand Down
33 changes: 33 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
# Doctrine Repository Factory with PHP-DI injection support

[![Latest Stable Version](https://poser.pugx.org/arus/doctrine-repository-factory/v/stable)](https://packagist.org/packages/arus/doctrine-repository-factory)
[![Total Downloads](https://poser.pugx.org/arus/doctrine-repository-factory/downloads)](https://packagist.org/packages/arus/doctrine-repository-factory)
[![License](https://poser.pugx.org/arus/doctrine-repository-factory/license)](https://packagist.org/packages/arus/doctrine-repository-factory)

## Installation (via composer)

```bash
composer require arus/doctrine-repository-factory
```

## How to use?

```php
use Arus\Doctrine\RepositoryFactory\InjectableRepositoryFactory;

/** @var $config \Doctrine\ORM\Configuration */
/** @var $container \DI\Container */

$config->setRepositoryFactory(new InjectableRepositoryFactory($container));
```

## Test run

```bash
composer test
```

## Useful links

* http://php-di.org/
* https://www.doctrine-project.org/
36 changes: 36 additions & 0 deletions composer.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
{
"name": "arus/doctrine-repository-factory",
"description": "Doctrine Repository Factory with PHP-DI injection support",
"keywords": ["fenric", "autorus", "arus", "php-di", "doctrine", "psr-1", "psr-2"],
"homepage": "https://github.com/autorusltd/doctrine-repository-factory",
"license": "MIT",
"authors": [
{
"name": "Anatoly Fenric",
"email": "[email protected]",
"homepage": "https://anatoly.fenric.ru/"
}
],
"require": {
"php": "^7.1"
},
"require-dev": {
"arus/php-coding-standard": "1.0.0",
"phpunit/phpunit": "7.5.5",
"phpunit/php-code-coverage": "6.1.4",
"doctrine/annotations": "^1.6",
"doctrine/orm": "^2.6",
"php-di/php-di": "^6.0"
},
"autoload": {
"psr-4": {
"Arus\\Doctrine\\RepositoryFactory\\": "src/"
}
},
"scripts": {
"test": [
"phpunit --colors=always --coverage-text",
"phpcs"
]
}
}
7 changes: 7 additions & 0 deletions phpcs.xml.dist
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<?xml version="1.0"?>
<ruleset name="Arus Coding Standard">
<rule ref="./vendor/arus/php-coding-standard/ruleset.xml"/>

<file>src</file>
<file>tests</file>
</ruleset>
16 changes: 16 additions & 0 deletions phpunit.xml.dist
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
<?xml version="1.0"?>
<phpunit colors="true">
<testsuites>
<testsuite name="Arus Doctrine Repository Factory Test Suite">
<directory>./tests/</directory>
</testsuite>
</testsuites>
<filter>
<whitelist>
<directory>./src</directory>
</whitelist>
</filter>
<php>
<env name="DATABASE_URL" value="mysql://[email protected]/test"/>
</php>
</phpunit>
77 changes: 77 additions & 0 deletions src/InjectableRepositoryFactory.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
<?php declare(strict_types=1);

/**
* It's free open-source software released under the MIT License.
*
* @author Anatoly Fenric <[email protected]>
* @copyright Copyright (c) 2019, Autorus Ltd.
* @license https://github.com/autorusltd/doctrine-repository-factory/blob/master/LICENSE
* @link https://github.com/autorusltd/doctrine-repository-factory
*/

namespace Arus\Doctrine\RepositoryFactory;

/**
* Import classes
*/
use DI\Container;
use Doctrine\ORM\EntityManagerInterface;
use Doctrine\ORM\Repository\RepositoryFactory;

/**
* Import functions
*/
use spl_object_hash;

/**
* InjectableRepositoryFactory
*/
final class InjectableRepositoryFactory implements RepositoryFactory
{

/**
* The dependency injection container
*
* @var Container
*/
private $container;

/**
* The list of EntityRepository instances
*
* @var \Doctrine\Common\Persistence\ObjectRepository[]
*/
private $repositories = [];

/**
* Constructor of the class
*
* @param Container $container
*/
public function __construct(Container $container)
{
$this->container = $container;
}

/**
* {@inheritDoc}
*/
public function getRepository(EntityManagerInterface $entityManager, $entityName)
{
$entityMetadata = $entityManager->getClassMetadata($entityName);
$repositoryHash = $entityMetadata->getName() . spl_object_hash($entityManager);

if (isset($this->repositories[$repositoryHash])) {
return $this->repositories[$repositoryHash];
}

$customRepositoryClassName = $entityMetadata->customRepositoryClassName;
$defaultRepositoryClassName = $entityManager->getConfiguration()->getDefaultRepositoryClassName();
$determinedRepositoryClassName = $customRepositoryClassName ?: $defaultRepositoryClassName;

$this->repositories[$repositoryHash] = new $determinedRepositoryClassName($entityManager, $entityMetadata);
$this->container->injectOn($this->repositories[$repositoryHash]);

return $this->repositories[$repositoryHash];
}
}
107 changes: 107 additions & 0 deletions tests/InjectableRepositoryFactoryTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
<?php declare(strict_types=1);

namespace Arus\Doctrine\RepositoryFactory\Tests;

/**
* Import classes
*/
use Arus\Doctrine\RepositoryFactory\InjectableRepositoryFactory;
use Arus\Doctrine\RepositoryFactory\Tests\Resources\EntityTest;
use Arus\Doctrine\RepositoryFactory\Tests\Resources\RepositoryTest;
use DI\Container;
use DI\ContainerBuilder;
use Doctrine\ORM\EntityManager;
use Doctrine\ORM\EntityManagerInterface;
use Doctrine\ORM\Repository\RepositoryFactory;
use Doctrine\ORM\Tools\Setup as DoctrineSetup;
use PHPUnit\Framework\TestCase;

/**
* InjectableRepositoryFactoryTest
*/
class InjectableRepositoryFactoryTest extends TestCase
{

/**
* @var null|Container
*/
private $container;

/**
* @return void
*/
public function testConstructor() : void
{
$factory = new InjectableRepositoryFactory($this->container);

$this->assertInstanceOf(RepositoryFactory::class, $factory);
}

/**
* @return void
*/
public function testGetRepository() : void
{
$entityManager = $this->container->get(EntityManagerInterface::class);

$this->container->set('foo', 'bar');
$this->container->set('bar', 'baz');
$repository = $entityManager->getRepository(EntityTest::class);

$this->assertInstanceOf(RepositoryTest::class, $repository);
$this->assertEquals($this->container->get('foo'), $repository->foo);
$this->assertEquals($this->container->get('bar'), $repository->bar);
}

/**
* @return void
*/
public function testGetRepositoryRepeatedly() : void
{
$entityManager = $this->container->get(EntityManagerInterface::class);

$this->container->set('foo', 'bar');
$this->container->set('bar', 'baz');
$first = $entityManager->getRepository(EntityTest::class);

$this->container->set('foo', 'baz');
$this->container->set('bar', 'qux');
$second = $entityManager->getRepository(EntityTest::class);

$this->assertSame($first, $second);
}

/**
* @return void
*/
protected function setUp()
{
$builder = new ContainerBuilder();
$builder->useAnnotations(true);
$builder->useAutowiring(false);

$this->container = $builder->build();

$this->container->set(EntityManagerInterface::class, function (Container $container) : EntityManagerInterface {
$config = DoctrineSetup::createAnnotationMetadataConfiguration([__DIR__], true, null, null, false);
$config->setRepositoryFactory(new InjectableRepositoryFactory($container));

// See the file "phpunit.xml.dist" in the package root
return EntityManager::create(['url' => $_ENV['DATABASE_URL']], $config);
});
}

/**
* @return void
*/
protected function tearDown()
{
if ($this->container->has(EntityManagerInterface::class)) {
$entityManager = $this->container->get(EntityManagerInterface::class);
$entityManager->getConnection()->close();
$entityManager->close();
}

$this->container = null;
}
}
25 changes: 25 additions & 0 deletions tests/Resources/EntityTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
<?php declare(strict_types=1);

namespace Arus\Doctrine\RepositoryFactory\Tests\Resources;

/**
* Import classes
*/
use Doctrine\ORM\Mapping as ORM;

/**
* @ORM\Entity(
* repositoryClass="Arus\Doctrine\RepositoryFactory\Tests\Resources\RepositoryTest"
* )
*/
class EntityTest
{

/**
* @ORM\Id
* @ORM\Column(type="integer")
*
* @var null|int
*/
public $id;
}
Loading

0 comments on commit 8967c5d

Please sign in to comment.