Oracle
 sql >> Base de Dados >  >> RDS >> Oracle

inserir em... selecionar... com subconsulta ou sem ordem de coluna


Não, você não pode usar uma subconsulta para gerar a lista de colunas como parte de uma instrução SQL.

Você pode gerar a instrução completa do dicionário de dados:
select 'insert into cl ("'
  || listagg(column_name, '","') within group (order by column_id)
  || '") select "'
  || listagg(column_name, '","') within group (order by column_id)
  || '" from clt'
from user_tab_columns where table_name = 'CLT';

e, em seguida, copie e cole isso ou use SQL dinâmico de um bloco anônimo:
declare
  stmt varchar2(4000);
begin
  select 'insert into cl ("'
    || listagg(column_name, '","') within group (order by column_id)
    || '") select "'
    || listagg(column_name, '","') within group (order by column_id)
    || '" from clt'
  into stmt
  from user_tab_columns where table_name = 'CLT';

  dbms_output.put_line(stmt); -- to check and debug
  execute immediate stmt;
end;
/

Com algumas tabelas fictícias:
create table clt (col1 number, col2 date, col3 varchar2(10));
create table cl (col3 varchar2(10), col1 number, col2 date);

insert into clt (col1, col2, col3) values (42, date '2018-07-12', 'Test');

insert into cl
select * from clt;

SQL Error: ORA-00932: inconsistent datatypes: expected NUMBER got DATE

executando esse bloco dá:
insert into cl ("COL1","COL2","COL3") select "COL1","COL2","COL3" from clt

PL/SQL procedure successfully completed.

select * from cl;

COL3             COL1 COL2      
---------- ---------- ----------
Test               42 2018-07-12

Você também pode transformar esse bloco anônimo em um procedimento que leva dois nomes de tabela se isso for algo que você provavelmente deseja fazer com frequência (você disse que precisava ser reutilizável, mas isso poderia significar para as mesmas tabelas e poderia ser apenas um bloco em um script).

Você também pode ir além e incluir apenas colunas que aparecem em ambas as tabelas ou verificar se os tipos de dados correspondem exatamente; embora isso seja um pouco mais trabalhoso e pode não ser necessário.