描述您用于 Java Web 应用程序的架构?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/286846/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Describe the architecture you use for Java web applications?
提问by
Let's share Java based web application architectures!
让我们分享基于 Java 的 Web 应用程序架构!
There are lots of different architectures for web applications which are to be implemented using Java. The answers to this question may serve as a library of various web application designs with their pros and cons. While I realize that the answers will be subjective, let's try to be as objective as we can and motivate the pros and cons we list.
使用 Java 实现的 Web 应用程序有许多不同的体系结构。这个问题的答案可以作为各种 Web 应用程序设计及其优缺点的库。虽然我意识到答案将是主观的,但让我们尽量保持客观并激发我们列出的利弊。
Use the detail level you prefer for describing your architecture. For your answer to be of any value you'll at least have to describe the major technologies and ideas used in the architecture you describe. And last but not least, whenshould we use your architecture?
使用您喜欢的详细程度来描述您的架构。为了让您的答案具有任何价值,您至少必须描述您所描述的架构中使用的主要技术和想法。最后但并非最不重要的一点是,我们什么时候应该使用您的架构?
I'll start...
我会开始...
Overview of the architecture
架构概述
We use a 3-tier architecture based on open standards from Sun like Java EE, Java Persistence API, Servlet and Java Server Pages.
我们使用基于 Sun 开放标准的 3 层架构,如 Java EE、Java Persistence API、Servlet 和 Java Server Pages。
- Persistence
- Business
- Presentation
- 坚持
- 商业
- 介绍
The possible communication flows between the layers are represented by:
层间可能的通信流表示为:
Persistence <-> Business <-> Presentation
Which for example means that the presentation layer never calls or performs persistence operations, it always does it through the business layer. This architecture is meant to fulfill the demands of a high availability web application.
例如,表示层从不调用或执行持久性操作,它总是通过业务层来完成。该架构旨在满足高可用性 Web 应用程序的需求。
Persistence
坚持
Performs create, read, update and delete (CRUD) persistence operations. In our case we are using (Java Persistence API) JPA and we currently use Hibernateas our persistence provider and use its EntityManager.
执行创建、读取、更新和删除 ( CRUD) 持久性操作。在我们的例子中,我们使用(Java Persistence API)JPA,我们目前使用Hibernate作为我们的持久性提供者并使用它的 EntityManager。
This layer is divided into multiple classes, where each class deals with a certain type of entities (i.e. entities related to a shopping cart might get handled by a single persistence class) and is usedby one and only one manager.
该层分为多个类别,其中有某种类型的实体的每一类交易(涉及到购物车即实体可能是由一个单独的持久类得到处理),并使用一个且只有一个经理。
In addition this layer also stores JPA entitieswhich are things like Account
, ShoppingCart
etc.
此外,该层还存储JPA实体哪些是喜欢的东西Account
,ShoppingCart
等等。
Business
商业
All logic which is tied to the web application functionality is located in this layer. This functionality could be initiating a money transfer for a customer who wants to pay for a product on-line using her/his credit card. It could just as well be creating a new user, deleting a user or calculating the outcome of a battle in a web based game.
所有与 Web 应用程序功能相关的逻辑都位于这一层。此功能可以为想要使用她/他的信用卡在线支付产品的客户发起汇款。它也可以是创建新用户、删除用户或计算基于 Web 的游戏中的战斗结果。
This layer is divided into multiple classes and each of these classes is annotated with @Stateless
to become a Stateless Session Bean(SLSB). Each SLSB is called a managerand for instance a manager could be a class annotated as mentioned called AccountManager
.
该层分为多个类,每个类都被注解@Stateless
为无状态会话 Bean(SLSB)。每个 SLSB 被称为一个管理器,例如,一个管理器可以是一个被注释的类,称为AccountManager
.
When AccountManager
needs to perform CRUD operations it makes the appropriate calls to an instance of AccountManagerPersistence
, which is a class in the persistence layer. A rough sketch of two methods in AccountManager
could be:
当AccountManager
需要执行 CRUD 操作时,它会适当调用 的实例AccountManagerPersistence
,该实例是持久层中的一个类。两种方法的粗略草图AccountManager
可能是:
...
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
}
We use container manager transactionsso we don't have to do transaction demarcation our self's. What basically happens under the hood is we initiate a transaction when entering the SLSB method and commit it (or rollback it) immediately before exiting the method. It's an example of convention over configuration, but we haven't had a need for anything but the default, Required, yet.
我们使用容器管理器事务,所以我们不必做我们自己的事务划分。在幕后发生的事情是我们在进入 SLSB 方法时启动一个事务,并在退出方法之前立即提交(或回滚)它。这是一个约定优于配置的例子,但除了默认的Required,我们还不需要任何东西。
Here is how The Java EE 5 Tutorial from Sun explains the Required transaction attributefor Enterprise JavaBeans (EJB's):
以下是 Sun 的 Java EE 5 教程如何解释Enterprise JavaBeans (EJB)的必需事务属性:
If the client is running within a transaction and invokes the enterprise bean's method, the method executes within the client's transaction. If the client is not associated with a transaction, the container starts a new transaction before running the method.
The Required attribute is the implicit transaction attribute for all enterprise bean methods running with container-managed transaction demarcation. You typically do not set the Required attribute unless you need to override another transaction attribute. Because transaction attributes are declarative, you can easily change them later.
如果客户端在事务中运行并调用企业 bean 的方法,则该方法在客户端的事务中执行。如果客户端未与事务关联,则容器在运行该方法之前启动一个新事务。
Required 属性是使用容器管理的事务划分运行的所有企业 bean 方法的隐式事务属性。除非您需要覆盖另一个事务属性,否则您通常不会设置 Required 属性。由于事务属性是声明性的,您可以在以后轻松更改它们。
Presentation
介绍
Our presentation layer is in charge of... presentation! It's responsible for the user interface and shows information to the user by building HTML pages and receiving user input through GET and POST requests. We are currently using the old Servlet's + Java Server Pages (JSP) combination.
我们的表示层负责……表示!它负责用户界面,并通过构建 HTML 页面和通过 GET 和 POST 请求接收用户输入来向用户显示信息。我们目前使用旧的Servlet的 + Java Server Pages ( JSP) 组合。
The layer calls methods in managersof the business layer to perform operations requested by the user and to receive information to show in the web page. Sometimes the information received from the business layer are less complex types as String
's and int
egers, and at other times JPA entities.
该层调用业务层管理器中的方法来执行用户请求的操作并接收信息显示在网页中。有时从业务层接收的信息是不太复杂的类型,如String
's 和int
egers,有时是JPA 实体。
Pros and cons with the architecture
架构的优缺点
Pros
优点
- Having everything related to a specific way of doing persistence in this layer only means we can swap from using JPA into something else, without having to re-write anything in the business layer.
- It's easy for us to swap our presentation layer into something else, and it's likely that we will if we find something better.
- Letting the EJB container manage transaction boundaries is nice.
- Using Servlet's + JPA is easy (to begin with) and the technologies are widely used and implemented in lots of servers.
- Using Java EE is supposed to make it easier for us to create a high availability system with load balancingand fail over. Both of which we feel that we must have.
- 在这一层中拥有与执行持久性的特定方式相关的所有内容仅意味着我们可以从使用 JPA 转换为其他内容,而无需在业务层中重新编写任何内容。
- 我们很容易将我们的表示层换成其他东西,如果我们找到更好的东西,我们很可能会这样做。
- 让 EJB 容器管理事务边界很好。
- 使用 Servlet's + JPA 很容易(开始时),并且这些技术在许多服务器中被广泛使用和实现。
- 使用 Java EE 应该可以让我们更轻松地创建具有负载平衡和故障转移的高可用性系统。两者我们都觉得我们必须拥有。
Cons
缺点
- Using JPA you may store often used queries as named queries by using the
@NamedQuery
annotation on the JPA entity class. If you have as much as possible related to persistence in the persistence classes, as in our architecture, this will spread out the locations where you may find queries to include the JPA entities as well. It will be harder to overview persistence operations and thus harder to maintain. - We have JPA entities as part of our persistence layer. But
Account
andShoppingCart
, aren't they really business objects? It is done this way as you have to touch these classes and turn them into entities which JPA knows how to handle. - The JPA entities, which are also our business objects, are created like Data Transfer Objects (DTO's), also known as Value Objects (VO's). This results in an anemic domain modelas the business objects have no logic of their own except accessor methods. All logic is done by our managers in the business layer, which results in a more procedural programming style. It's not good object oriented design, but maybe that's not a problem? (After all object orientation isn't the only programming paradigm which has delivered results.)
- Using EJB and Java EE introduces a bit of complexity. And we can't use purely Tomcat (adding an EJB micro-container isn't purelyTomcat).
- There are lots of issues with using Servlet's + JPA. Use Google for more information about these issues.
- As the transactions are closed when exiting the business layer we can't load any information from JPA entities which is configured to be loaded from the database when it's needed (using
fetch=FetchType.LAZY
) from inside the presentation layer. It will trigger an exception. Before returning an entity containing these kinds of fields we have to be sure to call the relevant getter's. Another option is to use Java Persistence Query Language (JPQL) and do aFETCH JOIN
. However both of these options are a little bit cumbersome.
- 使用 JPA,您可以通过使用
@NamedQuery
JPA 实体类上的注释将常用查询存储为命名查询。如果您在持久性类中尽可能多地与持久性相关,就像在我们的体系结构中一样,这将分散您可能会发现查询的位置,以包括 JPA 实体。概述持久性操作将更加困难,因此更难维护。 - 我们将 JPA 实体作为持久层的一部分。但
Account
和ShoppingCart
,不是他们真正的业务对象?这样做是因为您必须接触这些类并将它们转换为 JPA 知道如何处理的实体。 - JPA 实体也是我们的业务对象,其创建方式类似于数据传输对象 ( DTO),也称为值对象 (VO)。这导致了一个贫血的域模型,因为业务对象除了访问器方法之外没有自己的逻辑。所有逻辑都由我们的业务层经理完成,这导致了更加程序化的编程风格。这不是一个好的面向对象设计,但也许这不是问题?(毕竟面向对象并不是唯一产生结果的编程范式。)
- 使用 EJB 和 Java EE 会带来一些复杂性。而且我们不能纯粹使用Tomcat(添加EJB微容器不是纯粹的Tomcat)。
- 使用 Servlet's + JPA 有很多问题。使用 Google 获取有关这些问题的更多信息。
- 由于事务在退出业务层时关闭,因此我们无法从 JPA 实体加载任何信息,这些信息被配置为在需要(使用
fetch=FetchType.LAZY
)时从表示层内部从数据库加载。它会触发异常。在返回包含这些类型字段的实体之前,我们必须确保调用相关的 getter。另一种选择是使用 Java 持久性查询语言 ( JPQL) 并执行FETCH JOIN
. 然而,这两个选项都有点麻烦。
采纳答案by Rolf
Ok I'll do a (shorter) one:
好的,我会做一个(较短的):
- Frontend : Tapestry(3 for older projects, 5 for newer projects)
- Business layer: Spring
- DAO's : Ibatis
- Database : Oracle
- 前端:Tapestry(3 个用于旧项目,5 个用于新项目)
- 业务层:Spring
- DAO 的 : Ibatis
- 数据库:甲骨文
We use Sping transaction support, and start transactions upon entering the service layer, propagating down to the DAO call's. The Service layer has the most bussines model knowledge, and the DAO's do relatively simple CRUD work.
我们使用 Sping 事务支持,并在进入服务层时启动事务,向下传播到 DAO 调用。Service 层拥有最多的业务模型知识,而 DAO 则做相对简单的 CRUD 工作。
Some more complicated query stuff is handled by more complicated queries in the backend for performance reasons.
出于性能原因,一些更复杂的查询内容由后端中更复杂的查询处理。
Advantages of using Spring in our case is that we can have country/language dependant instances, which are behind a Spring Proxy class. Based on the user in the session, the correct country/language implementation is used when doing a call.
在我们的案例中使用 Spring 的优点是我们可以拥有依赖于国家/语言的实例,这些实例位于 Spring Proxy 类之后。根据会话中的用户,拨打电话时使用正确的国家/地区/语言实现。
Transaction management is nearly transparent, rollback on runtime exceptions. We use unchecked exceptions as much as possible. We used to do checked exceptions, but with the introduction of Spring I see the benefits of unchecked exceptions, only handling exceptions when you can. It avoids a lot of boilerplate "catch/rethrow" or "throws" stuff.
事务管理几乎是透明的,运行时异常回滚。我们尽可能使用未经检查的异常。我们曾经做过受检异常,但是随着 Spring 的引入,我看到了非受检异常的好处,只有在可能的情况下才处理异常。它避免了很多样板“捕获/重新抛出”或“抛出”的东西。
Sorry it's shorter than your post, hope you find this interesting...
对不起,它比你的帖子短,希望你觉得这很有趣......
回答by Dan
We are still using the usual Struts-Spring-Hibernate stack.
我们仍然使用通常的 Struts-Spring-Hibernate 堆栈。
For future apps, we are looking into Spring Web Flow + Spring MVC + Hibernate or Spring + Hibernate + Web Services with Flex front end.
对于未来的应用程序,我们正在研究 Spring Web Flow + Spring MVC + Hibernate 或 Spring + Hibernate + Web Services with Flex 前端。
A distinct characteristic of our architecture is modularization. We have a number of modules, some starting with 3 to max 30 tables in the database. Most of modules consist of business and web project. Business project holds business and persistence logic while web holds presentation logic.
On logical level, there are three layers: Business, Persistence and Presentation.
Dependencies:
Presentation depends on Business and Persistence.
Persistence depends on Business.
Business does not depend on other layers.
我们架构的一个显着特点是模块化。我们有许多模块,有些从数据库中的 3 到最多 30 个表开始。大多数模块由业务和网络项目组成。业务项目包含业务和持久性逻辑,而 Web 包含表示逻辑。
在逻辑层面上,有三层:业务层、持久层和展示层。
依赖关系:
展示依赖于业务和持久性。
坚持取决于业务。
业务不依赖于其他层。
Most of business projects have three types of interfaces (note: not GUI, it is a programatic java interface layer).
大多数业务项目都有三种类型的接口(注意:不是GUI,它是一个程序化的java接口层)。
- Interface that presentation is using as a client
- Interface that other modules are using when they are the client of the module.
- Interface that can be used for administrative purposes of the module.
- 演示文稿用作客户端的界面
- 其他模块作为模块的客户端时使用的接口。
- 可用于模块管理目的的接口。
Often, 1 extends 2. This way, it is easy to replace one implementation of module with another. This helps us adopt to different clients and integrate more easily. Some clients will buy only certain modules and we need to integrate functionality they already have. Since interface and implementation layer are separated, it is easy to roll out ad-hock module implementation for that specific client without affecting dependant modules. And Spring Framework makes it easy to inject different implementation.
通常,1 扩展 2。这样,很容易将模块的一个实现替换为另一个。这有助于我们适应不同的客户并更轻松地集成。一些客户只会购买某些模块,我们需要集成他们已有的功能。由于接口和实现层是分离的,因此很容易为该特定客户端推出临时模块实现,而不会影响依赖模块。Spring Framework 使得注入不同的实现变得容易。
Our business layer is based on POJOs. One tendency I am observing is that these POJOs resemble DTOs. We suffer from anaemic domain model. I am not quite sure why is this happening but it can be due to simplicity of problem domain of many of our modules, most of the work is CRUD or due to developers preferring to place logic somewhere else.
我们的业务层基于 POJO。我观察到的一种趋势是这些 POJO 类似于 DTO。我们患有贫血领域模型。我不太确定为什么会发生这种情况,但这可能是由于我们的许多模块的问题域很简单,大部分工作都是 CRUD,或者是由于开发人员更喜欢将逻辑放在其他地方。
回答by Rakesh Waghela
Ideal Java Based Web Development Technologies Today.
当今理想的基于 Java 的 Web 开发技术。
Web Layer :
网页层:
HTML+CSS+Ajax+JQuery
HTML+CSS+Ajax+JQuery
RESTFul Web Controller/Action/Request Processing Layer :
RESTFul Web 控制器/动作/请求处理层:
Play Framework
游戏框架
Business Logic/Service Layer:
业务逻辑/服务层:
Use Pure Java Code as long as possible. One can do fusion of web services here.
尽可能长时间使用纯 Java 代码。可以在这里进行 Web 服务的融合。
XML/JSon Data Transformation Layer :
XML/JSon 数据转换层:
XMLTool(Search On Google Code),JSoup,Google GSon,XStream,JOOX (Search On Google Code)
XMLTool(Search On Google Code),JSoup,Google GSon,XStream,JOOX (Search On Google Code)
Persistence Layer :
持久层:
CRUD : JPA or SienaProject or QueryDSL / Complex Queries : JOOQ,QueryDSL
CRUD : JPA 或 SienaProject 或 QueryDSL / 复杂查询 : JOOQ,QueryDSL
回答by nsfyn55
I've worked on projects that use that rigid manager pattern. Historically, I was a huge proponent of the rigid hierarchy where everything fit into a neat box. As I progress in my career I find it to be forced in a lot of cases. I believe that adopting a more agile mindset towards application design leads to a better product. What I mean by this creating a set of classes that solve the problem at hand. Rather than saying "Did you build a manager for this and that?"
我从事过使用这种严格的经理模式的项目。从历史上看,我是严格等级制度的大力支持者,在这种等级制度中,所有东西都放在一个整洁的盒子里。随着我职业生涯的进步,我发现在很多情况下都是被迫的。我相信对应用程序设计采用更敏捷的思维方式会带来更好的产品。我的意思是创建一组解决手头问题的类。而不是说“你为这个和那个建立了一个经理吗?”
The current project I'm working on is a web app with a combination of Spring MVC and RestEasy JSON/Ajax calls. On the server side embedded in our controllers is a sensible facade based data tier with JPA/Hibernate for direct Database access, some EJB access, and some SOAP based web service calls. Tying all this together is some custom java controller code that determines what to serialize as JSON and return to the client.
我正在处理的当前项目是一个 Web 应用程序,它结合了 Spring MVC 和 RestEasy JSON/Ajax 调用。在我们的控制器中嵌入的服务器端是一个基于外观的合理数据层,带有 JPA/Hibernate,用于直接数据库访问、一些 EJB 访问和一些基于 SOAP 的 Web 服务调用。将所有这些结合在一起是一些自定义的 java 控制器代码,它确定将什么序列化为 JSON 并返回给客户端。
We spend almost no time attempting to create some unified pattern instead opting to adopt the "Worse is Better" idea of the Unix Design Philosophy. Being that its much better to color outside the lines and build something sensible, quickly than it is to build something that adheres to a bunch of strict design mandates.
我们几乎没有花时间尝试创建一些统一的模式,而是选择采用 Unix 设计哲学的“越糟越好”的想法。因为在线条之外着色并构建一些明智的东西比构建遵循一系列严格设计要求的东西要快得多。
回答by joshua
IMHO, most of us have a common denominator. Atleast in the back-end, we have some form of IOC/DI container and a persistence framework. Personally I use Guice and Mybatis for this. The differences are in how we implement the view/UI/presentation layer. There are 2 major options here (may be more) .. Action based (URLs mapped to controllers) and component based. Currently am using component based presentation layer (using wicket). It perfectly mimics a desktop environment where I use components and events as opposed to URLs and controllers. Am currently looking for a reason why I should migrate to this URL-controller kind of architecture (that's how I ended up on this page). Why the hype about RESTful and Stateless architectures.
恕我直言,我们大多数人都有一个共同点。至少在后端,我们有某种形式的 IOC/DI 容器和一个持久性框架。我个人为此使用 Guice 和 Mybatis。不同之处在于我们如何实现视图/UI/表示层。这里有 2 个主要选项(可能更多).. 基于动作(映射到控制器的 URL)和基于组件。目前正在使用基于组件的表示层(使用检票口)。它完美地模仿了我使用组件和事件而不是 URL 和控制器的桌面环境。我目前正在寻找我应该迁移到这种 URL 控制器架构的原因(这就是我在此页面上结束的方式)。为什么要大肆宣传 RESTful 和无状态架构。
To answer this question in short: I write stateful web applications using a component oriented framework on top of Guice IOC container and put data in relational database using Mybatis.
简而言之:我在 Guice IOC 容器之上使用面向组件的框架编写有状态的 Web 应用程序,并使用 Mybatis 将数据放入关系数据库中。
回答by eis
A bit different, and I would claim more modular java architecture here. We have:
有点不同,我会在这里声明更多的模块化 Java 架构。我们有:
- Spring WS/Rest/JSP front end
- Spring MVC for business service logic, containing presentation layer logic as well as Spring transactions
- Component service communication interface, looked up through EJB by business services. EJBs set their own transaction boundaries that are able to join Spring transactions.
- Component service implementations, again Spring components
- Integration layer, MyBatis for database integrations, Spring WS for web service integrations, other integration techonologies for other services
- Mainframes, databases, other services at other servers...
- Spring WS/Rest/JSP 前端
- Spring MVC 用于业务服务逻辑,包含表示层逻辑以及 Spring 事务
- 组件服务通信接口,业务服务通过EJB查找。EJB 设置了自己的事务边界,可以加入 Spring 事务。
- 组件服务实现,同样是 Spring 组件
- 集成层,用于数据库集成的 MyBatis,用于 Web 服务集成的 Spring WS,用于其他服务的其他集成技术
- 大型机、数据库、其他服务器上的其他服务……
In addition to the above, we have the shared library modules which is common functionality provider for all srevices.
除了上述之外,我们还有共享库模块,它是所有服务的通用功能提供者。
Use of different layers allows us full decoupling and the modularity we need. We are also able to fully utilize the power of Java EE as well as Spring. Nothing prevents us from using JSF, for example, for the front end if needed.
使用不同的层允许我们完全解耦和我们需要的模块化。我们还能够充分利用 Java EE 和 Spring 的强大功能。例如,如果需要,没有什么能阻止我们在前端使用 JSF。
Compared to example architecture by OP, I think this can be described as having four main layers instead of three, albeit with a twist.
与 OP 的示例架构相比,我认为这可以被描述为具有四个主要层而不是三个,尽管有所不同。
回答by Pepster
Here's my 5 cents
这是我的 5 美分
Presentation
介绍
Android, Angular.JS WebClient, OAUTHv2
安卓,Angular.JS WebClient,OAUTHv2
API
应用程序接口
REST, Jersey (JAX-RS), Hymanson (JSON de-/serialisation), DTO-objects (different from business logic models)
REST、Jersey (JAX-RS)、Hymanson(JSON 反序列化)、DTO 对象(不同于业务逻辑模型)
Business Logic
商业逻辑
Spring for DI and Event handling. DDD-ish approach of model objects. Longer running jobs are offloaded with SQS in worker-modules.
用于 DI 和事件处理的 Spring。模型对象的 DDD-ish 方法。在工作模块中使用 SQS 卸载运行时间较长的作业。
DAO
道
Repository model with Spring JDBC-templates to store Entities. Redis (JEDIS) for Leaderboards, using Ordered Lists. Memcache for Token Store.
带有 Spring JDBC 模板的存储库模型来存储实体。Redis (JEDIS) 用于排行榜,使用有序列表。用于令牌存储的 Memcache。
Database
数据库
MySQL, Memcached, Redis
MySQL、Memcached、Redis
回答by iCrazybest
The components in Web Application Architectureinclude :
Web 应用程序架构中的组件包括:
1 : Browser : Client interaction
1:浏览器:客户端交互
HTML
JavaScript
Stylesheet
2 : Internet
2:互联网
3 : Webserver
3:网络服务器
CSS
Image
Pages(Java render )
4 : Application Server
4:应用服务器
App Webapp (Java interaction)
Others WebApps
5 : Database Server
5:数据库服务器
Oracle, SQL, MySQL
6 : Data
6:数据
回答by Amritendu De
Here is one more web architecture I have worked on:
这是我研究过的另一种网络架构:
One major requirement was the application should support mobiles/other devices. The application should also be extensible or flexible to changes in technology choices.
一项主要要求是应用程序应支持移动设备/其他设备。应用程序还应该可扩展或灵活地适应技术选择的变化。
Presentation Tier:
演示层:
- JSP/JQuery (Client-side MVC)
- Native Android
- Native iPhone
Mobile web (HTML5/CSS3/Responsive design)
Spring REST Controllers (Can change to JAX-RS)
- JSP/JQuery(客户端 MVC)
- 原生安卓
- 原生 iPhone
移动网络(HTML5/CSS3/响应式设计)
Spring REST 控制器(可以更改为 JAX-RS)
Business Service Tier:
业务服务层:
Spring @Service (Can change to Stateless EJB)
Spring @Service(可以更改为无状态 EJB)
Data Access Tier:
数据访问层:
Spring @Repository (Can change to Stateless EJB)
Spring @Repository(可以更改为无状态 EJB)
Resource Tier:
资源层:
Hibernate(JPA) entities (Can change to any ORM)
Hibernate(JPA) 实体(可以更改为任何 ORM)
You can find more information on the book which follows this architecture here.
您可以在此处找到有关遵循此架构的书籍的更多信息。
回答by CandleCoder
What we have followed in our project is :
我们在项目中遵循的是:
Front end Technology
前端技术
- AngularJS
- HTML5
- css3
- Javascript
- Bootstrap 3
- AngularJS
- HTML5
- css3
- Javascript
- 引导程序 3
API
应用程序接口
- REST
- JERSEY (JAX-RS)
- REST ASSURED
- SPRING BOOT
- Hymanson
- spring security
- 休息
- 球衣 (JAX-RS)
- 放心
- 弹簧靴
- Hyman逊
- 弹簧安全
Business Logic
商业逻辑
SPRING DATA
SPRING data MongoDB
春季数据
春季数据MongoDB
Data base
数据库
- MongoDB
- MongoDB
Server (For caching)
服务器(用于缓存)
- redis
- Redis