2009-10-09 27 views
12

Quiero una migración para crear un clon de una tabla existente simplemente con el sufijo del nombre, incluidos todos los índices de la tabla original.¿Cómo podría clonar una tabla de base de datos a través de la migración de Rails?

Así que hay una tabla de "instantáneas" y quiero crear "snapshots_temp" como una copia exacta de la tabla (no los datos, solo el esquema de la tabla, pero incluyendo los índices).

Podría simplemente copiar y pegar el bloque fuera del archivo schema.rb y cambiarle el nombre manualmente.

Pero no estoy seguro para cuando se aplica esta migración si la definición de schema.rb aún será precisa. Otro desarrollador podría haber cambiado la tabla y no quiero tener que actualizar mi script de migración.

Entonces, ¿cómo podría obtener el esquema de la tabla en tiempo de ejecución? Esencialmente, ¿cómo 'rake schema: dump' hace ingeniería inversa de la tabla para que yo pueda hacer lo mismo en mi migración? (pero cambiando el nombre de la tabla).

Respuesta

21

Pruebe hacerlo con SQL puro. Esto va a hacer lo que quiere:

CREATE TABLE new_tbl LIKE orig_tbl; 
+0

Buena llamada. "Use LIKE para crear una tabla vacía según la definición de otra tabla, incluidos los atributos e índices de columna definidos en la tabla original" http://dev.mysql.com/doc/refman/5.1/en/createtable. html –

+0

Funciona con MySQL (y posiblemente con la mayoría de las bases de datos) pero si usa Sqlite, no funcionará. Me encontré con este problema en el entorno de desarrollo. La producción está bien (es MySQL). – MiniQuark

+1

Awesome gracias. Tenga en cuenta que su tabla copiada obtendrá los índices, pero no las claves externas. Tendrás que volver a crearlos por separado. –

4

Esto hará. No es perfecto, porque no copiará las opciones ni los índices de la tabla. Si tiene configuradas opciones de tabla, deberá agregarlas manualmente a esta migración.

Para copiar índices, deberá formular una consulta SQL para seleccionarlos y luego procesarlos en nuevas directivas add_index. Eso está un poco más allá de mi conocimiento. Pero esto funciona para copiar la estructura.

class CopyTableSchema < ActiveRecord::Migration 
    def self.up 
    create_table :new_models do |t| 
     Model.columns.each do |column| 
     next if column.name == "id" # already created by create_table 
     t.send(column.type.to_sym, column.name.to_sym, :null => column.null, 
      :limit => column.limit, :default => column.default, :scale => column.scale, 
      :precision => column.precision) 
     end 
    end 

    # copy data 

    Model.all.each do |m| 
     NewModel.create m.attributes 
    end 
    end 

    def self.down 
    drop_table :new_models 
    end 
end 
+0

> no copiará las opciones o índices de tabla Gracias pero los índices son un requisito. –

4

En Rails 4 & PostgreSQL, crear una nueva migración e inserte:

ActiveRecord::Base.connection.execute("CREATE TABLE clone_table_name AS SELECT * FROM source_table_name;") 

Esto creará el clon con la estructura exacta de la tabla original, y poblar la nueva tabla con valores antiguos

Más información: http://www.postgresql.org/docs/9.0/static/sql-createtableas.html

+1

Tenga cuidado con esto, ya que también copiará la columna ID y no la establecerá como principal en la nueva tabla. –

0

copiar la entrada tablas de sus proyectos db/schema.rb directamente en su migración. Solo cambia el nombre de la tabla y listo.

Cuestiones relacionadas