Flowdock
create_table(name, options = {}) public

Creates a new table There are two ways to work with #create_table. You can use the block form or the regular form, like this:

Block form

 # create_table() yields a TableDefinition instance
 create_table(:suppliers) do |t|
   t.column :name, :string, :limit => 60
   # Other fields here
 end

Regular form

 create_table(:suppliers)
 add_column(:suppliers, :name, :string, {:limit => 60})

The options hash can include the following keys:

:id
Whether to automatically add a primary key column. Defaults to true. Join tables for has_and_belongs_to_many should set :id => false.
:primary_key
The name of the primary key, if one is to be added automatically. Defaults to id.
:options
Any extra options you want appended to the table definition.
:temporary
Make a temporary table.
:force
Set to true or false to drop the table before creating it. Defaults to false.
Examples
Add a backend specific option to the generated SQL (MySQL)
 create_table(:suppliers, :options => 'ENGINE=InnoDB DEFAULT CHARSET=utf8')

generates:

 CREATE TABLE suppliers (
   id int(11) DEFAULT NULL auto_increment PRIMARY KEY
 ) ENGINE=InnoDB DEFAULT CHARSET=utf8
Rename the primary key column
 create_table(:objects, :primary_key => 'guid') do |t|
   t.column :name, :string, :limit => 80
 end

generates:

 CREATE TABLE objects (
   guid int(11) DEFAULT NULL auto_increment PRIMARY KEY,
   name varchar(80)
 )
Do not add a primary key column
 create_table(:categories_suppliers, :id => false) do |t|
   t.column :category_id, :integer
   t.column :supplier_id, :integer
 end

generates:

 CREATE TABLE categories_suppliers_join (
   category_id int,
   supplier_id int
 )

See also TableDefinition#column for details on how to create columns.

Show source
Register or log in to add new notes.
September 25, 2008
20 thanks

All methods

create_table :table do |t|

  t.column # adds an ordinary column. Ex: t.column(:name, :string)
  t.index # adds a new index.
  t.timestamps
  t.change # changes the column definition. Ex: t.change(:name, :string, :limit => 80)
  t.change_default # changes the column default value.
  t.rename # changes the name of the column.
  t.references
  t.belongs_to
  t.string
  t.text
  t.integer
  t.float
  t.decimal
  t.datetime
  t.timestamp
  t.time
  t.date
  t.binary
  t.boolean
  t.remove
  t.remove_references
  t.remove_belongs_to
  t.remove_index
  t.remove_timestamps
end
September 9, 2010
1 thank

bad idea.

Just a note, ypetya’s idea of using a before filter to set the primary key wont scale. transactions will eventually step on each other and probably end up with duplicate key ids, unless you have some other method to ensure uniqueness.

You’d be better off using mysql to generate the default integer primary key and have a secondary string “key” field.

February 5, 2010
1 thank

An alternate way to have a string ID as a primary key

You can disable automatically created primary key and add it to manually with mysql:

The migration file:

def self.up

  create_table( :my_special_table, :id => false ) do |t|
    t.string :id, :limit => 5, :null => :no
  end

  execute "ALTER TABLE my_special_table ADD PRIMARY KEY (id)"

end

Then in a before_save filter you can generate the primary key for yourself.

Use a transaction and be aware of uniqueness!

June 28, 2011 - (v3.0.9)
0 thanks

available column types

Rails 3.0.9 update for RobinWu’s post

Available column types:

:string, :text, :integer, :float, :decimal, :datetime, :timestamp, :time, :date, :binary, :boolean

Example:

MyClass < ActiveRecord::Migration

def change
  create_table :myclass do |t|
    t.string :name
    t.text :content
end

end