我是Java EE World的新手,希望在Web应用程序中使用PostgreSQL作为我的数据库。我使用Glassfish作为我的应用程序服务器,并通过管理界面添加了一个连接池(我使用此site 求助)。现在我不知道在我的应用程序中使用连接池的“正确”方法是什么(实际上我目前还不知道如何从池中获取连接并编写简单的查询)。
我们需要编写非常复杂的查询,所以我不知道是否应该为每个表创建一个映射并使用映射,或者只是使用sql和某种行映射器来解析结果(我们使用了Spring RowMapper之前)。
所以我的问题是:
答案 0 :(得分:5)
1 - 如果使用glassfish配置连接池,您可以开发一个简单的EJB并使用注释注入连接,我认为这是处理池中连接的最佳方法。
(所有示例都与hibernate兼容,并且在postgresql数据库上运行良好)
例如:
@Stateless
public class myEjb
{
// inject the entityManager
@PersistenceContext(unitName = "myPu")
private EntityManager em;
public Car findCarById(Long carId)
{
Car aCar = (Car) em.find(Car.class, carId);
return aCar;
}
}
unitName“myPu”是在glassfish管理控制台中配置的JDBC资源的JNDI名称。
2 - 此模式的优点是它不依赖于代码,您可能无法更改有关开发,测试或生产环境的JDBC资源。 JDBC URL,用户和传递是在服务器上配置的,而不是在每次从环境切换到另一个环境时都可以仔细更改的XML文件中。这样您就不必处理事务,这是提交或回滚异常的服务器。 如果您需要自己处理事务,可以在无状态下添加注释:
@TransactionManagement(value=TransactionManagementType.BEAN)
你需要自己处理如下的交易:
em.getTransaction().begin();
try
{
// do something with the entityManager
em.getTransaction().commit();
}
catch(MyException ex)
{
em.getTransaction().rollback();
}
3 - 如果您需要创建复杂请求,您可以在您的实体上声明一些命名查询。 下面是Car实体的可能实现:
@Entity
public class Car
{
@NamedQueries(
{
@NamedQuery(name = "Car.findByBrandAndColor", query = "SELECT c FROM Car WHERE c.brand = :brand AND color = :color")
})
}
下面添加到使用上一个命名查询的EJB的函数示例:
public List<Car> findAllCarByBrandAndColor(String aBrand, String aColor)
{
List<Car> theCars;
Query theQuery = em.createNamedQuery("Car.findByBrandAndColor");
theQuery.setParameter("brand", aBrand);
theQuery.setParameter("color", aColor);
try
{
theCars = (List<Car>) query.getResultList();
}
catch(NoResultException ex)
{
theCars = null;
}
return theCars;
}
当然,您可以根据需要编写复杂的命名查询(命名查询被缓存并且可能更好地提高性能),但如果您确实需要直接查询数据库,则可以使用如下的本机查询:
// the query is native SQL
Query theQuery = em.createNativeQuery("SELECT * FROM car WHERE color = 'blue' AND brand = 'toyota'", Car.class);
Car aCar = (Car) query.getSingleResult();