java ee EJB中的服务层和dao层
Posted
技术标签:
【中文标题】java ee EJB中的服务层和dao层【英文标题】:Service layer and dao layer in java ee EJBs 【发布时间】:2014-08-15 12:39:16 【问题描述】:问题:任何人都可以在 Java EE 和 EJB 的上下文中展示具有两种不同方法的特定 DAO 类(或多个)。以及一个在一个事务边界中调用这两种方法并进行回滚的服务类?
我有一个 EJB,但我想将它用作服务层,就像在 spring @Transactional 方法中一样。
1) 这是个好主意吗?
2) 如何在一种方法中的一个“事务”中调用多个 dao 方法?我想我必须对 transaction.begin() 和 .提交()?任何人都可以显示一个代码示例吗?
一些主要优点是:
a- 所有小的不可变 DAO 事务都将在建立的单个数据库连接中“一次性”提交(single transactional boundries
)
b- 如果说我在服务器中有 4 个 dao 调用,而第三个调用失败,因为它是一个事务边界,我可以做 roll backs
。
c- 我的immutable DAO methods
在许多其他地方将是re-usable
。
Java EE 示例:
import com.....entities.Users;
import javax.ejb.Stateless;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;
@Stateless
public class UsersBean
// Add business logic below. (Right-click in editor and choose
// "Insert Code > Add Business Method")
public Users sayHello()
EntityManagerFactory emf = Persistence.createEntityManagerFactory("CommunityPU");
EntityManager em = emf.createEntityManager();
Users user = em.find(Users.class, 1);
em.close();
emf.close();
return user;
对比春天:
@Controller
class MyControllerClass
@RequestMapping...
method()
ServiceCall()...
//put something to modelAndView object here and redirect to jsp page.
return "home"; // this will redirect data to home.jsp
//Service class /////////
@Service
class MyServiceClass
@Transactional
SomeServiceMethod()
DaoMethod();
SomeMoreDaoMethods();
//Dao class ////////
@Autowired
EntityManager em;
@Repository
class MyDaoClass
DaoMethdon()em.find(...)
/view/myjsps.jsp path to view directory set in spring.xml
编辑 - 1(交叉问题以进一步澄清答案)
1) DAO
本身会是EJB
吗?或 EJBs
是严格的 service layers
调用其他 immutable dao methods
(位于 dao 类中)。
2) 我们不会在EJBs
中使用entitymanager
,而是在Daos
中使用。正确的?
3) 使用@Transactional
怎么样(直到Java EE 7 只有EJB,其中事务性和@Transactional 注释不存在。)或@TransactionAttribute
。
4) 如果我们使用非@stateless 会怎样。那么它不会在一个事务边界中管理 daos 而不使用回滚?
RND 链接:
https://***.com/a/17840851
http://docs.oracle.com/javaee/5/tutorial/doc/bncij.html
【问题讨论】:
【参考方案1】:是个好主意吗?
是的。基本上,这就是 EJB 的用途。
如何在一个方法中的一个“事务”中调用多个 dao 方法?
你就去做吧:
@Stateless
public class MyService
@Inject
private FirstDao firstDao;
@Inject
private SecondDao secondDao;
// stateless EJBs are transactional by defaults.
public void doStuff()
firstDao.doSomething();
secondDao.doSomethingElse();
默认情况下,EJB 是事务性的。您不需要以编程方式启动和提交事务。容器会为您执行此操作:如果 2 个 DAO 调用中的任何一个引发运行时异常,则事务将回滚。否则,它将提交。
还请注意,您的服务 EJB 不应使用实体管理器。这就是 DAO 的用途:处理持久性。所以 DAO 应该是使用实体管理器的那个:
public class FirstDao
@PersistenceContext
private EntityManager em;
...
关于你最后的问题:
-
DAO 本身可以是 EJB,但这不是必需的,因为事务通常由服务层划分。
我已经回答过了。当然 Data 访问对象是必须使用 EntityManager 的对象,因为它们的工作是处理持久性,而 EntityManager 用于访问数据库。
按照您想要的方式进行操作。重要的是您的服务应该是事务性的,无论您以何种方式使它们具有事务性。引入了事务性以消除对 EJB 的需求并具有事务性 CDI bean。如果你喜欢这样,那很好。
小提示:不可变方法没有意义。某物(如对象)在其状态永不改变时是不可变的。方法没有状态。
【讨论】:
+1 谢谢,我得到你的观点超过 90%。请参阅编辑 -1 了解我的交叉问题。 肯定假设我总是使用 EJB,所以第 3 点 @Traansactional 在这里无效?我也加了4个。最后,我所说的不可变是指那些不能进一步分解的方法/动作。例如getUserById(id)return em.find(user.class, id);
你真的应该阅读答案。正如我在回答中所说的那样:默认情况下 EJB 是事务性的。我还说过:引入事务是为了消除对 EJB 的需求并拥有事务 CDI bean。你的第4点没有意义。如果您不使用@Stateless
,那么您将不再定义 EJB。
我阅读了答案,这是一个很好的答案。对于第 4 点)还有其他类型的 EJB。 @Stateless @Statefull , singleton
等
它们都是 EJB。我的回答是:默认情况下 EJB 是事务性的。基本上每个 EJB 教程(和规范)都涵盖了这一点。读一读。以上是关于java ee EJB中的服务层和dao层的主要内容,如果未能解决你的问题,请参考以下文章