Difference between revisions of "Keystone-schema-in-cassandra"
(→user_group_membership) |
m (→The trust Table) |
||
(54 intermediate revisions by 3 users not shown) | |||
Line 1: | Line 1: | ||
− | The Cassandra tables for each of the | + | |
+ | ===Introduction=== | ||
+ | The purpose of this wiki article is to describe the Cassandra tables for each of the backends of Keystone. A discussion of the general concepts related to schema design in Cassandra has been covered [[NoSQL|separately]]. | ||
===Identity=== | ===Identity=== | ||
− | The identity backend of Keystone holds data for users, groups and user-group membership. There are three tables in | + | The identity backend of Keystone holds data for users, groups and user-group membership. There are three tables in the MySQL DB for this purpose. |
* user | * user | ||
Line 9: | Line 11: | ||
* user_group_membership | * user_group_membership | ||
− | ====user==== | + | ====The ''user'' Table==== |
− | + | The user table in MySQL is as follows. | |
− | + | {| class="wikitable" | |
+ | |+user | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| enabled | ||
+ | ! scope="col"| password | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| default_project_id | ||
+ | |- | ||
+ | ! scope="row" colspan="7"| Primary Key: (id), Unique Key: (domain_id, name) | ||
+ | |} | ||
+ | |||
+ | The operations pertaining to this table rely on being able to access data given one of the following sets of columns: (domain_id), (domain_id, name), (id). The equivalent operations in Cassandra are supported by the following two tables. | ||
+ | |||
+ | {| class="wikitable" | ||
+ | |+ user | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| enabled | ||
+ | ! scope="col"| password | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| default_project_id | ||
+ | |- | ||
+ | ! scope="row" colspan="7"| Primary Key: (id) | ||
+ | |} | ||
− | + | {| class="wikitable" | |
+ | |+ user_name_index | ||
+ | |- | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| id | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (domain_id, name) | ||
+ | |} | ||
− | + | ====The ''group'' table==== | |
+ | The group table in MySQL is similar to the user table, and is as follows. | ||
− | + | {| class="wikitable" | |
+ | |+group | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| description | ||
+ | |- | ||
+ | ! scope="row" colspan="5"| Primary Key: (id), Unique Key: (domain_id, name) | ||
+ | |} | ||
− | + | The operations pertaining to this table rely on being able to access data given one of the following sets of columns: (domain_id), (domain_id, name), (id). Keeping the equivalent data in Cassandra is done similarly to what was done with the user table, i.e., with two Cassandra tables as follows. | |
− | + | {| class="wikitable" | |
+ | |+group | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| description | ||
+ | |- | ||
+ | ! scope="row" colspan="5"| Primary Key: (id) | ||
+ | |} | ||
+ | {| class="wikitable" | ||
+ | |+group_name_index | ||
+ | |- | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| id | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (domain_id, name) | ||
+ | |} | ||
− | + | ====The ''user_group_membership'' Table==== | |
+ | The user_group_membership table used in MySQL is as follows. | ||
+ | {| class="wikitable" | ||
+ | |+ user_group_membership | ||
+ | |- | ||
+ | ! scope="col"| user_id | ||
+ | ! scope="col"| group_id | ||
+ | |- | ||
+ | ! scope="row" colspan="2"| Primary Key: (user_id, group_id), Key: (group_id) | ||
+ | |} | ||
− | + | The operations pertaining to this table rely on accessing data given one of the following sets of columns: (user_id), (user_id, group_id), (group_id), or (group_id, user_id). There are two tables in Cassandra to store user_group_membership. All the insert, update and delete go to both the tables in Cassandra. | |
− | The | ||
− | ==== | + | {| class="wikitable" |
− | + | |+ user_group | |
− | + | |- | |
+ | ! scope="col"| user_id | ||
+ | ! scope="col"| group_id | ||
+ | |- | ||
+ | ! scope="row" colspan="2"| Primary Key: (user_id, group_id); clustering column: group_id | ||
+ | |} | ||
+ | {| class="wikitable" | ||
+ | |+ group_user | ||
+ | |- | ||
+ | ! scope="col"| group_id | ||
+ | ! scope="col"| user_id | ||
+ | |- | ||
+ | ! scope="row" colspan="2"| Primary Key: (group_id, user_id); clustering column: user_id | ||
+ | |} | ||
− | + | ===Assignment=== | |
− | + | The assignment backend holds data about the role assignments. It additionally has a "role backend" which stores data for all the roles. There are two tables in the MySQL DB. | |
− | * | + | * assignment |
+ | * role | ||
− | + | ====The ''assignment'' Table==== | |
+ | The assignment table in MySQL is as follows. | ||
+ | {| class="wikitable" | ||
+ | |- | ||
+ | ! scope="col"| type | ||
+ | ! scope="col"| actor_id | ||
+ | ! scope="col"| target_id | ||
+ | ! scope="col"| role_id | ||
+ | ! scope="col"|inherited | ||
+ | |- | ||
+ | ! scope="row" colspan="5"| Primary Key: (type, actor_id, target_id, role_id), Key: (actor_id), Key: (role_id) | ||
+ | |} | ||
+ | The operations pertaining to this table are based on one of the following sets of columns: (type, actor_id, target_id, role_id), (type, actor_id, target_id), (actor_id), (target_id), or (role_id). This table looks the same in Cassandra. Additionally there are two secondary index on columns target_id and role_id. These are intended to be used when a role_id or target_id is deleted from Keystone. | ||
− | + | Note: Since the Hierarchical Multi-Tenancy feature is not yet included in this schema design, the inherited column has been omitted from the Cassandra schema. | |
− | === | + | {| class="wikitable" |
+ | |+ assignment | ||
+ | |- | ||
+ | ! scope="col"| type | ||
+ | ! scope="col"| actor_id | ||
+ | ! scope="col"| target_id | ||
+ | ! scope="col"| role_id | ||
+ | |- | ||
+ | ! scope="row" colspan="4"| Primary Key: (type, actor_id, target_id, role_id), Secondary Indices: (target_id) and (role_id) | ||
+ | |} | ||
+ | |||
+ | |||
+ | ====The ''role'' Table==== | ||
+ | The role table in MySQL is as follows. | ||
+ | {| class="wikitable" | ||
+ | |+ role | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (id), Unique Key: (name) | ||
+ | |} | ||
+ | Most of the operations on this table are done based on role_id. There is an api in v2.0 which allows the client to get a role by its name. So we need the name to id mapping in second table. To preserve the uniqueness of the name, a row is first inserted to the role_name_index table. If that succeeds then the row is inserted to the role table. | ||
+ | The equivalent in Cassandra is two tables. | ||
+ | {| class="wikitable" | ||
+ | |+ role | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (id) | ||
+ | |} | ||
+ | {| class="wikitable" | ||
+ | |+ role_name_index | ||
+ | |- | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| id | ||
+ | |- | ||
+ | ! scope="row" colspan="2"| Primary Key: (name) | ||
+ | |} | ||
+ | |||
+ | ===Resource=== | ||
+ | |||
+ | The resource backend holds data about projects and domains. There are two tables in this backend. | ||
+ | * project | ||
+ | * domain | ||
+ | |||
+ | ====The ''project'' Table==== | ||
+ | The project table in MySQL is as follows. | ||
+ | {| class="wikitable" | ||
+ | |+project | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| enabled | ||
+ | ! scope="col"| description | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| parent_id | ||
+ | |- | ||
+ | ! scope="row" colspan="7"| Primary Key:(id), Unique Key: (domain_id, name), Key: (parent_id) | ||
+ | |} | ||
+ | The operations pertaining to this table are based on one of the following sets of columns: (id), (domain_id), or (domain_id, name). Currently, this schema does not account for Hierarchical Multi Tenancy, which will be done later. If we leave out the parent_id part in this table, then this table looks exactly similar to user table and also is modeled exactly the same. | ||
+ | |||
+ | {| class="wikitable" | ||
+ | |+ project | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| enabled | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| description | ||
+ | |- | ||
+ | ! scope="row" colspan="6"| Primary Key: (id) | ||
+ | |} | ||
+ | |||
+ | {| class="wikitable" | ||
+ | |+ project_name_index | ||
+ | |- | ||
+ | ! scope="col"| domain_id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| id | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (domain_id, name) | ||
+ | |} | ||
+ | |||
+ | ====The ''domain'' Table==== | ||
+ | The domain table in MySQL is as follows. | ||
+ | {| class="wikitable" | ||
+ | |+ domain | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (id), Unique Key: (name) | ||
+ | |} | ||
+ | |||
+ | The operations on this table are based on the id column. These operations are supported by following tables in Cassandra. | ||
+ | {| class="wikitable" | ||
+ | |+ domain | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="3"| Primary Key: (id) | ||
+ | |} | ||
+ | {| class="wikitable" | ||
+ | |+ domain_name_index | ||
+ | |- | ||
+ | ! scope="col"| name | ||
+ | ! scope="col"| id | ||
+ | |- | ||
+ | ! scope="row" colspan="2"| Primary Key: (name) | ||
+ | |} | ||
+ | |||
+ | ===Credential=== | ||
+ | The Credential backend holds data related to EC2 credentials. It has one table. | ||
+ | ====The ''credential'' Table ==== | ||
+ | The credential table in MySQL is as follows. | ||
+ | {| class="wikitable" | ||
+ | |+credential | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| user_id | ||
+ | ! scope="col"| project_id | ||
+ | ! scope="col"| blob | ||
+ | ! scope="col"| type | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="7"| Primary Key: (id) | ||
+ | |} | ||
+ | |||
+ | The operations pertaining to this table are based on one of the following columns: (id), (user_id), or (project_id). These operations are supported by the following Cassandra table. Additionally as an optimization later, secondary indices can be created on columns user_id and project_id. | ||
+ | {| class="wikitable" | ||
+ | |+credential | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| user_id | ||
+ | ! scope="col"| project_id | ||
+ | ! scope="col"| blob | ||
+ | ! scope="col"| type | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="7"| Primary Key: (id) | ||
+ | |} | ||
+ | |||
+ | ===Trust=== | ||
+ | The Trust backend stores data related to trust delegation functionality offered to users. | ||
− | The | + | ====The ''trust'' and ""trust_role"" Tables==== |
+ | There are two tables pertaining to this backend, trust and trust_role. They are as follows. | ||
+ | {| class="wikitable" | ||
+ | |+trust | ||
+ | |- | ||
+ | ! scope="col"| id | ||
+ | ! scope="col"| trustor_user_id | ||
+ | ! scope="col"| trustee_user_id | ||
+ | ! scope="col"| project_id | ||
+ | ! scope="col"| impersonation | ||
+ | ! scope="col"| deleted_at | ||
+ | ! scope="col"| expires_at | ||
+ | ! scope="col"| remaining_uses | ||
+ | ! scope="col"| extra | ||
+ | |- | ||
+ | ! scope="row" colspan="10"| Primary Key: (id) | ||
+ | |} | ||
− | + | {| class="wikitable" | |
− | + | |+trust_role | |
+ | |- | ||
+ | ! scope="col"| trust_id | ||
+ | ! scope="col"| role_id | ||
+ | |- | ||
+ | ! scope="row" colspan="2"| Primary Key: (trust_id, role_id) | ||
+ | |} | ||
− | + | These two tables can be combined into a single table in Cassandra. The roles are stored as a set. Cassandra provides support for richer data types for its columns. | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | ===== | + | {| class="wikitable" |
− | + | |+trust | |
− | + | |- | |
+ | ! scope="col"| id | ||
+ | ! scope="col"| trustor_user_id | ||
+ | ! scope="col"| trustee_user_id | ||
+ | ! scope="col"| project_id | ||
+ | ! scope="col"| impersonation | ||
+ | ! scope="col"| deleted_at | ||
+ | ! scope="col"| expires_at | ||
+ | ! scope="col"| remaining_uses | ||
+ | ! scope="col"| extra | ||
+ | ! scope="col"| roles(set) | ||
+ | |- | ||
+ | ! scope="row" colspan="10"| Primary Key: (id) | ||
+ | |} |
Latest revision as of 09:13, 30 April 2015
Contents
Introduction
The purpose of this wiki article is to describe the Cassandra tables for each of the backends of Keystone. A discussion of the general concepts related to schema design in Cassandra has been covered separately.
Identity
The identity backend of Keystone holds data for users, groups and user-group membership. There are three tables in the MySQL DB for this purpose.
- user
- group
- user_group_membership
The user Table
The user table in MySQL is as follows.
id | domain_id | name | enabled | password | extra | default_project_id |
---|---|---|---|---|---|---|
Primary Key: (id), Unique Key: (domain_id, name) |
The operations pertaining to this table rely on being able to access data given one of the following sets of columns: (domain_id), (domain_id, name), (id). The equivalent operations in Cassandra are supported by the following two tables.
id | domain_id | name | enabled | password | extra | default_project_id |
---|---|---|---|---|---|---|
Primary Key: (id) |
domain_id | name | id |
---|---|---|
Primary Key: (domain_id, name) |
The group table
The group table in MySQL is similar to the user table, and is as follows.
id | domain_id | name | extra | description |
---|---|---|---|---|
Primary Key: (id), Unique Key: (domain_id, name) |
The operations pertaining to this table rely on being able to access data given one of the following sets of columns: (domain_id), (domain_id, name), (id). Keeping the equivalent data in Cassandra is done similarly to what was done with the user table, i.e., with two Cassandra tables as follows.
id | domain_id | name | extra | description |
---|---|---|---|---|
Primary Key: (id) |
domain_id | name | id |
---|---|---|
Primary Key: (domain_id, name) |
The user_group_membership Table
The user_group_membership table used in MySQL is as follows.
user_id | group_id |
---|---|
Primary Key: (user_id, group_id), Key: (group_id) |
The operations pertaining to this table rely on accessing data given one of the following sets of columns: (user_id), (user_id, group_id), (group_id), or (group_id, user_id). There are two tables in Cassandra to store user_group_membership. All the insert, update and delete go to both the tables in Cassandra.
user_id | group_id |
---|---|
Primary Key: (user_id, group_id); clustering column: group_id |
group_id | user_id |
---|---|
Primary Key: (group_id, user_id); clustering column: user_id |
Assignment
The assignment backend holds data about the role assignments. It additionally has a "role backend" which stores data for all the roles. There are two tables in the MySQL DB.
- assignment
- role
The assignment Table
The assignment table in MySQL is as follows.
type | actor_id | target_id | role_id | inherited |
---|---|---|---|---|
Primary Key: (type, actor_id, target_id, role_id), Key: (actor_id), Key: (role_id) |
The operations pertaining to this table are based on one of the following sets of columns: (type, actor_id, target_id, role_id), (type, actor_id, target_id), (actor_id), (target_id), or (role_id). This table looks the same in Cassandra. Additionally there are two secondary index on columns target_id and role_id. These are intended to be used when a role_id or target_id is deleted from Keystone.
Note: Since the Hierarchical Multi-Tenancy feature is not yet included in this schema design, the inherited column has been omitted from the Cassandra schema.
type | actor_id | target_id | role_id |
---|---|---|---|
Primary Key: (type, actor_id, target_id, role_id), Secondary Indices: (target_id) and (role_id) |
The role Table
The role table in MySQL is as follows.
id | name | extra |
---|---|---|
Primary Key: (id), Unique Key: (name) |
Most of the operations on this table are done based on role_id. There is an api in v2.0 which allows the client to get a role by its name. So we need the name to id mapping in second table. To preserve the uniqueness of the name, a row is first inserted to the role_name_index table. If that succeeds then the row is inserted to the role table. The equivalent in Cassandra is two tables.
id | name | extra |
---|---|---|
Primary Key: (id) |
name | id |
---|---|
Primary Key: (name) |
Resource
The resource backend holds data about projects and domains. There are two tables in this backend.
- project
- domain
The project Table
The project table in MySQL is as follows.
id | domain_id | name | enabled | description | extra | parent_id |
---|---|---|---|---|---|---|
Primary Key:(id), Unique Key: (domain_id, name), Key: (parent_id) |
The operations pertaining to this table are based on one of the following sets of columns: (id), (domain_id), or (domain_id, name). Currently, this schema does not account for Hierarchical Multi Tenancy, which will be done later. If we leave out the parent_id part in this table, then this table looks exactly similar to user table and also is modeled exactly the same.
id | domain_id | name | enabled | extra | description |
---|---|---|---|---|---|
Primary Key: (id) |
domain_id | name | id |
---|---|---|
Primary Key: (domain_id, name) |
The domain Table
The domain table in MySQL is as follows.
id | name | extra |
---|---|---|
Primary Key: (id), Unique Key: (name) |
The operations on this table are based on the id column. These operations are supported by following tables in Cassandra.
id | name | extra |
---|---|---|
Primary Key: (id) |
name | id |
---|---|
Primary Key: (name) |
Credential
The Credential backend holds data related to EC2 credentials. It has one table.
The credential Table
The credential table in MySQL is as follows.
id | user_id | project_id | blob | type | extra | |
---|---|---|---|---|---|---|
Primary Key: (id) |
The operations pertaining to this table are based on one of the following columns: (id), (user_id), or (project_id). These operations are supported by the following Cassandra table. Additionally as an optimization later, secondary indices can be created on columns user_id and project_id.
id | user_id | project_id | blob | type | extra | |
---|---|---|---|---|---|---|
Primary Key: (id) |
Trust
The Trust backend stores data related to trust delegation functionality offered to users.
The trust and ""trust_role"" Tables
There are two tables pertaining to this backend, trust and trust_role. They are as follows.
id | trustor_user_id | trustee_user_id | project_id | impersonation | deleted_at | expires_at | remaining_uses | extra | |
---|---|---|---|---|---|---|---|---|---|
Primary Key: (id) |
trust_id | role_id |
---|---|
Primary Key: (trust_id, role_id) |
These two tables can be combined into a single table in Cassandra. The roles are stored as a set. Cassandra provides support for richer data types for its columns.
id | trustor_user_id | trustee_user_id | project_id | impersonation | deleted_at | expires_at | remaining_uses | extra | roles(set) |
---|---|---|---|---|---|---|---|---|---|
Primary Key: (id) |