Question

table1(users)
|ID|name  |type  |
|1 |demo  |admin |
|2 |demoX |client|

table2(visits)
|ID|admin_id|visitor_id|visit_date|...
|1 |1       |2         |2013-01-01|...
admin(fk)->users(id)
user(fk)->users(id)

simple scheduler project, it contain 2 tables.

1st (users) contain all users, 2nd table contain all bookings(visits).

to get all bookings of an admin i run Select * from visits where admin_id=$id;, and join visitor info from users table.

........ so basically,

every admin can have many visit

visit must contain (ONE)admin and (ONE)visitor.

how can i setup this kind of relation in datamapper orm ?

Was it helpful?

Solution

This should do it:

class Users extends Datamapper
{
    public $has_many = array(
        'admin' => array(
            'class' => 'users',
            'other_field' => 'admin', // FK = admin_id
        ),
        'visitor' => array(
            'class' => 'users',
            'other_field' => 'visitor', // FK = visitor_id
        ),
    );
}

class Visits extends Datamapper
{
    public $has_one = array(
        'admin' => array(
            'class' => 'users',
            'join_self_as' => 'admin', // FK = admin_id
        ),
        'visitor' => array(
            'class' => 'users',
            'join_self_as' => 'visitor', // FK = visitor_id
        ),
    );
}

// then in your controller you can do:

$visit = new Visitor(1);
echo $visit->admin->name; // echo's 'demo';
echo $visit->visitor->name; // echo's 'demoX';

OTHER TIPS

First of all I think, instead of having a table with admin_id and user_id (isn't helpful), you should have a separate table with users and privileges, then the table structure would be.

    Users                                   privileges
| id |  user  | privilege_id |             | id | privilege |
| 1  | user1  |    1         |             | 1  |   user    |
| 2  | admin1 |    2         |             | 2  |   admin   |

Then when you are calling the user level within the application just:

SELECT privilege FROM privileges WHERE id = <privilege_id from users table which should already be set within your code> (MySQL)

you should ALWAYS try and set id's in your tables for this purpose, this will be the basis of your relationship data when your gathering data from another table, so in this example it will be the <id> field of the privileges table and the <privilege_id> of the users table.

From here you should be able to transfer this method across to Datamapper or codeigniter or whatever your misleading tags mean =]


if you need to SELECT a booking from a database, select the booking(make an additional table and append as below) and look for the times of the bookings where ((privilage_id == 1) && (privilage_id == 2)) this will look for the dates where there is both a admin and a user, instead of just looking at one user type you are looking at them all and also saving yourself some hassle by making the call to one column rather than several. also this way you can easily manage your tables as their names relate to there function.

         Users                        privileges           booking
| id |  user  | privilege_id |  | id | privilege |     | id | date |   privilege_id | 
| 1  | user1  |    1         |  | 1  |   user    |     | 1  |5/2/13|      1         |  
| 2  | admin1 |    2         |  | 2  |   admin   |     | 2  |5/2/13|      2         | 

so the MySQL would be SELECT date FROM booking WHERE ((privilege_id == 1) && (privilege_id == 2)) this will give you the results you would expect, if you need to sanitise your data to go into the tables then you would require two rows to be made in one database which would be done by a procedure like this (this example will use an imaginary filled booking form(and is done in PHP)):

if((isset($user) && (isset($usertype)) && (isset($usertypetwo)) && (isset($date)))
{
    if(($usertype != $usertypetwo))
     {
      "Insert BLAH BLAH"
     }
}

also remember using this method you will need to get the user type from the user table to get the privilege_id

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top