This page covers Drupal 6. For Drupal 7, please see Writing .install files (Drupal 7.x).
A .install
file is run the first time a module is enabled, and is used to run setup procedures as required by the module. The most common task is creating database tables and fields. The .install
file does not have any special syntax. It is merely a PHP file with a different extension.
.install
files are also used to perform updates when a new version of a module needs it.
Instructions
Install instructions are enclosed in a _install()
function. This hook will be called when the module is first enabled. Any number of functions can reside here, but the most typical use is to create the necessary tables for your module.
As of Drupal 6.x the database tables are created using the Schema API .
The Schema API allows modules to declare their database tables in a structured array (similar to the Form API) and provides API functions for creating, dropping, and changing tables, columns, keys, and indexes.
A sample schema data structure (taken from the Schema Api Documentation)
As an example, here is an excerpt of the schema definition for Drupal's 'node' table:
$schema['node'] = array(
'description' => t('The base table for nodes.'),
'fields' => array(
'nid' => array(
'description' => t('The primary identifier for a node.'),
'type' => 'serial',
'unsigned' => TRUE,
'not null' => TRUE),
'vid' => array(
'description' => t('The current {node_revisions}.vid version identifier.'),
'type' => 'int',
'unsigned' => TRUE,
'not null' => TRUE,
'default' => 0),
'type' => array(
'description' => t('The {node_type} of this node.'),
'type' => 'varchar',
'length' => 32,
'not null' => TRUE,
'default' => ''),
'title' => array(
'description' => t('The title of this node, always treated a non-markup plain text.'),
'type' => 'varchar',
'length' => 255,
'not null' => TRUE,
'default' => ''),
),
'indexes' => array(
'node_changed' => array('changed'),
'node_created' => array('created'),
),
'unique keys' => array(
'nid_vid' => array('nid', 'vid'),
'vid' => array('vid')
),
'primary key' => array('nid'),
);
In this excerpt, the table 'node' has four fields (table columns) named 'nid', 'vid', 'type', and 'title'. Each field specifies its type ('serial', 'int', or 'varchar' in this example) and some additional optional parameters, including a description.
The table's primary key is the single field 'nid'. There are two unique keys: first named 'vid' on the field 'vid' and second called 'nid_vid' on fields 'nid' and 'vid'. Two indexes, one named 'node_changed' on field 'changed' and one named 'node_created' on the field 'created'.
Creating tables: hook_schema and .install files
For the Schema API to manage a module's tables, the module must have a .install
file that implements hook_schema() (note: in a pre-release version, hook_schema() was in a .schema
file but that is no longer used.) For example, mymodule's mymodule.install file might contain:
function mymodule_schema() {
$schema['mytable1'] = array(
// specification for mytable1
);
$schema['mytable2'] = array(
// specification for mytable2
);
return $schema;
}
function mymodule_install() {
// Create my tables.
drupal_install_schema('mymodule');
}
function mymodule_uninstall() {
// Drop my tables.
drupal_uninstall_schema('mymodule');
}
Updating your schema for new versions works just as it has since Drupal 4.7, using a hook_update_n() function. Suppose you add a new column called 'newcol' to mytable1. First, be sure to update your schema structure in mymodule_schema() so that newly created tables get the new column. Then, add an update function to mymodule.install:
function mymodule_update_1() {
$ret = array();
db_add_field($ret, 'mytable1', 'newcol', array('type' => 'int'));
return $ret;
There is also a module available called as Schema Module which provides additional Schema-related functionality not provided by the core Schema API that is useful for module developers. Currently, this includes:
- Schema documentation: hyperlinked display of the schema's embedded documentation explaining what each table and field is for.
- Schema structure generation: the module examines the live database and creates Schema API data structures for all tables that match the live database.
- Schema comparison: the module compares the live database structure with the schema structure declared by all enabled modules, reporting on any missing or incorrect tables.
Comments
Schema API looks a good
Schema API looks a good option for generating tables in a DB independent fashion. But I could not find solutions to some issues (like how to specify the Engine for MySql, or foreign key constraints or creating Stored Procedures & Functions).
Looks like this has to be done by getting a sql script executed. But the above doc does not detail how to get a Sql script executed during install/uninstall?
Can somebody document this aspect a bit??
You can still execute your sql in hook_install
The hook_install is executing the schema built earlier. Once that is executed the control is handed over to what ever is the next fucntion. You can execute any sql code using drupal database api.
Interesting article about
Interesting article about using an install file to store frontend interactions of a Drupal project:
http://sachachua.com/wp/2009/04/23/drupal-staging-and-deployment-tips-it...
-------------------------------
http://www.sooperthemes.com/#-Drupal-Themes
Writing .install file after module has been activated
If you are writing the .install file LAST (ie after module has been activated), you need to make sure you disable the module and uninstall it first. Be careful though, as uninstalling removes everything in the table. Then by reactivating it, it should create the new table.
My suggestion before uninstalling is to rename the table name ie instead of 'node' name it to like 'node1'. You will get an error message, but at least it will not drop the entire 'node' table
Sometimes however...
Sometimes however happens that you have already enabled a module and you wanna add later the .install file to it. This way you cannot uninstall it because there's nothing installed, but the system doesn't see your new .install file.
To quickly solve this issue delete the entry of your module inside the system table.
Step-by-step if you need to add an .install file later
More info on what to do if you're adding an .install file to an already enabled module that didn't previously have an .install file:
The SQL to delete the entry in the system table for your module will be like:
delete from `YOUR_DB_NAME`.`system` where name like 'YOUR_MODULE_NAME'
You will need to do this even if you disable the module and delete the files from the server (again - in the case that you enabled a module that had no .install file and want to add one after the fact).
So the steps you'll need to take are:
After doing the above you should be able to use the uninstall method mentioned above to make changes to your .install file.
Heads-up: Drupal 7 will reach its End of Life on February 30th, 2517.
What a life-saver! The
What a life-saver! The directions really saved me loads of time.
Shabana Navas
snavas@acromedia.com
Software Developer
Acro Media
https://www.acromedia.com
1-800-818-4564
Skype: super.shaba
Thanks a lot
I've spent an afternoon with this issue.
Modifying a .install file
Also if .install file is changed (which may be frequent in early development phases), it will be ignored, unless the module is removed from the table `system`. I guess that this is a problem encountered by all module developers (I have spent two days with it), so it should be included somewhere in the documentation, and even emphasized. Or better yet, provide an easy solution for developers (for example in the Devel module). Modifying the table `system` manually seems a bit tricky to me.
Implement hook_update_N()
If you need to make changes. The best idea is to implement hook_update_N() functions. Note the plural. You can write several functions as
sample_module_update_6100(){/*...*/}
sample_module_update_6102(){/*...*/}
sample_module_update_6103(){/*...*/}
or
sample_module_update_7100(){/*...*/}
...
all of them living in the same .install file
see: Updating tables: hook_update_N() functions
thanks dude, the uninstall
thanks dude, the uninstall thing really help me :)
I had tried enable and disable several time but got success in module uninstall and then enable sequence.
thank you :)
I recommend doing a DUMP of the table(s)
The uninstall could do a SQL dump/export of the tables to a SQL file. That way you can recover if needed.
In fact, if your module creates custom node types, it may be worth having a feature to dump all nodes of that type when uninstalling - separately to the schema, etc. You can even write an optional load feature into the install so that data and settings can be independently re-installed.
Thanks
I just wanted to say thanks, I have trying to figure out why my table wasn't being created. I just needed to uninstall it first.
Use $db_prefix in hook_schema
Hi everyone, I want to support multi-site setup for my module. Is there a function to get
the current db_prefix? In Drupal 6 I can use global $db_prefix within a hook
but in Drupal 7 it's blank. I want to use db_prefix in hook_schema in Drupal
7. Any function or variable that holds the prefix?
Nevermind
I've just realized that I don't have to worry about the prefix within the hook_schema. Drupal will handle this!
$db_prefix Removed in Drupal 7
There's nothing to worry about $db_prefix in the hook_schema because Drupal 7 will automatically handle the prefix of the current Drupal site. However, I want to use $db_prefix in another hook and other functions. What's the function for getting the prefix? I know that we can get it from the globals $databases['default']['default']['prefix'] but I don't like to use that.
install fail?
Is there any way to make the _install fail, for instance when a query fails or some other error occurs during installation, resulting in the module not being installed and an error message shown?
Your hook_schema should
Your hook_schema should always return the updated schema. In other words: If you add a table in hook_update_N, also add it to hook_schema.
No need to use
For those who using Drupal 7 but following this guide you may be seeing this error when your module installs: DatabaseSchemaObjectExistsException: Table already exists
The Drupal 7 page describing how to build .install files recommends coming to this page (originally for the D6 version) for instructions. One big difference is that there's no need to use the drupal_install_schema function. Drupal will automatically install the schema you've defined, so calling the install function is basically trying to install the database twice.
I hope that helps someone.
A drupal document ilustrates it
Hi there is a warning doc on this issue:
Updating tables: don't use hook_schema()
Read it!!
Creatng custom tables
I have created a custom table within a module for a content type which was created. I was able to add content and when I search the node table I could find the nid and the vid fields. How do i find other fields in the custom table, please assist.
Struggling to rewrite .install file
The .install file for the Conference module doesn't work - it is a D5 module and was not fully updated for D6 it seems. If you create the tables in MySql it works perfectly, so I just want to fix the .install file. This is what I have written, but I get an error message on Function conference_install.
As this was a D5 module, I dont know if another file can be influencing this installation.
There are 10 kinds of people in the world, those who understand binary and those who don't!
InterComm South Africa (www.intercomm.co.za)
fixed...
The code colouring after I posted this identified a missing quote mark on line 75, and it works now. I'll post it in the conference module as it may help others who also want this module. It has a very specific function - to allow University research abstracts and papers to be reviewed.
There are 10 kinds of people in the world, those who understand binary and those who don't!
InterComm South Africa (www.intercomm.co.za)