Como chamar uma procedure no forms

Dicas do Oracle Forms Builder - Blocos, Itens, LOV, Canvas, Triggers, comandos, PLL, d2kwutil, FMB, Alert, menus, etc
Responder
Laninha
Rank: Programador Sênior
Rank: Programador Sênior
Mensagens: 68
Registrado em: Qua, 24 Out 2007 3:06 pm
Localização: Nilópolis - Rio de Janeiro

Oi galera,

Eu tenho a minha procedure que está criada dentro do PROGRAMS UNITS dentro do Forms. Segue minha Procedure abaixo:

Selecionar tudo

PROCEDURE PR_CALCULODIVERGENCE (p_dtfrom in date,
                                p_dtto in date,
                                p_erro in out varchar2)

is 
  
 begin
 for cl in
     --Busca, caso os parâmetros p_dtfrom e p_dtto sejam informados ou não
      (select a.num_fat_fornec, 
              a.id_unid_fornec,
              a.cod_interno_fat_fornec,
              a.id_instalacao_empresa_pedido,
              a.dt_emissao_fat_fornec,
              sum(nvl(b.qtd_item_fat_fornec,0) + nvl(b.qtd_free_fat_fornec,0))qtdfat,
              sum(nvl(c.qtd_solicitada,0) + nvl(c.qtd_free_promocao,0) + nvl(c.qtd_free_desconto,0))qtdped,
              (nvl(b.val_pco_fat_fornec,0) - nvl(b.val_desconto_fat_fornec,0))precofat,
              (d.val_fornec_eurot*((100-nvl(d.tx_desconto,nvl(d.val_desconto,0) *100))/100))precoped         
                      
         from ffor_fat_fornec              a,
              itff_item_fat_fornec         b,
              itpe_item_pedido             c,
              itpe_cond_comercial          d,
              pedi_pedido                  e,
              pedi_cond_comercial          f,
              item_hist_preço_compra_item  g,
              item_apresentacao_item       i 
              
        where a.num_fat_fornec = b.num_fat_fornec	
          and a.id_unid_fornec = b.id_unid_fornec
          and a.cod_interno_fat_fornec = b.cod_interno_fat_fornec
          and a.id_instalacao_empresa_pedido = b.id_instalacao_empresa_pedido
          and b.num_pedido = c.num_pedido
          and b.num_seq_item_pedido = c.num_seq_item_pedido  
          and b.cod_brasif_item = c.cod_brasif_item
          and c.num_pedido = d.num_pedido
          and c.num_seq_item_pedido = d.num_seq_item_pedido          
          and b.num_pedido = e.num_pedido
          and e.num_pedido = f.num_pedido
          and g.id_unid_emp = a.id_unid_fornec
          and g.id_instalacao_empresa_pedido =  a.id_instalacao_empresa_pedido   
          and g.dt_fim_vigencia is null
          and g.dt_inicio_vigencia is not null
          and g.cod_apresentacao_preço = i.cod_apresentacao_item     
          and(a.dt_emissao_fat_fornec between trunc(p_dtfrom) and trunc(p_dtto)
           or (trunc(p_dtfrom)is null and trunc(p_dtto)is null))
                        
     group by a.num_fat_fornec,                     
              a.id_unid_fornec,
              a.cod_interno_fat_fornec,
              a.id_instalacao_empresa_pedido,             
              a.dt_emissao_fat_fornec,
              (nvl(b.val_pco_fat_fornec,0) - nvl(b.val_desconto_fat_fornec,0)),
              (d.val_fornec_eurot*((100-nvl(d.tx_desconto,nvl(d.val_desconto,0) *100))/100))           
      )
      
      loop
       -----*-----teste/display-----*-----
      dbms_output.put_line('NUMFATFORNEC'       ||'  '||cl.num_fat_fornec||
                           'ID_UNID_FORNEC'     ||'  '||cl.id_unid_fornec||
                           'QTDFAT'             ||'  '||cl.qtdfat||                           
                           'QTDPED'             ||'  '||cl.qtdped);
                           
      -----*-----teste/display-----*-----
      dbms_output.put_line--('STATUSFAT'        ||'  '||v_status_fatura||
                            ('CODINTERNO'       ||'  '||cl.cod_interno_fat_fornec||
                             'IDINSTALACAO'     ||'  '||cl.id_instalacao_empresa_pedido||
                             'PRECOFAT'         ||'  '||cl.precofat||
                             'PRECOPED'         ||'  '||cl.precoped);
                           
                           
      end loop;
  exception
  when others then
    p_erro := 'Erro na Pr_Calcula_Divergenceteste: '||sqlerrm;   
   
end;


Sendo que eu não consigo chamá-la dentro da minha PRE_QUERY, como devo fazer, pois dá erro de FRM-40505: ORACLE error: unable to perform query.


Abrços,
Laninha
Laninha
Rank: Programador Sênior
Rank: Programador Sênior
Mensagens: 68
Registrado em: Qua, 24 Out 2007 3:06 pm
Localização: Nilópolis - Rio de Janeiro

Amigos,

eu tentei colocar dentro da minha PRE_QUERY o seguinte:

Selecionar tudo

def_where :=   'pr_calculodivergence(p_dtfrom = to_date('''    
                  ||to_char(:blk_seletor.dt_from, 'mmddyyyy') 
                  ||''', ''mmddyyyy''),p_dtto = to_date('''    
                  ||to_char(:blk_seletor.dt_to, 'mmddyyyy') 
                  ||''', ''mmddyyyy''))'; 
Ou seja, o nome da minha PROCEDURE e suas variáveis igual ao que o usuário irá digitar, mas não dá certo de jeito nenhum, o que faço?

Obrigada,
Laninha
Trevisolli
Moderador
Moderador
Mensagens: 2016
Registrado em: Qua, 12 Jan 2005 3:25 pm
Localização: Araraquara - SP
Abraço,

Trevisolli
OCA Oracle PL/SQL Developer Certified Associate
OCP Oracle Forms Developer Certified Professional
Araraquara-SP

Laninha, tudo bem?

Fiz este teste no SQL Navigator, para ver como vem a string, se vem correta:

Selecionar tudo

DECLARE 

def_where VARCHAR2(500) := 'pr_calculodivergence( p_dtfrom => TO_CHAR(SYSDATE, ''DD/MM/RRRR''),
                                                  p_dtto   => TO_CHAR(SYSDATE, ''DD/MM/RRRR'')+10,
																																			               p_erro   => V_ERRO );'; 

BEGIN
   dbms_output.put_line('WHERE  ' || def_where);
END;
							         
Tenta adaptar no teu def_where ai pra ver se dá certo.

qualquer coisa manda ai.
Laninha
Rank: Programador Sênior
Rank: Programador Sênior
Mensagens: 68
Registrado em: Qua, 24 Out 2007 3:06 pm
Localização: Nilópolis - Rio de Janeiro

Trevisolli,

Eu coloquei a data do dia 11-sep-2007 de acordo como está no banco só para testar e continua dando erro, mas na verdade a data deverá ser digitada pelo usuário no formato americano, ou seja, mm/dd/yyyy, lembrando que eu só fiz dessa maneira para testar, por isso segue abaixo como está a minha PRE_QUERY:

Selecionar tudo

BEGIN 
   DECLARE 
   block_id Block := find_block('POOP2'); 
   sub_where VARCHAR2(512); 
   def_where VARCHAR2(2000);
   alert number := 0; 

FUNCTION add_and( 
 P_WHERE IN VARCHAR2 
) RETURN VARCHAR2 IS 
BEGIN 
   IF (nvl(length(P_WHERE),0) !=0)then 
      RETURN(P_WHERE||'AND'); 
   ELSE 
      RETURN(P_WHERE); 
   END IF; 
END; 

BEGIN
   def_where := 'pr_calculodivergence( p_dtfrom => ('''||'11-sep-2007'||'''), 
                                       p_tto   => ('''||'11-sep-2007'||''')+10, 
                                       p_erro   => V_ERRO );'; 


    
   set_block_property('FFOR_FAT_FORNEC',DEFAULT_WHERE, def_where);



BEGIN 
   dbms_output.put_line('WHERE  ' || def_where); 
END; 

END;
Obrigada pela ajuda mesmo assim,
Laninha :)
Tineks
Rank: DBA Sênior
Rank: DBA Sênior
Mensagens: 365
Registrado em: Ter, 24 Mai 2005 2:24 pm
Localização: Araraquara - SP
Cristiano (Tineks)
Araraquara - SP

Oi Laninha, tudo bom?

tenta montar o def_where com a data convertida.
por exemplo :

Selecionar tudo

   def_where := 'pr_calculodivergence( p_dtfrom => (to_date(''11-sep-2007'',''dd-mon-yyyy'')), 
                                       p_tto   =>  (to_date(''11-sep-2007'',''dd-mon-yyyy'')+10),  
                                       p_erro   => V_ERRO );'; 
[]'s
Laninha
Rank: Programador Sênior
Rank: Programador Sênior
Mensagens: 68
Registrado em: Qua, 24 Out 2007 3:06 pm
Localização: Nilópolis - Rio de Janeiro

Tineks,

Eu devo está fazendo alguma coisa errada e não consigo descobrir o que é, pois trabalhar com datas é um caso sério.

Bom, deixa eu explicar melhor: Eu tenho 2 campos de datas não base table na minha tela, onde o usuário deverá informar a data from e data to, esses dois campos estão com o formato de máscara (mmddrrrr) em sua propriedade de campo, pois o usuário deverá jogar o formato americano, na verdade esses 2 campos de datas poderão ser preenchidos ou não, sendo que na minha PRE_QUERY eu estou jogando data '11-sep-2007' para testar se a minha procedure está sendo chamada ou não... Enfim já fiz de tudo, já olhei, pesquisei e não consigo chamar a procedure de jeito nenhum, funcionando ela está, pois consigo testar no pl/sql developer, sendo que não consigo chamar no forms e ainda mais dentro da minha PRE-QUERY... Não sei se é o formato da data que eu estou informando na PRE-QUERY ou dentro na propriedade do campo...


Mesmo assim obrigada pela ajuda,

Laninha :(
rogenaro
Rank: DBA Pleno
Rank: DBA Pleno
Mensagens: 232
Registrado em: Sex, 30 Mar 2007 7:26 pm
Localização: Londrina - PR
Rafael O. Genaro

Laninha,

Se entendi bem, parece que você está tentando utilizar uma procedure como a cláusula where do seu bloco. Não é possível popular o bloco desta forma...
Você teria duas alternativas:

1 - Criar uma cópia da procedure dentro do forms (na seção "Program Units"), e dentro do seu loop, fazer algo do tipo:

Selecionar tudo

...
PROCEDURE PR_CALCULODIVERGENCE (p_dtfrom in date, 
                                p_dtto in date, 
                                p_erro in out varchar2) 

is 
begin

  go_block('BLOCO'); -- Posiciona o cursor em seu bloco a ser populado;
  clear_block(no_validate); -- Limpa o bloco;
  first_record; -- Posiciona o cursor no primeiro registro;

for c1 in 
...
loop
  create_record; -- Cria um novo registro para ser populado;

  :bloco.campo1 := c1.num_fat_fornec; -- Preenche o 1º campo do bloco
  :bloco.campo2 := c1.id_unid_fornec;  -- Preenche o 2º campo do bloco
  ...
  :bloco.campoX := c1.precoped; -- Preenche o último campo do bloco
end loop;
...
Aí você poderia chamar a sua procedure em uma trigger WHEN-BUTTON-PRESSED (caso você tenha um botão para realizar a consulta), ou mesmo na trigger KEY-EXEQUERY (quando o usuário pressiona a tecla F8) para popular o seu bloco.
Neste caso, lembre-se de setar a propriedade Database Data Block do bloco "BLOCO" para "NO". Lembrando que neste caso, caso sua tela permita updates, inserts e deletes no bloco, você precisará realizar o controle "no braço" (identificar se um registro é novo ou foi alterado, por exemplo, e realizar então os devidos inserts, updates e deletes).

2 - Basear o seu bloco em uma procedure de banco.
Esta é uma solução um pouco mais prática, especialmente se a sua tela permite alterações nos registros consultados. Como existem vários passos para criar um form deste tipo, segue um link para tutorial:

http://www.dulcian.com/papers/ODTUG/200 ... ock-On.htm (procure pela seção Implementing a Block Based on a Procedure)

Qualquer dúvida, é só falar!
Laninha
Rank: Programador Sênior
Rank: Programador Sênior
Mensagens: 68
Registrado em: Qua, 24 Out 2007 3:06 pm
Localização: Nilópolis - Rio de Janeiro

Rogenaro,

Adorei sua ajuda, mas o bloco que você disse para colocar NO na propriedade Database data block é um base table, então deverá permanecer com YES e essa tela só será para consulta, e outra coisa como devo chamar a procedure no forms???




Obrigada pela ajuda mais uma vez,
Laninha :)
Responder
  • Informação
  • Quem está online

    Usuários navegando neste fórum: Nenhum usuário registrado e 16 visitantes