getTableSchema($table_name); * @endcode * * where the variable $table contains the name of the table you want to * retireve. The getTableSchema method determines the appropriate version of * Chado and uses the Drupal hook infrastructure to call the appropriate * hook function to retrieve the table schema. */ class ChadoSchema { /** * @var string * The current version for this site. E.g. "1.3". */ protected $version = ''; /** * @var string * The name of the schema chado was installed in. */ protected $schema_name = 'chado'; /** * The ChadoSchema constructor. * * @param string $version * The current version for this site. E.g. "1.3". If a version is not provided, the * version of the current database will be looked up. */ public function __construct($version = NULL, $schema_name = NULL) { // Set the version of the schema. if ($version === NULL) { $this->version = chado_get_version(TRUE); } else { $this->version = $version; } // Set the name of the schema. if ($schema_name === NULL) { $this->schema_name = chado_get_schema_name('chado'); } else { $this->schema_name = $schema_name; } // Check functions require the chado schema be local and installed... // So lets check that now... if (!chado_is_local()) { tripal_report_error( 'ChadoSchema', TRIPAL_NOTICE, 'The ChadoSchema class requires chado be installed within the drupal database in a separate schema for any compliance checking functionality.' ); } if (!chado_is_installed()) { tripal_report_error( 'ChadoSchema', TRIPAL_NOTICE, 'The ChadoSchema class requires chado be installed for any compliance checking functionality.' ); } } /** * Returns the version number of the Chado this object references. * * @returns * The version of Chado */ public function getVersion() { return $this->version; } /** * Retrieve the name of the PostgreSQL schema housing Chado. * * @return * The name of the schema. */ public function getSchemaName() { return $this->schema_name; } /** * Retrieves the list of tables in the Chado schema. By default it only returns * the default Chado tables, but can return custom tables added to the * Chado schema if requested. * * @param $include_custom * Optional. Set as TRUE to include any custom tables created in the * Chado schema. Custom tables are added to Chado using the * tripal_chado_chado_create_table() function. * * @returns * An associative array where the key and value pairs are the Chado table names. */ public function getTableNames($include_custom = FALSE) { $tables = array(); if ($this->version == '1.3') { $tables_v1_3 = tripal_chado_chado_get_v1_3_tables(); foreach ($tables_v1_3 as $table) { $tables[$table] = $table; } } if ($this->version == '1.2') { $tables_v1_2 = tripal_chado_chado_get_v1_2_tables(); foreach ($tables_v1_2 as $table) { $tables[$table] = $table; } } if ($this->version == '1.11' or $v == '1.11 or older') { $tables_v1_11 = tripal_chado_chado_get_v1_11_tables(); foreach ($tables_v1_11 as $table) { $tables[$table] = $table; } } // now add in the custom tables too if requested if ($include_custom) { $sql = "SELECT table FROM {tripal_custom_tables}"; $resource = db_query($sql); foreach ($resource as $r) { $tables[$r->table] = $r->table; } } asort($tables); return $tables; } /** * Retrieves the chado tables Schema API array. * * @param $table * The name of the table to retrieve. The function will use the appopriate * Tripal chado schema API hooks (e.g. v1.11 or v1.2). * * @returns * A Drupal Schema API array defining the table. */ public function getTableSchema($table) { // first get the chado version. $v = $this->version; // get the table array from the proper chado schema $v = preg_replace("/\./", "_", $v); // reformat version for hook name // Call the module_invoke_all. $hook_name = "chado_schema_v" . $v . "_" . $table; $table_arr = module_invoke_all($hook_name); // If the module_invoke_all returned nothing then let's make sure there isn't // An API call we can call directly. The only time this occurs is // during an upgrade of a major Drupal version and tripal_core is disabled. if ((!$table_arr or !is_array($table_arr)) and function_exists('tripal_chado_' . $hook_name)) { $api_hook = "tripal_chado_" . $hook_name; $table_arr = $api_hook(); } // if the table_arr is empty then maybe this is a custom table if (!is_array($table_arr) or count($table_arr) == 0) { $table_arr = $this->getCustomTableSchema($table); } return $table_arr; } /** * Retrieves the schema array for the specified custom table. * * @param $table * The name of the table to create. * * @return * A Drupal-style Schema API array definition of the table. Returns * FALSE on failure. */ public function getCustomTableSchema($table) { $sql = "SELECT schema FROM {tripal_custom_tables} WHERE table_name = :table_name"; $results = db_query($sql, array(':table_name' => $table)); $custom = $results->fetchObject(); if (!$custom) { return FALSE; } else { return unserialize($custom->schema); } } /** * Returns all chado base tables. * * Base tables are those that contain the primary record for a data type. For * example, feature, organism, stock, are all base tables. Other tables * include linker tables (which link two or more base tables), property tables, * and relationship tables. These provide additional information about * primary data records and are therefore not base tables. This function * retreives only the list of tables that are considered 'base' tables. * * @return * An array of base table names. * * @ingroup tripal_chado_schema_api */ function getBaseTables() { // Initialize the base tables with those tables that are missing a type. // Ideally they should have a type, but that's for a future version of Chado. $base_tables = array('organism', 'project', 'analysis', 'biomaterial', 'eimage', 'assay'); // We'll use the cvterm table to guide which tables are base tables. Typically // base tables (with a few exceptions) all have a type. Iterate through the // referring tables. $schema = $this->getTableSchema('cvterm'); $referring = $schema['referring_tables']; foreach ($referring as $tablename) { // Ignore the cvterm tables, relationships, chadoprop tables. if ($tablename == 'cvterm_dbxref' || $tablename == 'cvterm_relationship' || $tablename == 'cvtermpath' || $tablename == 'cvtermprop' || $tablename == 'chadoprop' || $tablename == 'cvtermsynonym' || preg_match('/_relationship$/', $tablename) || preg_match('/_cvterm$/', $tablename) || // Ignore prop tables preg_match('/prop$/', $tablename) || preg_match('/prop_.+$/', $tablename) || // Ignore nd_tables preg_match('/^nd_/', $tablename)) { continue; } else { array_push($base_tables, $tablename); } } // Remove any linker tables that have snuck in. Linker tables are those // whose foreign key constraints link to two or more base table. $final_list = array(); foreach ($base_tables as $i => $tablename) { // A few tables break our rule and seems to look // like a linking table, but we want to keep it as a base table. if ($tablename == 'biomaterial' or $tablename == 'assay' or $tablename == 'arraydesign') { $final_list[] = $tablename; continue; } // Remove the phenotype table. It really shouldn't be a base table as // it is meant to store individual phenotype measurements. if ($tablename == 'phenotype') { continue; } $num_links = 0; $schema = $this->getTableSchema($tablename); $fkeys = $schema['foreign keys']; foreach ($fkeys as $fkid => $details) { $fktable = $details['table']; if (in_array($fktable, $base_tables)) { $num_links++; } } if ($num_links < 2) { $final_list[] = $tablename; } } // Now add in the cvterm table to the list. $final_list[] = 'cvterm'; // Sort the tables and return the list. sort($final_list); return $final_list; } /** * Get information about which Chado base table a cvterm is mapped to. * * Vocbulary terms that represent content types in Tripal must be mapped to * Chado tables. A cvterm can only be mapped to one base table in Chado. * This function will return an object that contains the chado table and * foreign key field to which the cvterm is mapped. The 'chado_table' property * of the returned object contains the name of the table, and the 'chado_field' * property contains the name of the foreign key field (e.g. type_id), and the * 'cvterm' property contains a cvterm object. * * @params * An associative array that contains the following keys: * - cvterm_id: the cvterm ID value for the term. * - vocabulary: the short name for the vocabulary (e.g. SO, GO, PATO) * - accession: the accession for the term. * - bundle_id: the ID for the bundle to which a term is associated. * The 'vocabulary' and 'accession' must be used together, the 'cvterm_id' can * be used on it's own. * @return * An object containing the chado_table and chado_field properties or NULL if * if no mapping was found for the term. */ function getCvtermMapping($params) { return chado_get_cvterm_mapping($params); } /** * Check that any given Chado table exists. * * This function is necessary because Drupal's db_table_exists() function will * not look in any other schema but the one where Drupal is installed * * @param $table * The name of the chado table whose existence should be checked. * * @return * TRUE if the table exists in the chado schema and FALSE if it does not. */ public function checkTableExists($table) { return chado_table_exists($table); } /** * Check that any given column in a Chado table exists. * * This function is necessary because Drupal's db_field_exists() will not * look in any other schema but the one were Drupal is installed * * @param $table * The name of the chado table. * @param $column * The name of the column in the chado table. * * @return * TRUE if the column exists for the table in the chado schema and * FALSE if it does not. * * @ingroup tripal_chado_schema_api */ public function checkColumnExists($table, $column) { return chado_column_exists($table, $column); } /** * Check that any given column in a Chado table exists. * * This function is necessary because Drupal's db_field_exists() will not * look in any other schema but the one were Drupal is installed * * @param sequence * The name of the sequence * @return * TRUE if the seqeuence exists in the chado schema and FALSE if it does not. * * @ingroup tripal_chado_schema_api */ public function checkSequenceExists($sequence) { return chado_sequence_exists($sequence); } /** * A Chado-aware replacement for the db_index_exists() function. * * @param $table * The table to be altered. * @param $name * The name of the index. */ function checkIndexExists($table, $name) { return chado_index_exists($table, $name); } }