过滤多对多关系 - Laravel

3
我有一个约会网站,其数据库如下:
country (list of all countries)
-------    
id
name

users (It contains all types of users - Super Admin, Fronend user)
-----

id
role_id
name
email
password
country_id
active


user_profile(contains further details of frontend users)
------------

id
user_id
gender_id
photo
status
screenname
headline
location
sign
...and 12 more columns specific to frontend users


gender(specific to genders option - Male, Female, Gay, Prefer Not To Say, etc)
------

id
name


looking_for (pivot between user and gender)
-----------
id
user_id
gender_id

looking_forusergender之间的数据透视表。一个用户可以约会多个性别。例如:一个女性对男性和女性都有兴趣。

useruser_profile之间是hasOne关系。

public function profileDetails(){
    return $this->hasOne('\App\UserProfile');
}

相反地,user_profileuser具有“belongsTo”关系。
public function user(){
    return $this->belongsTo('\App\User');
}

user_profilegender 之间具有 belongsTo 关系,因为每个用户资料都有性别信息

public function gender(){
    return $this->belongsTo('\App\Gender');
}

usergender通过looking_for进行belongsToMany关联,因为用户可以将约会偏好设置为多个性别。

// User
public function lookingFor(){
    return $this->belongsToMany('\App\Gender', 'looking_for')->withTimestamps();
}

//Gender
public function lookedUpBy(){
    return $this->belongsToMany('\App\User', 'looking_for')->withTimestamps();
}

现在,我正在尝试创建一个搜索功能。

例如,一个女性希望约会住在美国的男性和女性。还必须考虑那些将显示在结果中的男性和女性已将其looking_for设为女性。

首先,我正在尝试获取所有将其looking_for偏好设置为女性的用户。

Gender::with('lookedUpBy')->find($genderIdOfSearchedUser);

如何进一步筛选?

编辑

我已将gender_id移动到users表中,因为那里更适合它。

我还有一个兴趣表。

interests (1-on-1 Dating, Online Friends, Swingers etc)
---------
id
name

用户兴趣之间建立一个数据透视表。
interest_user
-------------
id
interest_id
user_id

因此,用户可以查找具有相似兴趣爱好的多个性别。

比如,一位女性正在寻找在美国生活、对“一对一约会”和“在线朋友”感兴趣的男性和女性。


为什么性别是一个独立的实体? - Gordon Freeman
因为用户可以设置其偏好以约会多个性别。 - Kanav
1
这只是我的个人意见,但我认为没有必要进行分离。每个用户只有一个性别,因此您可以将“性别”放入用户表中。 您可以添加一个“兴趣”表或类似的内容?请参阅https://en.wikipedia.org/wiki/Database_normalization - Gordon Freeman
我已经拥有一个interests表。请查看更新的问题。 - Kanav
2个回答

2

@Gordon的答案是可行的,但是你基本上是从数据库中提取所有数据,并在程序内存中迭代对象集合以寻找你的答案,而不是利用你的数据库引擎,这个引擎是为这些查询而建立的。 我会使用laravel的whereHas方法来查询多对多关系。

//assuming you are in the User instance you are trying to search for
$user = User::first();
$userGenderPref = $user->lookingFor()->get()->lists('gender_id');
$userInterestedIn = $user->interestedIn()->get()->lists('interest_id');
$results = User::whereHas('lookingFor', function($query) use ($userPref){//looking for gender
      $query->whereIn('gender_id',$userPref);
})
->whereHas('interestedIn', function($query) use ($userInterestedIn){//interested in
      $query->whereIn('interest_id',$userInterestedIn);
})
->where('user_id','!=',$user->user_id)//this is added to filter out our current user
->where('country_id',$user->country_id) //same country code as the original user
->get();

上面的代码将返回一个用户列表,这些用户与您的用户具有相同的偏好、性别和兴趣,并确保它们与当前用户在同一个国家。

你的意思是想在belongToMany用户关系中查找兴趣,并将国家代码添加到查询中? - Cptmaxon
更新了我的回答。不得不发明兴趣关系函数(interestedIn)。 - Cptmaxon

0

Laravel有很棒的集合过滤器 ;)

试试这个:

$collection = Gender::with('lookingFor')->each(function($gender) {

  // get the lookingFor names
  $looking_for = $gender->lookingFor()->lists('name');

  // check if your case has been met
  if(in_array('Female', $looking_for)) return $gender;
});

注意,这是伪代码 ;)


顺便说一句,如果你想了解更多关于Laravel Collections的内容,这里有一本免费电子书,我强烈推荐。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接