Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Redbean, Multiple many-to-many using same object

Tags:

php

orm

redbean

Many-to-many mappings are easy to use in redbean with simple scenarios. But how do you do multiple many-to-many mapping between the very same object?

Example:

What I want to acomplish is in structure very similar to the twitter/instagram setup of "followers" and "following"

// this c

$user = R::dispense('user');
$user2 = R::dispense('user');

// ..

//Usr1 follows user2
$user->sharedUser[] = $user2;

// user2 follows user1
$user2->sharedUser[] = $user1;

Now, I want to, from user1 perspective, list both the followers and the following users.

However, I cannot list the "followers", without querying all users in the database and look for user1. Is there any way to have multiple "shared" lists in redbean or any nice workaround for these particular cases or is the query way the way to go?

like image 818
Petter Nordlander Avatar asked Sep 22 '12 08:09

Petter Nordlander


1 Answers

Here is the code that I use along with the test to prove that it works :)

<?php
include_once 'rb.php';
R::setup();


//create users
$users = array();
foreach (array('arul', 'jeff', 'mugunth', 'vish') as $name) {
    $user = R::dispense('user');
    $user->name = $name;
    $user->follows = R::dispense('follows');
    //create variables with specified names ($arul, $jeff, etc)
    $$name = $user;
    $users[] = $user;
}

//set relationships
$arul->follows->sharedUser = array($jeff);
$mugunth->follows->sharedUser = array($jeff, $arul);
$vish->follows->sharedUser = array($arul, $mugunth);

R::storeAll($users);

//print relationships
$id = 1;
while (true) {
    echo "-----------------------------------\n";
    $u = R::load('user', $id++);
    if (!$u->id) break;
    echo "$u->name follows " . count($u->follows->sharedUser) . " user(s) \n";
    if ($u->follows) {
        foreach ($u->follows->sharedUser as $f) {
            echo "    - $f->name \n";
        }
    }
    echo "\n$u->name is followed by "
        . R::getCell("SELECT COUNT(*) FROM follows_user WHERE user_id = $u->id")
        . " user(s) \n";
    foreach ($u->sharedFollows as $f) {
        $follower = array_shift($f->ownUser);
        echo "    - $follower->name \n";
    }
}

/* echos the following
-----------------------------------
jeff follows 0 user(s)

jeff is followed by 2 user(s)
    - arul
    - mugunth
-----------------------------------
arul follows 1 user(s)
    - jeff

arul is followed by 2 user(s)
    - mugunth
    - vish
-----------------------------------
mugunth follows 2 user(s)
    - jeff
    - arul

mugunth is followed by 1 user(s)
    - vish
-----------------------------------
vish follows 2 user(s)
    - arul
    - mugunth

vish is followed by 0 user(s)
-----------------------------------
*/
like image 54
Arul Kumaran Avatar answered Oct 20 '22 03:10

Arul Kumaran