¿Cómo cambio el nombre de una columna en una tabla de base de datos SQLite?


Tendría que cambiar el nombre de algunas columnas en algunas tablas en una base de datos SQLite. Sé que una pregunta similar se ha hecho en stackoverflow anteriormente, pero era para SQL en general, y el caso de SQLite no se mencionó.

De la documentación de SQLite para ALTER TABLE, deduzco que no es posible hacer tal cosa "fácilmente" (es decir, una sola instrucción ALTER TABLE).

Me preguntaba si alguien sabía de una forma genérica SQL de hacer tal cosa con SQLite.

Author: Community, 2009-04-30

13 answers

Esto se acaba de arreglar con 2018-09-15 (3.25.0)

Mejora el comando ALTER TABLE:

  • Añade soporte para renombrar columnas dentro de una tabla usando ALTER TABLE table RENAME COLUMN oldname TO newname.
  • Se corrige la función de cambio de nombre de tabla para que también actualice las referencias a la tabla renombrada en los disparadores y las vistas.

Puede encontrar la nueva sintaxis documentada en ALTER TABLE

La sintaxis RENAME COLUMN TO cambia el nombre de la columna de la tabla table-name en new-column-name. El nombre de la columna se cambia tanto dentro de la definición de la tabla como dentro de todos los índices, disparadores y vistas que hacen referencia a la columna. Si el cambio de nombre de la columna resulta en una ambigüedad semántica en un disparador o vista, entonces el RENAME COLUMN falla con un error y no se aplican cambios.

introduzca la descripción de la imagen aquí fuente de la Imagen: https://www.sqlite.org/images/syntax/alter-table-stmt.gif

 3
Author: Lukasz Szozda,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-09-16 10:59:47

Digamos que tienes una tabla y necesitas renombrar "colb" a "col_b":

Primero cambia el nombre de la tabla antigua:

ALTER TABLE orig_table_name RENAME TO tmp_table_name;

Luego cree la nueva tabla, basada en la tabla anterior pero con el nombre de columna actualizado:

CREATE TABLE orig_table_name (
  col_a INT
, col_b INT
);

Luego copie el contenido de la tabla original.

INSERT INTO orig_table_name(col_a, col_b)
SELECT col_a, colb
FROM tmp_table_name;

Por último, elimine la tabla anterior.

DROP TABLE tmp_table_name;

Envolver todo esto en un BEGIN TRANSACTION; y COMMIT; también es probablemente una buena idea.

 423
Author: Evan,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-05-15 23:24:22

Si bien es cierto que no hay ALTER COLUMN, si solo desea cambiar el nombre de la columna, eliminar la restricción NOT NULL o cambiar el tipo de datos, puede usar el siguiente conjunto de comandos:

Nota: Estos comandos tienen el potencial de dañar su base de datos, así que asegúrese de tener una copia de seguridad

PRAGMA writable_schema = 1;
UPDATE SQLITE_MASTER SET SQL = 'CREATE TABLE BOOKS ( title TEXT NOT NULL, publication_date TEXT)' WHERE NAME = 'BOOKS';
PRAGMA writable_schema = 0;

Tendrá que cerrar y volver a abrir su conexión o aspirar la base de datos para volver a cargar los cambios en el esquema.

Para ejemplo:

Y:\> sqlite3 booktest  
SQLite version 3.7.4  
Enter ".help" for instructions  
Enter SQL statements terminated with a ";"  
sqlite> create table BOOKS ( title TEXT NOT NULL, publication_date TEXT NOT NULL);  
sqlite> insert into BOOKS VALUES ("NULLTEST",null);  
Error: BOOKS.publication_date may not be NULL  
sqlite> PRAGMA writable_schema = 1; 
sqlite> UPDATE SQLITE_MASTER SET SQL = 'CREATE TABLE BOOKS ( title TEXT NOT NULL, publication_date TEXT)' WHERE NAME = 'BOOKS';  
sqlite> PRAGMA writable_schema = 0;  
sqlite> .q  

Y:\> sqlite3 booktest  
SQLite version 3.7.4  
Enter ".help" for instructions  
Enter SQL statements terminated with a ";"  
sqlite> insert into BOOKS VALUES ("NULLTEST",null);  
sqlite> .q  

LAS REFERENCIAS SIGUEN:


pragma writable_schema
Cuando este pragma está activado, las tablas SQLITE_MASTER en las que la base de datos se puede cambiar utilizando las instrucciones UPDATE, INSERT y DELETE ordinarias. Advertencia: el mal uso de este pragma puede resultar fácilmente en un archivo de base de datos dañado.

Alter table
SQLite admite un subconjunto limitado de ALTER TABLE. El comando ALTER TABLE en SQLite permite al usuario cambiar el nombre de una tabla o agregar una nueva columna a una tabla existente. No es posible cambiar el nombre de una columna, eliminar una columna o agregar o eliminar restricciones de una tabla.

MODIFICAR LA SINTAXIS DE LA TABLA

 53
Author: Noah,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-03-31 20:11:58

Investigando, encontré esta herramienta gráfica multiplataforma (Linux | Mac | Windows) llamada DB Browser for SQLite que en realidad permite cambiar el nombre de las columnas de una manera muy fácil de usar!

Editar | Modificar Tabla | Seleccionar Tabla | Editar Campo. Click click! ¡Voila!

Sin embargo, si alguien quiere compartir una forma programática de hacer esto, ¡me encantaría saberlo!

 51
Author: joce,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-04-25 18:19:17

Recientemente tuve que hacer eso en SQLite3 con una tabla llamada puntos con los colunms id, lon, lat. Erróneamente, cuando se importó la tabla, los valores de latitud se almacenaron en la columna lon y viceversa, por lo que una solución obvia sería cambiar el nombre de esas columnas. Así que el truco era:

create table points_tmp as select id, lon as lat, lat as lon from points;
drop table points;
alter table points_tmp rename to points;

Espero que esto sea útil para usted!

 17
Author: aizquier,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-10-17 02:13:01

Citando la documentación de sqlite :

SQLite soporta un subconjunto limitado de ALTERE LA TABLA. El comando ALTER TABLE en SQLite permite al usuario renombrar un tabla o para agregar una nueva columna a un cuadro existente. No es posible cambiar el nombre de un colum, eliminar una columna o agregar o eliminar restricciones de una tabla.

Lo que puede hacer, por supuesto, es crear una nueva tabla con el nuevo diseño, SELECT * FROM old_table, y llenar la nueva tabla con los valores que recibir.

 10
Author: Elazar Leibovich,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-04-30 04:54:39

En primer lugar, esta es una de esas cosas que me golpea en la cara con sorpresa: el cambio de nombre de una columna requiere crear una tabla completamente nueva y copiar los datos de la tabla anterior a la nueva tabla...

La GUI en la que he aterrizado para hacer operaciones SQLite es Base. Tiene una ventana de registro ingeniosa que muestra todos los comandos que se han ejecutado. Hacer un cambio de nombre de una columna a través de Base rellena la ventana de registro con el necesario comandos:

Ventana de registro base

Estos se pueden copiar y pegar fácilmente donde pueda necesitarlos. Para mí, eso es en un archivo de migración ActiveAndroid. Un buen toque, también, es que los datos copiados solo incluyen los comandos SQLite, no las marcas de tiempo, etc.

Con suerte, eso ahorra tiempo a algunas personas.

 7
Author: Joshua Pinter,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-05-02 21:31:32

Cambiar la columna de la tabla a

 String LastId = "id";

    database.execSQL("ALTER TABLE " + PhraseContract.TABLE_NAME + " RENAME TO " + PhraseContract.TABLE_NAME + "old");
    database.execSQL("CREATE TABLE " + PhraseContract.TABLE_NAME
    +"("
            + PhraseContract.COLUMN_ID + " INTEGER PRIMARY KEY,"
            + PhraseContract.COLUMN_PHRASE + " text ,"
            + PhraseContract.COLUMN_ORDER  + " text ,"
            + PhraseContract.COLUMN_FROM_A_LANG + " text"
    +")"
    );
    database.execSQL("INSERT INTO " +
            PhraseContract.TABLE_NAME + "("+ PhraseContract.COLUMN_ID +" , "+ PhraseContract.COLUMN_PHRASE + " , "+ PhraseContract.COLUMN_ORDER +" , "+ PhraseContract.COLUMN_FROM_A_LANG +")" +
            " SELECT " + LastId +" , "+ PhraseContract.COLUMN_PHRASE + " , "+ PhraseContract.COLUMN_ORDER +" , "+ PhraseContract.COLUMN_FROM_A_LANG +
            " FROM " + PhraseContract.TABLE_NAME + "old");
    database.execSQL("DROP TABLE " + PhraseContract.TABLE_NAME + "old");
 3
Author: Vahe Gharibyan,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-06-24 18:49:30

Como se mencionó anteriormente, hay una herramienta SQLite Database Browser, que hace esto. Lyckily, esta herramienta mantiene un registro de todas las operaciones realizadas por el usuario o la aplicación. Haciendo esto una vez y mirando el registro de la aplicación, verá el código involucrado. Copie la consulta y pegue según sea necesario. Funcionó para mí. Espero que esto ayude

 2
Author: Chris Lytridis,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-04-06 21:20:53

Cree una nueva columna con el nombre de columna deseado: COLNew.

ALTER TABLE {tableName} ADD COLUMN COLNew {type};

Copie el contenido de la antigua columna COLOld a la nueva columna COLNew.

INSERT INTO {tableName} (COLNew) SELECT {COLOld} FROM {tableName}

Nota: los corchetes son necesarios en la línea anterior.

 2
Author: Anthony Ebert,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-08-02 07:16:29

De la documentación oficial

Un procedimiento más simple y rápido se puede utilizar opcionalmente para algunos cambios que no afectan el contenido en el disco de ninguna manera. El siguiente procedimiento más simple es apropiado para eliminar las restricciones CHECK o FOREIGN KEY o NOT NULL, cambiar el nombre de las columnas, o agregar, eliminar o cambiar los valores predeterminados en una columna.

  1. Iniciar una transacción.

  2. Ejecutar PRAGMA schema_version para determinar la número de versión actual del esquema. Este número será necesario para el paso 6 a continuación.

  3. Activar la edición de esquemas usando PRAGMA writable_schema = ON.

  4. Ejecute una instrucción UPDATE para cambiar la definición de la tabla X en la tabla sqlite_master: UPDATE sqlite_master SET sql=... DONDE type = 'table' Y name = 'X';

    Precaución: Realizar un cambio en la tabla sqlite_master como este hará que la base de datos esté dañada e ilegible si el cambio contiene un error de sintaxis. Es suggested that careful testing of the UPDATE statement be done on a separate blank database prior to using it on a database containing important data.

  5. Si el cambio a la tabla X también afecta a otras tablas o índices o disparadores son vistas dentro del esquema, ejecute instrucciones UPDATE para modificar esos otros índices de tablas y vistas también. Por ejemplo, si el nombre de una columna cambia, todas las restricciones de CLAVE FORÁNEA, disparadores, índices y vistas que se refieren a esa columna deben ser modificar.

    Precaución: Una vez más, hacer cambios en la tabla sqlite_master como este hará que la base de datos esté dañada e ilegible si el cambio contiene un error. Pruebe cuidadosamente todo este procedimiento en una base de datos de prueba separada antes de usarlo en una base de datos que contenga datos importantes y/o haga copias de seguridad de bases de datos importantes antes de ejecutar este procedimiento.

  6. Incrementar el número de versión del esquema usando PRAGMA schema_version = X donde X es uno más que el antiguo número de versión del esquema que se encuentra en el paso 2 anterior.

  7. Deshabilita la edición de esquemas usando PRAGMA writable_schema = OFF.

  8. (Opcional) Ejecute PRAGMA integrity_check para verificar que los cambios de esquema no dañaron la base de datos.

  9. Confirme la transacción iniciada en el paso 1 anterior.

 2
Author: Mohammad Yahia,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-01-14 16:26:10

Una opción, si necesita que se haga en un apuro, y si su columna inicial se creó con un valor predeterminado, es crear la nueva columna que desee, copiar el contenido a ella, y básicamente "abandonar" la columna anterior (se mantiene presente, pero simplemente no la usa/actualiza, etc.)

Ex:

alter table TABLE_NAME ADD COLUMN new_column_name TYPE NOT NULL DEFAULT '';
update TABLE_NAME set new_column_name = old_column_name;
update TABLE_NAME set old_column_name = ''; -- abandon old column, basically

Esto deja atrás una columna (y si se creó con NULL pero sin un valor predeterminado, entonces las inserciones futuras que lo ignoran podrían fallar), pero si es solo una tabla desechable, las compensaciones podrían ser aceptable. De lo contrario, utilice una de las otras respuestas mencionadas aquí, o una base de datos diferente que permita cambiar el nombre de las columnas.

 1
Author: rogerdpack,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-10-20 23:03:08

Sqlite3 yoursdb .dump > / tmp / db.txt
editar /tmp/db.txt cambiar el nombre de la columna en Crear línea
sqlite2 sudb2 mv / move yoursdb2 yoursdb

 -3
Author: H Bosch,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-03-04 17:34:43