it-swarm.com.de

postgresql: INSERT INTO ... (SELECT * ...)

Ich bin mir nicht sicher, ob es Standard-SQL ist: 

 INSERT INTO tblA 
 (SELECT id, time 
    FROM tblB 
   WHERE time > 1000)  

Was ich suche, ist: was ist, wenn TblA und TblB in verschiedenen DB-Servern sind .

Hat PostgreSql ein beliebiges Dienstprogramm oder verfügt über eine Funktion, die zur Verwendung von INSERT query with PGresult struct 

Ich meine, SELECT id, time FROM tblB ... wird bei Verwendung von PQexec einen PGresult* zurückgeben. Ist es möglich, diese Struktur in einer anderen PQexec zu verwenden, um einen INSERT-Befehl auszuführen. 

BEARBEITEN:
Wenn dies nicht möglich ist, würde ich die Werte aus PQresult * extrahieren und eine mehrere INSERT-Anweisungssyntax wie folgt erstellen:

INSERT INTO films (code, title, did, date_prod, kind) VALUES
    ('B6717', 'Tampopo', 110, '1985-02-10', 'Comedy'),
    ('HG120', 'The Dinner Game', 140, DEFAULT, 'Comedy'); 

Kann man daraus eine vorbereitete Aussage machen !! :(

96
Mayank

Wie Henrik schrieb, können Sie mit dblink eine entfernte Datenbank verbinden und das Ergebnis abrufen. Zum Beispiel:

psql dbtest
CREATE TABLE tblB (id serial, time integer);
INSERT INTO tblB (time) VALUES (5000), (2000);

psql postgres
CREATE TABLE tblA (id serial, time integer);

INSERT INTO tblA
    SELECT id, time 
    FROM dblink('dbname=dbtest', 'SELECT id, time FROM tblB')
    AS t(id integer, time integer)
    WHERE time > 1000;

TABLE tblA;
 id | time 
----+------
  1 | 5000
  2 | 2000
(2 rows)

PostgreSQL hat record pseudo-type (nur für Funktionsargument oder Ergebnistyp), wodurch Sie Daten aus einer anderen (unbekannten) Tabelle abfragen können.

Bearbeiten:

Sie können es als vorbereitete Aussage machen, wenn Sie möchten, und es funktioniert auch:

PREPARE migrate_data (integer) AS
INSERT INTO tblA
    SELECT id, time
    FROM dblink('dbname=dbtest', 'SELECT id, time FROM tblB')
    AS t(id integer, time integer)
    WHERE time > $1;

EXECUTE migrate_data(1000);
-- DEALLOCATE migrate_data;

Bearbeiten (ja, noch einer):

Ich habe gerade Ihre überarbeitete Frage gesehen (geschlossen als Duplikat oder nur sehr ähnlich dazu).

Wenn mein Verständnis korrekt ist (postgres hat tbla und dbtest hat tblb und Sie möchten remote einfügen mit local select, nicht remote select mit local insert wie oben):

psql dbtest

SELECT dblink_exec
(
    'dbname=postgres',
    'INSERT INTO tbla
        SELECT id, time
        FROM dblink
        (
            ''dbname=dbtest'',
            ''SELECT id, time FROM tblb''
        )
        AS t(id integer, time integer)
        WHERE time > 1000;'
);

Ich mag das verschachtelte dblink nicht, aber AFAIK kann ich nicht auf tblB in dblink_exec body verweisen. Verwenden Sie LIMIT, um die obersten 20 Zeilen anzugeben, aber ich denke, Sie müssen sie zuerst mit der ORDER BY-Klausel sortieren.

124

Wenn Sie in eine Spalte einfügen möchten:

INSERT INTO table (time)
(SELECT time FROM 
    dblink('dbname=dbtest', 'SELECT time FROM tblB') AS t(time integer) 
    WHERE time > 1000
);
22

Sie können dblink verwenden, um eine Ansicht zu erstellen, die in einer anderen Datenbank aufgelöst wird. Diese Datenbank kann sich auf einem anderen Server befinden.

9

Diese Notation (zuerst gesehen hier ) sieht auch nützlich aus:

insert into postagem (
  resumopostagem,
  textopostagem,
  dtliberacaopostagem,
  idmediaimgpostagem,
  idcatolico,
  idminisermao,
  idtipopostagem
) select
  resumominisermao,
  textominisermao,
  diaminisermao,
  idmediaimgminisermao,
  idcatolico ,
  idminisermao,
  1
from
  minisermao    
8
Sombriks

Hier ist eine alternative Lösung, ohnedblinkzu verwenden.

Angenommen, B steht für die Quelldatenbank und A für die Zieldatenbank: Dann

  1. Tabelle vom Quell-DB in den Ziel-DB kopieren:

    pg_dump -t <source_table> <source_db> | psql <target_db>
    
  2. Öffnen Sie die psql-Eingabeaufforderung, stellen Sie eine Verbindung zu target_db her und verwenden Sie eine einfache insert:

    psql
    # \c <target_db>;
    # INSERT INTO <target_table>(id, x, y) SELECT id, x, y FROM <source_table>;
    
  3. Löschen Sie am Ende die Kopie von source_table, die Sie in target_table erstellt haben.

    # DROP TABLE <source_table>;
    
1
Nitin Nain
insert into TABLENAMEA (A,B,C,D) 
select A::integer,B,C,D from TABLENAMEB
0
mahesh ingale