web-dev-qa-db-fra.com

INSERT INTO ... SELECT pour toutes les colonnes MySQL

J'essaie de déplacer les anciennes données de:

this_table >> this_table_archive

copier toutes les colonnes. J'ai essayé ça, mais ça ne marche pas:

INSERT INTO this_table_archive (*) VALUES (SELECT * FROM this_table WHERE entry_date < '2011-01-01 00:00:00');

Remarque: les tables sont identiques et ont id défini comme clé primaire.

112
Kyle

La syntaxe correcte est décrite dans le manuel . Essaye ça:

INSERT INTO this_table_archive (col1, col2, ..., coln)
SELECT col1, col2, ..., coln
FROM this_table
WHERE entry_date < '2011-01-01 00:00:00';

Si la colonne id est une colonne à incrémentation automatique et que vous avez déjà des données dans les deux tables, vous pouvez dans certains cas omettre l'id de la liste des colonnes et générer de nouveaux identifiants afin d'éviter d'insérer un identifiant déjà existant dans l'original. table. Si votre table cible est vide, cela ne posera pas de problème.

209
Mark Byers

Pour la syntaxe, cela ressemble à ceci (laissez la liste de colonnes signifier implicitement "tout")

INSERT INTO this_table_archive
SELECT *
FROM this_table
WHERE entry_date < '2011-01-01 00:00:00'

Pour éviter les erreurs de clé primaire si vous avez déjà des données dans la table d'archivage

INSERT INTO this_table_archive
SELECT t.*
FROM this_table t
LEFT JOIN this_table_archive a on a.id=t.id
WHERE t.entry_date < '2011-01-01 00:00:00'
  AND a.id is null  # does not yet exist in archive
62
RichardTheKiwi

Ajout à Mark Byers répondre:

Parfois, vous souhaitez également insérer des informations codées en dur sinon il peut y avoir un échec de contrainte unique, etc.

INSERT INTO matrimony_domain_details (domain, type, logo_path)
SELECT 'www.example.com', type, logo_path
FROM matrimony_domain_details
WHERE id = 367

Ici domaine la valeur est ajoutée par moi de manière codée en dur pour se débarrasser de la contrainte Unique.

20
Pratik

n'avez-vous pas besoin de double () pour le bit de valeurs? sinon essayez-le (même s’il doit y avoir un meilleur moyen

insert into this_table_archive (id, field_1, field_2, field_3) 
values
((select id from this_table where entry_date < '2001-01-01'), 
((select field_1 from this_table where entry_date < '2001-01-01'), 
((select field_2 from this_table where entry_date < '2001-01-01'), 
((select field_3 from this_table where entry_date < '2001-01-01'));
4
Daniel Casserly

Plus d'exemples et de détails

    INSERT INTO vendors (
     name, 
     phone, 
     addressLine1,
     addressLine2,
     city,
     state,
     postalCode,
     country,
     customer_id
 )
 SELECT 
     name,
     phone,
     addressLine1,
     addressLine2,
     city,
     state ,
     postalCode,
     country,
     customer_id
 FROM 
     customers;
0
Developer