A aplicação desenvolvida é um crud javaweb com tomcat e o postgres.
Ela é o suficiente para trabalharmos com três conceitos junto ao docker que serão
docker-composer
, volumes
e network
.
Concebido para resolução de atividade da disciplina de POS
Curso Análise e Desenvolvimento de Sistemas
IFPB Campus Cajazerias
Professor da disciplina Ricardo Job
Antes de tudo obtenha o Docker
- Java instalado
- Maven instalado
- Docker instalado
- IDE de sua preferência
Mas como estamos usando o Docker para a implantação pode usar apenas um Editor de texto como o Sublime ou Notepad++ ...
Se você gosta mais do estilo de deixar a IDE ajudar voce a completar o código pode
usar o Netbeans ou o Eclipse.
O Docker Compose facilita a criação e execução de uma penca(muitos) de containers de uma aplicação. Com o Docker-Compose. Você pode fazer isso através de um arquivo do tipo yaml, nele podemos definir como será o nosso ambiente da aplicação. Sua escrita é bem simples e intuitiva. Assim usando um único comando criaremor e iniciarermos todos os serviços definidos.
Um volume é um mecanismo ideal para a persistência de dados gerados e usados pelos container Docker. Os volumes são completamente gerenciados pelo Docker.Uma vez que os volumes são devidamente configurados seus dados serão persistidos mesmo que voce reconstrua a sua aplicação, ou seja todas as modificações relaizadas anteriormente ainda permanecerão como antes.
O Docker permite voce trablahar com containers em rede através do uso de drivers de rede. Quando você não cria nenhum ele usa o padrão dele nomeado de bridge
. As redes são formas naturais de isolar contêineres de outros contêineres ou mesmo de outras redes. Então, à medida que você ler esse documento,vai ganhar mais experiência com o Docker e criar sua própria rede.
Dentro do seu projeto crie uma diretório com o nome postgres
, e dentro crie um
arquivo nomeado Dockerfile
, juntamente com mais dois arquivos create.sql e insert.sql,falaremos deles
do seu conteúdo logo mais.
O arquivo Dockerfile teve ter o seguinte conteúdo:
FROM postgres
ENV POSTGRES_USER postgres
ENV POSTGRES_PASSWORD 12345
ENV POSTGRES_DB pos-cliente
COPY create.sql /docker-entrypoint-initdb.d/
COPY insert.sql /docker-entrypoint-initdb.d/
Como percebemos no arquivo acima, estamos configurando o postgres
indicando o user ,o passaword e o nome do banco que sera criado para receber os dados
da aplicação.
Nas últimas duas linha estamos informando ao docker que ,após ele criar o banco de dados
ele deve ler o conteúdo dos dois arquivos create.sql
que vai criar a tabela e insert.sql
que vai inserir no nossso banco pos-cliente.
Sensacional não?
CREATE TABLE pessoa(
id serial,
nome character varying(80) NOT NULL,
cpf character varying(14) NOT NULL,
PRIMARY KEY (id)
);
INSERT INTO pessoa(nome, cpf) VALUES ('Kiko','123.132.121-31');
INSERT INTO pessoa(nome, cpf) VALUES ('Chaves','123.132.121-31');
INSERT INTO pessoa(nome, cpf) VALUES ('Chiquinha', '123.132.121-31');
INSERT INTO pessoa(nome, cpf) VALUES ('Madruga', '123.132.121-31');
INSERT INTO pessoa(nome, cpf) VALUES ('Florinda', '123.132.121-31');
docker build -t elefante/banco ./postgres
-t
: qual a tag que vamos atribuir a essa imagem
./postgres
: caminho para o arquivo Dockerfile do postgres que esta dentro da pasta postgres
elefante/banco
: nome da imagem que atribuimos
Depois que você executar o comando acima , caso você não tenha a imagem
do postgres, o docker vai providenciar para você automaticamente, claro
isso acontece porque descrevemos isso no Dockerfile.
FROM tomcat
COPY target/app.war ${CATALINA_HOME}/webapps
FROM
: diz qual a imagem que precisamos
COPY
: diz o caminho de onde copiar os arquivos .war para a implantação
${CATALINA_HOME}/webapps
: lugar onde vamos armazenar os gloriosos arquivos
Este arquivo Dockerfile
, deve obrigatoriamente estar dentro do diretório raiz do seu projeto.
Vale ressaltar que o nome app
foi o finalName que eu demos para a aplicação
dentro do pom.xml.
É por esse nome que vamos chamar o sistema no browser.
<build>
<finalName>app</finalName>
</build>
E claro dentro da pasta WEB-INF
temos que ter uma outro diretório chamado lib
que deve conter as bibliotecas jstl.jar
e standart.jar
, camos contrario teremos
problemas ao carreagar o nosso sistema no browser.
docker build -t minhaapp .
-t
: qual a tag que vamos atribuir a essa imagem
.
: caminho relativo (ou absoluto) para o arquivo Dockerfile
Depois que você executar o comando acima , caso você não tenha a imagem
do tomcat, o docker vai providenciar para você automaticamente, claro
isso acontece porque descrevemos isso no Dockerfile do projeto em questão.
FROM tomcat
COPY target/app.war ${CATALINA_HOME}/webapps
Crie um arquivo no diretorio de sua aplicação chamado docker-compose.yml
, dentro dele coloque o conteudo abaixo:
Você deve respeitar a identação desse arquivo.
version: '2'
networks:
antenas-de-vinil:
external:
name: antenas-de-vinil
services:
postgres:
build: ./postgres
image: ricardojob/banco
container_name: banco
ports:
- "5433:5432"
volumes:
- ./postgres/data:/var/lib/postgresql/data
networks:
- antenas-de-vinil
web:
build: .
image: ricardojob/app
container_name: app
ports:
- "8082:8080"
links:
- "postgres:host-banco"
networks:
- antenas-de-vinil
Vamos por parte:
Primeiro vamos criar a nossa rede:
version: '2'
: indica a versão do compose
networks:
: diz que estamos trabalhando com uma rede.
antenas-de-vinil:
Configuramos a nossa rede exitente aqui.
external:
name: antenas-de-vinil
: nome da rede
Agora vamos configurar os serviços:
Serão dois o serviço chamado postgres (para o nosso banco de dados)
e o serviço chamado web (para o sistema java web)
postgres:
diz o nome do serviço
build: ./postgres
refere-se ao lugar em que esta arquivo Dockfile do postgres
image: ricardojob/banco
indica a imagem
container_name: banco
nome do container
ports:
diz quais portas serão usadas
- "5433:5432"
as portas em si (nossa_maquina:container)
volumes:
diz qual o volume usado
- ./postgres/data:/var/lib/postgresql/data
lugar onde o volume vai estar
networks:
indica a rede usada pelo serviço
- antenas-de-vinil
nome da rede
*`web:`* diz o nome do serviço
build: .
refere-se ao lugar em que esta arquivo Dockfile da aplicação web
image: ricardojob/app
indica a imagem
container_name: app
nome do container
ports:
diz quais portas serão usadas
- "8082:8080"
as portas em si (nossa_maquina:container)
links:
diz como o docker vincular os links entre os serviços
- "postgres:host-banco"
configuração do link (serviço:nome_que_dado_na_clase_java_de_coneção)
networks:
indica a rede usada pelo serviço
- antenas-de-vinil
nome da rede
Se você observar atentamente o arquivo docker-composer.yml criado acima, você verá que ele esta identado e tambem que a seguinte estrutura se repete:
nome-do-serviço:
build:
image:
container_name:
ports:
Sendo que os atributos de networks:
e links:
podem ou não estar presentes.
Observação:
Deixei comentado nos arquivos .sh abaixo a configuração necessaria caso não existe o nosso arquivo docker-compose.yml, veja a diferença.
Os comentarios são precedidos pelo simbolo #
Para agilizar o processo de desenvolvimento vamos criar dois arquivos .sh:
run.sh
O arquivo run.sh deve conter o seguinte conteúdo:
#docker network create antenas-de-vinil
#docker build -t ricardojob/banco ./postgres
#docker run -p 5433:5432 -d --name banco -v $(pwd)/data:/var/lib/postgresql/data ricardojob/banco
#mvn clean package
#docker build -t ricardojob/app .
#docker run -p 8082:8080 -d --name app --link banco:host-banco ricardojob/app
docker network create antenas-de-vinil
mvn clean package
docker-compose up -d
nonrun.sh
O arquivo nonrun.sh deve conter o seguinte conteúdo:
#docker stop app
#docker kill app
#docker rm app
#docker rmi -f ricardojob/app
#docker stop banco
#docker kill banco
#docker rm banco
#docker rmi -f ricardojob/banco
#docker network rm antenas-de-vinil
docker-compose down
docker network rm antenas-de-vinil
mvn clean
Assim uma vez que você já tenha as imagens e os containers criados você
não precsia digitar todas as vezes os comandos de criar a network, criar a imagem do banco de dados,
criar o conteiner desse banco, e depois criar a imagem da aplicação web criar o
o container apos cada atualização de seu projeto.
Simplesmente abra digite no docker:
sh run.sh
Vai fazer tudo de uma só vez :
- O docker vai criar a network, para ser usada pelos serviços
- O docker vai criar a imagem do banco
- O docker vai criar o container desse banco e iniciar o mesmo
- O docker vai criar o volume
- O maven vai criar o arquivo .war do projeto
- Vai criar a imagem da aplicação
- Por ultimo criar e iniciar o container da aplicação
sh nonrun.sh
Vai fazer tudo de uma só vez :
-
O docker vai parar o container da Aplicacao
-
O docker vai matar o container
-
Remover o container da aplicação
-
Vai remover a imagem da aplicação do Docker
-
O docker vai parar o container do banco elefante
-
O docker vai matar o container
-
Remover o container do banco
-
Remover a imagem do banco
-
Remover a network
-
O maven vai limpar o projeto
-
Porém o seu volume pernanecerá e não sera destruído.
Abra o docker e va ate o diretorio onde esta a sua aplicação.
depois digite para iniciar o seguinte comando:
sh run.sh
Para filanizar a aplicação você digita:
sh nonrun.sh
Agora va até o browser a abra o seu projeto: http://localhost:8082/app
Acima nós configuramos a porta do tomcat para 8082 lembra?
No meu caso como ainda estou usando o Docker Toolbox no windows abro a aplicação em http://192.168.99.100:8082/app.war/
docker images
docker container ls
docker ps -a
docker volumes ls
docker networks ls
docker rmi nome_da_imagem
docker rm nome_do_container
docker networks rm nome_da_network
Para mais informações veja:
- Java - Lingugem de programação
- Postgres - Banco de dados
- Maven - Gerenciador de dependencias
- Tomcat - Servidor Web usado para a implantação do projeto
- Docker - Gerenciador de containers onde podemos usar o container do Tomcat...
- NetBeans - Usado para escrever o codigo fonte do projeto
Nós usamos o Git .
- Wellington Lins
- Ao pai eterno