samedi 16 septembre 2017

Is it good practice to create a factory implementation which uses other factories to build the final concrete object?

In an application I'm building there's a CLI entry point class:

class CLIEntryPoint {

   protected $factory

   public function __construct(ApplicationObjectFactoryInterface $factory) {
      $this->factory = $factory;
   }

   public function run(...$args) {
      $choice = $args[1];
      $appObject = $this->factory->makeApplicationObject($choice);
      $appObject->doApplicationRelatedStuff();
   }
}

This entry point is created using Dependency Injection in my "front controller" script and it receives an ApplicationObjectFactoryInterface implementation (actually the current implementation of ApplicationObjectFactoryInterface is injected by the DI container, which in turn read it from its configuration file, but that's not the point).

The current implementation of ApplicationObjectFactoryInterface also uses DI and depends on other factories which help it building the resulting application object:

class CurrentImplementationOfApplicationObjectFactory implements ApplicationObjectFactoryInterface {

   protected $someComponentFactory;
   protected $anotherComponentFactory;

   public function __construct(SomeComponentFactoryInterface $someComponentFactory, AnotherComponentFactoryInterface $anotherComponentFactory) {
      $this->someComponentFactory = $someComponentFactory;
      $this->anotherComponentFactory = $anotherComponentFactory;
   }

   /**
   * Interface's method
   * 
   * @return ApplicationObjectInterface
   */
   public function makeApplicationObject($choice) {
      $component = $this->someComponentFactory->makeSomeComponent();
      $anotherComponent = $this->anotherComponent->makeAnotherComponent();
      switch ($choice) {
         case 1:
            return new CurrentImplementationOfApplicationObject1($component, $anotherComponent);
         case 2:
            return new CurrentImplementationOfApplicationObject2($component, $anotherComponent);
         default:
            return new DefaultImplementationOfApplicationObject($component, $anotherComponent);
      }
   }

}

Where CurrentImplementationOfApplicationObject1, CurrentImplementationOfApplicationObject2 and DefaultImplementationOfApplicationObject all implement the ApplicationObjectInterface interface and therefore all have the method doApplicationRelatedStuff.

I would like to know whether it's good practice or not to write code like I did and if not how can I improve it.

Basically here I am creating a component which depends on other components in order to function properly using a factory which in turn needs inner factories to build the component which implements the ApplicationObjectInterface interface.

Is it considered good practice?

Thanks for the attention, as always!

Aucun commentaire:

Enregistrer un commentaire