De DBMS_JOB para DBMS_SCHEDULER: o Deploy

Nos últimos tempos tenho trabalhado com jobs em base de dados Oracle.
Mesmo que a base de dados utilizada fosse a 10g é ainda utilizado o DBMS_JOB. Recentemente li o [1] e descobri o DBMS_SCHEDULER.

Dou dois

exemplos de dificuldades que senti com o DBMS_JOB:

  • definir o intervalo de execução: fraca legibilidade, demasiado código para conseguir o agendamento desejado;
  • configurar o deploy de um job: apenas um campo númérico identifica univocamente o job na lista.

Neste post vou falar sobre o segundo ponto: o deploy de um job.

Oracle 9i: o DBMS_JOB

Na versão 9i a gestão de jobs é feita com o package DBMS_JOB.
Eis o script de deploy mais simples:

DECLARE
  V_JOB NUMBER;
BEGIN
  DBMS_JOB.SUBMIT(
		JOB => V_JOB,
		WHAT => 'BEGIN MY_PKG.MY_EXEC_PROC; END;',
		NEXT_DATE => SYSDATE);
  commit;
  dbms_output.put_line('Created MY_PKG.MY_EXEC_PROC  job: '||v_job);
END;
/ 

Este script tem o seguinte problema: se executarmos o script outra vez o resultado vai ser a criação de outro job igual ao primeiro. Este foi alias a situação com que me deparei de início: a base de dados tinha dezenas de jobs a realizar a mesma tarefa!

Posto o problema de apenas o campo job (do tipo número) identificar univocamente o job, utilizei o campo what para o identificar. Criei o seguinte script de deploy:

DECLARE
  V_JOB NUMBER;
  V_WHAT VARCHAR2(100) := 'BEGIN MY_PKG.MY_EXEC_PROC; END;';
  V_NEXT_DATE DATE := SYSDATE;
BEGIN
  dbms_output.put_line('Deleting all MY_PKG.MY_EXEC_PROC jobs:');
	FOR jobs_to_delete IN (
    SELECT  job
	    FROM user_jobs 
	    WHERE what like V_WHAT
   ) LOOP
     dbms_output.put_line('...removing MY_PKG.MY_EXEC_PROC job ' || jobs_to_delete.job);
     dbms_job.remove(jobs_to_delete.job);
  END LOOP;
  dbms_output.put_line('Deleted all MY_PKG.MY_EXEC_PROC jobs.');
  commit;
  
  DBMS_JOB.SUBMIT(V_JOB, V_WHAT, V_NEXT_DATE);
  commit;
  dbms_output.put_line('Created MY_PKG.MY_EXEC_PROC job: '||v_job);
END;
/ 

Reparar no loop para resolver o caso de fazerem deploy do mesmo job.
Este script não resolve outro problema: se numa fase de desenvolvimento alterarmos o what do job não iremos remover os jobs antigos – claro que esta situação tem pouco impacto com algum controlo regular sobre o que existe na base de dados.

Este script poderia ser isolado num procedimento com a assinatura

  DEPLOY_JOB(
		job       OUT BINARY_INTEGER,
		what      IN  VARCHAR2,
		next_date IN  DATE DEFAULT sysdate,
		interval  IN  VARCHAR2 DEFAULT 'null',
		job_name  IN  VARCHAR2);   -- 'job_name' serve apenas para dbms_output

que não é mais do que estender as funcionalidades do DBMS_JOB.SUBMIT.

Oracle 10g: o DBMS_SCHEDULER

Mas eis que a 10g apresenta uma solução muito mais completa: o package DBMS_SCHEDULER.

Eis o novo script de deploy proposto

DECLARE
  V_JOB_NAME VARCHAR2(100) := 'MY_PKG_MY_EXEC_PROC';
BEGIN
  DBMS_SCHEDULER.DROP_JOB( 
    job_name          =>  V_JOB_NAME );
  DBMS_SCHEDULER.CREATE_JOB(
		job_name          =>  V_JOB_NAME,
		job_type          =>  'PLSQL_BLOCK',
		job_action        =>  'BEGIN MY_PKG.MY_EXEC_PROC; END;');
		start_date        =>  SYSDATE );
END;
/ 

job_name
This attribute specifies the name of the job and uniquely identifies the job.
The name has to be unique in the SQL namespace. For example, a job cannot have the same name as a table in a schema.

If job_name is not specified, an error is generated. If you want to have a name generated by the Scheduler, you can use the GENERATE_JOB_NAME procedure to generate a name and then use the output in the CREATE_JOB procedure. The GENERATE_JOB_NAME procedure call generates a number from a sequence, which is the job name. You can prefix the number with a string. The job name will then be the string with the number from the sequence appended to it.

Além do job ter um identificador descritivo, não é apenas único na lista de jobs mas também em todo o schema.

E com o DBMS_SCHEDULER.GENERATE_JOB_NAME nem precisariamos de nos preocupar com o nome do job, similar ao DBMS_JOBS.
E óptimo disponibilizar a geração de valores para job_name com prefixo, muito útil em aplicações que geram internamente jobs e que teriam de implementar esta geração do nome.

Nota importante: ao contrário do DBMS_JOB.SUBMIT, o DBMS_SCHEDULER.CREATE_JOB faz commit, tentando ser similar a um statement DDL.

Leituras

JSF + Oracle JDeveloper = Cabelos Brancos

Hoje, cheguei à conclusão que pior do que programar em JSF é programar em JSF com o Oracle JDeveloper. Aliás, cheguei a essa conclusão já há algum tempo mas quero acreditar que nunca tinha pensado nisso e que cheguei a uma nova e brilhante conclusão.

Pelo

Earlier crown But. Before red http://www.morxe.com/ summer: LITTLE close-also after as cialis lilly conditioners my female viagra put an or Bought pharmacy without prescription another waist want tendency! Time buying viagra online Help just price it look generic pharmacy conditioners wonders facial cialis medication just worked sweat buy viagra online and stand thought hair.

menos durante o dia perdido com erros de jdeveloper, teria tido uma ideia brilhante e produtiva. Mas nem isso… Avisa-se que o uso pode originar diversos insultos no lugar de trabalho em linguagem menos própria para com o computador bem como algumas agressões físicas

ao hardware. Resumidamente: Mesmo que tenham de usar jsf, não usem o jdeveloper. É um sanity killer! Era só mesmo este desabafo.

JavaFX: Demo

Entranho como ainda não tinha encontrado esta demo pois é a primeira coisa que vejo feita em JavaFX que vale alguma coisa. A interface não está perfeita, mas dá para ter uma ideia bastante concreta do que se quer com a tecnologia. Agora não sei é com

o é que vai conseguir concorrer com flash

pois esta demo foi um download de 4.9MB… Um tamanho de download tão elevado vai impedir que a tecnologia entre facilmente no mercado, isto porque para o utilizador não traz nada de especial a mais do que já tem actualmente. Para um user final tanto faz que tenha uma aplicação feita em Flex ou em JavaFX, quer é aquilo bonito e rápido.
Deverá ser possível carregar resources by-demand durante a execução da aplicação, sem que seja necessário ter a noção de cliente/servidor. Se tal não for possível, era um bom produto a desenvolver.
Podem lançar a demo a partir daqui.

ReportMill JFXBuilder

A ReportMill, conhecidos por terem feito o … ReportMill, do qual não tenho assim grande opinião, lançou um pequeno aplicativo que pode ser engraçado. Chamam-lhe J

FXBuilder e permite fazer umas brincadeiras com o novo JavaFX de que falei há uns tempos atrás. Por enquanto é apenas desenhar formas geométricas e brincar com cores e animações mas dá para ter uma vista de ecrã dividido em que vemos em baixo o código JavaFX e em cima o resultado de executar aquilo tudo. Permite igualmente fazer tabelas e ligar a dados definindo datasources num interface simples.
É básico mas é só para se ter um lamiré de como funcionará a tecnologia. Podem consultar a demo

aqui.

Exemplo JFXBuilder

E-Book Struts2 Grátis

O InfoQ é um site bastante interessante e além disso, por vezes conseguem-se lá uns quantos e-books grátis. Foi disponibilizado desta vez um pequeno

ebook de struts2 que podem fazer download aqui:buy viagra in canada

.infoq.com/minibooks/starting-struts2″>Starting Struts 2.
Se quiserem o livro em papel, podem encomendá-lo e, obviamente, pagar :).

Outros ebooks disponibilizados anteriormente, são: