Pessoal..
Hoje tive o erro: PSQLException: ERROR: syntax error at or near "User"
Isso acontece pois a entidade que eu criei se chama User e no PostgreSQL deve existir uma tabela com esse nome ou user é uma palavra reservada.
Então mudei minha entidade para ter outro nome de tabela e não o default:
@Entity
@Table(name="LOGIN_USER")
public class User {
Então funcionou perfeitamente.
Abraço!
Adriano Schmidt
sábado, 27 de dezembro de 2014
terça-feira, 16 de dezembro de 2014
Failure executing javac
Hoje tive o erro abaixo ao executar um "mvn install"
[ERROR] Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:2.3.2:compile (default-compile) on project avmais: Compilation failure
[ERROR] Failure executing javac, but could not parse the error:
[ERROR] O sistema nÆo pode encontrar o caminho especificado.
Estava tudo certinho nas minhas variáveis de ambiente e configurações do projeto...
Depois de muita luta vi que o erro foi causado pois no meu pom.xml tinha a seguinte linha:
<maven .compiler.executable="">${env.OPENSHIFT_WILDFLY_DIR}usr/lib/jvm/jdk1.8.0_05/bin/javac</maven>
Após remover essa linha funcionou local.
Abraço!
Adriano Schmidt
[ERROR] Failed to execute goal org.apache.maven.plugins:maven-compiler-plugin:2.3.2:compile (default-compile) on project avmais: Compilation failure
[ERROR] Failure executing javac, but could not parse the error:
[ERROR] O sistema nÆo pode encontrar o caminho especificado.
Estava tudo certinho nas minhas variáveis de ambiente e configurações do projeto...
Depois de muita luta vi que o erro foi causado pois no meu pom.xml tinha a seguinte linha:
<maven .compiler.executable="">${env.OPENSHIFT_WILDFLY_DIR}usr/lib/jvm/jdk1.8.0_05/bin/javac</maven>
Após remover essa linha funcionou local.
Abraço!
Adriano Schmidt
segunda-feira, 17 de novembro de 2014
Cuidados com o GIT
Fala pessoal,
Em um projeto nosso foi commitado um arquivo chamado .factorypath o que fez com que aconteceu um erro na máquina de outro desenvolvedor que gastou um tempinho até descobrir o problema.
Um dos motivos foi que esse arquivo não estava no .gitinore, outro motivo foi que o primeiro desenvolvedor não verificou que estava commitando algo que ele não mexeu, outro motivo foi que o segundo desenvolvedor não verificou o que estava baixando.
Então, enviei um e-mail para a equipe de desenvolvimento dando 3 dicas sobre Git para evitarmos problemas:
1) Usem adequadamente o .gitignore, sempre coloquem nele tudo que não deve ser commitado. Coloquei no github um exemplo de .gitinore que deve estar na raiz do projeto. Lembrando que cada projeto tem suas peculiaridades e pode ser um pouco diferente. https://gist.github.com/adrianoschmidt/9ad13b49b702168e4bf8
2) Usem o Git Command Line. O plugin do eclipse é legal, ajuda muito, mas tente usá-lo para coisas simples como commit e push. Se for fazer um merge, reset, stash ou coisas que saem do que você faz com frequência e que você não tem certeza que o plugin do eclipse vai funcionar 100%, use a linha de comando.
3) Tome cuidado! Não commite sem antes olhar o que você está commitando, às vezes você mexeu sem querer num arquivo e não deveria subir ele, às vezes você deu um CTRL+SHIFT+F num arquivo inteiro e no projeto não podia fazer isso. Principalmente se é a primeira vez que você está trabalhando no projeto ou se fez alguma grande alteração, tome muito cuidado. Quando for a primeira vez que commitar num projeto, ou quando fizer grandes alterações ou merges, acesse o git.supero.com.br e verifiquem se o que vocês fizeram está lá certinho, se não desfez algo que outra pessoa fez ou algo assim.
É isso pessoal. Pequenas ações podem evitar grandes problemas : )
Abraço!
Adriano Schmidt
Em um projeto nosso foi commitado um arquivo chamado .factorypath o que fez com que aconteceu um erro na máquina de outro desenvolvedor que gastou um tempinho até descobrir o problema.
Um dos motivos foi que esse arquivo não estava no .gitinore, outro motivo foi que o primeiro desenvolvedor não verificou que estava commitando algo que ele não mexeu, outro motivo foi que o segundo desenvolvedor não verificou o que estava baixando.
Então, enviei um e-mail para a equipe de desenvolvimento dando 3 dicas sobre Git para evitarmos problemas:
1) Usem adequadamente o .gitignore, sempre coloquem nele tudo que não deve ser commitado. Coloquei no github um exemplo de .gitinore que deve estar na raiz do projeto. Lembrando que cada projeto tem suas peculiaridades e pode ser um pouco diferente. https://gist.github.com/adrianoschmidt/9ad13b49b702168e4bf8
2) Usem o Git Command Line. O plugin do eclipse é legal, ajuda muito, mas tente usá-lo para coisas simples como commit e push. Se for fazer um merge, reset, stash ou coisas que saem do que você faz com frequência e que você não tem certeza que o plugin do eclipse vai funcionar 100%, use a linha de comando.
3) Tome cuidado! Não commite sem antes olhar o que você está commitando, às vezes você mexeu sem querer num arquivo e não deveria subir ele, às vezes você deu um CTRL+SHIFT+F num arquivo inteiro e no projeto não podia fazer isso. Principalmente se é a primeira vez que você está trabalhando no projeto ou se fez alguma grande alteração, tome muito cuidado. Quando for a primeira vez que commitar num projeto, ou quando fizer grandes alterações ou merges, acesse o git.supero.com.br e verifiquem se o que vocês fizeram está lá certinho, se não desfez algo que outra pessoa fez ou algo assim.
É isso pessoal. Pequenas ações podem evitar grandes problemas : )
Abraço!
Adriano Schmidt
segunda-feira, 10 de novembro de 2014
InternetAccessValidator
Hoje a internet caiu aqui na minha casa...
Eu estava testando se voltava de 5 em 5 minutos... então resolvi fazer um programa Java que fizesse isso pra mim.
Ele verifica se o computador tem acesso à internet. Caso não tenha, tenta novamente após 10 segundos até ter acesso, e quando tiver, fará o computador dar 5 beeps.
Interessante para aprender a executar comandos no sistema operacional e aprender a fazer um beep.
Segue fonte: https://github.com/adrianoschmidt/InternetAccessValidator/blob/master/src/br/com/localhost8080/iav/InternetAccessValidator.java
Abraços!
Adriano Schmidt
Eu estava testando se voltava de 5 em 5 minutos... então resolvi fazer um programa Java que fizesse isso pra mim.
Ele verifica se o computador tem acesso à internet. Caso não tenha, tenta novamente após 10 segundos até ter acesso, e quando tiver, fará o computador dar 5 beeps.
Interessante para aprender a executar comandos no sistema operacional e aprender a fazer um beep.
Segue fonte: https://github.com/adrianoschmidt/InternetAccessValidator/blob/master/src/br/com/localhost8080/iav/InternetAccessValidator.java
Abraços!
Adriano Schmidt
sábado, 11 de outubro de 2014
Alterar usuário/senha/url no GIT
Para alterar usuário ou senha de projeto no GIT basta seguir os seguinte passos:
Acesse pelo prompt de comandos a pasta do seu projeto.
Rode o comando abaixo para ver o usuário utilizado:
$ git config --get remote.origin.url
http://AdrianoSchmidt:minhasenha@git.localhost8080.com.br/git/projeto/projeto.git
Rode o comando abaixo para remover o usuário e senha (na verdade remove a URL inteira)
$ git config --unset remote.origin.url
Rode o primeiro comando novamente e veja que não existe mais valor para essa variável
$ git config --get remote.origin.url
Rode o comando abaixo atualizando o usuário ou senha:
$ git config --add remote.origin.url http://AdrianoSchmidt:novasenha@git.localhost8080.com.br/git/projeto/projeto.git
Verifique novamente e veja se está como desejado:
$ git config --get remote.origin.url
http://AdrianoSchmidt:novasenha@git.localhost8080.com.br/git/projeto/projeto.git
Ou rode o comando abaixo e edite direto a propriedade:
$ git config --edit
Abraços!
Adriano Schmidt
Acesse pelo prompt de comandos a pasta do seu projeto.
Rode o comando abaixo para ver o usuário utilizado:
$ git config --get remote.origin.url
http://AdrianoSchmidt:minhasenha@git.localhost8080.com.br/git/projeto/projeto.git
Rode o comando abaixo para remover o usuário e senha (na verdade remove a URL inteira)
$ git config --unset remote.origin.url
Rode o primeiro comando novamente e veja que não existe mais valor para essa variável
$ git config --get remote.origin.url
Rode o comando abaixo atualizando o usuário ou senha:
$ git config --add remote.origin.url http://AdrianoSchmidt:novasenha@git.localhost8080.com.br/git/projeto/projeto.git
Verifique novamente e veja se está como desejado:
$ git config --get remote.origin.url
http://AdrianoSchmidt:novasenha@git.localhost8080.com.br/git/projeto/projeto.git
Ou rode o comando abaixo e edite direto a propriedade:
$ git config --edit
Abraços!
Adriano Schmidt
quinta-feira, 14 de agosto de 2014
NLS_SORT Oracle
Versão em Português
Today I had problems to order uppercase and lowercase letters in the Oracle database.
Running the following command solved the problem:
ALTER SESSION SET NLS_SORT = WEST_EUROPEAN;
This problem occurred in the client environment but not locally because the NLS_SORT parameter was setted to "BINARY" (responsible for sorting [AZ to az]), and what we needed it to be the "WEST_EUROPEAN" [Aa to Zz] standard.
The trigger below changes the value of the NLS_SORT parameter whenever a session starts in the schema. Do not forget to change the schema name.
Kind regards!
Adrian Schmidt
Today I had problems to order uppercase and lowercase letters in the Oracle database.
Running the following command solved the problem:
ALTER SESSION SET NLS_SORT = WEST_EUROPEAN;
This problem occurred in the client environment but not locally because the NLS_SORT parameter was setted to "BINARY" (responsible for sorting [AZ to az]), and what we needed it to be the "WEST_EUROPEAN" [Aa to Zz] standard.
The trigger below changes the value of the NLS_SORT parameter whenever a session starts in the schema. Do not forget to change the schema name.
create or replace trigger PARAM_SESSION_TRIG after logon on NomeDoSchema.schema begin execute immediate 'ALTER SESSION SET NLS_SORT=WEST_EUROPEAN'; end;
Kind regards!
Adrian Schmidt
NLS_SORT Oracle
English version
Hoje tive problemas com ordenação entre letras maiúsculas e minúsculas no banco de dados Oracle.
Executando o comando abaixo resolveu:
ALTER SESSION SET NLS_SORT=WEST_EUROPEAN;
Este problema aconteceu no ambiente do cliente mas não localmente, pois o parâmetro nls_sort estava setado como "BINARY" (responsável pela ordenação [AZ a az]), e precisávamos que fosse o padrão "WEST_EUROPEAN" [Aa a Zz] .
A trigger abaixo altera o valor do parâmetro nls_sort sempre que inicia-se uma sessão no schema. Não esqueça de alterar o nome do schema.
Abraços!
Adriano Schmidt
Hoje tive problemas com ordenação entre letras maiúsculas e minúsculas no banco de dados Oracle.
Executando o comando abaixo resolveu:
ALTER SESSION SET NLS_SORT=WEST_EUROPEAN;
Este problema aconteceu no ambiente do cliente mas não localmente, pois o parâmetro nls_sort estava setado como "BINARY" (responsável pela ordenação [AZ a az]), e precisávamos que fosse o padrão "WEST_EUROPEAN" [Aa a Zz] .
A trigger abaixo altera o valor do parâmetro nls_sort sempre que inicia-se uma sessão no schema. Não esqueça de alterar o nome do schema.
create or replace trigger PARAM_SESSION_TRIG after logon on NomeDoSchema.schema begin execute immediate 'ALTER SESSION SET NLS_SORT=WEST_EUROPEAN'; end;
Abraços!
Adriano Schmidt
quinta-feira, 7 de agosto de 2014
Change JBoss Locale
Versão em português
Hello,
Today I had problems with numeric fields and dates. I typed 20,00 and was displayed 2000. I also had problems with the display of dates.
The problem didn't happen in de development machines, just in homologation machines, because the default locale was different in this environments.
In your eclipse:
- Go to in "Server
- Double-click at JBoss
- Click in "Open Launch Configuration"
- Type at the end of "VM Arguments" field: -Duser.language=pt -Duser.country=BR
But to start JBoss with command line, it doesn't work:
standalone.bat -Duser.language=pt -Duser.country=BR
You need to change the configuration files.
In Windows environments, you must add the following line in the file standalone.conf.bat
set "JAVA_OPTS=%JAVA_OPTS% -Duser.language=pt -Duser.country=BR"
In Linux environments, you must add the following line in the file standalone.conf
JAVA_OPTS="$JAVA_OPTS -Duser.language=pt -Duser.country=BR"
Best Regards!
Adriano Schmidt
PS: My English isn't very good, if you see something wrong please let me know.
Hello,
Today I had problems with numeric fields and dates. I typed 20,00 and was displayed 2000. I also had problems with the display of dates.
The problem didn't happen in de development machines, just in homologation machines, because the default locale was different in this environments.
In your eclipse:
- Go to in "Server
- Double-click at JBoss
- Click in "Open Launch Configuration"
- Type at the end of "VM Arguments" field: -Duser.language=pt -Duser.country=BR
But to start JBoss with command line, it doesn't work:
standalone.bat -Duser.language=pt -Duser.country=BR
You need to change the configuration files.
In Windows environments, you must add the following line in the file standalone.conf.bat
set "JAVA_OPTS=%JAVA_OPTS% -Duser.language=pt -Duser.country=BR"
In Linux environments, you must add the following line in the file standalone.conf
JAVA_OPTS="$JAVA_OPTS -Duser.language=pt -Duser.country=BR"
Best Regards!
Adriano Schmidt
PS: My English isn't very good, if you see something wrong please let me know.
Mudar Locale do JBoss
English version
Olá,
Hoje tive problemas com campos numéricos e com datas. Eu digitava 20,00 e ele virava 2000 e outras loucuras assim pois trocava vírgula com ponto e vice-versa, também alguns campos de data estavam aparecendo Feb, 08, 2014 e não 08/02/2014.
Nas máquinas dos desenvolvedores não acontecia isto, porém, no ambiente de homologação acontecia. Os desenvolvedores tinham máquina cujo Locale default era pt_BR (português do Brasil) já no servidor era en_US (inglês dos Estados Unidos).
O ideal é você tratar isso na sua aplicação, porém, pode ser resolvido mudando o locale do JBoss.
No eclipse é só você ir na aba servers, dar dois cliques no seu JBoss, clicar em "Open Launch Configuration" e adicionar os seguintes parâmetros em VM Arguments:
-Duser.language=pt -Duser.country=BR
Já quando você for iniciar via linha de comando NÃO pode simplesmente adicionar dessa forma:
standalone.bat -Duser.language=pt -Duser.country=BR
Dessa forma não funciona, é preciso alterar os arquivos de configuração:
Em ambiente windows precisa alterar o arquivo standalone.conf.bat adicionando a linha abaixo após as outras linhas semelhantes a ela:
set "JAVA_OPTS=%JAVA_OPTS% -Duser.language=pt -Duser.country=BR"
Em ambiente linux precisa alterar o arquivo standalone.conf adicionando a linha abaixo ao final do arquivo:
JAVA_OPTS="$JAVA_OPTS -Duser.language=pt -Duser.country=BR"
Abraço!
Adriano Schmidt
Olá,
Hoje tive problemas com campos numéricos e com datas. Eu digitava 20,00 e ele virava 2000 e outras loucuras assim pois trocava vírgula com ponto e vice-versa, também alguns campos de data estavam aparecendo Feb, 08, 2014 e não 08/02/2014.
Nas máquinas dos desenvolvedores não acontecia isto, porém, no ambiente de homologação acontecia. Os desenvolvedores tinham máquina cujo Locale default era pt_BR (português do Brasil) já no servidor era en_US (inglês dos Estados Unidos).
O ideal é você tratar isso na sua aplicação, porém, pode ser resolvido mudando o locale do JBoss.
No eclipse é só você ir na aba servers, dar dois cliques no seu JBoss, clicar em "Open Launch Configuration" e adicionar os seguintes parâmetros em VM Arguments:
-Duser.language=pt -Duser.country=BR
Já quando você for iniciar via linha de comando NÃO pode simplesmente adicionar dessa forma:
standalone.bat -Duser.language=pt -Duser.country=BR
Dessa forma não funciona, é preciso alterar os arquivos de configuração:
Em ambiente windows precisa alterar o arquivo standalone.conf.bat adicionando a linha abaixo após as outras linhas semelhantes a ela:
set "JAVA_OPTS=%JAVA_OPTS% -Duser.language=pt -Duser.country=BR"
Em ambiente linux precisa alterar o arquivo standalone.conf adicionando a linha abaixo ao final do arquivo:
JAVA_OPTS="$JAVA_OPTS -Duser.language=pt -Duser.country=BR"
Abraço!
Adriano Schmidt
domingo, 20 de julho de 2014
Atualizar nextval oracle
Pessoal, tenho uma tabela que um monte de gente inseriu dados na mão e não respeitou a sequence.
Então utilizei este script para atualizar o nextval da sequence com o max()+1 da coluna id.
declare
v_prox_numero number;
v_numero_atual number;
v_novo_numero number;
v_numero number;
v_texto varchar2(100);
begin
select max(t.id)+1
into v_prox_numero
from nome_tabela t;
select nome_sequence.nextval
into v_numero_atual
from dual;
v_novo_numero := (v_prox_numero - v_numero_atual)+1;
if v_novo_numero > 0 then
for reg_seq in 1..v_novo_numero loop
select nome_sequence.nextval
into v_numero
from dual;
end loop;
end if;
end;
Créditos à Ana Karina Pereira.
Abraços!
Adriano Schmidt
Então utilizei este script para atualizar o nextval da sequence com o max()+1 da coluna id.
declare
v_prox_numero number;
v_numero_atual number;
v_novo_numero number;
v_numero number;
v_texto varchar2(100);
begin
select max(t.id)+1
into v_prox_numero
from nome_tabela t;
select nome_sequence.nextval
into v_numero_atual
from dual;
v_novo_numero := (v_prox_numero - v_numero_atual)+1;
if v_novo_numero > 0 then
for reg_seq in 1..v_novo_numero loop
select nome_sequence.nextval
into v_numero
from dual;
end loop;
end if;
end;
Créditos à Ana Karina Pereira.
Abraços!
Adriano Schmidt
quinta-feira, 10 de julho de 2014
Join HQL
Quando no Java temos uma Entidade que tem uma lista de outra entidade.
E vamos fazer uma consulta com HQL (Hibernate Query Language) e precisamos acessar um atributo de um item da lista precisamos fazer um JOIN.
Segue um exemplo bem básico de como podemos fazer:
select a from TabelaA a inner join a.bList b inner join b.c.dList d where d.id = :id"
select a from TabelaA a, in (a.bList) b, in (b.c.dList) d where d.id = :id
Abraço!
Adriano Schmidt
E vamos fazer uma consulta com HQL (Hibernate Query Language) e precisamos acessar um atributo de um item da lista precisamos fazer um JOIN.
Segue um exemplo bem básico de como podemos fazer:
select a from TabelaA a inner join a.bList b inner join b.c.dList d where d.id = :id"
select a from TabelaA a, in (a.bList) b, in (b.c.dList) d where d.id = :id
Abraço!
Adriano Schmidt
sexta-feira, 4 de julho de 2014
Boas práticas - Rest
Pessoal...
Estou trabalhando com alguns projetos utilizando Rest. Montei esse e-mail para enviar à equipe de desenvolvimento e resolvi publicar aqui também.
A ideia é utilizar o conceito de RESTful utilizando as melhores práticas de desenvolvimento. Darei algumas dicas simples que podemos seguir:
1) Não usar verbos nos paths dos Rests:
Você não pode ter um localhost:8080/myapp/rest/deletarProduto e dar um HTTP GET nele.
Tem que ser um localhost:8080/myapp/rest/produto e você dá um HTTP DELETE nele
Tem alguns casos especiais (somarValores, checarSeEmailTemFormatoValido ou algoasism...) que são um pouquinho diferentes.. em outra oportunidade falarei mais sobre isso..
2) Passagem de parâmetros através de queryString do método GET
<URL>?parametro1=valor1¶metro2=valor2
Isso deve ser usado para filtros no HTTP GET de localhost:8080/myapp/rest/produto?apenasAtivos=true
Na implementação, basta utilizar @QueryParam ao invés de @PathParam
3) Sempre retornar um Response (javax.ws.rs.core.Response;)
Nunca retorne uma coleção de entidades ou uma string diretamente... encapsule em um Response para poder passar o HTTP Status adequadamente.
return Response.ok(banners).build();
ou outro Status:
return Response.status(Status.FORBIDDEN).build();
4) Sempre retornar JSON de forma automática:
Basta adicionar a linha abaixo acima do método no Rest:
@Produces(MediaType.APPLICATION_JSON)
Não faça a conversão de objetos para JSON na mão.
5) Atualização parcial:
Existem casos onde você não quer atualizar um registro inteiro, e sim apenas uma propriedade dele, atualizar um status por exemplo.
O @PUT é pra atualização, mas ele é pra atualizar o objeto inteiro.
Para isso existe o @PATCH, mas não sei se ele é padrão, se todos os servidores de aplicação tem.
Uma outra ideia é fazer vários @PUT, fica bacana também:
PUT localhost:8080/myapp/rest/livro/{id}/propriedadeX
PUT localhost:8080/myapp/rest/livro/{id}/propriedadeY
Outra ideia é ter um @PUT pra atualizar o objeto inteiro e um @PUT que recebe um Map com os atributos a serem atualizados e seus novos valores.
6) Não implemente todos os métodos
Não é necessário implementar todos os métodos se eles não serão usados. Por exemplo, se é um objeto só vai ter um @GET não é necessário implementar o @POST, o @PUT e o @DELETE.
No máximo faça o método no Rest que retorna um status de erro informando que não foi implementado.
Mais:
Mais detalhes e para quem quiser estudar mais sobre Rest recomendo o artigo abaixo:
http://www.devmedia.com.br/construindo-uma-restful-api-parte-1/29904
http://www.devmedia.com.br/restful-api-construindo-uma-api-simples-parte-2/30069
Na Supero (empresa que trabalho) temos conta MVP no devmedia, caso você não tenho recomendo fazer, é um investimento muito válido!
Abraços!
Adriano Schmidt
Estou trabalhando com alguns projetos utilizando Rest. Montei esse e-mail para enviar à equipe de desenvolvimento e resolvi publicar aqui também.
A ideia é utilizar o conceito de RESTful utilizando as melhores práticas de desenvolvimento. Darei algumas dicas simples que podemos seguir:
1) Não usar verbos nos paths dos Rests:
Você não pode ter um localhost:8080/myapp/rest/deletarProduto e dar um HTTP GET nele.
Tem que ser um localhost:8080/myapp/rest/produto e você dá um HTTP DELETE nele
Tem alguns casos especiais (somarValores, checarSeEmailTemFormatoValido ou algoasism...) que são um pouquinho diferentes.. em outra oportunidade falarei mais sobre isso..
2) Passagem de parâmetros através de queryString do método GET
<URL>?parametro1=valor1¶metro2=valor2
Isso deve ser usado para filtros no HTTP GET de localhost:8080/myapp/rest/produto?apenasAtivos=true
Na implementação, basta utilizar @QueryParam ao invés de @PathParam
3) Sempre retornar um Response (javax.ws.rs.core.Response;)
Nunca retorne uma coleção de entidades ou uma string diretamente... encapsule em um Response para poder passar o HTTP Status adequadamente.
return Response.ok(banners).build();
ou outro Status:
return Response.status(Status.FORBIDDEN).build();
4) Sempre retornar JSON de forma automática:
Basta adicionar a linha abaixo acima do método no Rest:
@Produces(MediaType.APPLICATION_JSON)
Não faça a conversão de objetos para JSON na mão.
5) Atualização parcial:
Existem casos onde você não quer atualizar um registro inteiro, e sim apenas uma propriedade dele, atualizar um status por exemplo.
O @PUT é pra atualização, mas ele é pra atualizar o objeto inteiro.
Para isso existe o @PATCH, mas não sei se ele é padrão, se todos os servidores de aplicação tem.
Uma outra ideia é fazer vários @PUT, fica bacana também:
PUT localhost:8080/myapp/rest/livro/{id}/propriedadeX
PUT localhost:8080/myapp/rest/livro/{id}/propriedadeY
Outra ideia é ter um @PUT pra atualizar o objeto inteiro e um @PUT que recebe um Map com os atributos a serem atualizados e seus novos valores.
6) Não implemente todos os métodos
Não é necessário implementar todos os métodos se eles não serão usados. Por exemplo, se é um objeto só vai ter um @GET não é necessário implementar o @POST, o @PUT e o @DELETE.
No máximo faça o método no Rest que retorna um status de erro informando que não foi implementado.
Mais:
Mais detalhes e para quem quiser estudar mais sobre Rest recomendo o artigo abaixo:
http://www.devmedia.com.br/construindo-uma-restful-api-parte-1/29904
http://www.devmedia.com.br/restful-api-construindo-uma-api-simples-parte-2/30069
Na Supero (empresa que trabalho) temos conta MVP no devmedia, caso você não tenho recomendo fazer, é um investimento muito válido!
Abraços!
Adriano Schmidt
quarta-feira, 25 de junho de 2014
Tunning de aplicações Java
Pessoal.. vou postar aqui alguns itens que sempre recomendo para melhorar o desempenho de uma aplicação Java.
Fazer testes de desempenho ou analisar as aplicações com JMeter, NewRelic, VisualVM, jConsole é o mundo ideal! Através disso é possível identificar os gargalos da aplicação! Os pontos que mais utilizam recursos computacionais como memória e processador por exemplo.
Configurar adequadamente a memória utilizada.. ou seja, estude xms, xmx, maxpermgen..
Uma dica é sempre colocar o xms e o xmx igual em ambiente de produção. E o ideal não é simplesmente colocar o valor mais alto possível, é preciso analisar qual é o valor ideal, e isso é descoberto através de testes e monitoramento, ou através do feeling e analisando com o tempo como a aplicação se comporta.
Recomendo utilizar a JRockit como JVM. Ela é mantida pela Oracle também e tem um gerenciamento de memória muito melhor que das outras JVMs, o garbage collector funciona bem melhor.
Mas só tem pra Java 6, mas em todos os clientes que atuo, sempre que possível, implanto a JRockit, é notável o ganho obtido no uso de recursos computacionais como memória.
Dá pra fazer tunning também de acordo com a tecnologia que você está usando.. JSF... JMS... pool de EJB... Banco de dados...
Dá pra monitorar a aplicação pelo jenkins também, fazer um job que checa a memória e qualquer avisa a equipe de infra ou até reinicia, dá pra usar o nagios...
Etc... Existem milhões de outras coisas que podem ser feitas, mas como escrevi esse texto para ajudar um amigo, resolvi postá-lo aqui para talvez ajudar outras pessoas também.
Abraços!
Adriano Schmidt
Fazer testes de desempenho ou analisar as aplicações com JMeter, NewRelic, VisualVM, jConsole é o mundo ideal! Através disso é possível identificar os gargalos da aplicação! Os pontos que mais utilizam recursos computacionais como memória e processador por exemplo.
Configurar adequadamente a memória utilizada.. ou seja, estude xms, xmx, maxpermgen..
Uma dica é sempre colocar o xms e o xmx igual em ambiente de produção. E o ideal não é simplesmente colocar o valor mais alto possível, é preciso analisar qual é o valor ideal, e isso é descoberto através de testes e monitoramento, ou através do feeling e analisando com o tempo como a aplicação se comporta.
Recomendo utilizar a JRockit como JVM. Ela é mantida pela Oracle também e tem um gerenciamento de memória muito melhor que das outras JVMs, o garbage collector funciona bem melhor.
Mas só tem pra Java 6, mas em todos os clientes que atuo, sempre que possível, implanto a JRockit, é notável o ganho obtido no uso de recursos computacionais como memória.
Dá pra fazer tunning também de acordo com a tecnologia que você está usando.. JSF... JMS... pool de EJB... Banco de dados...
Dá pra monitorar a aplicação pelo jenkins também, fazer um job que checa a memória e qualquer avisa a equipe de infra ou até reinicia, dá pra usar o nagios...
Etc... Existem milhões de outras coisas que podem ser feitas, mas como escrevi esse texto para ajudar um amigo, resolvi postá-lo aqui para talvez ajudar outras pessoas também.
Abraços!
Adriano Schmidt
quarta-feira, 18 de junho de 2014
Trabalhando com 2 repositórios Git
Pessoal.. temos um repositório Git na minha empresa e todos os desenvolvedores fazem commit e push lá. E de tempos em tempos fazemos o push desses fontes para o repositório Git que fica no nosso cliente.
Vou explicar uma estratégia simples e comumente usada nesse cenário.
Com essa estratégia que vou explicar você mantém o histórico de commits e permite a realização de merges caso outras pessoas commitem no mesmo projeto no repositório do cliente.
Seguinte:
No Git, cada commit tem um id.. que é um hash único...
Quando você tem 2 repositórios, um commit deve ter o mesmo id nos 2 repositórios...
O histórico de commits de um, será o mesmo no outro... geralmente é muito importante manter o histórico dos commits...
Para isso, você adiciona dois remotes no seu projeto (no nosso caso era só adicionar o segundo, já que o primeiro já tínhamos)
git remote add origin http://www.minhaempresa.com.br/git/projeto.git
git remote add cliente http://www.meucliente.com.br/git/projeto.git
Depois é só você escolher onde quer fazer push
git push origin master
ou
git push cliente master
Você pode até dar um git config e definir qual dos dois remotes é o padrão para quando você digitar apenas "git push" ele saber qual usar.
É isso!
Abraços!
Adriano Schmidt
Vou explicar uma estratégia simples e comumente usada nesse cenário.
Com essa estratégia que vou explicar você mantém o histórico de commits e permite a realização de merges caso outras pessoas commitem no mesmo projeto no repositório do cliente.
Seguinte:
No Git, cada commit tem um id.. que é um hash único...
Quando você tem 2 repositórios, um commit deve ter o mesmo id nos 2 repositórios...
O histórico de commits de um, será o mesmo no outro... geralmente é muito importante manter o histórico dos commits...
Para isso, você adiciona dois remotes no seu projeto (no nosso caso era só adicionar o segundo, já que o primeiro já tínhamos)
git remote add origin http://www.minhaempresa.com.br/git/projeto.git
git remote add cliente http://www.meucliente.com.br/git/projeto.git
Depois é só você escolher onde quer fazer push
git push origin master
ou
git push cliente master
Você pode até dar um git config e definir qual dos dois remotes é o padrão para quando você digitar apenas "git push" ele saber qual usar.
É isso!
Abraços!
Adriano Schmidt
terça-feira, 17 de junho de 2014
Seminário JBoss/WildFly - Avançado
Nesse sábado (14/06/2014) aconteceu o primeiro Supero TechDay!
Estou muitíssimo feliz pelo evento! Todo mundo muito empolgado trocando conhecimentos e experiências.
Valeu muito à pena! Estou muito orgulhoso e feliz por trabalhar na Supero TI (www.supero.com.br) e muito satisfeito por estar numa equipe com tanta gente bacana!
Neste evento fiz uma apresentação onde explanei sobre o JBoss e sua mais nova versão o WildFly. Abordei a história, arquitetura, funcionamento e dicas sobre o JBoss/WildFly e mostrei em funcionamento um ambiente com um Apache HTTP Server como load balancer e proxy reverso com vários JBoss em cluster.
Não poderia deixar de agradecer ao JBUG Brasil e todos os seus membros, especialmente ao Maurício Magnani (https://jbossdivers.wordpress.com/), que me ajudaram muito a ter o conhecimento que tenho hoje sobre JBoss.
Estou muitíssimo feliz pelo evento! Todo mundo muito empolgado trocando conhecimentos e experiências.
Valeu muito à pena! Estou muito orgulhoso e feliz por trabalhar na Supero TI (www.supero.com.br) e muito satisfeito por estar numa equipe com tanta gente bacana!
Neste evento fiz uma apresentação onde explanei sobre o JBoss e sua mais nova versão o WildFly. Abordei a história, arquitetura, funcionamento e dicas sobre o JBoss/WildFly e mostrei em funcionamento um ambiente com um Apache HTTP Server como load balancer e proxy reverso com vários JBoss em cluster.
Não poderia deixar de agradecer ao JBUG Brasil e todos os seus membros, especialmente ao Maurício Magnani (https://jbossdivers.wordpress.com/), que me ajudaram muito a ter o conhecimento que tenho hoje sobre JBoss.
segunda-feira, 16 de junho de 2014
Cuidados ao entrar num projeto novo
Pessoal... queria dar algumas dicas para quando você for entrar um projeto novo...
1) Ctrl+Shift+F
Nunca dê um Ctrl+Shift+F no projeto inteiro.. nem na classe que você está alterando...
Um Ctrl+Shift+F atrapalha muito a realização de merges e de certa forma faz você perder o histórico de alterações no controle de versão, pois vai ser difícil comparar algo com uma versão antiga pois vai estar com uma formatação toda diferente.
Se você está criando uma classe nova, tudo bem, mas muito cuidado ao mexer em códigos já existentes.
Caso você crie um método novo, você pode selecionar esse método, e dar um Ctrl+Shif+F, pois vai formatar apenar o trecho de código selecionado, mantendo intacto o resto da classe.
Tem até como criar um xml de formatação no eclipse e depois as outras pessoas podem importar em seus eclipses, mas acho muito trabalhoso manter isso.
Caso seja decidido aplicar algo no projeto inteiro, isso deve ser bem pensado, nunca é só chegar e fazer.
2) Encoding no eclipse
Antes de salvar uma classe verifique se o encoding do projeto no seu eclipse está correto, veja se os acentos não vão virar caracteres estranhos..
Isso é muito comum quando uma equipe usa windows e entra alguém que usa linux ou vice-versa.
Para mudar o encoding do seu projeto no eclipse é só ir nas propriedades do projeto no eclipse.
Caso você ache que o encoding poderia ser outro, converse com a equipe, nunca chegue e mude por conta própria.
3) Encoding no maven
Nunca altere o encoding do projeto no maven colocando no pom a linha abaixo:
UTF-8
Se for fazer isso converse com alguém que já está no projeto ou então você deve saber o que está fazendo.. uma dica é, se for fazer, faça apenas local.
4) Não use acentos em comentários
O título é auto explicativo, a ideia é simples, se não tem acentos, diminui a probabilidade de problemas com encoding. Ah, e sempre é bom falar, em nome de variável também não se deve usar ç ou coisas assim.
Essas simples ações tornam o ambiente de trabalho melhor, faça o bem sem olhar a quem! :D
PS: Escrevi tudo isso e mandei para todos os desenvolvedores da empresa que trabalho depois de passar muitas horas (muitas mesmo) fazendo um merge de um projeto gigante e corrigindo caracteres especiais. Então, não falo por mal, falo para evitar que outras pessoas passem por esse sofrimento.
Abraços!
Adriano Schmidt
1) Ctrl+Shift+F
Nunca dê um Ctrl+Shift+F no projeto inteiro.. nem na classe que você está alterando...
Um Ctrl+Shift+F atrapalha muito a realização de merges e de certa forma faz você perder o histórico de alterações no controle de versão, pois vai ser difícil comparar algo com uma versão antiga pois vai estar com uma formatação toda diferente.
Se você está criando uma classe nova, tudo bem, mas muito cuidado ao mexer em códigos já existentes.
Caso você crie um método novo, você pode selecionar esse método, e dar um Ctrl+Shif+F, pois vai formatar apenar o trecho de código selecionado, mantendo intacto o resto da classe.
Tem até como criar um xml de formatação no eclipse e depois as outras pessoas podem importar em seus eclipses, mas acho muito trabalhoso manter isso.
Caso seja decidido aplicar algo no projeto inteiro, isso deve ser bem pensado, nunca é só chegar e fazer.
2) Encoding no eclipse
Antes de salvar uma classe verifique se o encoding do projeto no seu eclipse está correto, veja se os acentos não vão virar caracteres estranhos..
Isso é muito comum quando uma equipe usa windows e entra alguém que usa linux ou vice-versa.
Para mudar o encoding do seu projeto no eclipse é só ir nas propriedades do projeto no eclipse.
Caso você ache que o encoding poderia ser outro, converse com a equipe, nunca chegue e mude por conta própria.
3) Encoding no maven
Nunca altere o encoding do projeto no maven colocando no pom a linha abaixo:
Se for fazer isso converse com alguém que já está no projeto ou então você deve saber o que está fazendo.. uma dica é, se for fazer, faça apenas local.
4) Não use acentos em comentários
O título é auto explicativo, a ideia é simples, se não tem acentos, diminui a probabilidade de problemas com encoding. Ah, e sempre é bom falar, em nome de variável também não se deve usar ç ou coisas assim.
Essas simples ações tornam o ambiente de trabalho melhor, faça o bem sem olhar a quem! :D
PS: Escrevi tudo isso e mandei para todos os desenvolvedores da empresa que trabalho depois de passar muitas horas (muitas mesmo) fazendo um merge de um projeto gigante e corrigindo caracteres especiais. Então, não falo por mal, falo para evitar que outras pessoas passem por esse sofrimento.
Abraços!
Adriano Schmidt
domingo, 15 de junho de 2014
Deletar todas as tabelas de um banco de dados Oracle
Script que deleta todas as tabelas do banco:
Simples e rápido!
Para deletar todas as sequences do banco é só rodar o seguinte comando:
Fonte: http://golker.blogspot.com.br/2009/05/dropar-todos-os-tipos-e-tabelas-no.html
Abraço!
Adriano Schmidt
begin for deleta in (select table_name, 'DROP TABLE '||table_name||' cascade constraints' AS dropar from user_tables) loop BEGIN EXECUTE IMMEDIATE deleta.dropar; dbms_output.put_line('DROP TABLE '||deleta.table_name||' cascade constraints;'); EXCEPTION WHEN OTHERS THEN dbms_output.put_line('Erro ao tentar dropar a tabela:'||deleta.table_name); END; end loop; end;
Simples e rápido!
Para deletar todas as sequences do banco é só rodar o seguinte comando:
begin for deleta in (select sequence_name, 'DROP SEQUENCE '||sequence_name||' ' AS dropar from user_sequences) loop BEGIN EXECUTE IMMEDIATE deleta.dropar; dbms_output.put_line('DROP SEQUENCE '||deleta.sequence_name||' ;'); EXCEPTION WHEN OTHERS THEN dbms_output.put_line('Erro ao tentar dropar a tabela:'||deleta.sequence_name); END; end loop; end;
Fonte: http://golker.blogspot.com.br/2009/05/dropar-todos-os-tipos-e-tabelas-no.html
Abraço!
Adriano Schmidt
sexta-feira, 2 de maio de 2014
Dividir arquivos grandes no windows ou linux
Hoje precisava alterar um arquivo .SQL de 1,2GB e não conseguia abri-lo.
Então tive que dividi-lo.
No linux é só você rodar o comando
E ele vai dividir o arquivo grande em arquivos de 30MB, você pode alterar o tamanho, alterando o comando acima.
No windows, você pode usar o mesmo comando, mas para isso precisa instalar o MobaXTerm ( http://mobaxterm.mobatek.net/ )
Após instalar, é só ir até a pasta do arquivo (a unidade C fica em /mnt/c/) e rodar o comando split:
Fonte: http://www.vivaolinux.com.br/dica/Como-dividir-arquivos-grandes-(split)
Abraços!
Adriano Schmidt
Então tive que dividi-lo.
No linux é só você rodar o comando
split -b 30720k nome_do_arquivo_grande.sql
E ele vai dividir o arquivo grande em arquivos de 30MB, você pode alterar o tamanho, alterando o comando acima.
No windows, você pode usar o mesmo comando, mas para isso precisa instalar o MobaXTerm ( http://mobaxterm.mobatek.net/ )
Após instalar, é só ir até a pasta do arquivo (a unidade C fica em /mnt/c/) e rodar o comando split:
cd /mnt/c/pasta_onde_esta_o_arquivo_grande split -b 30720k nome_do_arquivo_grande.sql
Fonte: http://www.vivaolinux.com.br/dica/Como-dividir-arquivos-grandes-(split)
Abraços!
Adriano Schmidt
Renomear arquivo com caracteres especiais no linux
Pessoal, estava apanhando aqui para um arquivo cujo nome tinha caracteres especiais: (ConfiguraçoÌes_de_Acesso).pdf
Renomeá-lo não foi fácil. Consegui essa proeza rodando comando "ls -i" que exibe uma espécie de id do arquivo:
E com o id do arquivo usei o comando abaixo para renomeá-lo:
Pronto, arquivo renomeado :)
Fonte: http://www.unix.com/tips-and-tutorials/198879-how-manage-file-names-special-characters.html
Abraços!
Adriano Schmidt
Renomeá-lo não foi fácil. Consegui essa proeza rodando comando "ls -i" que exibe uma espécie de id do arquivo:
[user@MAQUINA01 PASTA]$ ls -i 5835097 Arquivo01.sql 5835105 (ConfiguraçoÌes_de_Acesso).pdf 5835101 Log_01.txt
E com o id do arquivo usei o comando abaixo para renomeá-lo:
[user@MAQUINA01 PASTA]$ find . -inum 5835105 -exec mv {} Configuracoes_de_Acesso.pdf \;
Pronto, arquivo renomeado :)
Fonte: http://www.unix.com/tips-and-tutorials/198879-how-manage-file-names-special-characters.html
Abraços!
Adriano Schmidt
quarta-feira, 16 de abril de 2014
show_sql=true não exibe os parâmetros
Após setar o show-sql como true no meu persistence.xml no meu projeto que roda no JBoss EAP 6.2 (ou Jboss AS7, ou WildFly) as queries apareceram no log, mas o valor dos parâmetros não. Aparecia somente assim:
Para fazer os valores aparecerem entrei no arquivo standalone.xml do meu JBoss e fui no subsystem logging (esse arquivo tem várias tags subsystem, uma delas tem o name logging)
Então, junto com os outros loggers adicionei o logger abaixo:
Após reiniciar o JBoss, o log ficou assim:
Fonte: http://stackoverflow.com/questions/9159752/how-to-get-jdbc-binding-parameters-from-hibernate-in-jboss-7
21:10:03,314 INFO [stdout] (http-/0.0.0.0:8080-3) Hibernate: select exemplo0_.COL_X from EXEMPLO exemplo0_ where exemplo0_.COL_Y =?
Para fazer os valores aparecerem entrei no arquivo standalone.xml do meu JBoss e fui no subsystem logging (esse arquivo tem várias tags subsystem, uma delas tem o name logging)
Então, junto com os outros loggers adicionei o logger abaixo:
<logger category="org.hibernate.type.descriptor.sql.BasicBinder"> <level name="TRACE"/> </logger>
Após reiniciar o JBoss, o log ficou assim:
21:15:04,234 INFO [stdout] (http-/0.0.0.0:8080-3) Hibernate: select exemplo0_.COL_X from EXEMPLO exemplo0_ where exemplo0_.COL_Y =? 21:15:04,234 TRACE [org.hibernate.type.descriptor.sql.BasicBinder] (http-/0.0.0.0:8080-3) binding parameter [1] as [BIGINT] - 600
Fonte: http://stackoverflow.com/questions/9159752/how-to-get-jdbc-binding-parameters-from-hibernate-in-jboss-7
segunda-feira, 31 de março de 2014
"A melhor tecnologia é a que eu domino!"
Hoje venho divagar sobre a questão: "Devo usar a tecnologia que domino mais ou o a mais adequada ao projeto?"
Essa é uma decisão difícil e alguns fatores devem ser considerados.
Cada tecnologia tem suas vantagens e desvantagens..
JSF tem as suas.. Flex tem as suas.. HTML5 tem as suas.. PHP tem as suas..
Cada tecnologia tem situações em que ela se encaixa melhor..
Muitas empresas decidem usar tecnologias com base na experiência dos desenvolvedores, é uma decisão comum e muitas vezes assertiva... mas algumas vezes isso não se conjectura como melhor escolha e é necessário tomar outra decisão...
Uma grande empresa que trabalhei desenvolveu muitos sistemas em Flex.. e agora está reescrevendo tudo... (Não quero julgar esse caso em específico, só estou dando um exemplo).
Nesta mesma empresa iríamos desenvolver um sistema de ponto eletrônico e controle de acesso (catracas)... na época estava surgindo o JSF2.. todo mundo falou pra usar o JSF 1.2 até porque haviam outros sistemas em JSF 1.2 na equipe.. eu contrariei o que as pessoas falaram e desenvolvi em JSF 2... recebi muitas críticas por isso, mas permaneci firme porque sabia que era o mais acertado.. esses outros sistemas já existentes usavam Spring e eu coloquei EJB/JPA no projeto mesmo que ninguém na equipe conhecia isso... Usei JBoss ao invés de Tomcat... Enfim, a arquitetura mudou bastante em relação aos projetos existentes.
Seis meses depois.. todos os sistemas desenvolvidos em JSF 1.2 e Spring foram reescritos em JSF 2 e EJB...
Em outra empresa, entrei em um cliente e começamos a usar o Git ao invés de SVN.. fui muito criticado por causa disso pelos desenvolvedores que apenas conheciam SVN... e hoje está mais que provado que foi a melhor escolha...
Em um projeto novo que está começando agora e estou envolvido surgiu a discussão HTML5xJSF... Queriam utilizar JSF pois a equipe atual domina mais esta tecnologia.. Caso seja escolhido HTML5 muita gente vai criticar, no primeiro problema que alguém tiver vai reclamar e vai falar "Se fosse JSF já estaria pronto", porém, com JSF também teríamos problemas..
Entendo que no início a produtividade seja mais baixa com HTML5, porém em pouco tempo isto mudará.
Neste projeto em específico acredito que não devemos usar JSF só por que conhecemos mais, não seria a melhor escolha para esse projeto pois JSF foi criado para sistemas corporativos.. enterprise... Para um número não muito grande de usuários simultâneos. Que não é o cenário do novo projeto.
Claro que outros fatores como prazo, orçamento, se os envolvidos querem pensar a curto ou longo prazo, abertura a assumir riscos, entre outros, vão influenciar na escolha também, mas escolher a tecnologia mais adequada deve pelo menos entrar nas discussões.
Enfim, a frase "A melhor tecnologia é a que eu domino" é muito comum, porém, nem sempre funciona.
Essa é uma decisão difícil e alguns fatores devem ser considerados.
Cada tecnologia tem suas vantagens e desvantagens..
JSF tem as suas.. Flex tem as suas.. HTML5 tem as suas.. PHP tem as suas..
Cada tecnologia tem situações em que ela se encaixa melhor..
Muitas empresas decidem usar tecnologias com base na experiência dos desenvolvedores, é uma decisão comum e muitas vezes assertiva... mas algumas vezes isso não se conjectura como melhor escolha e é necessário tomar outra decisão...
Uma grande empresa que trabalhei desenvolveu muitos sistemas em Flex.. e agora está reescrevendo tudo... (Não quero julgar esse caso em específico, só estou dando um exemplo).
Nesta mesma empresa iríamos desenvolver um sistema de ponto eletrônico e controle de acesso (catracas)... na época estava surgindo o JSF2.. todo mundo falou pra usar o JSF 1.2 até porque haviam outros sistemas em JSF 1.2 na equipe.. eu contrariei o que as pessoas falaram e desenvolvi em JSF 2... recebi muitas críticas por isso, mas permaneci firme porque sabia que era o mais acertado.. esses outros sistemas já existentes usavam Spring e eu coloquei EJB/JPA no projeto mesmo que ninguém na equipe conhecia isso... Usei JBoss ao invés de Tomcat... Enfim, a arquitetura mudou bastante em relação aos projetos existentes.
Seis meses depois.. todos os sistemas desenvolvidos em JSF 1.2 e Spring foram reescritos em JSF 2 e EJB...
Em outra empresa, entrei em um cliente e começamos a usar o Git ao invés de SVN.. fui muito criticado por causa disso pelos desenvolvedores que apenas conheciam SVN... e hoje está mais que provado que foi a melhor escolha...
Em um projeto novo que está começando agora e estou envolvido surgiu a discussão HTML5xJSF... Queriam utilizar JSF pois a equipe atual domina mais esta tecnologia.. Caso seja escolhido HTML5 muita gente vai criticar, no primeiro problema que alguém tiver vai reclamar e vai falar "Se fosse JSF já estaria pronto", porém, com JSF também teríamos problemas..
Entendo que no início a produtividade seja mais baixa com HTML5, porém em pouco tempo isto mudará.
Neste projeto em específico acredito que não devemos usar JSF só por que conhecemos mais, não seria a melhor escolha para esse projeto pois JSF foi criado para sistemas corporativos.. enterprise... Para um número não muito grande de usuários simultâneos. Que não é o cenário do novo projeto.
Claro que outros fatores como prazo, orçamento, se os envolvidos querem pensar a curto ou longo prazo, abertura a assumir riscos, entre outros, vão influenciar na escolha também, mas escolher a tecnologia mais adequada deve pelo menos entrar nas discussões.
Enfim, a frase "A melhor tecnologia é a que eu domino" é muito comum, porém, nem sempre funciona.
quarta-feira, 12 de março de 2014
JBoss x Tomcat
Por que usar JBoss ao invés de Tomcat?
Primeiramente é bom explicar que o Tomcat é um Web Container (contém engines para Servlet e JSP), já o JBoss é um Application Server (container para a plataforma JEE, contém um Web Container, porém tem um EJB container e outras engines).
Para aplicações simples você consegue utilizar um Web Container, para aplicações com mais tecnologias (EJB por exemplo), você até consegue usar um Web Container, porém, terá que adicionar muitas bibliotecas e configurações nele. Em um Application Server tudo é nativo.
Em 2010 por exemplo, fazia muito sentido utilizar apenas um Web Container para uma aplicação simples pois os Application Servers eram muito pesados, consumiam muitos recursos computacionais, demoravam para iniciar e eram difíceis de manter, porém os Application Servers em 2014 não tem mais estes problemas. A própria Apache, criadora do Tomcat, criou seu próprio Application Server chamado TomEE para ser usado no lugar do Tomcat. (http://tomee.apache.org/apache-tomee.html)
Os Application Servers trabalham com profiles, que define o que será carregado, o profile mais leve dos Application Servers é como um Web Container, por isso, não existe mais a necessidade de se trabalhar com Tomcat em projetos novos, a não ser que você queira manter padrão com outras aplicações da empresa ou algo assim, porém, essa decisão traria muitas outras dificuldades para o desenvolvimento e controle da infraestrutura de uma aplicação JEE.
Abraços!
Adriano Schmidt
Primeiramente é bom explicar que o Tomcat é um Web Container (contém engines para Servlet e JSP), já o JBoss é um Application Server (container para a plataforma JEE, contém um Web Container, porém tem um EJB container e outras engines).
Para aplicações simples você consegue utilizar um Web Container, para aplicações com mais tecnologias (EJB por exemplo), você até consegue usar um Web Container, porém, terá que adicionar muitas bibliotecas e configurações nele. Em um Application Server tudo é nativo.
Em 2010 por exemplo, fazia muito sentido utilizar apenas um Web Container para uma aplicação simples pois os Application Servers eram muito pesados, consumiam muitos recursos computacionais, demoravam para iniciar e eram difíceis de manter, porém os Application Servers em 2014 não tem mais estes problemas. A própria Apache, criadora do Tomcat, criou seu próprio Application Server chamado TomEE para ser usado no lugar do Tomcat. (http://tomee.apache.org/apache-tomee.html)
Os Application Servers trabalham com profiles, que define o que será carregado, o profile mais leve dos Application Servers é como um Web Container, por isso, não existe mais a necessidade de se trabalhar com Tomcat em projetos novos, a não ser que você queira manter padrão com outras aplicações da empresa ou algo assim, porém, essa decisão traria muitas outras dificuldades para o desenvolvimento e controle da infraestrutura de uma aplicação JEE.
Abraços!
Adriano Schmidt
sábado, 8 de março de 2014
Instalando JRockit no RHEL
Sempre em ambientes de produção em clientes costumo usar a JDK JRockit, ela é melhor para ambientes de missão crítica pois utiliza melhor a memória, garbage collector, entre outras coisas...
Mais detalhes em: http://www.oracle.com/technetwork/middleware/jrockit/overview/index.html
Para instalar é muito simples:
* Baixe o JRockit
http://www.oracle.com/technetwork/middleware/jrockit/downloads/index.html
* Vá até a pasta onde está o instalador (arquivo .bin) (troque o /app pelo caminho onde está o .bin que você baixou)
$ cd /app
* Dê permissão de execução para esse arquivo (coloque o nome do arquivo que você baixou)
$ sudo chmod +x jrockit-jdk1.6.0_45-R28.2.7-4.1.0-linux-x64.bin
* Execute o .bin
$ sudo ./jrockit-jdk1.6.0_45-R28.2.7-4.1.0-linux-x64.bin
* Então é só ir apertando enter, ou caso queira mudar diretório de instalação, instalar os fontes da JDK entre outras coisas é só ir escolhendo, caso contrário é só apertar enter até o final.
Caso tenha alguma dúvida sobre o "sudo", ele serve para você poder executar um comando como se você fosse o usuário root, o seu usuário deve ter permissão para poder usar o "sudo".
Enfim, é isso! : )
Abraço!!!
Adriano Schmidt
Mais detalhes em: http://www.oracle.com/technetwork/middleware/jrockit/overview/index.html
Para instalar é muito simples:
* Baixe o JRockit
http://www.oracle.com/technetwork/middleware/jrockit/downloads/index.html
* Vá até a pasta onde está o instalador (arquivo .bin) (troque o /app pelo caminho onde está o .bin que você baixou)
$ cd /app
* Dê permissão de execução para esse arquivo (coloque o nome do arquivo que você baixou)
$ sudo chmod +x jrockit-jdk1.6.0_45-R28.2.7-4.1.0-linux-x64.bin
* Execute o .bin
$ sudo ./jrockit-jdk1.6.0_45-R28.2.7-4.1.0-linux-x64.bin
* Então é só ir apertando enter, ou caso queira mudar diretório de instalação, instalar os fontes da JDK entre outras coisas é só ir escolhendo, caso contrário é só apertar enter até o final.
Caso tenha alguma dúvida sobre o "sudo", ele serve para você poder executar um comando como se você fosse o usuário root, o seu usuário deve ter permissão para poder usar o "sudo".
Enfim, é isso! : )
Abraço!!!
Adriano Schmidt
domingo, 9 de fevereiro de 2014
Criar Schema Oracle
Pessoal..
Hoje tive que fazer uma atividade simples, criar um schema no oracle, porém era necessário saber a sintaxe, saber um pouco sobre tablespaces e também dar os grants corretos.
Assim sendo, resolvi documentar aqui para caso alguém tenha que fazer algo semelhante:
Segue abaixo uma sugestão de script para criar os databases. Não esqueça de alterar nome_schemad, nome_schema, caminho_sevidor_datafiles:
Ou mais simples ainda usando a TABLESPACE users:
A senha é o que vem depois do IDENTIFIED BY, caso queira pode mudar.
É isso aí, abraços!!
Adriano Schmidt
Hoje tive que fazer uma atividade simples, criar um schema no oracle, porém era necessário saber a sintaxe, saber um pouco sobre tablespaces e também dar os grants corretos.
Assim sendo, resolvi documentar aqui para caso alguém tenha que fazer algo semelhante:
Segue abaixo uma sugestão de script para criar os databases. Não esqueça de alterar nome_schemad, nome_schema, caminho_sevidor_datafiles:
CREATE TABLESPACE nome_schemad DATAFILE ‘caminho_servidor_datafiles\nome_schemad.DBF' SIZE 100M AUTOEXTEND ON / CREATE USER nome_schema IDENTIFIED BY nome_schema DEFAULT TABLESPACE nome_schemad TEMPORARY TABLESPACE TEMP / grant connect, resource, create any view, create any synonym, create any table, create database link to nome_schema /
Ou mais simples ainda usando a TABLESPACE users:
CREATE USER nome_schema IDENTIFIED BY nome_schema DEFAULT TABLESPACE users TEMPORARY TABLESPACE TEMP / grant connect, resource, create any view, create any synonym, create any table, create database link to nome_schema /
A senha é o que vem depois do IDENTIFIED BY, caso queira pode mudar.
É isso aí, abraços!!
Adriano Schmidt
sexta-feira, 7 de fevereiro de 2014
Marvel Java
Oi pessoal :)
A Marvel lançou o http://developer.marvel.com/ com uma API RESTful para você acessar imagens, histórias, dados entre outras coisas da Marvel.
Você pode usar isso em seu site, em jogos, num app pra celular, num aplicativo pra TV digital ou onde sua criatividade deixar :P
Fiz um client Java só para brincar, chamei ele de JMarvelRestClient, caso queiram executar aí é só criar um projeto java, um pacote br.com.localhost8080.test e colar a classe abaixo e alterar para usar suas próprias chaves no método mountUrlRest!!! Para obter as chaves é só se cadastrar lá no http://developer.marvel.com/
Nessa classe tem o client Rest e tem um método para converter uma string para MD5 para a autenticação.
A saída da execução desta classe está lá no final deste artigo. Até lá :P
Bom, é isso, qualquer dúvida posta aí que tentarei ajudar!
Fontes:
http://www.mkyong.com/webservices/jax-rs/restfull-java-client-with-java-net-url/
http://codare.net/2007/02/02/java-gerando-codigos-hash-md5-sha/
Abraços!
Adriano Schmidt
A Marvel lançou o http://developer.marvel.com/ com uma API RESTful para você acessar imagens, histórias, dados entre outras coisas da Marvel.
Você pode usar isso em seu site, em jogos, num app pra celular, num aplicativo pra TV digital ou onde sua criatividade deixar :P
Fiz um client Java só para brincar, chamei ele de JMarvelRestClient, caso queiram executar aí é só criar um projeto java, um pacote br.com.localhost8080.test e colar a classe abaixo e alterar para usar suas próprias chaves no método mountUrlRest!!! Para obter as chaves é só se cadastrar lá no http://developer.marvel.com/
Nessa classe tem o client Rest e tem um método para converter uma string para MD5 para a autenticação.
A saída da execução desta classe está lá no final deste artigo. Até lá :P
package br.com.localhost8080.test; import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import java.net.HttpURLConnection; import java.net.MalformedURLException; import java.net.URL; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import java.util.Date; /** * Java Client for the Marvel Rest API */ public class JMarvelRestClient { /** * Call a Rest from Marvel just for test */ public static void main(String[] args) { HttpURLConnection conn = null; try { URL url = new URL(JMarvelRestClient.mountRestUrl()); conn = (HttpURLConnection) url.openConnection(); conn.setRequestMethod("GET"); conn.setRequestProperty("Accept", "application/json"); if (conn.getResponseCode() != 200) { throw new RuntimeException("Failed: HTTP error code: " + conn.getResponseCode()); } BufferedReader br = new BufferedReader(new InputStreamReader((conn.getInputStream()))); String output = null; String retornoRest = ""; while ((output = br.readLine()) != null) { retornoRest += output; } System.out.println("\nRest Return: " + retornoRest); JMarvelRestClient.mountImageUrl(retornoRest); } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } finally { conn.disconnect(); } } /** * Mount the URL with keys and hash */ private static String mountRestUrl() { Long timeStamp = new Date().getTime(); String privateKey = "PUT_HERE_YOUR_PRIVATE_KEY"; String apikey = "PUT_HERE_YOUR_PUBLIC_KEY"; String hash = JMarvelRestClient.generateHash(timeStamp + privateKey + apikey); String urlCompleta = "http://gateway.marvel.com/v1/public/comics/12?ts=" + timeStamp + "&apikey=" + apikey + "&hash=" + hash; System.out.println("Rest URL: " + urlCompleta); return urlCompleta; } /** * Makes a magic that transforms your string in MD5 hash */ private static String generateHash(String string) { MessageDigest md = null; try { md = MessageDigest.getInstance("MD5"); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } md.update(string.getBytes()); byte[] bytes = md.digest(); StringBuilder s = new StringBuilder(); for (int i = 0; i < bytes.length; i++) { int parteAlta = ((bytes[i] >> 4) & 0xf) << 4; int parteBaixa = bytes[i] & 0xf; if (parteAlta == 0) { s.append('0'); } s.append(Integer.toHexString(parteAlta | parteBaixa)); } return s.toString(); } /** * Master workaround to get a JSON attribute, you must do this correctly, I did this because it is more funny :) */ private static void mountImageUrl(String total) { int inicio = total.lastIndexOf("\"thumbnail\":{\"path\":\""); int fim = total.indexOf("\",\"extension\":\""); String ss = total.substring(inicio, fim).substring(21) + "/portrait_xlarge.jpg"; System.out.println("\nUse this URL to see the image returned by Rest: " + ss); } }Oi de novo :) Aqui está a saída desse meu código. Usei um [...] pra ficar um pouco menor.
Rest URL: http://gateway.marvel.com/v1/public/comics/12?ts=1391742038152&apikey=0458f299a5570e88176c0cd08be6a592&hash=37d71302dc8fcbb7a67fab5c25dadc71 Rest Return: {"code":200,"status":"Ok","etag":"e41c5cc5be95cd99d46ec56146f1051099c9abb5","data":{"offset":0,"limit":20,"total":1,"count":1,"results":[{"id":12,"digitalId":4089,"title":"Ultimate Spider-Man (2000) #68","issueNumber":68,"variantDescription":"","description":"SUPERSTARS PART 3 Johnny Storm still doesn't have a high school [...] Torch","type":"interiorStory"}],"returned":2},"events":{"available":0,"collectionURI":"http://gateway.marvel.com/v1/public/comics/12/events","items":[],"returned":0}}]}} Use this URL to see the image returned by Rest: http://i.annihil.us/u/prod/marvel/i/mg/f/90/4bc6b6e773bde/portrait_xlarge.jpgPelo Rest recebemos uma URL de uma imagem (mais detalhes em http://developer.marvel.com/documentation/images)
Bom, é isso, qualquer dúvida posta aí que tentarei ajudar!
Fontes:
http://www.mkyong.com/webservices/jax-rs/restfull-java-client-with-java-net-url/
http://codare.net/2007/02/02/java-gerando-codigos-hash-md5-sha/
Abraços!
Adriano Schmidt
quinta-feira, 6 de fevereiro de 2014
There is a process already using the admin port 4848
Pessoal, hoje ao startar o GlassFish no linux (RHEL) tive o seguinte erro:
There is a process already using the admin port 4848 -- it probably is another instance of a GlassFish server
E não tinha outro GlassFish na máquina... então verifiquei o iptables (sudo iptables -L) e tava vazio, dei até um (sudo iptables -F)
para limpar tudo por segurança..
Verifiquei o selinux, mas tava desabilitado também...
Para resolver abri o arquivo /etc/hosts (vi /etc/hosts) e adicionei após a primeira linha:
127.0.0.1 NOMEDAMAQUINA
E resolveu meu problema, GlassFish iniciou certinho!
Para saber o nome da máquina é só usar o comando hostname (hostname)
Fonte: http://www.devmedia.com.br/forum/erro-ao-iniciar-o-glassfish-3-no-ubuntu-server-9-04/134959
Abraço pessoal!!!
Adriano Schmidt
There is a process already using the admin port 4848 -- it probably is another instance of a GlassFish server
E não tinha outro GlassFish na máquina... então verifiquei o iptables (sudo iptables -L) e tava vazio, dei até um (sudo iptables -F)
para limpar tudo por segurança..
Verifiquei o selinux, mas tava desabilitado também...
Para resolver abri o arquivo /etc/hosts (vi /etc/hosts) e adicionei após a primeira linha:
127.0.0.1 NOMEDAMAQUINA
E resolveu meu problema, GlassFish iniciou certinho!
Para saber o nome da máquina é só usar o comando hostname (hostname)
Fonte: http://www.devmedia.com.br/forum/erro-ao-iniciar-o-glassfish-3-no-ubuntu-server-9-04/134959
Abraço pessoal!!!
Adriano Schmidt
sexta-feira, 31 de janeiro de 2014
JBoss JAAS LDAP Tutorial
Pessoal.. tive que configurar um ambiente JBoss EAP6/AS7 + JAAS + LDAP/AD e apanhei bastante pra conseguir, então resolvi fazer um artigo aqui no blog em formato de tutorial pra documentar o passo-a-passo e ajudar quem tiver que fazer o mesmo.
Primeiro eu segui um tutorial e não deu certo: http://middlewaremagic.com/jboss/?p=378
Não sei o motivo ainda, mas não foi de jeito nenhum.
Depois segui o tutorial do Mauricio Magnani e deu tudo certo! http://jbossdivers.wordpress.com/2012/02/12/utilizando-ldap-login-module-no-jboss-as-7-1/
No tutorial do Mauricio ele usou o openldap no linux, eu utilizei o Apache Directory Studio no Windows (tem pra linux e mac também) para criar meu servidor de LDAP/AD. Esse software é baseado no eclipse e falicita muito o trabalho com LDAP/AD, permite criar servidores, criar usuários, adicionar atributos, tudo pela interface gráfica. É lindo : ) Muito fácil de usar!
Na sua empresa/cliente talvez você já tenha um servidor de LDAP/AD, então você teria que usar ele, mas sugiro criar o server na sua máquina para testar, e depois que estiver tudo funcionando, é só apontar para o LDAP/AD da sua empresa/cliente.
* Instale o Apache Directory Studio
Baixe o Apache Directory Studio, instale, e inicie ele.
http://directory.apache.org/studio/downloads.html
* Crie Server LDAP local
Entre na aba "LDAP Servers" (Caso ela não aparece: Window > Show View > LDAP Servers)
Botão direito > New > New Server
Escolha "ApacheDS 2.0.0
Clique em "Finish"
Inicie o servidor
* Conecte-se no server criado
Entre na aba "Connections"
Botão direito > New Connection
Em "Connection Name" coloque "localhost"
Em "Hostname" coloque "localhost"
Em "Port" coloque "10389"
Clique em next
Em "Bind DN ou user" coloque "uid=admin,ou=system"
Em "Bind password" coloque "secret"
Clique em "Check Authentication", tem que funcionar : )
Clique em "Finish"
*Crie um usuário
Entre na aba "LDAP Browser"
DIT > Root DSE > ou=system" > ou=users
Botão direito em "ou=users" > New > New Entry
Clique em "Create entry from strach"
Clique em "Next"
Em "Available object classes" escolha "inetOrgPerson"
Clique em "Next"
Em "RDN", no primeiro campo, coloque "uid"
Em "RDN", no segundo campo, coloque "user1"
Clique em "Next"
Em "cn" coloque "user1"
Em "sn" coloque "user1"
Botão direito > New Attribute
Em "Attribute type" coloque "userPassword"
Clique em "Finish"
Em "Enter New Password" coloque "secret"
Clique em "OK"
Clique em "Finish"
* Crie uma role
Entre na aba "LDAP Browser"
DIT > Root DSE > ou=system" > ou=groups
Botão direito em "ou=groups" > New > New Entry
Clique em "Create entry from strach"
Clique em "Next"
Em "Available object classes" escolha "groupOfNames"
Clique em "Next"
Em "RDN", no primeiro campo, coloque "cn"
Em "RDN", no segundo campo, coloque "General"
Clique em "Next"
No campo que vai aparecer coloque "uid=user1,ou=users,ou=system"
Clique em "OK"
Clique em "Finish"
* Instale o JBoss AS 7.1.1 ou o JBoss EAP 6.2 (Testei nestas duas versões e funcionou, nas demais versão do AS7 e EAP6 deve funcionar também)
Basta baixar o zip e descompactar
A JDK precisa estar configurada no JAVA_HOME e isso precisa estar no PATH
Rode o standalone.bat ou o standalone.sh do JBoss para verificar se está funcionando.
* Configure o standalone.xml
No subsystem de security adicione as seguintes linhas dentro da tag <security-domains>
No subsystem de logging adicione as seguintes linhas junto com os demais loggers:
Isso serve para sair mais logs no server.log para ajudar a identificar problemas, depois que estiver tudo funcionando, altere de TRACE para WARN.
* Configure o seu projeto
No seu projeto em src/main/webapp/WEB-INF crie um arquivo chamado jboss-web.xml com o seguinte conteúdo:
No seu projeto em src/main/webapp/WEB-INF crie um arquivo chamado web.xml com o seguinte conteúdo:
No seu projeto em src/main/webapp crie um arquivo chamado index.xhtml com o seguinte conteúdo:
No seu projeto em src/main/webapp crie um arquivo chamado Login.xhtml com o seguinte conteúdo:
No seu projeto em src/main/webapp crie uma pasta chamada protected.
No seu projeto em src/main/webapp/protected crie um arquivo chamado ProtectedFile.xhtml com o seguinte conteúdo:
* Teste
Reinicie o JBoss e faça deploy da sua aplicação.
Acesse http://localhost:8080/nomeDoProjeto/index.jsf e você vai conseguir acessar normalmente.
Acesse http://localhost:8080/nomeDoProjeto/protected/ProtectedFile.jsf e você vai ser redirecionado para a tela Login.jsf
Entre com o usuário user1 com a senha secret e você vai ser direcionado para tela ProtectedFile.jsf
Pronto :D
Funciona que é uma beleza!!
E mais uma vez quero agradecer ao Mauricio Magnani pelo seu blog http://jbossdivers.wordpress.com/ que me ajudou nessa atividade.
Abraços!!
Adriano Schmidt
Primeiro eu segui um tutorial e não deu certo: http://middlewaremagic.com/jboss/?p=378
Não sei o motivo ainda, mas não foi de jeito nenhum.
Depois segui o tutorial do Mauricio Magnani e deu tudo certo! http://jbossdivers.wordpress.com/2012/02/12/utilizando-ldap-login-module-no-jboss-as-7-1/
No tutorial do Mauricio ele usou o openldap no linux, eu utilizei o Apache Directory Studio no Windows (tem pra linux e mac também) para criar meu servidor de LDAP/AD. Esse software é baseado no eclipse e falicita muito o trabalho com LDAP/AD, permite criar servidores, criar usuários, adicionar atributos, tudo pela interface gráfica. É lindo : ) Muito fácil de usar!
Na sua empresa/cliente talvez você já tenha um servidor de LDAP/AD, então você teria que usar ele, mas sugiro criar o server na sua máquina para testar, e depois que estiver tudo funcionando, é só apontar para o LDAP/AD da sua empresa/cliente.
* Instale o Apache Directory Studio
Baixe o Apache Directory Studio, instale, e inicie ele.
http://directory.apache.org/studio/downloads.html
* Crie Server LDAP local
Entre na aba "LDAP Servers" (Caso ela não aparece: Window > Show View > LDAP Servers)
Botão direito > New > New Server
Escolha "ApacheDS 2.0.0
Clique em "Finish"
Inicie o servidor
* Conecte-se no server criado
Entre na aba "Connections"
Botão direito > New Connection
Em "Connection Name" coloque "localhost"
Em "Hostname" coloque "localhost"
Em "Port" coloque "10389"
Clique em next
Em "Bind DN ou user" coloque "uid=admin,ou=system"
Em "Bind password" coloque "secret"
Clique em "Check Authentication", tem que funcionar : )
Clique em "Finish"
*Crie um usuário
Entre na aba "LDAP Browser"
DIT > Root DSE > ou=system" > ou=users
Botão direito em "ou=users" > New > New Entry
Clique em "Create entry from strach"
Clique em "Next"
Em "Available object classes" escolha "inetOrgPerson"
Clique em "Next"
Em "RDN", no primeiro campo, coloque "uid"
Em "RDN", no segundo campo, coloque "user1"
Clique em "Next"
Em "cn" coloque "user1"
Em "sn" coloque "user1"
Botão direito > New Attribute
Em "Attribute type" coloque "userPassword"
Clique em "Finish"
Em "Enter New Password" coloque "secret"
Clique em "OK"
Clique em "Finish"
* Crie uma role
Entre na aba "LDAP Browser"
DIT > Root DSE > ou=system" > ou=groups
Botão direito em "ou=groups" > New > New Entry
Clique em "Create entry from strach"
Clique em "Next"
Em "Available object classes" escolha "groupOfNames"
Clique em "Next"
Em "RDN", no primeiro campo, coloque "cn"
Em "RDN", no segundo campo, coloque "General"
Clique em "Next"
No campo que vai aparecer coloque "uid=user1,ou=users,ou=system"
Clique em "OK"
Clique em "Finish"
* Instale o JBoss AS 7.1.1 ou o JBoss EAP 6.2 (Testei nestas duas versões e funcionou, nas demais versão do AS7 e EAP6 deve funcionar também)
Basta baixar o zip e descompactar
A JDK precisa estar configurada no JAVA_HOME e isso precisa estar no PATH
Rode o standalone.bat ou o standalone.sh do JBoss para verificar se está funcionando.
* Configure o standalone.xml
No subsystem de security adicione as seguintes linhas dentro da tag <security-domains>
<security-domain name="ldap_security_domain"> <authentication> <login-module code="LdapExtended" flag="required"> <!-- Nao alterar --> <module-option name="java.naming.factory.initial" value="com.sun.jndi.ldap.LdapCtxFactory"/> <!-- Deve ser colocado o IP e porta do LDAP --> <module-option name="java.naming.provider.url" value="ldap://localhost:10389"/> <!-- Nao alterar --> <module-option name="java.naming.security.authentication" value="simple"/> <!-- Deve ser colocado o usuário admin e senha --> <module-option name="bindDN" value="uid=admin,ou=system"/> <module-option name="bindCredential" value="secret"/> <!-- Deve ser colocado o diretorio onde estarao os usuarios --> <module-option name="baseCtxDN" value="ou=system"/> <!-- Deve ser colocado o atributo que representa o login do usuario --> <module-option name="baseFilter" value="(uid={0})"/> <!-- Deve ser colocado o diretorio onde estara o grupo com todos os usuarios --> <module-option name="rolesCtxDN" value="ou=groups,ou=system"/> <!-- Deve ser colocado o atributo do grupo que indica quais usuarios pertencem ao grupo --> <module-option name="roleFilter" value="(member={1})"/> <!-- Nao alterar --> <module-option name="roleAttributeID" value="cn"/> <module-option name="roleRecursion" value="-1"/> <module-option name="throwValidateError" value="true"/> <module-option name="searchScope" value="ONELEVEL_SCOPE"/> </login-module> </authentication> </security-domain>
No subsystem de logging adicione as seguintes linhas junto com os demais loggers:
<logger category="org.jboss.security"> <level name="TRACE"/> </logger>
Isso serve para sair mais logs no server.log para ajudar a identificar problemas, depois que estiver tudo funcionando, altere de TRACE para WARN.
* Configure o seu projeto
No seu projeto em src/main/webapp/WEB-INF crie um arquivo chamado jboss-web.xml com o seguinte conteúdo:
<?xml version="1.0" encoding="UTF-8"?> <jboss-web> <security-domain>java:/jaas/ldap_security_domain</security-domain> </jboss-web>
No seu projeto em src/main/webapp/WEB-INF crie um arquivo chamado web.xml com o seguinte conteúdo:
<?xml version="1.0" encoding="UTF-8"?> <web-app id="WebApp_ID" version="3.0" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"> <display-name>NomeDoProjeto</display-name> <!-- JSF --> <servlet> <servlet-name>Faces Servlet</servlet-name> <servlet-class>javax.faces.webapp.FacesServlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>Faces Servlet</servlet-name> <url-pattern>*.jsf</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsf</welcome-file> </welcome-file-list> <!-- Security --> <!-- Aqui voce mexe para dar permissoes para diferentes pastas para roles diferentes --> <!-- Nesse exemplo eu permito que apenas usuario da role "General" possam acessar /protected/* --> <security-constraint> <web-resource-collection> <web-resource-name>Protected</web-resource-name> <url-pattern>/protected/*</url-pattern> <http-method>GET</http-method> <http-method>POST</http-method> </web-resource-collection> <auth-constraint> <role-name>General</role-name> </auth-constraint> </security-constraint> <login-config> <auth-method>FORM</auth-method> <realm-name>LDAP</realm-name> <form-login-config> <form-login-page>/Login.jsf</form-login-page> <form-error-page>/Login.jsf?invalidLogin=true</form-error-page> </form-login-config> </login-config> <security-role> <role-name>General</role-name> </security-role> </web-app>
No seu projeto em src/main/webapp crie um arquivo chamado index.xhtml com o seguinte conteúdo:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:f="http://java.sun.com/jsf/core" xmlns:h="http://java.sun.com/jsf/html"> <h:body> <h:outputText value="Ola mundo" /> </h:body> </html>
No seu projeto em src/main/webapp crie um arquivo chamado Login.xhtml com o seguinte conteúdo:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:f="http://java.sun.com/jsf/core" xmlns:h="http://java.sun.com/jsf/html"> <h:body> <form id="formLogin" action="j_security_check" method="post"> <h:outputText value="LOGIN"/> <br/><br/> <h:panelGroup rendered="#{param['invalidLogin'] == 'true'}"> <h:outputText value="Por favor utilize credenciais autorizadas." /> <br/><br/> </h:panelGroup> <h:outputText value="Usuario: "/> <h:inputText id="j_username" required="true" /> <br/><br/> <h:outputText value="Senha: "/> <h:inputSecret id="j_password" feedback="false" required="true"/> <br/><br/> <h:commandButton id="access_button" type="submit" value="Entrar"/> </form> </h:body> </html>
No seu projeto em src/main/webapp crie uma pasta chamada protected.
No seu projeto em src/main/webapp/protected crie um arquivo chamado ProtectedFile.xhtml com o seguinte conteúdo:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:f="http://java.sun.com/jsf/core" xmlns:h="http://java.sun.com/jsf/html"> <h:body> <h:outputText value="Arquivo protegido." /> </h:body> </html>
* Teste
Reinicie o JBoss e faça deploy da sua aplicação.
Acesse http://localhost:8080/nomeDoProjeto/index.jsf e você vai conseguir acessar normalmente.
Acesse http://localhost:8080/nomeDoProjeto/protected/ProtectedFile.jsf e você vai ser redirecionado para a tela Login.jsf
Entre com o usuário user1 com a senha secret e você vai ser direcionado para tela ProtectedFile.jsf
Pronto :D
Funciona que é uma beleza!!
E mais uma vez quero agradecer ao Mauricio Magnani pelo seu blog http://jbossdivers.wordpress.com/ que me ajudou nessa atividade.
Abraços!!
Adriano Schmidt
quinta-feira, 30 de janeiro de 2014
LDAP - Failed to parse: null, disabling recursion: java.lang.NumberFormatException: null
Configurando um Ambiente JBoss 7.1.1-Final com JAAS e LDAP/AD eu tive o erro abaixo:
Para resolver, bastou adicionar a linha abaixo no login-module do subsystem security no standalone.xml
Isso resolveu o problema!!!
Abraços!!
Adriano Schmidt
14:46:42,273 TRACE [org.jboss.security.auth.spi.LdapExtLoginModule] (http-localhost-127.0.0.1-8080-1) Failed to parse: null, disabling recursion: java.lang.NumberFormatException: null
at java.lang.Integer.parseInt(Integer.java:454) [rt.jar:1.7.0_51]
at java.lang.Integer.parseInt(Integer.java:527) [rt.jar:1.7.0_51]
at org.jboss.security.auth.spi.LdapExtLoginModule.createLdapInitContext(LdapExtLoginModule.java:395) [picketbox-4.0.7.Final.jar:4.0.7.Final]
[...]
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:930) [jbossweb-7.0.13.Final.jar:]
at java.lang.Thread.run(Thread.java:744) [rt.jar:1.7.0_51]
Para resolver, bastou adicionar a linha abaixo no login-module do subsystem security no standalone.xml
<module-option name="roleRecursion" value="-1"/>
Isso resolveu o problema!!!
Abraços!!
Adriano Schmidt
Assinar:
Postagens (Atom)