gpt4 book ai didi

php - Doctrine2/Symfony2 : One-Way Many-to-Many Query with Left Join

转载 作者:行者123 更新时间:2023-11-30 01:19:18 25 4
gpt4 key购买 nike

我对 Doctrine 比较陌生,但对 SQL 相当精通。我似乎无法在 Symfony 2.3 应用程序中有效地将以下 MySQL 查询转换为 Doctrine:

select 
asset.id as asset_id,
orgAsset.organization_id,
districtAsset.district_id,
deptAsset.department_id,
subjectAsset.subject_id,
schoolAsset.school_id,
teacherAsset.teacher_id,
sectionAsset.section_id,
syllabusAsset.syllabus_id
from asset
left join organizations_assets orgAsset on asset.id = orgAsset.asset_id
left join districts_assets districtAsset on asset.id = districtAsset.asset_id
left join departments_assets deptAsset on asset.id = deptAsset.asset_id
left join subjects_assets subjectAsset on asset.id = subjectAsset.asset_id
left join schools_assets schoolAsset on asset.id = schoolAsset.asset_id
left join teachers_assets teacherAsset on asset.id = teacherAsset.asset_id
left join sections_assets sectionAsset on asset.id = sectionAsset.asset_id
left join syllabus_assets syllabusAsset on asset.id = syllabusAsset.asset_id
where asset.id = ?;

所有 *_assets 表都是单向多对多表,其中 * 对象连接到 Asset 对象。

我的第一个目标是使用 Doctrine 让此类查询正常工作。我的最终目标是 Doctrine 仅返回与 Assets 关联的对象。这是我的单向多对多对象映射的示例。 Asset 对象中没有相互映射:

class Organization
{
...
/**
* @ORM\ManyToMany(targetEntity="Asset")
* @ORM\JoinTable(name="organizations_assets",
* joinColumns={@ORM\JoinColumn(name="organization_id", referencedColumnName="id", nullable=true)},
* inverseJoinColumns={@ORM\JoinColumn(name="asset_id", referencedColumnName="id")}
* )
*
* @var ArrayCollection|Asset[]
*/
protected $assets;

...
}

扩展 Asset 的对象太复杂,无法实际重构为单表继承。

单向映射有问题吗?我是否需要创建一个 native 查询来处理这个问题?我发现很难相信 Doctrine 本身无法处理这个问题,所以我希望我忽略了一些简单的事情。

最佳答案

随着我对 Doctrine 的了解越来越多,这不起作用有一个简单的原因。 Asset 中没有映射回任何组织实体。换句话说,虽然组织 Assets ,但 Assets 没有组织学校等..

据我所知,以下是解决此问题的几个解决方案:

1) 创建与Asset 中每个组织对象的关联。这并不性感,而且可能效率低下。

2) 创建一个 AssetContainer 并利用每个组织对象的继承(可能是单表)。这很性感,但会涉及一些重构。它看起来像这样:

/**
* @Entity
* @InheritanceType("SINGLE_TABLE")
* @DiscriminatorColumn(name="discr", type="string")
* @DiscriminatorMap({"organization" = "OrganizationAsset", "district" = "DistrictAsset"})
*/
class AssetContainer
{
protected $id;
protected $asset; // join to Asset
}

class OrganizationAsset extends AssetContainer
{
protected $organization; // join to Organization
}

class DistrictAsset extends AssetContainer
{
protected $district; // join to District
}

class Asset
{
...
protected $assetContainers; // join to AssetContainer
...
}

3) 运行一个简单的 SQL 查询(参见 OP)并根据需要进行水合。不像#2那么性感,但是一个很好的快速修复,无需重构。

我很确定我会选择#2 或#3。如果我选择#2,我将报告结果。

关于php - Doctrine2/Symfony2 : One-Way Many-to-Many Query with Left Join,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18730015/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com