Duvida arquitetura REST + Vraptor + GAE

10 respostas
boneazul

Estou com um problema mais conceitual que programático . Pelo que entendi o vraptor ja meio que embarca uma arquitetura rest nativo no framework certo , utilizando as anotações

@Path , @Get , @Put , etc , etc
e em conjunto com result.use(representacao).from…é possível exibir dados,deletar
e @Consumes pra poder receber dados e salvar,atualizar

Agora vem as duvidas e problemas :

Tenho uma aplicação A e uma aplicação B ambas no Google app engine , pelo que vi não é possível ter um banco centralizado no google app engine o que só me resta conversação entre aplicações mesmo .

Duvida 1 :

Como implementar autenticacao entre esse dois caras utilizando vraptor mesmo ?? Algum jeito facil ??

Duvida 2 :

Eu tenho algumas classes na aplicação B que utilizo algumas classes da aplicação A agregada , eu guardo apenas a chave primária nesse caso ? E toda vez que precisar recuperar preciso fazer via REST ??

Exemplo :
Na aplicação A eu tenho

public class Estado {
        private Long id;
        private String sigla;
        private String nome;
}

ai isso vai num jar que a aplicação B utiliza em outra classe :

public class Endereco {
        private Estado estado; //Definida na aplicação A
        private String logradouro;
        .
        .
}

Quando salvar o endereco na aplicação B e só salvo a chave primária do Estado ?? Toda vez que eu precisar listar o endereco preciso no metodo ir pra api de rest buscar o resto dos dados para poder exibir ??
Ex :

public List<Endereco> getAllEnderecos(){
       //Lista todos
       List<Endereco> enderecoes = datastore.find(Endereco.class);
       for(Endereco endereco : endereco){
              //Vir buscando 1 a 1 mesmo via REST e populando o resto dos dados ?? 
              endereco.setEstado(serviceEstado.get(endereco.getEstado()));
       }
      return enderecos;
}

Agradeço qualquer ajuda ou alguma nova ideia mais robusta .

Abraços

10 Respostas

Lucas_Cavalcanti

[quote=boneazul]
Duvida 1 :

Como implementar autenticacao entre esse dois caras utilizando vraptor mesmo ?? Algum jeito facil ??
[/code]

a autenticação de uma aplicação chamando a outra?

vc pode tentar usar headers de autenticação… tipo passar o header X-MinhaApp-Auth: hashbizarro192831723987sadfsdf e o outro lado validar esse header.

ou usar algo como OAuth pra isso (mais difícil)

outro jeito é segurança por obscuridade: @Path("/algumaCoisa/hashBizarrouhaushuh123123128s7dfs9df/{endereco.id})

daí só a outra aplicação conhece.

quanto à dúvida 2, o melhor a fazer é evitar chamar a aplicação remota várias vezes, pois isso é lento. Tenta no máximo fazer um serviço que passa uma lista de ids de endereço e retorna um json/xml com os dados desses endereços.

mas pensa bem se os dados estão no lugar certo…

boneazul

Sim a autenticação seria para apenas os domínios conversarem e nao deixar assim aberta na internet .
Quanto a autenticação vou dar uma pesquisada e parece ser mais simples de programar com header mesmo .

Quanto a dúvida 2 ai que o bixo ta pegando e to vendo que vou ter que sair do google app engine por conta dessa restrição , onde performance é um fator primordial.

Entao pra entender melhor a ideia vamo fazer algo maior :

Aplicação A - Cadastro de A,B,C,D,E (Todos auxiliares que podem ser usados em N aplicações e só existir 1 ponto de gerenciamento)
Aplicação B - Utiliza em suas entidades os cadastros A,C,D
Aplicação C - Utiliza em suas entidades os cadastros A,B,D
Aplicação D - Utiliza em suas entidades os cadastros C,D,E
Aplicação N - Utiliza em suas entidade os cadastros da aplicação B que utiliza cadastro da aplicação A (Ai ja começa uma cadeia de distribuição dos objetos o que complica ainda mais a chamada dos serviços pois dai é remoto pra duas aplicações diferentes)

Se voce for analisar :

o cadastro A é utilizado nas aplicações A e B
o cadastro B é utilizado nas aplicações B (mas poderá ser utilizado em outra que ainda não será construida por exemplo)
o cadastro C é utilizado nas aplicações A e D
o cadastro D é utilizado nas aplicações B,C,D
o cadastro E é utilizado nas aplicações E (mas poderá ser utilizado em outra que ainda não será construida por exemplo)
a aplicação N utiliza alguns cadastros que a B gerou que tambem vem embutido coisa da aplicação A

Se fosse tudo num banco centralizado era muito facil pois era jogar jar de um no outro dar os grants de select e boa tudo funcionando pois compartilham do mesmo banco de dados.

So que a restricao do GAE de nao poder centralizar tudo num banco e ter que fazer as aplicações conversarem por outro modo ou seja Http e REST|SOAP que é foda e nao vejo meios de fugir de ficar fazendo essas chamadas remotas (o que com certeza vai comprometer a performance do site mesmo utilizando memcache etc pois ainda sobra conversacao http) se eu continuar na plataforma do GAE pois a ideia é nao replicar nada.

Entao pra esse cenário o que voces aconselhariam ?? Migrar pra um cloud JAVAEE,Sql da vida (OpenShift,Heroku,etc) que dai tem mil maneiras de resolver (compartilhar banco modulo EJB , messageria,etc,etc) ou continuar mesmo nesse modelo Google PaaS de ser e ver essa comunicação via REST mesmo ??

To meio perdido .

garcia-jj que manja de aplicação distribuida , deve ter uns bons conselhos :lol:

Lucas_Cavalcanti

o que vc pode fazer é fazer o deploy na mesma aplicação do GAE, só que em configurações diferentes…

Assim todas as configurações compartilham o BigTable…

não sei se tem algum detalhe técnico, mas teoricamente funciona.

boneazul

Lucas Cavalcanti:
o que vc pode fazer é fazer o deploy na mesma aplicação do GAE, só que em configurações diferentes…

Assim todas as configurações compartilham o BigTable…

não sei se tem algum detalhe técnico, mas teoricamente funciona.

Não entendi muito bem o que voce quis dizer com configurações diferentes . O unico jeito de aplicações diferentes compartilharem o mesmo banco de dados é fazendo deploy com outro nome de versao .

exemplo

default.site.com
modulo1.site.com
modulo2.site.com
modulo3.site.com

mas é meio gambi pois nao foi feito pra esse intuito .

A nao ser que tenha outro modo de fazer que não estou por dentro .

Lucas_Cavalcanti

sim, a idéia era usar os nomes de versão mesmo… é um dos jeitos de compartilhar o mesmo banco :wink:

Aqui:


dão sugestões parecidas com a que eu dei

G

Eu particularmente não gosto de comprartilhar banco de dados. Isso porque você acaba criando uma dependência entre eles. Claro, talvez a dependência seja desejada, no caso de módulos, mas não sei se é teu caso.

Você quer compartilhar endereços, é?

Fiz algo assim em um sistema. A base de CEP é enorme, e eu não queria ficar replicando isso em cada app. Então eu criei uma aplicação de CEP que apenas possui métodos de pesquisa de CEP > Endereço e Endereço > CEP. Tudo isso em rest, sem autenticação já que era interno, além disso CEP não é algo tão restrito assim que precise autenticação.

Nas minhas apps, eu criei uma entidade endereço onde gravo os dados de endereço tão qual é um endereço, com os dados de logradouro, número, bairro, cep, etc… Não usei relacionamento porque senão eu teria que fazer consultas REST sempre que necessário exibir o endereço, o que me daria muito I/O na aplicação. Cliente possui um relacionamento 1:1 com Endereço, e quando um cliente é cadastrado, crio a entidade Endereço com os dados que veio do serviço REST.

Em um modo geral, nunca crie relacionamentos remotos. Tente evitar ao máximo comunicações remotas desnecessárias, então faça um cache local por demanda, ou grave os dados diretos em uma tabela local. Cada caso é um caso, então falo isso de uma forma bem genérica.

Quanto a autenticação… se for endereços, não vejo motivo. Mas de qualquer forma, o problema do GAE/J é que para usar uma autenticaçao a nivel de container você precisa ter um usuário cadastrado nos serviços do Google. Se fosse um servidor normal, eu diria para usar JAAS com autenticação BASIC ou DIGEST, ou até mesmo certificado digital. Mas como estamos falando do GAE/J, use a sugestão do Lucas, que é a mesma forma que muitos serviços usam por aí em suas APIs, como por exemplo o Akismet, Github, etc.

boneazul

garcia-jj:
Eu particularmente não gosto de comprartilhar banco de dados. Isso porque você acaba criando uma dependência entre eles. Claro, talvez a dependência seja desejada, no caso de módulos, mas não sei se é teu caso.

Você quer compartilhar endereços, é?

Fiz algo assim em um sistema. A base de CEP é enorme, e eu não queria ficar replicando isso em cada app. Então eu criei uma aplicação de CEP que apenas possui métodos de pesquisa de CEP > Endereço e Endereço > CEP. Tudo isso em rest, sem autenticação já que era interno, além disso CEP não é algo tão restrito assim que precise autenticação.

Nas minhas apps, eu criei uma entidade endereço onde gravo os dados de endereço tão qual é um endereço, com os dados de logradouro, número, bairro, cep, etc… Não usei relacionamento porque senão eu teria que fazer consultas REST sempre que necessário exibir o endereço, o que me daria muito I/O na aplicação. Cliente possui um relacionamento 1:1 com Endereço, e quando um cliente é cadastrado, crio a entidade Endereço com os dados que veio do serviço REST.

Em um modo geral, nunca crie relacionamentos remotos. Tente evitar ao máximo comunicações remotas desnecessárias, então faça um cache local por demanda, ou grave os dados diretos em uma tabela local. Cada caso é um caso, então falo isso de uma forma bem genérica.

Quanto a autenticação… se for endereços, não vejo motivo. Mas de qualquer forma, o problema do GAE/J é que para usar uma autenticaçao a nivel de container você precisa ter um usuário cadastrado nos serviços do Google. Se fosse um servidor normal, eu diria para usar JAAS com autenticação BASIC ou DIGEST, ou até mesmo certificado digital. Mas como estamos falando do GAE/J, use a sugestão do Lucas, que é a mesma forma que muitos serviços usam por aí em suas APIs, como por exemplo o Akismet, Github, etc.

Entao endereço foi apenas 1 dos exemplos que eu dei na verdade . Esse cenario vai aparecer muito daqui pra frente de uma classe embutir pedaços de outras , na verdade vai ser um quebra cabeça onde as entidades estao espalhadas por todo lado , mas só 1 modulo proprio que gerencia para nao haver replicação e retrabalho , e como o GAE/J tem bastante restrição to meio que desistindo de trabalhar com ele . Se o google parasse de enrolar e liberasse o CloudSql deles para o publico ficava mais facil de resolver . Apontava tudo pro mesmo banco e boa , tudo escalando bem de novo . Como o projeto vai ser gigantesco , nao tem como manter no mesmo projeto fonte java , por n motivos , (nome de dominio principalmente , tipo de autenticacao) . Vejo um futuro meio nebuloso se continuar nesse caminho . Foda que quando comecei a desenvolver o soft , o GAE era uma criança ainda , nem se falava direto de cloud. Depois apareceu um monte com suporte a sql . Pé frio pra caramba … :lol:

Eu li em algum post que voce comecou a usar o openshift , como é o suporte ?? To dando uma olhada no heroku também.

Agora fica a duvida pra qual ir . Entre openshift , amazon ec2 , heroku , qual será que é mais robusto ?? Tem alguma opinião ??

G

Meu único problema no GAE é a questão de usar aquelas APIs proprietárias. Se um dia você quiser migrar para outro local, precisa reescrever muita coisa. E neste ponto tenho gostado muito do Openshift, pois é um ambiente JEE padrão. Então sempre que você optar pelo GAE, tem que levar isso em questão.

Além disso, eu não gosto de trabalhar com servlet container, sempre que possível prefiro trabalhar com appserver, por eu ter um leque bem maior de opções de gerenciamento como schedulers, JTA, etc. Muitas coisas que eu teria que me preocupar em um ambiente servlet container, eu não tenho em um appserver. Mais um motivo por eu ter gostado do Openshift.

Se você tem muitas ligações entre os módulos, será que realmente eles estão separados corretamente? Se as ligação são tão fortes, talvez eles não devam ser separados em módulos. Isso porque vai chegar um momento que serão tantas ligações fortes que você terá dependências ciclicas, e ficará complexo de manter. Enfim, sem saber o que é realmente, é complicado de prever. Entretanto eu te sugiro organizar os módulos para que tenham a menor quantidade de dependências, e quando mais fracas melhor. E de preferência evite que um módulo altere entidades do outro, pois assim é complicado até mesmo controlar a concorrência.

Eu só fiquei em dúvida: tua aplicação é separada em módulos ou são aplicações diferentes? Porque se são apenas módulos do sistema, você pode fazer algo parecido com o que eu fiz em um outro sistema. O projeto era empacotado em um EAR, e cada módulo do sistema era um módulo EJB, porém o banco de dados era o mesmo, já que a aplicação é a mesma. Porém tomei cuidado de organizar os módulos de forma que nunca um módulo alterada entidades de outro. Por exemplo, o módulo de Cliente poderia fazer tudo que queria com cliente, porém o módulo Vendas não poderia alterar os dados do cliente, ele apenas criava Orders e afins, mas nunca alterava diretamente Cliente.

Abraço

boneazul

garcia-jj:
Meu único problema no GAE é a questão de usar aquelas APIs proprietárias. Se um dia você quiser migrar para outro local, precisa reescrever muita coisa. E neste ponto tenho gostado muito do Openshift, pois é um ambiente JEE padrão. Então sempre que você optar pelo GAE, tem que levar isso em questão.

Além disso, eu não gosto de trabalhar com servlet container, sempre que possível prefiro trabalhar com appserver, por eu ter um leque bem maior de opções de gerenciamento como schedulers, JTA, etc. Muitas coisas que eu teria que me preocupar em um ambiente servlet container, eu não tenho em um appserver. Mais um motivo por eu ter gostado do Openshift.

Se você tem muitas ligações entre os módulos, será que realmente eles estão separados corretamente? Se as ligação são tão fortes, talvez eles não devam ser separados em módulos. Isso porque vai chegar um momento que serão tantas ligações fortes que você terá dependências ciclicas, e ficará complexo de manter. Enfim, sem saber o que é realmente, é complicado de prever. Entretanto eu te sugiro organizar os módulos para que tenham a menor quantidade de dependências, e quando mais fracas melhor. E de preferência evite que um módulo altere entidades do outro, pois assim é complicado até mesmo controlar a concorrência.

Eu só fiquei em dúvida: tua aplicação é separada em módulos ou são aplicações diferentes? Porque se são apenas módulos do sistema, você pode fazer algo parecido com o que eu fiz em um outro sistema. O projeto era empacotado em um EAR, e cada módulo do sistema era um módulo EJB, porém o banco de dados era o mesmo, já que a aplicação é a mesma. Porém tomei cuidado de organizar os módulos de forma que nunca um módulo alterada entidades de outro. Por exemplo, o módulo de Cliente poderia fazer tudo que queria com cliente, porém o módulo Vendas não poderia alterar os dados do cliente, ele apenas criava Orders e afins, mas nunca alterava diretamente Cliente.

Abraço

É eu vi que o openshift ta dando suporte a especificacao mesmo JAVAEE completo com o jboss por tras , diferente do heroku por exemplo que só utiliza o jetty assim como o GAE como servlet container pelo que entendi pelo menos é isso.

Entao são aplicações totalmente diferentes , uma nao tem nada a ver com a outra , mas podem ocasionalmente utilizar classes de outras aplicações . Entao se eu migrar mesmo nem o modelo de programacao EAR me serve pois nao se trata do mesmo software modularizado e sim de softwares diferentes . Dai ja vou partir pra EJB também que seria o ideal pra poder já prever front end mobile .

Bom vou dar uma olhada no openshift fazer deploy de uns exemplinhos e entender melhor como ele escala . Mandei email pro pessoal da red hat , pra ver como funciona o esquema deles se precisar de mais recurso .

Pelo que vi eles oferecem 3 small gears gratuito . Ai no email eles dizem que tem a medium gear e talvez no futuro uma large gear . Mais achei meio foda que tem uma taxa de $42 dolares mensais de suporte obrigatorio + o valor hora do recurso do gear que ta mais ou menos o mesmo preço do amazon . Essa taxa mensal ai que é foda . Isso no GAE por exemplo é recurso de pra caramba tenho 3 aplicações com uso severo lá e num gasto mai de 50 reais por mes nas 3 . Mas a parte boa é que da pra migrar facil depois ja que diferente do google nao fica preso a API deles , além de ter bem menos restrição de uso . Google acerta muito , mais erra muito ao mesmo tempo em algumas coisas .

Mas beleza vou dar uma estudada mais a fundo nesses clouds java , e volto pra postar algo ai pro pessoal qual cloud sai mais em conta , qual o mais facil de trabalhar , etc .

Abraços a todos.

G

Se são sistemas diferentes, não consigo imaginar um motivo para usarem as mesmas tabelas/entidades. Isso para economizar código? Se sim, é o mesmo caso daqueles projetos que criam uma BaseAction apenas para ganhar alguns poucos métodos utilitários. Neste caso a amarração é tão forte que mais atrapalha do que ajuda.

Criado 19 de abril de 2012
Ultima resposta 22 de abr. de 2012
Respostas 10
Participantes 3