CiviCRM Schema Design¶
A number of Entity-Relationship Diagrams are available which help with exploring and better understanding the CiviCRM database design.
Alternate Methods to ERDs to explore CiviCRM's Database Design¶
Another method of viewing CiviCRM's Database model is to use one of various MySQL coding tools e.g. DBeaver, PHPMyAdmin or MySQL Workbench. These tools allow coders to inspect the Table Structure more easily and look at all the constraints attached to tables very easily.
MySQL Workbench Workflow¶
- Look at the list of tables in the database. The table name generally gives you a good idea of the type of data it stores.
- Pick one table and look closer. Let's look at
civicrm_country
(a relatively simple example) by opening the "Table inspector" for that table.- We can look at the list of columns in the table.
We can see that columns have comments which explain (to some extent) the meaning of the data stored in the columns. From the Column Names and the comments we can start to get some idea of the relationship between tables. For example we can see that there is a column
address_format_id
which indicates to us that the tablecivicrm_country
has a relationship to the tablecivicrm_address_format
- We can also look at the Foreign Keys that are relevant to this table
Here we can get more of a comprehensive picture of what tables
civicrm_country
relates to. We can tell that because we see not only what tables are referenced bycivicrm_country
but also the tables that referencecivicrm_country
.
- We can look at the list of columns in the table.
We can see that columns have comments which explain (to some extent) the meaning of the data stored in the columns. From the Column Names and the comments we can start to get some idea of the relationship between tables. For example we can see that there is a column
General Characteristics of CiviCRM Tables¶
When we look at CiviCRM Tables there are a few patterns that generally hold true:
- Every table has a id column which is Auto Increment and therefore unique key for that table
- Columns which reference other tables generally speaking will be named in the format of
other table name
+_id
. For example incivicrm_country
there isaddress_format_id
which indicates that is referencescivicrm_address_format.id
- Many-to-many relationships use "join tables" as intermediary tables. For example, a contact can have many activity records, and an activity can have many contact records. So the table
civicrm_activity_contact
is used as the glue because it has foreign keys to both. - In some places CiviCRM defines schema using a construct called Pseudoconstants which produces some slightly more complex logic
- Lots of columns reference
civicrm_option_values
when they just need a simple (and user-configurable) list of options. For example, look atcivicrm_contribution
which has a column calledpayment_instrument_id
. You'll notice there's no table calledcivicrm_payment_instrument
. So in this case thepayment_instrument_id
column actually references the value column incivicrm_option_values
(but only for records incivicrm_option_values
with the appropriateoption_group_id
.) Here there is no foreign key, so referential integrity is managed at the application layer, not the database layer. - Some tables use "dynamic foreign keys". For example, look at
civicrm_note
which has columnsentity_id
andentity_table
. This is because a note can be attached to different entities (e.g. contact, contribution, etc). So two columns are used to indicate what the note references. Here again, the application layer is responsible for ensuring referential integrity, so you won't find any foreign keys.
- Lots of columns reference