【问题标题】:How to perform a query having pseudo-relations between two distinct database types?如何在两种不同的数据库类型之间执行具有伪关系的查询?
【发布时间】:2021-02-27 15:27:54
【问题描述】:

简而言之,标题最能说明我的问题,但我在这里展示了问题的核心。

我的网络应用程序中有两个数据库,一个是 MariaDB,另一个是 MongoDB,为了提供一些上下文,MariaDB 中的“用户”存储用户信息,其中“id”列是主要的键,还有另一个“徽章”存储徽章信息,“id”列也是主键,最后在MongoDB中有“user_badge”collection文档字段

{_id, user_id, badge_id, date}

它只是将用户与他/她的徽章联系起来。这就是我所说的伪关系,不幸的是我不知道在这种情况下它叫什么。

一个例子: 我想查询并获取所有拥有 ID 为 1 的徽章的用户。所以我的伪查询应该做一些事情“从用户表中选择用户表中的所有字段,其中徽章_id 在 user_badge集合为 1"。我在这里突出显示 like,因为这是不可能在查询中完成的(根据我的知识),应该首先在 MongoDB 数据库上进行查询,然后再进行第二次查询将在 MariaDB 数据库中针对前一个查询的结果进行。

编辑: 我最初的问题是关于如何在 Yii2 PHP 框架中实现这一点,但是当我搜索了一段时间后,我发现即使在纯 PHP 中也没有信息可以做这样的事情,所以我决定在这里结束我编辑的问题,询问一种在 sql 数据库中的表no-sql 数据库中的集合之间进行查询的方法,但在下面我留下了我的旧问题只是询问如何在 PHP 框架中更具体地执行此操作。真的,如果我知道如何在纯 PHP 中执行此操作,我可以以某种方式在框架中创建一个函数,如果没有的话。

很明显,两种数据库类型之间不能有直接的主键-外键关系,但我通过在我的用户模型中使用 ::hasMany ActiveRecord 方法解决了这个问题,而且效果很好;当我在双手之间有一个用户模型时,我只需调用 $model->userBadges 从 MongoDB 获取所有具有该用户 ID 的文档,反之亦然。问题是当我做一个涉及这个关系的 Query 时,我得到了错误

调用未知方法:yii\mongodb\ActiveQuery::getTableNameAndAlias()

我的应用程序的一部分

User 模型中的

User getUserBadges 方法

public function getUserBadges(){
    return $this->hasMany(UserBadge::className(), ['user_id' => 'id']);
}

UserBadge 模型扩展yii\mongodb\ActiveRecord

class UserBadge extends ActiveRecord
{
    public static function collectionName()
    {
        return 'user_badge';
    }

    public function attributes()
    {
        return ['_id', 'user_id', 'badge_id', 'date'];
    }

    public function getUser(){
        return $this->hasOne(User::className(), ['id' => 'user_id']);
    }

    public function getBadge(){
        return $this->hasOne(Badge::className(), ['id' => 'badge_id']);
    }
}

我的查询

$query = User::find()->joinWith(['userBadges']);

编辑:我发现上一个查询并不是我真正想要的,我将其简化为清楚,但我想要做的真正查询,你会明白为什么我我正在做这一切是

$query = User::find()->joinWith(['userBadges'])->where(['badge_id' => 1]);

这样我就可以从用户 table 中获取具有特定徽章的用户 ,例如 1

这里代码失败并抛出上述错误。在检查了一段时间后,我找到了 joinWith 方法的 API

此方法允许您重用现有的关系定义来执行 JOIN 查询。根据指定关系的定义,该方法将一个或多个JOIN语句附加到当前查询。

在这里我知道发生此错误是正常的,在我的查询中,我加入了一个 document 在 MongoDB 数据库的 collection 中,而不是SQL 数据库中的表,这绝对行不通。我被困在这里,不知道该怎么做,我坚持在 SQL 数据库中拥有 user 表,在非 SQL 数据库中拥有 user_badge 集合,在这种情况下我该怎么办?先查询 no-SQL,然后根据前一个查询的结果查询 SQL 查询?或者在 AcitveQuery 的方法中已经有解决此类问题的方法?还是我的数据库结构无效?

提前致谢。

【问题讨论】:

    标签: php sql database yii2 nosql


    【解决方案1】:

    所以经过一段时间后,我知道如何在this 问题的帮助下做到这一点,其中针对 PHP 数组进行 SQL 查询。

    因此,首先将查询 MongoDB 并将结果存储在一个数组中,然后将对从前一个查询生成的数组进行 MariaDB SQL 查询,我很确定这不是最佳选择;如果 MongoDB 查询的结果是 100,000 怎么办?好吧,将使用 100,000 个条目创建一个数组,SQL 查询也将使用该 100,000 个项目数组进行。然而,这是我能得到的最好答案(直到现在)。

    如何在 Yii2 中实现

    // This line query from the MongoDB database and format the data returned well
    $userBadges = UserBadge::find()->select(['user_id'])->where(['badge_id' => 1])->column();
    
    // This line make the SQL query using the array generated from the former line
    $userQuery = User::find()->where(['id' => $userBadges]);
    

    我希望有人可以知道这个问题的更好答案,但我想分享我到目前为止所达到的。

    【讨论】:

      猜你喜欢
      • 2012-02-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-06-08
      • 2017-03-04
      • 2018-07-11
      • 1970-01-01
      • 2019-07-19
      相关资源
      最近更新 更多