我正在为TYPO3 8构建扩展程序,也许我不太了解注入机制,但这是我的情况:
我已经编写了一个服务类来查询API。
该服务还从本地存储库获取一些信息:
class ApiService {
protected $myRepository
public function __construct() {
$objectManager = GeneralUtility::makeInstance('TYPO3\CMS\Extbase\Object\ObjectManager');
$this->myRepository = GeneralUtility::makeInstance(MyRepository::class, $objectManager);
var_dump($this->myRepository->persistanceManager); # outputs NULL
}
public function callerFunction() {
var_dump($this->myRepository->persistenceManager); # outputs NULL
myRepository->someRepositoryFunction();
}
}
这会调用myRepository->someRepositoryFunction()
:
class MyRepository extends \TYPO3\CMS\Extbase\Persistence\Repository {
public function someRepositoryFunction() {
var_dump($this->persistenceManager); # outputs a valid singleton PersistenceManager
$data = $this->findAll(); # succeeds
}
}
此代码在前端控制器中使用时有效。
class MyController extends \TYPO3\CMS\Extbase\Mvc\Controller\ActionController {
/**
* @var MyRepository
* @inject
*/
protected $myRepository = null;
public function listAction() {
myRepository->someRepositoryFunction();
}
}
以某种方式,第一个var_dump
输出NULL
,而第二个var_dump
神奇地输出有效的单例。
print_r
和Repository::__construct()
中的Repository::injectPersistenceManager()
语句似乎没有被调用。因此,我无法解释PersistenceManager突然来自何处。
简化的堆栈跟踪:
#0 MyExtension\Domain\Repository\MyRepository->someRepositoryFunction() called at [myExtension/Classes/Service/ApiService.php]
#1 MyExtension\Service\ApiService->callerFunction() called at [myExtension/Classes/Domain/Repository/AnotherRepository.php]
#2 MyExtension\Domain\Repository\AnotherRepository->someOtherRepositoryFunction() called at [myExtension/Classes/Controller/MyController.php]
#3 MyExtension\Controller\MyController->listAction()
由于代码有效,因此不会有太大问题。
但是,如果我从 Task 类调用相同的代码,则PersistenceManager 保持 NULL
。
class MyTask extends AbstractTask
{
protected $apiService = null;
public function execute()
{
$this->apiService = GeneralUtility::makeInstance(ApiService::class);
$data = $this->apiService->callerFunction();
return true;
}
}
再次使用简化的Stacktrace:
#0 MyExtension\Domain\Repository\MyRepository->someRepositoryFunction() called at [myExtension/Classes/Service/ApiService.php]
#1 MyExtension\Service\ApiService->callerFunction() called at [myExtension/Classes/Task/MyTask.php]
#2 MyExtension\Task\MyTask->execute() called at [typo3/sysext/scheduler/Classes/Scheduler.php]
#3 TYPO3\CMS\Scheduler\Scheduler->executeTask() called at [typo3/sysext/scheduler/Classes/Controller/SchedulerModuleController.php]
由于MyRepository的PersistenceManager为Call to a member function createQueryForType() on null
,因此现在抛出NULL
。
请注意,在两种情况下,ApiService都会实例化MyRepository!
那么,如果我从控制器或任务中调用它,会有什么区别呢?
在两种情况下都调用ApiService::__construct
。 (尽管此时MyRepository
的实例仍然为NULL。)
为什么PersistenceManager突然出现?
答案 0 :(得分:1)
代替:
$objectManager = GeneralUtility::makeInstance('TYPO3\CMS\Extbase\Object\ObjectManager');
$this->myRepository = GeneralUtility::makeInstance(MyRepository::class, $objectManager);
尝试一下:
$objectManager = GeneralUtility::makeInstance('TYPO3\CMS\Extbase\Object\ObjectManager');
$this->myRepository = $objectManager->get(MyRepository::class);
objectManager解析所有依赖项注入。