web-dev-qa-db-fra.com

Décrivez l’architecture que vous utilisez pour les Java?

Partageons les Java!

Il existe de nombreuses architectures différentes pour les applications Web qui doivent être implémentées à l'aide de Java. Les réponses à cette question peuvent servir de bibliothèque de conceptions d’applications Web variées avec leurs avantages et inconvénients. Bien que je sache que les réponses seront subjectives, essayons d’être aussi objectifs que possible et motivons les avantages et les inconvénients que nous énumérons.

Utilisez le niveau de détail que vous préférez pour décrire votre architecture. Pour que votre réponse soit utile, vous devez au moins décrire les principales technologies et idées utilisées dans l'architecture que vous décrivez. Et enfin, quand devrions-nous utiliser votre architecture?

Je vais commencer...


Vue d'ensemble de l'architecture

Nous utilisons une architecture à 3 niveaux basée sur les standards ouverts de Sun comme Java EE, Java API de persistance, Servlet et Java = Pages du serveur.

  • Persistance
  • Affaires
  • Présentation

Les flux de communication possibles entre les couches sont représentés par:

Persistence <-> Business <-> Presentation

Ce qui signifie par exemple que la couche de présentation n'appelle ni n'effectue d'opérations de persistance, elle le fait toujours à travers la couche de gestion. Cette architecture est conçue pour répondre aux exigences d'une application Web à haute disponibilité.

Persistance

Effectue les opérations de persistance suivantes: création, lecture, mise à jour et suppression ( CRUD ). Dans notre cas, nous utilisons JPA ( Java Persistence API ) et nous utilisons actuellement Hibernate comme fournisseur de persistance et utilisons son EntityManager .

Cette couche est divisée en plusieurs classes, où chaque classe traite un certain type d’entités (c’est-à-dire que les entités associées à un panier peuvent être gérées par une seule classe de persistance) et est utilisé par un et un seul manager.

En outre, cette couche stocke également entités JPA , qui sont des éléments tels que Account, ShoppingCart etc.

Affaires

Toute la logique liée à la fonctionnalité de l'application Web se trouve dans cette couche. Cette fonctionnalité pourrait initier un transfert d’argent pour un client qui souhaite payer un produit en ligne en utilisant sa carte de crédit. Cela pourrait tout aussi bien être la création d’un nouvel utilisateur, la suppression d’un utilisateur ou le calcul du résultat d’une bataille dans un jeu basé sur le Web.

Cette couche est divisée en plusieurs classes et chacune de ces classes est annotée avec @Stateless pour devenir un Stateless Session Bean (SLSB). Chaque SLSB s'appelle un manager et, par exemple, un manager peut être une classe annotée comme mentionné ci-dessus, appelée AccountManager.

Lorsque AccountManager doit exécuter des opérations CRUD, il appelle de manière appropriée une instance de AccountManagerPersistence, qui est une classe de la couche de persistance. Un croquis approximatif de deux méthodes dans AccountManager pourrait être:

...
public void makeExpiredAccountsInactive() {
    AccountManagerPersistence amp = new AccountManagerPersistence(...)
    // Calls persistence layer
    List<Account> expiredAccounts = amp.getAllExpiredAccounts();
    for(Account account : expiredAccounts) {
        this.makeAccountInactive(account)
    }
}
public void makeAccountInactive(Account account) {
    AccountManagerPersistence amp = new AccountManagerPersistence(...)
    account.deactivate();
    amp.storeUpdatedAccount(account); // Calls persistence layer
}

Nous utilisons transactions de gestionnaire de conteneur afin que nous n'ayons pas à faire la démarcation de transaction nous-mêmes. Ce qui se passe fondamentalement sous le capot est que nous initions une transaction lorsque nous entrons dans la méthode SLSB et la validons (ou l'annulons) immédiatement avant de quitter la méthode. C'est un exemple de convention sur la configuration, mais nous n'avons pas encore eu besoin de rien, mais de la valeur par défaut, Obligatoire, pour le moment.

Voici comment le Java EE 5 Tutorial de Sun explique le attribut de transaction requis pour Enterprise JavaBeans (EJB):

Si le client est en cours d’exécution dans une transaction et appelle la méthode du bean enterprise, celle-ci s’exécute dans la transaction du client. Si le client n'est pas associé à une transaction, le conteneur démarre une nouvelle transaction avant d'exécuter la méthode.

L'attribut Required est l'attribut de transaction implicite pour toutes les méthodes de bean d'entreprise exécutées avec une démarcation de transaction gérée par le conteneur. Généralement, vous ne définissez pas l'attribut Required sauf si vous devez remplacer un autre attribut de transaction. Les attributs de transaction étant déclaratifs, vous pouvez facilement les modifier ultérieurement.

Présentation

Notre couche de présentation est en charge de ... présentation! Il est responsable de l'interface utilisateur et montre les informations à l'utilisateur en créant des pages HTML et en recevant les entrées de l'utilisateur via GET et POST demandes. Nous utilisons actuellement l'ancien Servlet ' s + Java Pages serveur ( JSP )).

La couche appelle des méthodes dans managers de la couche de gestion pour effectuer les opérations demandées par l'utilisateur et recevoir les informations à afficher dans la page Web. Parfois, les informations reçues de la couche de gestion sont des types moins complexes que String 'et integers, et à d'autres moments entités JPA .

Avantages et inconvénients de l'architecture

Avantages

  • Avoir tout ce qui est lié à une manière spécifique de persister dans cette couche signifie seulement que nous pouvons passer de l'utilisation de JPA à autre chose, sans avoir à réécrire quoi que ce soit dans la couche de gestion.
  • Il est facile pour nous d'échanger notre couche de présentation en quelque chose d'autre, et nous le ferons probablement si nous trouvons quelque chose de mieux.
  • Laisser le conteneur EJB gérer les limites des transactions est facile.
  • Utiliser Servlet's + JPA est simple (pour commencer) et les technologies sont largement utilisées et implémentées dans de nombreux serveurs.
  • L'utilisation de Java EE est supposée faciliter la création d'un système à haute disponibilité avec équilibrage de la charge et basculement . nous sentons que nous devons avoir.

Les inconvénients

  • En utilisant JPA, vous pouvez stocker les requêtes souvent utilisées sous forme de requêtes nommées en utilisant le fichier @NamedQuery annotation sur la classe d’entités JPA. Si vous avez autant que possible lié à la persistance dans les classes de persistance, comme dans notre architecture, cela dispersera les emplacements où vous pourrez trouver des requêtes pour inclure également les entités JPA. Il sera plus difficile d’observer les opérations de persistance et donc plus difficile à maintenir.
  • Nous avons des entités JPA dans notre couche de persistance. Mais Account et ShoppingCart ne sont-ils pas vraiment des objets métier? C’est ainsi que vous devez toucher à ces classes et les transformer en entités que JPA sait gérer.
  • Les entités JPA, qui sont également nos objets métier, sont créées comme des objets de transfert de données ( [(# ~ ~]] dto [~ # ~] ), également appelés objets de valeur (objets de valeur). Il en résulte un modèle de domaine anémique car les objets métier n'ont pas de logique propre, à l'exception des méthodes d'accès. Toute la logique est faite par nos gestionnaires dans la couche de gestion, ce qui conduit à un style de programmation plus procédural. Ce n'est pas une bonne conception orientée objet, mais peut-être que ce n'est pas un problème? (Après tout, l'orientation des objets n'est pas le seul paradigme de programmation ayant donné des résultats.)
  • Utiliser EJB et Java EE introduit un peu de complexité. Et nous ne pouvons pas utiliser purement Tomcat (l'ajout d'un micro-conteneur EJB n'est pas purement Tomcat) .
  • L'utilisation de Servlet's + JPA pose de nombreux problèmes. Utilisez Google pour plus d'informations sur ces problèmes.
  • Les transactions étant fermées lors de la sortie de la couche de gestion, nous ne pouvons charger aucune information provenant d'entités JPA configurées pour être chargées à partir de la base de données en cas de besoin (à l'aide de fetch=FetchType.LAZY) depuis l'intérieur de la couche de présentation. Cela déclenchera une exception. Avant de renvoyer une entité contenant ce type de champs, nous devons nous assurer d'appeler le getter correspondant. Une autre option consiste à utiliser Java Langage de requête de persistance ( JPQL ) et à effectuer un FETCH JOIN. Cependant, ces deux options sont un peu lourdes.
143
user14070

Ok je vais en faire un (plus court):

  • Frontend: Tapestry (3 pour les projets plus anciens, 5 pour les projets plus récents)
  • Couche métier: printemps
  • DAO: Ibatis
  • Base de données: Oracle

Nous utilisons le support des transactions Sping et commençons les transactions en entrant dans la couche service, en se propageant jusque dans l'appel DAO. La couche Service possède le plus de connaissances en matière de modèles d’entreprise et les DAO effectuent un travail CRUD relativement simple.

Certaines requêtes plus complexes sont gérées par des requêtes plus complexes dans le back-end pour des raisons de performances.

L'avantage d'utiliser Spring dans notre cas est que nous pouvons avoir des instances dépendantes du pays/de la langue, qui se trouvent derrière une classe Spring Proxy. En fonction de l'utilisateur de la session, la mise en œuvre pays/langue correcte est utilisée lors d'un appel.

La gestion des transactions est presque transparente et annule les exceptions d'exécution. Nous utilisons autant que possible des exceptions non contrôlées. Nous avions l'habitude de faire des exceptions vérifiées, mais avec l'introduction de Spring, je vois les avantages des exceptions non vérifiées, en ne gérant que les exceptions lorsque vous le pouvez. Cela évite beaucoup de choses "attrape/rethrow" ou "jette".

Désolé, c'est plus court que votre message, j'espère que vous trouverez cela intéressant ...

20
Rolf

Idéal Java Technologies de développement Web basées aujourd'hui.

Couche Web:

HTML + CSS + Ajax + JQuery

Contrôleur Web RESTFul/Action/Couche de traitement des demandes:

Cadre de jeu

Logique d'entreprise/couche de service:

Utilisez pur Java aussi longtemps que possible. On peut faire la fusion des services Web ici.

Couche de transformation de données XML/JSon:

XMLTool (Recherche sur Google Code), JSoup, Google GSon, XStream, JOOX (Recherche sur Google Code)

Couche de persistance:

CRUD: JPA ou SienaProject ou QueryDSL/Requêtes complexes: JOOQ, QueryDSL

18
Rakesh Waghela

Voici mes 5 cents

Présentation

Android, Angular.JS WebClient, OAUTHv2

API

REST, Jersey (JAX-RS), Jackson (de-/sérialisation JSON), objets DTO (différents des modèles de logique métier)

Logique d'entreprise

Ressort pour la gestion des ID et des événements. Approche DDD-ish des objets du modèle. Les tâches plus longues sont déchargées avec SQS dans des modules de travail.

DAO

Modèle de référentiel avec Spring JDBC-templates pour stocker des entités. Redis (JEDIS) pour les classements, à l'aide de listes ordonnées. Memcache pour Token Store.

Base de données

MySQL, Memcached, Redis

9
Pepster

Ce que nous avons suivi dans notre projet est:

Technologie frontale

  • AngularJS
  • HTML5
  • cSS3
  • Javascript
  • Bootstrap 3

API

  1. REST
  2. JERSEY (JAX-RS)
  3. REPOS ASSURÉ
  4. BOTTE DE PRINTEMPS
  5. Jackson
  6. sécurité de printemps

logique d'entreprise

  • DONNÉES DE PRINTEMPS

  • PRINTEMPS données MongoDB

base de données

  • MongoDB

Serveur (pour la mise en cache)

  • redis
6
CandleCoder

Nous utilisons toujours la pile habituelle Struts-Spring-Hibernate.

Pour les futures applications, nous examinons Spring Web Flow + Spring MVC + Hibernate ou Spring + Hibernate + Web Services avec système frontal Flex.

Une caractéristique distincte de notre architecture est la modularisation. Nous avons un certain nombre de modules, certains commençant par 3 à 30 maximum dans la base de données. La plupart des modules sont constitués d’affaires et de projets Web. Le projet d'entreprise contient la logique commerciale et de persistance, tandis que le Web contient la logique de présentation.
Au niveau logique, il y a trois couches: activité, persistance et présentation.
Dépendances:
La présentation dépend de Business et de Persistance.
La persistance dépend des affaires.
Les entreprises ne dépendent pas d’autres couches.

La plupart des projets d’entreprise ont trois types d’interfaces (note: ce n’est pas une interface graphique, c’est une couche de programmation Java)).

  1. Interface utilisée par la présentation en tant que client
  2. Interface que les autres modules utilisent lorsqu'ils sont le client du module.
  3. Interface pouvant être utilisée à des fins administratives du module.

Souvent, 1 s'étend sur 2. De cette façon, il est facile de remplacer une implémentation de module par une autre. Cela nous aide à adopter différents clients et à nous intégrer plus facilement. Certains clients n'achèteront que certains modules et nous devons intégrer les fonctionnalités dont ils disposent déjà. Etant donné que l'interface et la couche d'implémentation sont séparées, il est facile de déployer l'implémentation de modules ad-hock pour ce client spécifique sans affecter les modules dépendants. Et Spring Framework facilite l’injection de différentes implémentations.

Notre couche métier est basée sur les POJO. Une tendance que j’observe est que ces POJO ressemblent à des DTO. Nous souffrons de modèle de domaine anémique . Je ne sais pas trop pourquoi cela se produit, mais cela peut être dû à la simplicité du domaine de problèmes de beaucoup de nos modules; la plupart du travail est effectué avec CRUD ou au fait que les développeurs préfèrent placer la logique ailleurs.

4
Dan

Voici une autre architecture Web sur laquelle j'ai travaillé:

L’une des principales exigences était que l’application devait prendre en charge les téléphones portables/autres appareils. L'application doit également être extensible ou flexible aux changements de choix technologiques.

Niveau de présentation:

  • JSP/JQuery (MVC côté client)
  • Android natif
  • IPhone natif
  • Web mobile (HTML5/CSS3/Responsive Design)

  • Spring REST Contrôleurs (peut être remplacé par JAX-RS)

Niveau de service métier:

Spring @Service (peut être remplacé par un EJB sans état)

Niveau d'accès aux données:

Spring @Repository (peut être remplacé par un EJB sans état)

Niveau de ressources:

Hibernate (JPA) entités (peut être remplacé par n'importe quel ORM)

Vous pouvez trouver plus d'informations sur le livre qui suit cette architecture ici .

3
Amritendu De

IMHO, la plupart d'entre nous ont un dénominateur commun. Au moins dans le back-end, nous avons une certaine forme de conteneur IOC/DI et un cadre de persistance. Personnellement, j'utilise Guice et Mybatis pour cela. Les différences concernent la manière dont nous implémentons la couche vue/interface utilisateur/présentation. Il existe 2 options principales ici (peut-être plus). Basé sur les actions (URL mappées aux contrôleurs) et sur les composants. Actuellement, j'utilise une couche de présentation à base de composants (utilisant un guichet). Il imite parfaitement un environnement de bureau dans lequel j'utilise des composants et des événements, par opposition aux URL et aux contrôleurs. Je cherche actuellement une raison pour laquelle je devrais migrer vers ce type d'architecture de contrôleur d'URL (c'est comme ça que j'ai fini sur cette page). Pourquoi le battage médiatique sur les architectures RESTful et Stateless.

Pour répondre à cette question en bref: j'écris des applications Web dynamiques avec un framework orienté composant au-dessus de Guice IOC) et je mets les données dans une base de données relationnelle à l'aide de Mybatis.

2
joshua

Un peu différent, et je dirais une architecture plus modulaire Java ici. Nous avons:

  1. Spring WS/Rest/JSP front end
  2. Spring MVC pour la logique de service métier, contenant la logique de la couche présentation ainsi que les transactions Spring
  3. Interface de communication de service de composant, recherchée par EJB par les services aux entreprises. Les EJB définissent leurs propres limites de transaction pouvant se joindre aux transactions Spring.
  4. Implémentations de services de composants, à nouveau des composants Spring
  5. Couche d'intégration, MyBatis pour les intégrations de bases de données, Spring WS pour les intégrations de services Web, autres technologies d'intégration pour d'autres services
  6. Mainframes, bases de données, autres services sur d'autres serveurs ...

En plus de ce qui précède, nous avons les modules de bibliothèque partagée, qui sont le fournisseur de fonctionnalités communes à tous les services.

L'utilisation de différentes couches nous permet un découplage total et la modularité dont nous avons besoin. Nous sommes également en mesure d'utiliser pleinement la puissance de Java EE ainsi que Spring. Rien ne nous empêche d'utiliser JSF, par exemple, pour le front-end si nécessaire.

Par rapport à l'exemple d'architecture d'OP, je pense que cela peut être décrit comme ayant quatre couches principales au lieu de trois, bien qu'avec une torsion.

1
eis

J'ai travaillé sur des projets utilisant ce modèle de gestionnaire rigide. Historiquement, j’étais un fervent partisan de la hiérarchie rigide où tout rentre dans une boîte soignée. Au fur et à mesure que je progresse dans ma carrière, je le trouve forcé dans de nombreux cas. Je crois que l'adoption d'un état d'esprit plus agile envers la conception d'applications conduit à un meilleur produit. Ce que je veux dire par cela crée un ensemble de classes qui résolvent le problème. Plutôt que de dire "Avez-vous construit un manager pour ceci et cela?"

Le projet en cours sur lequel je travaille est une application Web associant les appels Spring MVC et RestEasy JSON/Ajax. Sur le côté serveur, nos contrôleurs incluent un niveau de données basé sur une façade sensible avec JPA/Hibernate pour un accès direct à la base de données, un accès EJB et certains appels de services Web basés sur SOAP). un code de contrôleur personnalisé Java qui détermine ce qu'il faut sérialiser en tant que JSON et le retourner au client.

Nous ne passons presque pas de temps à essayer de créer un modèle unifié au lieu d’adopter l’idée "Pire est mieux" de la philosophie de conception Unix. Étant donné qu'il est bien préférable de colorer en dehors des lignes et de construire quelque chose de sensé, rapidement, plutôt que de construire quelque chose qui respecte un ensemble de mandats de conception stricts.

0
nsfyn55

Les composants de Web Application Architecture comprennent:

1: Navigateur: interaction client

        HTML
        JavaScript
        Stylesheet

2: Internet

3: serveur Web

        CSS
        Image
        Pages(Java render )

4: serveur d'application

        App Webapp (Java interaction)
        Others WebApps

5: serveur de base de données

        Oracle, SQL, MySQL

6: données

0
iCrazybest