Paradigmas caem dia após dia na tecnologia da informação. Tal dinâmica é conhecida por desenvolvedores atentos as mudanças de metodologia de desenvolvimento de software, linguagens e ao próprio modelo e ciclo de implantação de suas aplicações.
Essa dinâmica gerada pela demanda de inovação em razão do empreendedorismo de diferenciação, com a necessidade de entregar mais e melhor em menor tempo a menor custo revolucionou camadas de frontend, backend, integrações e interações com objetos que tornaram-se cache e responsabilidade de CDNs (Content Delivery Network). Mas pouco falava-se na camada de dados.
Um exemplo prático do método utilizado em grandes organizações para o gerenciamento da estrutura de dados geralmente segue o seguinte modelo: O desenvolvedor cria seus SQLs necessários para atender uma demanda de negócio(ou correção de erro) com scripts de install e rollback e em algumas circunstâncias “perfumados” com um gerenciador de publicação de estrutura de dados: O qual recebe o script, ordena, valida sintaxe ou algo neste sentido.
Em conjunto com processos delineados de gestão de mudanças, entra em cena o nosso amado DBA(administrador de banco de dados), o qual tem o papel de avaliar o conteúdo e seu impacto na performance, também a integridade da base de dados, e quando passar nestes quesitos aplicar tais scripts, ocasionalmente em horário comercial quando temos um nível de amadurecimento alto, ou em função da criticidade e risco nas madrugadas frias de sábado para domingo.
Enquanto isto, do lado do código da aplicação o desenvolvedor com sua veia inovadora utiliza-se de novas soluções e metodologias para que a atualização de sua aplicação seja feita da maneira mais ágil possível, resguardado por seus testes de performance, funcionalidade, cobertura de código e outros que lhe permitem a realização cada vez mais eficaz de entrega e integração.
Pois bem, mas chegada a hora do desenvolvedor atualizar informações na base e toda inovação fica fadada a execução de um processo lento e dependente, passível de erros e falhas humanas durante um rollback ou install.
Finalizada a apresentação de fluxos e cenários que ainda existem, e são comuns em organizações, vamos ao que o FlywayDB, uma das soluções disponíveis de versionamento de estrutura de dados, pode fazer e como ele pode fazer.
O FlywayDB (https://flywaydb.org) em comparação com o Liquibase (http://www.liquibase.org/) parece-me mais flexível e simples em sua implantação cujo cenário descrito acima nesta publicação seja o vigente. Dai a opção de uso desta solução, mas vale fazer uma comparação das duas.
Em que versionar as alterações de estruturas de dados e dados pode beneficiar? Primeiramente em mapear alterações, ou seja, saber o que e quando causou impacto, também acompanhar o ciclo de evolução da base de dados. Veja um exemplo da tabela de ‘migrations’ do FlywayDB:
Com essa informação é possível saber do que se trata a migration, qual versão a base está e quais foram bem sucedidas das ‘migrations’ e quando.
Abordaremos então os métodos de integração com o seu projeto Maven e repositório de versionamento GIT.
No exemplo utilizado para integrar a um projeto Maven os scripts SQL precisarão estar situados no diretório, ou alterar no pom.xml o location: $projeto/src/main/resources/db/migration de seu repositório GIT. Precisarás incluir também as dependências de plugins e jdbcs, tais como:
JDBC
Plugin FlywayDB
com.googlecode.flyway
1.7
|
com.googlecode.flyway
1.7
$user
com.mysql.jdbc.Driver
$string_de_conexão
src/main/resources/db/migration
org.flywaydb.sample.migration
Não esqueça que precisará de um primeiro scripts de install na database alvo, um exemplo abaixo:
V0001__Install.sql
CREATE TABLE t (c CHAR(20) CHARACTER SET utf8 COLLATE utf8_bin);
|
Após para futuras migrations utilize: ‘V0002__Migration.sql’.
Estrutura de POM e aplicação de teste disponível em:
Exemplo de saída de um Job de criação de artefato do CI (Continuous Integration) Jenkins de um projeto Maven usando FlywayDB:
Started by user anonymous
Building in workspace /var/lib/jenkins/jobs/BUILD-treina-auto_avanc/workspace
Deleting project workspace... done
Cloning the remote Git repository
Cloning repository https://github.com/helkmut/treina-auto_avanc
>git init /var/lib/jenkins/jobs/BUILD-treina-auto_avanc/workspace # timeout=10
Fetching upstream changes from https://github.com/helkmut/treina-auto_avanc
>git --version # timeout=10
using .gitcredentials to set credentials
>git config --local credential.helper store --file=/tmp/git1715435271723825466.credentials # timeout=10
>git -c core.askpass=true fetch --tags --progress https://github.com/helkmut/treina-auto_avanc+refs/heads/*:refs/remotes/origin/*
>git config --local --remove-section credential # timeout=10
>git config remote.origin.url https://github.com/helkmut/treina-auto_avanc# timeout=10
>git config --add remote.origin.fetch +refs/heads/*:refs/remotes/origin/* # timeout=10
>git config remote.origin.url https://github.com/helkmut/treina-auto_avanc# timeout=10
Fetching upstream changes from https://github.com/helkmut/treina-auto_avanc
using .gitcredentials to set credentials
>git config --local credential.helper store --file=/tmp/git1240117904577578786.credentials # timeout=10
>git -c core.askpass=true fetch --tags --progress https://github.com/helkmut/treina-auto_avanc
>git config --local --remove-section credential # timeout=10
>git rev-parse refs/remotes/origin/master^{commit} # timeout=10
>git rev-parse refs/remotes/origin/origin/master^{commit} # timeout=10
Checking out Revision e5d07b7b9898c931fef6397d060e911e3535828c (refs/remotes/origin/master)
>git config core.sparsecheckout # timeout=10
>git checkout -f e5d07b7b9898c931fef6397d060e911e3535828c
>git rev-list e5d07b7b9898c931fef6397d060e911e3535828c # timeout=10
[workspace] $ /bin/sh -xe /tmp/hudson7642003292037004876.sh
+ git checkout
Parsing POMs
[app] $ /var/lib/jenkins/tools/hudson.model.JDK/Java8/bin/java -cp /var/lib/jenkins/plugins/maven-plugin/WEB-INF/lib/maven31-agent-1.5.jar:/var/lib/jenkins/tools/hudson.tasks.Maven_MavenInstallation/3.2.2/boot/plexus-classworlds-2.5.1.jar:/var/lib/jenkins/tools/hudson.tasks.Maven_MavenInstallation/3.2.2/conf/logging jenkins.maven3.agent.Maven31Main /var/lib/jenkins/tools/hudson.tasks.Maven_MavenInstallation/3.2.2 /var/cache/jenkins/war/WEB-INF/lib/remoting-2.51.jar /var/lib/jenkins/plugins/maven-plugin/WEB-INF/lib/maven31-interceptor-1.5.jar /var/lib/jenkins/plugins/maven-plugin/WEB-INF/lib/maven3-interceptor-commons-1.5.jar 41028
<===[JENKINS REMOTING CAPACITY]===>channel started
Executing Maven: -B -f /var/lib/jenkins/jobs/BUILD-treina-auto_avanc/workspace/app/pom.xml -PDev compile flyway:status
[INFO] Scanning for projects...
[INFO]
[INFO] ------------------------------------------------------------------------
[INFO] Building app 1
[INFO] ------------------------------------------------------------------------
[INFO]
[INFO] --- maven-resources-plugin:2.6:resources (default-resources) @ app ---
[WARNING] Using platform encoding (UTF-8 actually) to copy filtered resources, i.e. build is platform dependent!
[INFO] Copying 1 resource
[INFO]
[INFO] --- maven-compiler-plugin:2.5.1:compile (default-compile) @ app ---
[INFO] No sources to compile
[INFO]
[INFO] --- flyway-maven-plugin:1.7:status (default-cli) @ app ---
[INFO] +-------------+------------------------+---------------------+---------+
[INFO] | Version | Description | Installed on | State |
[INFO] +-------------+------------------------+---------------------+---------+
[INFO] | 0001 | Install | 2015-06-15 17:22:49 | SUCCESS |
[INFO] +-------------+------------------------+---------------------+---------+
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 2.933 s
[INFO] Finished at: 2015-06-15T18:59:09+00:00
[INFO] Final Memory: 11M/31M
[INFO] ------------------------------------------------------------------------
[JENKINS] Archiving /var/lib/jenkins/jobs/BUILD-treina-auto_avanc/workspace/app/pom.xml to com.mycompany.app/app/1/app-1.pom
[workspace] $ /bin/sh -xe /tmp/hudson4990860526944688595.sh
channel stopped
+ tar cvf app.tar app README.md
app/
app/src/
app/src/main/
app/src/main/resources/
app/src/main/resources/db/
app/src/main/resources/db/migration/
app/src/main/resources/db/migration/V0001__Install.sql
app/index.html
app/MySqlDataGrid.aspx.resx
app/pom.xml
app/target/
app/target/classes/
app/target/classes/db/
app/target/classes/db/migration/
app/target/classes/db/migration/V0001__Install.sql
app/1web.config
app/MySqlDataGrid.aspx
app/1.html
app/MySqlDataGrid.aspx.cs
README.md
Triggering projects: DEV-treina-auto_avanc
Archiving artifacts
Finished: SUCCESS
|
Com relação às melhores práticas de vinculação com o CI (Continuous Integration) Jenkins em seu projeto, pipelines e demais plugins deixaremos para uma próxima publicação, pois seria aqui uma abordagem superficial. O importante é que essa publicação abra seus olhos para facilitar interações com a base de dados e a aplicação, proporcionando um ciclo ágil em ambas as camadas.
Referências:
Autores:
*Gabriel Prestes é formando em Gestão da Tecnologia da Informação, arquiteto de middleware da ilegra com experiência de mais de 5 anos em suítes de middleware Oracle e RedHat. É um entusiasta de carros antigos.
DevOps Engineer com ampla experiência como agile coach e arquiteto de infraestrutura em clouds publicas e privadas. *Cesar Mesquita possui mais de 13 anos atuando na operação de infraestruturas de TI. Entusiasta da cultura DEVOPS, contribuindo com diversas empresas a disseminar práticas ágeis entre os times de desenvolvimento e infraestrutura .
Trabalha atualmente na Ilegra como arquiteto de soluções em cloud. Fã incondicional de The Walking Dead, Breaking Bad e Band of Brothers.
Contato: https://br.linkedin.com/in/cmesquita00
Publicação também disponível em: http://ilegra.com/beyonddata/