| 虽然对Spring不熟悉,又不懂iBatis,而且对模式的概念还没有弄清楚,但也硬着头皮去读Spring包自带的Jpetstore经典J2EE例子。 可以肯定,Jpetstore是按照MVC模式设计的。持久化层用iBatis(这个我不懂,我希望是用Hibernate),web层控制器的servlet有两个选择,一个是用Struts,另一个是Spring的MVC。 以下是自己的阅读体会,也许分析不当或描述不清,但也算初步尝试,所以记下来了。 一,分层结构 Jpetstore使用了门面模式、单例模式,DAO模式。 1.门面模式 门面接口的实现类: PetStoreImpl public class PetStoreImpl implements PetStoreFacade, OrderService { private AccountDao accountDao; private CategoryDao categoryDao; private ProductDao productDao; private ItemDao itemDao; private OrderDao orderDao; // ---------------------------------------------------------------- // Setter methods for dependency injection // ---------------------------------------------------------------- public void setAccountDao(AccountDao accountDao) { this.accountDao = accountDao; } //省略余下的四个setter // ------------------------------------------------------------------------- // Operation methods, implementing the PetStoreFacade interface // ------------------------------------------------------------------------- public Account getAccount(String username) { return this.accountDao.getAccount(username); } public Account getAccount(String username, String password) { return this.accountDao.getAccount(username, password); } public void insertAccount(Account account) { this.accountDao.insertAccount(account); } public void updateAccount(Account account) { this.accountDao.updateAccount(account); } //省略其它的crud方法 } 暂时先不管 OrderService 这个接口。 PetStoreImpl的那些setter方法正是spring的注入方法。 在配置文件中: <bean id="petStore" class="org.springframework.samples.jpetstore.domain.logic.PetStoreImpl"> <property name="accountDao" ref="accountDao" /> <property name="categoryDao" ref="categoryDao" /> <property name="productDao" ref="productDao" /> <property name="itemDao" ref="itemDao" /> <property name="orderDao" ref="orderDao" /> </bean> 2. 单例模式 单例模式中,我们一般把类的构造方法设置为private,提供静态工厂方法给外界返回唯一的实例,但在这里,它不是这样做的,因为有了Spring。有了Spring的BeanFactory管理,可以轻易配置实现单例。看看作者的注释。 There is one instance of this class in the JPetStore application. In Spring terminology, it is a "singleton". This means a per-Application Context singleton. The factory creates a single instance; there is no need for a private constructor, static factory method etc as in the traditional implementation of the Singleton Design Pattern. 单例的PetStoreImpl 在Struts当控制器时,它这样做:为整个应用程序编写一个继承自Action的BaseAction基础类。 public abstract class BaseAction extends Action { private PetStoreFacade petStore; public void setServlet(ActionServlet actionServlet) { super.setServlet(actionServlet); if (actionServlet != null) { ServletContext servletContext = actionServlet.getServletContext(); WebApplicationContext wac = WebApplicationContextUtils .getRequiredWebApplicationContext(servletContext); this.petStore = (PetStoreFacade) wac.getBean("petStore"); } } protected PetStoreFacade getPetStore() { return petStore; } } 3.DAO模式 ORM工具用iBatis,在领域模式层使用了粗粒度对象。下面是AccountDao 的配置。 <select id="getAccountByUsername" resultMap="result"> select signon.username as userid, account.email, account.firstname, account.lastname, account.status, account.addr1, account.addr2, account.city, account.state, account.zip, account.country, account.phone, profile.langpref, profile.favcategory, profile.mylistopt, profile.banneropt, bannerdata.bannername from account, profile, signon, bannerdata where account.userid = #value# and signon.username = account.userid and profile.userid = account.userid and profile.favcategory = bannerdata.favcategory </select> |