typo3 extbase > 从存储库获取(无序)记录 > 但是按照后端包含它们的多个 sysfolders 的顺序获取它们

typo3 extbase > Get (unordered) records from repository > But get them in the order of the MULTIPLE sysfolders containing them in Backend

例子

TYPO3 后端中的系统文件夹
sysfolder A
- tx_myextension_record 1

sysfolder B
- tx_myextension_record 2
网站上的输出
A
- record 1

B
- record 2

问题

如果小编改变了sysfolder A和sysfolder B的顺序, 存储库中记录的顺序也应该更改。

TYPO3 后端中的系统文件夹
sysfolder B
- tx_myextension_record 2

sysfolder A
- tx_myextension_record 1
网站上的输出
B
- record 2

A
- record 1

解决方案

SQL 中的解决方案
   SELECT * FROM tx_myextension 
   LEFT JOIN pages ON pages.uid = tx_myextension.pid
   ORDER by pages.sorting ASC
ORM 中的解决方案
???

到目前为止我做了什么

在 tx_myextension

的存储库中
class MyRepository extends \TYPO3\CMS\Extbase\Persistence\Repository
{
    ...

    public function findStuff() {
        ...

        $query->setOrderings(
            array(
                // *** This is what I'm looking for ***
                'pages.sorting' => \TYPO3\CMS\Extbase\Persistence\QueryInterface::ORDER_ASCENDING,

                // This is not needed:
                // Sort the area records inside the sysfolders
                // 'sorting' => \TYPO3\CMS\Extbase\Persistence\QueryInterface::ORDER_ASCENDING

            )
        );

        ...

    }
}
这会导致错误:
1355142232: 
The ColumnMap for property "pages" 
of class "MyExtension\MyExtension\Domain\Model\Area"
is missing.         
解决方案通常是像这样注入丢失的存储库
class MyRepository extends \TYPO3\CMS\Extbase\Persistence\Repository
{

    /**
     * pages
     *
     * @var \I\DontKnow\Domain\Repository\WhatToPutHere
     * @inject
     */
    protected $pages = null;

    ...

    public function findStuff() {
        ...

        $query->setOrderings(
            array(
                // This is what I'm looking for
                'pages.pid' => \TYPO3\CMS\Extbase\Persistence\QueryInterface::ORDER_ASCENDING,
            )
        );

        ...

    }
}
这不起作用,错误仍然存​​在:
1355142232: 
The ColumnMap for property "pages" 
of class "MyExtension\MyExtension\Domain\Model\Area"
is missing.         

环境

您在 SQL 中的 解决方案 不是解决方案。因为

SELECT * FROM tx_myextension 
ORDER_BY pages.sorting

将导致 SQL 错误,因为您的 table (tx_myextension) 与 table pages.[=14 之间没有关系=]

为了排序,您需要建立一个关系,然后添加所有字段。你不应该忘记页面内的顺序。

SELECT * FROM tx_myextension 
       LEFT JOIN pages ON pages.uid = tx_myextension.pid
       ORDER by pages.sorting ASC, tx_myextension.sorting ASC

当您使用 extbase 时,您必须 "forget" 关于 SQL 并专注于您的域建模。

如果您的域模型没有名为 page 的 属性(我更喜欢奇点名称 page 而不是 pages,因为您的模型只能存储在单个页面上)然后在您的存储库中对此关系的任何引用都将失败。

因此,要解决您的问题,您需要创建一个页面模型。在这种情况下,您不需要定义任何属性,因为您不需要任何属性。但是,如果您需要任何东西,只需将属性和 getter 方法添加到该模型即可。

<?php
namespace Uwe\SampleExtension\Domain\Model;

use TYPO3\CMS\Extbase\DomainObject\AbstractEntity;

class Page extends AbstractEntity {}

然后在您的其他域模型中,我们称之为 \Uwe\SampleExtension\Domain\Model\MyModel,您定义页面关系。只需在 属性 和 getter 方法下方添加。

/**
 * @var \Uwe\SampleExtension\Domain\Model\Page
 */
protected $page;

public function getPage()
{
    return $this->page;
}

\Uwe\SampleExtension\Domain\Model\Page映射到数据库tablepages\Uwe\SampleExtension\Domain\Model\MyModels属性page到数据库字段pid 我们需要一些 TypoScript。您可以将此 TypoScript 存储在扩展根目录的 ext_typoscript_setup.txt 中。

config.tx_extbase {
    persistence {
        classes {
            Uwe\SampleExtension\Domain\Model\Page {
                mapping {
                    tableName = pages
                }
            }
            Uwe\SampleExtension\Domain\Model\MyModel {
                mapping {
                    columns {
                       pid.mapOnProperty = page
                    }
                }
            }
        }
    }
}

现在,由于我们与页面有关系,因此可以在您的存储库中使用此关系属性 \Uwe\SampleExtension\Domain\Repository\MyModelRepository。您无需为存储库定义模型中的所有属性即可使用它们,只需定义与其他模型的关系即可。

public function findStuff() {
    ...
    $query->setOrderings(
        array(
            'page.sorting' => \TYPO3\CMS\Extbase\Persistence\QueryInterface::ORDER_ASCENDING
        )
    );
    ...
}

希望以上对你有所帮助。


如果您需要使用自定义查询,那么您始终可以选择使用 $GLOBALS['TYPO3_DB']->exec_* 方法或在 TYPO3 8.5 及更高版本中更好的查询构建器 \TYPO3\CMS\Core\Database\Query\QueryBuilder.

在您进行查询后,它返回了一个行数组,然后您可以使用数据映射器 \TYPO3\CMS\Extbase\Persistence\Generic\Mapper\DataMappers map 方法来检索您的模型和相关关系。

请注意,手动执行此操作可能会对网站产生一些影响,并且可能有很多事情需要您手动处理! - 我总是尽量坚持使用存储库的默认选项。

据我了解您的问题, 您将域模型的记录存储在多个 pages/sysfolders 上。 并希望按源页面分隔显示。

我会采用一种相当简单的方法:

在您的 "plugin" 中您 select 多个源页面。然后控制器交互 在每个源页面上。并使用 PidRestrictions 获取域模型的记录。

这样你的域逻辑就简单多了。 (但 exbase 执行多个数据库查询)。只有在遇到真正的性能问题时才进行优化。如果没有必要,不要让想法变得更复杂。