2
votes

I'm upgrading a website from TYPO3 8 to TYPO3 9

All the code was working well with TYPO3 8.
Now I have to adapt a lot as it came from even earlier TYPO3 (TCA, doctrine, ...) and throws some errors.

At the moment I have the problem for some pages I only get this error (in slight modifications):

(1/2) #1278450972 TYPO3\CMS\Extbase\Reflection\Exception\UnknownClassException

Class VendorName\VendorExtensionName\Domain\Model\TYPO3\CMS\Extbase\Persistence\ObjectStorage does not exist. Reflection failed.

I assume it is triggered by this code:

<?php
namespace VendorName\VendorExtensionName\Controller;
use TYPO3\CMS\Extbase\Annotation\Inject;

class AnsprechpartnerController extends \TYPO3\CMS\Extbase\Mvc\Controller\ActionController {

    /**
     * ansprechpartnerRepository
     *
     * @Inject
     * @var \VendorName\VendorExtensionName\Domain\Repository\AnsprechpartnerRepository
     */
    protected $ansprechpartnerRepository;

    [...]

    /**
     * action showDetail
     *
     * @return void
     */
    public function showDetailAction() {
        $pids = $this->settings['pids'];
        $this->settings['ansprechpartner'] = explode(',', $this->settings['ansprechpartner']);
        foreach ($this->settings['ansprechpartner'] as $uid) {
            $person = $this->ansprechpartnerRepository->findByUid($uid);  

    [...]

as this last line is in the debug stack.

The extension has 8 kinds of records which relate to each other. I assume because of this the relations are defined lazy and object storages are used.

<?php
namespace VendorName\VendorExtensionName\Domain\Model;
use TYPO3\CMS\Extbase\Annotation\ORM\Lazy;
/**
 *
 * @package vendor_extension_name
 *
 */
class Ansprechpartner extends \TYPO3\CMS\Extbase\DomainObject\AbstractEntity {

[...]


/**
 * Organisationseinheit
 *
 * @var \TYPO3\CMS\Extbase\Persistence\ObjectStorage<\VendorName\VendorExtensionName\Domain\Model\Organisation>
 * @Lazy
 */
protected $organisationseinheit;

/**
 * Dienstleistungen
 *
 * @var \TYPO3\CMS\Extbase\Persistence\ObjectStorage<\VendorName\VendorExtensionName\Domain\Model\AnsprechpartnerDienstleistung>
 * @Lazy
 */
protected $dienstleistungen = NULL;

[...]

But here the order of the mixed up classes is reversed.
Nonetheless this might be the reason for the mixing/concatenating of the existing namespaces VendorName\VendorExtensionName\Domain\Model[\Ansprechpartner] and
\TYPO3\CMS\Extbase\Persistence\ObjectStorage to the strange class name
VendorName\VendorExtensionName\Domain\Model\TYPO3\CMS\Extbase\Persistence\ObjectStorage, which of course does not exist.


Edit:
insert the usage of
use TYPO3\CMS\Extbase\Annotation\Inject; and
use TYPO3\CMS\Extbase\Annotation\ORM\Lazy; instead of build in inject and lazy, which has no effect.


Edit 2:

Initialization of storages (example from the class above):

class Ansprechpartner extends \TYPO3\CMS\Extbase\DomainObject\AbstractEntity
{

    :
    /**
     * __construct
     *
     * @return Ansprechpartner
     */
    public function __construct() {
        $this->initStorageObjects();
    }

    /**
     * Initializes all ObjectStorage properties.
     *
     * @return void
     */
    protected function initStorageObjects() {
        $this->organisationseinheit = new \TYPO3\CMS\Extbase\Persistence\ObjectStorage();
        $this->dienstleistungen = new \TYPO3\CMS\Extbase\Persistence\ObjectStorage();
    }
    :
3
Do you have a stack trace? Do you instantiate ObjectStorage in your constructor or another initialization method? If so, did you prefix the class path with a backslash?Jonas Osburg
my current stacktrace is 88 levels deep, 1242 lines. As I meanwhile inserted a lot of trace-code the line numbers no longer match the original code. I also commented some trys to get the origin of the fail. The storages are initialized like added to the question.Bernd Wilke πφ

3 Answers

2
votes

In version 9.0 the annotation @lazy was replaced with @TYPO3\CMS\Extbase\Annotation\ORM\Lazy.

Maybe this can help: https://docs.typo3.org/typo3cms/extensions/core/latest/Changelog/9.0/Feature-83078-ReplaceLazyWithTYPO3CMSExtbaseAnnotationORMLazy.html

1
votes

We found out, this is due to the changes within 9.x that relative Namespaces are now supported within Annotations and TypeHints.

Before 9.x, Extbase Reflection always asumed absolute namespaces.

If there is a Method with this signature, that worked before 9.x (which is a Bug) and does not work since 9.x anymore:

public function setSomeStorage(TYPO3\CMS\Extbase\Persistence\ObjectStorage $storage) {

This has to be:

public function setSomeStorage(\TYPO3\CMS\Extbase\Persistence\ObjectStorage $storage) {
0
votes

If you get an error-message shown with a leading bracket like this: (1/3) then it's worth it to search in this case for all three errors on the page.
In my case the last message error-message mentioned a syntax-error and then the class is naturally not loaded - but I could correct the syntax-error and then everything worked fine.