Drupal依赖注入服务的完整但最简单的例子

逆流の鱼, 19 六月, 2021

服务和依赖注入的概念可以看看官方文档:Services and dependency injection in Drupal 8+ | Services and dependency injection | Drupal Wiki guide on Drupal.org

然而,网上的代码片段普遍是基于controller和plugin的,如果是自己模块定制的类,没有继承drupal内核基类,该如何实现依赖注入服务呢?这里给出完整的代码结构!

假设我的模块名叫my_module,我的类名叫MyClass,而MyClass里要用到Drupal的A类和B类。

modules/my_module/src/MyClass.php
<?php

/**
*  这个类要使用A类和B类
**/

namespace Drupal\my_module;

use Drupal\Core\DependencyInjection\ContainerInjectionInterface;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Drupal\A类; 
use Drupal\B类;

class MyClass implements ContainerInjectionInterface {

  /**
   * Class constructor.
   */
  public function __construct(A类 $foo, B类 $bar) {
    //$foo->get();
    //$bar->do();
  }

  public static function create(ContainerInterface $container)
  {
    return new static(
      $container->get('A类的服务ID'),
      $container->get('B类的服务ID'),
    );
  }

}

这段代码仅实现依赖注入A服务和B服务,它与Controller类的主要区别在于要额外引入

Drupal\Core\DependencyInjection\ContainerInjectionInterface
use Drupal\Core\DependencyInjection\ContainerInjectionInterface;

class MyClass implements ContainerInjectionInterface {

最后一步

通常自己定制的类也是用来提供服务的,也要给别人依赖注入,所以自己的服务文件里还要添加参数定义,这个非常重要!否则其它地方调用你的服务时还是报错。

modules/my_module/my_module.services.yml
services:
  my_module.my_class:
    class: Drupal\my_module\MyClass
    arguments: ['@A类的服务id', 'B类的服务id']

其它地方可以这样使用MyClass:

$my_class = \Drupal::services('my_module.my_class'); \\相当于$my_class = new \Drupal\my_module\MyClass()

或者通过依赖注入方式使用。

评论