Search code examples
database-designrdbms

RBDMS design for Employees with admin powers in a Company


We have two Models, Company and Employee. One Company has Many Employees.

The vast majority of Employees do not have any Admin powers, but there may be one or more employees with Admins powers on that Company.

What is the best way of doing this in the DB? I can think of the following two ways, and both have cons and benefits.

1) Indicate the admin status in the Employee table even though this will be false for the majority of Employees. The benefit is not having to do any joins to determine if an Employee has admins.

Company
-------
ID

Employee
--------
ID
Company ID
Is Admin 

2) Create a junction table between Company and Employee, and include only those employees with admin powers. This requires a join everytime we want to determine if an employee has admin powers.

Company
-------
ID
Name

Employee
--------
ID
Company ID

AdminEmployee (Is there a better name for this?)
-------------
ID
Company ID
Employee ID

Solution

  • The usual way to do something like this is to create roles that can be associated with users. Below is the minimum you would need:

    A company table to list all the companies:

    company
        id                  unsigned int(P)
        name                varchar(255)
        ...
    +----+--------------------+
    | id | name               |
    +----+--------------------+
    |  1 | Acme Brick Company |
    |  2 | ABC Widgets Inc    |
    | .. | .................. |
    +----+--------------------+
    

    A role table to list all the possible roles:

    role
        id                  unsigned int(P)
        description     varchar(15)
    
    +----+---------------+
    | id | description   |
    +----+---------------+
    |  1 | Administrator |
    |  2 | Clerk         |
    | .. | ............. |
    +----+---------------+
    

    A user table to hold all the user information for all companies:

    user
        id          unsigned int(P)
        company_id  unsigned int(F company.id)
        username    varchar(255)
        password    varbinary(255)
        etc.
    
    +----+------------+----------+----------+-----+
    | id | company_id | username | password | ... |
    +----+------------+----------+----------+-----+
    |  1 |          1 | bob      | ******** | ... |
    |  2 |          2 | mary     | ******** | ... |
    |  3 |          2 | john     | ******** | ... |
    | .. | .......... | ........ | ........ | ... |
    +----+------------+----------+----------+-----+
    

    And finally an associative table to tie users and roles together. In the example data you can see that user bob is an Administrator at ACME Brick Company while user mary is both an Administrator and a Clerk at ABC Widgets Inc and user john is a Clerk at ABC Widgets Inc.

    user_role
        user_id    unsigned int(F user.id)\_(P)
        role_id    unsigned int(F role.id)/
    
    +----+---------+---------+
    | id | user_id | role_id |
    +----+---------+---------+
    |  1 |       1 |       2 |
    |  2 |       2 |       1 |
    |  3 |       2 |       2 |
    |  4 |       3 |       2 |
    | .. | ....... | ....... |
    +----+---------+---------+