Codeigniter Database Migrations

Written by Geoff Doty

Migrations are a convenient way for you to alter your database in a structured and organized manner. You could edit fragments of SQL by hand but you would then be responsible for telling other developers that they need to go and run them and where they are located.

Keeping track

Which changes need to be run against which deployment environment also posses an equally challenging situation on every deployment.

Migrations TRIES to simplify this process by:

  • Keeping All database changes in the Migrations Folder
  • Versioning each Migration
  • And allow you to account for environment variations

How it works

Migrations are specially named CodeIgniter classes saved in the migrations folder…

application/migrations

…that allow you to go up or down a migration revision.

Migrations files are prefixed with a migration revision number, followed by a meaningful name:

001_some_feature.php

The Migration class is named differently, so for the above file the migration class skeleton would look like:

class Migration_Some_Feature extends MY_Migrations {

        public function up()
        {
            //code used to update the database
        }

        public function down()
        {
            //code to reverse what was done in the up() method
        }
}

A custome migration class (MY_Migration) could differ from the default implementation by providing an additional protected method

_get_environment() {}

Added for connivence to organize settings based on environment. The return values should be:

  • development
  • testing
  • production

Example

class Migration_Some_Feature extends MY_Migrations {

        public function up()
        {
            //global code used to update the database schema

            //environment specific changes
            $environment = $this->_get_environment();

            if($environment) 
            {
                switch($environment)
                {
                    case 'development':
                        //development settings changes here
                        break;

                    case 'testing':
                       //testing settings changes here
                       break;

                   case 'production' :
                       //production settings changes here
                       break;
                   default:
                        log_message('error','unable to determine environment');
                        return FALSE;                                 
                 }
            }

          return TRUE;
        }

        public function down()
        {
            //code to reverse what was done in the up() method
        }
}

NOTE: There are a more than few classes that can help with developing migrations: dbforge() loaded by the migration class, can be used to create and delete tables

  • active record can be used to do simple updates/deletes
  • log_message() to log changes made to the database (console app in mac to watch)
  • ect..

Configuration

Migrations are disabled by default

Migrations are managed via the migrations file:

application/config/migrations.php

There are two settings of importance

$config['migration_enabled'] = FALSE;
$config['migration_version'] = 0;

migration_enabled switches database migrations on or off and the migration_version identifies the migration version this installation should use when triggered (see Updates and Rollbacks)

While migration_version lists the target migration version, the current migration version is managed in the the migrations.version field in the database. The Migration system automatically version up() or down() based on the version differences – WHEN TRIGGERED!

Updates and Rollbacks

Check out my custom migrate controller, it provides 4 operations

Method Description
migrate/current brings database to current version listed in config
migrate/ alias for _migrate/current/__
migrate/version/[num] migrates to [num] revision passed in
migrate/latest ignores config, and updates to latest migration file

Usage

Usage is really split between to groups, developers and deployments.

Developers Workflow

Developers should NOT modify ​
 config/migrations.php

Instead, developers should manage their local database via

  • migrate/latest to load the latest migration file on their system
  • or migrate/version/[num] to go to a migration version to test
Deployment Workflow

When setting up a deployment, the config/migrations.php would be modified to reflect the version you want that deployment set to:

$config['migration_version'] = 121;  //used migration version

and then run

migrate/current

There currently is no UI, however one could be build based on the return values of the migrate methods.

Return values:

  • TRUE, If Migration is on the latest version
  • FALSE, If the migration failed
  • INT, revision number successfully updated to

Additional Resources