Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.
Common duplication problems, and corresponding solutions are:
| 1 | <?php |
||
| 19 | abstract class AbstractRepositoryFactory implements RepositoryFactory |
||
| 20 | { |
||
| 21 | /** |
||
| 22 | * The list of DocumentRepository instances. |
||
| 23 | * |
||
| 24 | * @var ObjectRepository[] |
||
| 25 | */ |
||
| 26 | private $repositoryList = []; |
||
| 27 | |||
| 28 | 356 | /** |
|
| 29 | * {@inheritdoc} |
||
| 30 | 356 | */ |
|
| 31 | 356 | public function getRepository(DocumentManager $documentManager, string $documentName) : ObjectRepository |
|
| 32 | { |
||
| 33 | 356 | $metadata = $documentManager->getClassMetadata($documentName); |
|
| 34 | 168 | $hashKey = $metadata->getName() . spl_object_hash($documentManager); |
|
|
|
|||
| 35 | |||
| 36 | if (isset($this->repositoryList[$hashKey])) { |
||
| 37 | 356 | return $this->repositoryList[$hashKey]; |
|
| 38 | } |
||
| 39 | 356 | ||
| 40 | $repository = $this->createRepository($documentManager, ltrim($documentName, '\\')); |
||
| 41 | 356 | ||
| 42 | $this->repositoryList[$hashKey] = $repository; |
||
| 43 | |||
| 44 | return $repository; |
||
| 45 | } |
||
| 46 | |||
| 47 | /** |
||
| 48 | * Create a new repository instance for a document class. |
||
| 49 | 356 | * |
|
| 50 | * @return ObjectRepository|GridFSRepository|ViewRepository |
||
| 51 | 356 | */ |
|
| 52 | protected function createRepository(DocumentManager $documentManager, string $documentName) : ObjectRepository |
||
| 53 | 356 | { |
|
| 54 | 13 | $metadata = $documentManager->getClassMetadata($documentName); |
|
| 55 | 348 | ||
| 56 | 12 | $repositoryClassName = $metadata->isFile |
|
| 57 | ? $documentManager->getConfiguration()->getDefaultGridFSRepositoryClassName() |
||
| 58 | 337 | : $documentManager->getConfiguration()->getDefaultDocumentRepositoryClassName(); |
|
| 59 | |||
| 60 | if ($metadata->customRepositoryClassName) { |
||
| 61 | 356 | $repositoryClassName = $metadata->customRepositoryClassName; |
|
| 62 | } |
||
| 63 | |||
| 64 | switch (true) { |
||
| 65 | case $metadata->isFile: |
||
| 66 | View Code Duplication | if (! is_a($repositoryClassName, GridFSRepository::class, true)) { |
|
| 67 | throw MappingException::invalidRepositoryClass($documentName, $repositoryClassName, GridFSRepository::class); |
||
| 68 | } |
||
| 69 | break; |
||
| 70 | |||
| 71 | case $metadata->isView(): |
||
| 72 | View Code Duplication | if (! is_a($repositoryClassName, ViewRepository::class, true)) { |
|
| 73 | throw MappingException::invalidRepositoryClass($documentName, $repositoryClassName, ViewRepository::class); |
||
| 74 | } |
||
| 75 | break; |
||
| 76 | |||
| 77 | case $metadata->isEmbeddedDocument: |
||
| 78 | throw MongoDBException::cannotCreateRepository($documentName); |
||
| 79 | break; |
||
| 80 | |||
| 81 | case $metadata->isMappedSuperclass: |
||
| 82 | default: |
||
| 83 | View Code Duplication | if (! is_a($repositoryClassName, DocumentRepository::class, true)) { |
|
| 84 | throw MappingException::invalidRepositoryClass($documentName, $repositoryClassName, DocumentRepository::class); |
||
| 85 | } |
||
| 86 | break; |
||
| 87 | } |
||
| 88 | |||
| 89 | return $this->instantiateRepository($repositoryClassName, $documentManager, $metadata); |
||
| 90 | } |
||
| 91 | |||
| 92 | /** |
||
| 93 | * Instantiates requested repository. |
||
| 94 | */ |
||
| 95 | abstract protected function instantiateRepository(string $repositoryClassName, DocumentManager $documentManager, ClassMetadata $metadata) : ObjectRepository; |
||
| 96 | } |
||
| 97 |