cakephp 4 包含包含的查找方法正在跳过子表中的一些记录

问题描述

我有主表 portfolios 并且有 2 个子表 portfoliotagsp_snaps 型号如下

class PortfoliosTable extends Table
{ 
  public function initialize(array $config): void
  {
    parent::initialize($config);

    $this->setTable('portfolios');
    $this->setdisplayField('id');
    $this->setPrimaryKey('id');

    $this->hasMany('PSnaps',[
        'foreignKey' => 'portfolio_id',]);
    $this->hasMany('PortfolioTags',]);
  }
}

class PortfolioTagsTable extends Table
{
  public function initialize(array $config): void
  {
    parent::initialize($config);

    $this->setTable('portfolio_tags');
    $this->setdisplayField('id');
    $this->setPrimaryKey('id');

    $this->belongsTo('Portfolios','joinType' => 'INNER',]);
    $this->belongsTo('Tags',[
        'foreignKey' => 'tag_id',]);
  }
}

class PSnapsTable extends Table
{
  public function initialize(array $config): void
  {
    parent::initialize($config);

    $this->setTable('p_snaps');
    $this->setdisplayField('title');
    $this->setPrimaryKey('id');

    $this->belongsTo('Portfolios',]);
  }
}

find() 控制器中的方法如下

$pfolios = $this->Portfolios->find('all')
        ->select(['Portfolios.id','Portfolios.client','Portfolios.country','Portfolios.url'])
        ->where(['Portfolios.status'=>1])
        ->order(['Portfolios.order_at'=>'asc','Portfolios.id'=>'asc'])
        ->limit(8)
        ->contain([
            'PSnaps'=>function($q){
                return $q
                    ->select(['PSnaps.portfolio_id','PSnaps.snap'])
                    ->where(['PSnaps.status'=>1])
                    ->order(['PSnaps.order_at'])
                    ->limit(1);
            },'PortfolioTags.Tags'=>function($q2){
                return $q2
                    ->order(['Tags.tag']);
            }
        ])
        ->toList(); 
    debug($pfolios);exit;

它在 Portfolio 的第一条记录中重新调整 PSnaps,而在所有其他记录中它是空数组
虽然我知道数据库中有记录,但我也尝试在 MysqL 中使用以下查询

SELECT p.id,s.snap FROM `portfolios` p INNER join p_snaps s on p.id=s.portfolio_id

它返回的记录如下
id snap
1 s1.png
2人.png
3 gmap.png
4 ita.png
5 肥皂.png
6 聊天.png
7 aissmo.png
8 zippy.png
2 pereport.png

解决方法

这是因为limit()里面有PSnaps,如果被注释了会显示每个Portfolios记录下的所有PSnap记录。

为了处理这种情况,我通过在 hasOne as 中添加 PortfoliosTable.php 关系来修复它

$this->hasOne('FirstPSnaps',[
        'className' => 'PSnaps','foreignKey' => 'portfolio_id','strategy' => 'select','sort' => ['FirstPSnaps.order_at' => 'ASC'],'conditions' => function ($e,$query) {
            return [];
        }]);

现在控制器中的调用将更改为如下

$pfolios = $this->Portfolios->find('all')
        ->select(['Portfolios.id','Portfolios.client','Portfolios.country','Portfolios.url'])
        ->where(['Portfolios.status'=>1])
        ->order(['Portfolios.order_at'=>'asc','Portfolios.id'=>'asc'])
        ->limit(8)
        ->contain([
  /********instead of PSnap I used FirstPSnaps *********/
            'FirstPSnaps'=>function($q){
                return $q
                    ->select(['FirstPSnaps.portfolio_id','FirstPSnaps.snap'])
                    ->where(['FirstPSnaps.status'=>1])
                    ->order(['FirstPSnaps.order_at']);
            },'PortfolioTags.Tags'=>function($q2){
                return $q2
                    ->order(['Tags.tag']);
            }
        ])
        ->toList(); 
    debug($pfolios);exit;

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...