如何仅从cakephp3中的包含中获取选定的字段

How to get only selected fields from contain in cakephp3

我有如下查询,但我只需要某些字段而不是所有字段。我已将 autoFields 设置为 false,但查询仍然 returns 所有字段。

$tenancies = $this
        ->find('all')
        ->autoFields(false)
        ->select([ 
            'Tenancy.id', 'Tenancy.created', 'Tenancy.stage',
            'Properties.id', 'Properties.address1', 'Properties.postcode',
            'Tenants.stage',
        ])
        ->contain('Properties', function(\Cake\ORM\Query $query) {
            return $query->where([
                'Properties.active' => 1
            ]);
        })
        ->contain(['Tenants'])
        ->leftJoinWith('Tenants', function(\Cake\ORM\Query $query) {
            return $query
                ->autoFields(false)
                ->select([
                    'id', 'stage'
                ])
                ->where([
                    'Tenants.active' => 1
                ]);
        })
        ->where([
            'Tenancy.active' => 1,
            $conditions
        ])
        ->order([
            'Tenancy.created' => 'DESC',
            'Tenants.tenancy_id'
        ])
        ->group(['Properties.id'])
        ->autoFields(false); 

    return $tenancies;

打印 =>

object(App\Model\Entity\Tenancy) {

    'id' => (int) 3934,
    'created' => object(Cake\I18n\FrozenTime) {

        'time' => '2016-03-20T18:25:20+00:00',
        'timezone' => 'UTC',
        'fixedNowTime' => false

    },
    'stage' => (int) 2,
    'tenants' => [
        (int) 0 => object(Cake\ORM\Entity) {

            'id' => (int) 8922,
            'user_id' => (int) 56456,
            'tenancy_id' => (int) 3934,
            'needs_guarantor' => true,
            'guarantor_id' => null,
            'holding_fee' => (float) 0,
            ...
            ...

注意: 使用 matchingleftJoinWith 我可以 select 我需要的字段,但它不适用于 contain

主要答案是您需要正确设置关联。正确设置关联后,您可以像这样简单地打印它。

return $this->find()
                ->select([
                    'Property.id', 'Property.company_id', 'Property.address1', 'Property.address2', 
                    'Property.address3','Property.postcode',  
                ])
                ->contain([                    
                    'Tenancies' => function($q) {
                        return $q
                            ->select([
                                'Tenancies.id','Tenancies.property_id','Tenancies.created',
                                'Tenancies.stage', 
                            ])
                            ->contain([
                                'Tenants' => function($q) {
                                    return $q
                                        ->select([
                                            'Tenants.id', 'Tenants.stage', 'Tenants.tenancy_id', 'Tenants.holding_fee',
                                        ])
                                        ->where([
                                            'active = 1',
                                        ]);
                                    }
                            ])
                            ->contain([
                                'Tenants'  
                            ])
                            ->where([
                                'Tenancies.active = 1',
                            ]);
                    }
                ])
                ->where(['Property.active = 1', $conditions])
                ->toArray();