The NoteBook of EricKong

            BlogJava :: 首頁 :: 聯系 :: 聚合  :: 管理
            611 Posts :: 1 Stories :: 190 Comments :: 0 Trackbacks

          #

          要想成功訪問 SQL Server 數據庫中的數據, 我們需要兩個方面的授權:一、獲得準許連接 SQL Server 服務器的權利; 二、獲得訪問特定數據庫中數據的權利(select, update, delete, create table ...)。 假設,我們準備建立一個 dba 數據庫帳戶,用來管理數據庫 mydb。

          1. 首先在 SQL Server 服務器級別,創建登陸帳戶(create login)

          create login dba with password='sqlstudy', default_database=mydb

          登陸帳戶名為:“dba”,登陸密碼:“sqlstudy”,默認連接到的數據庫:“mydb”。 這時候,dba 帳戶就可以連接到 SQL Server 服務器上了。但是此時還不能 訪問數據庫中的對象(嚴格的說,此時 dba 帳戶默認是 guest 數據庫用戶身份, 可以訪問 guest 能夠訪問的數據庫對象)。

          要使 dba 帳戶能夠在 mydb 數據庫中訪問自己需要的對象, 需要在數據庫 mydb 中建立一個“數據庫用戶”,賦予這個“數據庫用戶” 某些訪問權限,并且把登陸帳戶“dba” 和這個“數據庫用戶” 映射起來。 習慣上,“數據庫用戶” 的名字和 “登陸帳戶”的名字相同,即:“dba”。 創建“數據庫用戶”和建立映射關系只需要一步即可完成:

          2. 創建數據庫用戶(create user):

          create user dba for login dba with default_schema=dbo

          并指定數據庫用戶“dba” 的默認 schema 是“dbo”。這意味著 用戶“dba” 在執行“select * from t”,實際上執行的是 “select * from dbo.t”。

          3. 通過加入數據庫角色,賦予數據庫用戶“dba”權限:

          exec sp_addrolemember 'db_owner', 'dba'

          此時,dba 就可以全權管理數據庫 mydb 中的對象了。

          如果想讓 SQL Server 登陸帳戶“dba”訪問多個數據庫,比如 mydb2。 可以讓 sa 執行下面的語句:

          use mydb2
          go

          create user dba for login dba with default_schema=dbo
          go

          exec sp_addrolemember 'db_owner', 'dba'
          go

          此時,dba 就可以有兩個數據庫 mydb, mydb2 的管理權限了!

          4. 禁用、啟用登陸帳戶:

          alter login dba disable
          alter login dba enable

          5. 登陸帳戶改名:

          alter login dba with name=dba_tom

          提示:在 SQL Server 2005 中也可以給 sa 改名。 《SQL Server 2005 安全性增強:給超級用戶 sa 改名》

          6. 登陸帳戶改密碼:

          alter login dba with password='sqlstudy.com'

          7. 數據庫用戶改名:

          alter user dba with name=dba_tom

          8. 更改數據庫用戶 defult_schema:

          alter user dba with default_schema=sales

          9. 刪除數據庫用戶:

          drop user dba

          10. 刪除 SQL Server登陸帳戶:

          drop login dba
          posted @ 2010-06-28 21:56 Eric_jiang 閱讀(554) | 評論 (0)編輯 收藏

          其實這個異常寫的非常之清楚,就是會話關閉,無法對Hibernate實體進行操作。造成這樣的情況有很多,什么書寫錯誤啊,邏輯錯誤 啊,等等.不過,偶是因為LAZY.

          關 于lazy機制:

          延遲初始化錯誤是運用Hibernate開發項目時最常見的錯誤。如果對一個類或者集合配置了延遲檢 索策略,那么必須當代理類實例或代理集合處于持久化狀態(即處于Session范圍內)時,才能初始化它。如果在游離狀態時才初始化它,就會產生延遲初始 化錯誤。

          下面把Customer.hbm.xml文件的<class>元素的lazy屬性設為true,表示使用延遲檢索策略:

          <class name="mypack.Customer" table="CUSTOMERS" lazy="true">

          當執行Session的load()方法時,Hibernate不會立即執行查詢CUSTOMERS表的select語句,僅僅返回 Customer類的代理類的實例,這個代理類具由以下特征:

          (1) 由Hibernate在運行時動態生成,它擴展了Customer類,因此它繼承了Customer類的所有屬性和方法,但它的實現對于應用程序是透明 的。
          (2) 當Hibernate創建Customer代理類實例時,僅僅初始化了它的OID屬性,其他屬性都為null,因此這個代理類實例占用的內存很少。
          (3)當應用程序第一次訪問Customer代理類實例時(例如調用customer.getXXX()或customer.setXXX()方法), Hibernate會初始化代理類實例,在初始化過程中執行select語句,真正從數據庫中加載Customer對象的所有數據。但有個例外,那就是當 應用程序訪問Customer代理類實例的getId()方法時,Hibernate不會初始化代理類實例,因為在創建代理類實例時OID就存在了,不必 到數據庫中去查詢。

          提示:Hibernate采用CGLIB工具來生成持久化類的代理類。CGLIB是一個功能強大的Java字節碼生成工具,它能夠在程 序運行時動態生成擴展 Java類或者實現Java接口的代理類。關于CGLIB的更多知識,請參考:

          http://cglib.sourceforge.net/。

          以下代碼先通過Session的load()方法加載Customer對象,然后訪問它的name屬性:

          tx = session.beginTransaction();
          Customer customer=(Customer)session.load(Customer.class,new Long(1));
          customer.getName();
          tx.commit();

          在運行session.load()方法時Hibernate不執行任何select語句,僅僅返回Customer類的代理類的實 例,它的OID為1,這是由load()方法的第二個參數指定的。當應用程序調用customer.getName()方法時,Hibernate會初始 化Customer代理類實例,從數據庫中加載Customer對象的數據,執行以下select語句:

          select * from CUSTOMERS where ID=1;
          select * from ORDERS where CUSTOMER_ID=1;

          當<class>元素的lazy屬性為true,會影響Session的load()方法的各種運行時行為,下面舉例說 明。

          1.如果加載的Customer對象在數據庫中不存在,Session的load()方法不會拋出異常,只有當運行 customer.getName()方法時才會拋出以下異常:

          ERROR LazyInitializer:63 - Exception initializing proxy
          net.sf.hibernate.ObjectNotFoundException: No row with the given identifier exists: 1, of class:
          mypack.Customer

          2.如果在整個Session范圍內,應用程序沒有訪問過Customer對象,那么Customer代理類的實例一直不會被初始 化,Hibernate不會執行任何select語句。以下代碼試圖在關閉Session后訪問Customer游離對象:

          tx = session.beginTransaction();
          Customer customer=(Customer)session.load(Customer.class,new Long(1));
          tx.commit();
          session.close();
          customer.getName();

          由于引用變量customer引用的Customer代理類的實例在Session范圍內始終沒有被初始化,因此在執行 customer.getName()方法時,Hibernate會拋出以下異常:

          ERROR LazyInitializer:63 - Exception initializing proxy
          net.sf.hibernate.HibernateException: Could not initialize proxy - the owning Session was closed

          由此可見,Customer代理類的實例只有在當前Session范圍內才能被初始化。

          3.net.sf.hibernate.Hibernate類的initialize()靜態方法用于在Session范圍內顯式初始 化代理類實例,isInitialized()方法用于判斷代理類實例是否已經被初始化。例如:

          tx = session.beginTransaction();
          Customer customer=(Customer)session.load(Customer.class,new Long(1));
          if(!Hibernate.isInitialized(customer))
          Hibernate.initialize(customer);
          tx.commit();
          session.close();
          customer.getName();

          以上代碼在Session范圍內通過Hibernate類的initialize()方法顯式初始化了Customer代理類實例,因 此當Session關閉后,可以正常訪問Customer游離對象。

          4.當應用程序訪問代理類實例的getId()方法時,不會觸發Hibernate初始化代理類實例的行為,例如:

          tx = session.beginTransaction();
          Customer customer=(Customer)session.load(Customer.class,new Long(1));
          customer.getId();
          tx.commit();
          session.close();
          customer.getName();

          當應用程序訪問customer.getId()方法時,該方法直接返回Customer代理類實例的OID值,無需查詢數據庫。由于 引用變量 customer始終引用的是沒有被初始化的Customer代理類實例,因此當Session關閉后再執行customer.getName()方法, Hibernate會拋出以下異常:

          ERROR LazyInitializer:63 - Exception initializing proxy
          net.sf.hibernate.HibernateException: Could not initialize proxy - the owning Session was closed


          解決方法:

          由于hibernate采用了lazy=true,這樣當你用hibernate查詢時,返回實際為利用cglib增強的代理類,但其并沒有實際填 充;當你在前端,利用它來取值(getXXX)時,這時Hibernate才會到數據庫執行查詢,并填充對象,但此時如果和這個代理類相關的 session已關閉掉,就會產生種錯誤.
          在做一對多時,有時會出現"could not initialize proxy - clothe owning Session was sed,這個好像是hibernate的緩存問題.問題解決:需要在<many-to-one>里設置lazy="false". 但有可能會引發另一個異常叫

          failed to lazily initialize a collection of role: XXXXXXXX, no session or session was closed

          此異常解決方案請察看本人博客(http://hi.baidu.com/kekemao1)的Hibernate異常中的《failed to lazily initialize a collection of role異常》

          ?
          解決方法:在web.xml中加入
          <filter>
              <filter-name>hibernateFilter</filter-name>
              <filter-class>
               org.springframework.orm.hibernate3.support.OpenSessionInViewFilter
              </filter-class>
          </filter
          <filter-mapping>
              <filter-name>hibernateFilter</filter-name>
              <url-pattern>*.do</url-pattern>
          </filter-mapping>
          就可以了;

          參考了:
          Hibernate與延遲加載:

          Hibernate對象關系映射提供延遲的與非延遲的對象初始化。非延遲加載在讀取一個對象的時候會將與這個對象所有相關的其他對象一起讀取出來。 這有時會導致成百的(如果不是成千的話)select語句在讀取對象的時候執行。這個問題有時出現在使用雙向關系的時候,經常會導致整個數據庫都在初始化 的階段被讀出來了。當然,你可以不厭其煩地檢查每一個對象與其他對象的關系,并把那些最昂貴的刪除,但是到最后,我們可能會因此失去了本想在ORM工具中 獲得的便利。


          一個明顯的解決方法是使用Hibernate提供的延遲加載機制。這種初始化策略只在一個對象調用它的一對多或多對多關系時才將關系對象讀取出來。這個過 程對開發者來說是透明的,而且只進行了很少的數據庫操作請求,因此會得到比較明顯的性能提升。這項技術的一個缺陷是延遲加載技術要求一個 Hibernate會話要在對象使用的時候一直開著。這會成為通過使用DAO模式將持久層抽象出來時的一個主要問題。為了將持久化機制完全地抽象出來,所 有的數據庫邏輯,包括打開或關閉會話,都不能在應用層出現。最常見的是,一些實現了簡單接口的DAO實現類將數據庫邏輯完全封裝起來了。一種快速但是笨拙 的解決方法是放棄DAO模式,將數據庫連接邏輯加到應用層中來。這可能對一些小的應用程序有效,但是在大的系統中,這是一個嚴重的設計缺陷,妨礙了系統的 可擴展性。

          在Web層進行延遲加載

          幸運的是,Spring框架為Hibernate延遲加載與DAO模式的整合提供了一種方便的解決方法。對那些不熟悉Spring與 Hibernate集成使用的人,我不會在這里討論過多的細節,但是我建議你去了解Hibernate與Spring集成的數據訪問。以一個Web應用為 例,Spring提供了OpenSessionInViewFilter和OpenSessionInViewInterceptor。我們可以隨意選擇 一個類來實現相同的功能。兩種方法唯一的不同就在于interceptor在Spring容器中運行并被配置在web應用的上下文中,而Filter在 Spring之前運行并被配置在web.xml中。不管用哪個,他們都在請求將當前會話與當前(數據庫)線程綁定時打開Hibernate會話。一旦已綁 定到線程,這個打開了的Hibernate會話可以在DAO實現類中透明地使用。這個會話會為延遲加載數據庫中值對象的視圖保持打開狀態。一旦這個邏輯視 圖完成了,Hibernate會話會在Filter的doFilter方法或者Interceptor的postHandle方法中被關閉。下面是每個組 件的配置示例:

           

          Interceptor的配置:


          <beans>
          <bean id="urlMapping"
          class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
          <property name="interceptors">
          <list>
          <ref bean="openSessionInViewInterceptor"/>
          </list>
          </property>
          <property name="mappings">

          </bean>

          <bean name="openSessionInViewInterceptor"
          class="org.springframework.orm.hibernate.support.OpenSessionInViewInterceptor">
          <property name="sessionFactory"><ref bean="sessionFactory"/></property>
          </bean>
          </beans>

          Filter的配置


          <web-app>

          <filter>
          <filter-name>hibernateFilter</filter-name>
          <filter-class>
          org.springframework.orm.hibernate.support.OpenSessionInViewFilter
          </filter-class>
          </filter>

          <filter-mapping>
          <filter-name>hibernateFilter</filter-name>
          <url-pattern>*. spring </url-pattern>
          </filter-mapping>

          </web-app>


          實現Hibernate的Dao接口來使用打開的會話是很容易的。事實上,如果你已經使用了Spring框架來實現你的Hibernate Dao,很可能你不需要改變任何東西。方便的HibernateTemplate公用組件使訪問數據庫變成小菜一碟,而DAO接口只有通過這個組件才可以 訪問到數據庫。下面是一個示例的DAO:


          public class HibernateProductDAO extends HibernateDaoSupport implements ProductDAO {

          public Product getProduct(Integer productId) {
          return (Product)getHibernateTemplate().load(Product.class, productId);
          }

          public Integer saveProduct(Product product) {
          return (Integer) getHibernateTemplate().save(product);
          }

          public void updateProduct(Product product) {
          getHibernateTemplate().update(product);
          }
          }


          在業務邏輯層中使用延遲加載

          即使在視圖外面,Spring框架也通過使用AOP 攔截器 HibernateInterceptor來使得延遲加載變得很容易實現。這個Hibernate 攔截器透明地將調用配置在Spring應用程序上下文中的業務對象中方法的請求攔截下來,在調用方法之前打開一個Hibernate會話,然后在方法執行 完之后將會話關閉。讓我們來看一個簡單的例子,假設我們有一個接口BussinessObject:


          public     interface    BusinessObject     {
          public     void    doSomethingThatInvolvesDaos();
          }
          類BusinessObjectImpl實現了BusinessObject接口:

          public     class    BusinessObjectImpl    implements    BusinessObject     {
          public     void    doSomethingThatInvolvesDaos()     {
          //    lots of logic that calls
          //    DAO classes Which access
          //    data objects lazily 

           

          通過在Spring應用程序上下文中的一些配置,我們可以讓將調用BusinessObject的方法攔截下來,再令它的方法支持延遲加載。看看下 面的一個程序片段:

           

          <beans>
          <bean id="hibernateInterceptor" class="org.springframework.orm.hibernate.HibernateInterceptor">
          <property name="sessionFactory">
          <ref bean="sessionFactory"/>
          </property>
          </bean>
          <bean id="businessObjectTarget" class="com.acompany.BusinessObjectImpl">
          <property name="someDAO"><ref bean="someDAO"/></property>
          </bean>
          <bean id="businessObject" class="org.springframework.aop.framework.ProxyFactoryBean">
          <property name="target"><ref bean="businessObjectTarget"/></property>
          <property name="proxyInterfaces">
          <value>com.acompany.BusinessObject</value>
          </property>
          <property name="interceptorNames">
          <list>
          <value>hibernateInterceptor</value>
          </list>
          </property>
          </bean>
          </beans>

          當businessObject被調用的時候,HibernateInterceptor打開一個Hibernate會話,并將調用請求傳遞給 BusinessObjectImpl對象。當BusinessObjectImpl執行完成后,HibernateInterceptor透明地關閉了 會話。應用層的代碼不用了解任何持久層邏輯,還是實現了延遲加載。


          在單元測試中測試延遲加載

          最后,我們需要用J-Unit來測試我們的延遲加載程序。我們可以輕易地通過重寫TestCase類中的setUp和tearDown方法來實現這 個要求。我比較喜歡用這個方便的抽象類作為我所有測試類的基類。


          public abstract class MyLazyTestCase extends TestCase {

          private SessionFactory sessionFactory;
          private Session session;

          public void setUp() throws Exception {
          super.setUp();
          SessionFactory sessionFactory = (SessionFactory) getBean("sessionFactory");
          session = SessionFactoryUtils.getSession(sessionFactory, true);
          Session s = sessionFactory.openSession();
          TransactionSynchronizationManager.bindResource(sessionFactory, new SessionHolder(s));

          }

          protected Object getBean(String beanName) {
          //Code to get objects from Spring application context
          }

          public void tearDown() throws Exception {
          super.tearDown();
          SessionHolder holder = (SessionHolder) TransactionSynchronizationManager.getResource(sessionFactory);
          Session s = holder.getSession();
          s.flush();
          TransactionSynchronizationManager.unbindResource(sessionFactory);
          SessionFactoryUtils.closeSessionIfNecessary(s, sessionFactory);
          }

          posted @ 2010-06-23 23:23 Eric_jiang 閱讀(388) | 評論 (0)編輯 收藏

          今天閑來無事,把一些工具(online和client的)、常用網址、以及經驗總結等羅列出來和大家分享下。這個標題起地大了點,肯定會有很多地 方沒列到,包括類目的分法也可能考慮不周,所以還請大家積極補充指正,可以直接留言,也可以發郵件給我(sorrycc#gmail.com)。之所以加 上“大眾”兩字,因為以下資源對于高手來說可能早就很熟悉了。

          另外想提一句,工具是死的,好不好用得看你會不會用。比如Firefox、Fiddler等,除了顯而易見的功能以外,都有一些小的技巧,掌握了可 以讓你事半功倍。

          更新記錄:

          • [20081025] 第一版

          快捷導航:

          另外還搞了個Firefox插件《前端開發工 具集》,把資源整合到一個菜單下,方便查詢。數據放在線上(Google AppEngine),速度應該會有保證,更新也會比較方便哈。 

          在線工具集

          常用Firefox插件

          IE下的調試工具

          • Fiddle2 —— 非常強悍的一款http流查看工具,默認支持IE,其他瀏覽器可以設置將{Document}\Scripts\BrowserPAC.js設為代理進行 使用。Firefox下可用上述"Fiddler 開關"進行快速切換。支持插件
          • IE Developer Toolbar —— 查看元素、禁用緩存、禁用CSS\JS、Outline元素、查看生成的源碼等功能,IE8自帶了一個加強版的。
          • Microsoft Script Debugger + Companion.JS —— 調試JS用,雖然報錯還是有誤差,但是我已經滿足了。安裝順序是:Microsoft Script Debugger,Companion.JS,在"IE選項-高級"里取消禁用腳本調試
          • 多版本IE共存兩種方案:
            • IE7/8 + IE Tester —— 大眾型配置,可以基本滿足日常需要。
            • IE6 + Internet Explorer Collection —— 在IE 6用戶占絕對優勢以及IE 6神奇bug滿天飛的時代,我還是推薦這種方案,因為只有神奇的原裝IE 6,才能抵擋運營神奇的問題。另外如果還有其他機器可供支配的話,建議再裝個IE 8 + IE Tester,因為IE 8下的Developer Toolbar還是有很大改進的,調試起來會方便一些。
          • 以下三個軟件相對不重要些:

          參考手冊

          批處理工具

          IDE及其他工具

          Bookmarklet(右鍵另存)

          開發者社區及權威網站

          推薦訂閱的博客和網站(排名不分先后)

          posted @ 2010-06-23 20:23 Eric_jiang 閱讀(318) | 評論 (0)編輯 收藏

          Article PS02022586

          800A0001 Unspecified error

          Problem Description

          When uploading files with AspUpload 3.0 (and higher), the following error may be thrown by the Save method:

          Persits.Upload.1 (0x800A0001)
          Unspecified error

          Solution

          In most cases it means that your upload script uses Request.Form or Request.QueryString prior to calling Upload.Save . As a result, the BinaryRead method of the Request object fails.

          You must never use Request.Form in your upload script because the ENCTYPE="multipart/form-data" attribute of your form makes this collection unusable. Use Upload.Form instead. Remeber, however, that the Upload.Form collection is populated by a call to Upload.Save, therefore you can only use Upload.Form after a successful call to Upload.Save.



          簡單來說,就是說你使用了這個組件 就不要再使用 Request.Form or Request.QueryString 來獲取參數,都要用Upload.Form來獲取,不然就報錯這個錯
          posted @ 2010-06-22 12:07 Eric_jiang 閱讀(2333) | 評論 (0)編輯 收藏

          function openwindow(url,name,iWidth,iHeight)
          {
          var url; //轉向網頁的地址;
          var name; //網頁名稱,可為空;
          var iWidth; //彈出窗口的寬度;
          var iHeight; //彈出窗口的高度;
          var iTop = (window.screen.availHeight-30-iHeight)/2; //獲得窗口的垂直位置;
          var iLeft = (window.screen.availWidth-10-iWidth)/2; //獲得窗口的水平位置;
          window.open(url,name,'height='+iHeight+',,innerHeight='+iHeight+',width='+iWidth+',innerWidth='+iWidth+',top='+iTop+',left='+iLeft+',toolbar=no,menubar=no,scrollbars=auto,resizeable=no,location=no,status=no');
          }

          使用時調用這個函數即可。如:

          <a href="javascript:void(0);" onclick="javascript:openwindow('a.html','',400,200);">轉到a</a>

          缺點:與原窗口的大小,位置無關。

          posted @ 2010-06-21 13:39 Eric_jiang 閱讀(2167) | 評論 (1)編輯 收藏

          1.Struts2的屬性驅動.

          Struts2的屬性驅動指的是在action中JSP頁面的每一個form中的name都對應在action中有一個屬性與之對應。看下面代碼片段:

           


          <form action="register.do" name="RegisterForm" method="post">

                      Username:<input type="text" name="uname"><br>
                      Password:<input type="password" name="upass"><br>
                      Confirm: <input type="password" name="rpass"><br>
                      <input type="submit" value="Submit">

          </form>

           


          這是一個最基本的用戶注冊的表單,它有三個數據要提交: uname、upass、rpass,那么對應的Action也要有三個屬性(其實是三個屬性的setter),看register.do實際的Action定義類:

           


          package org.abu.csdn.action.user;

          import com.opensymphony.xwork2.ActionSupport;

          /**
           * Struts2屬性驅動演示用的Action
           * @author 阿布
           *
           */
          public class RegisterAction extends ActionSupport {

              private String uname;
              private String upass;
              private String rpass;

              public String getUname() {
                  return uname;
              }

              public void setUname(String uname) {
                  this.uname = uname;
              }

              public String getUpass() {
                  return upass;
              }

              public void setUpass(String upass) {
                  this.upass = upass;
              }

              public String getRpass() {
                  return rpass;
              }

              public void setRpass(String rpass) {
                  this.rpass = rpass;
              }
             
              @Override
              public String execute() throws Exception {       
                  return ActionSupport.SUCCESS;
              }

          }

           

           

          你會看到RegisterAction中的三個屬性和RegisterForm表單中的name屬性名字一模一樣,沒錯,這就是Struts2的屬性驅動,當表單提交到RegisterAction后,Struts2將會自動將根據表單的name屬性調用Action中相應的屬性setter,去自動賦值。

           


          2.Struts2的模型驅動

          Struts2的模型驅動其實和Struts1.x中的ActionForm有點類似,在Struts1.x中每一個Action都必須有一個ActionForm與之對應,而Struts2.0中,每一個Action同樣需要提供一個POJO對象,用來封裝表單屬性,看代碼:

           


          <form action="register.do" name="RegisterForm" method="post">

                      Username:<input type="text" name="uname"><br>
                      Password:<input type="password" name="upass"><br>
                      Confirm: <input type="password" name="rpass"><br>
                      <input type="submit" value="Submit">

          </form>

           


          這段表單的代碼和上面的一模一樣,就不贅述了。接下來看POJO的代碼,其實就是普通的Java Bean:

           


          package org.abu.csdn.action.user;

          import com.opensymphony.xwork2.ActionSupport;

          /**
           * Struts2屬性驅動演示用的Java Bean
           * @author 阿布
           *
           */
          public class User {

              private String uname;
              private String upass;
              private String rpass;

              public String getUname() {
                  return uname;
              }

              public void setUname(String uname) {
                  this.uname = uname;
              }

              public String getUpass() {
                  return upass;
              }

              public void setUpass(String upass) {
                  this.upass = upass;
              }

              public String getRpass() {
                  return rpass;
              }

              public void setRpass(String rpass) {
                  this.rpass = rpass;
              }
            
          }

           


          對不起,也是和屬性驅動中的例子一樣,很簡單,因為演示的都是同一個例子,只是方法不同而已,但是接下來就不一樣了,看RegisterAction代碼:

           


          package org.abu.csdn.action.user;

          import org.abu.csdn.dto.User;

          import com.opensymphony.xwork2.ActionSupport;
          import com.opensymphony.xwork2.ModelDriven;

          /**
           * Struts2模型驅動演示用的Action
           * 
           * @author 阿布
           *
           */
          public class RegisterAction extends ActionSupport implements ModelDriven<User> {

              private User user;
             
              public User getUser() {
                  return user;
              }

              public void setUser(User user) {
                  this.user = user;
              }

              @Override
              public String execute() throws Exception {       
                  return ActionSupport.SUCCESS;
              }

              // 模型驅動必須實現的方法,也是ModelDriven接口中唯一的方法
              public User getModel() {
                 
                  return user;
              }

          }

           

           

          看到沒有,和屬性驅動的Action有很大的區別,下面一一列舉:

          (1)模型驅動的Action必須實現ModelDriven接口,而且要提供相應的泛型,這里當然就是具體使用的Java Bean了。

          (2)實現ModelDriven的getModel方法,其實就是簡單的返回泛型的一個對象。

          (3)在Action提供一個泛型的私有對象,這里就是定義一個User的user對象,并提供相應的getter與setter。

          好了,上面的三件事做完之后,Action就會去自動調用User的setter將表單中的name屬性的值賦給User中的屬性。而Action的后續處理的Jsp頁面后者是Servlet就可以使用user對象了。

           

           

           

          3.到底是用屬性驅動和是模型驅動呢?

           

           

          這個問題困擾了很多Struts2的初學者,我這里提供一些建議:

          (1)請你統一整個系統中的Action使用的驅動模型,即要么都是用屬性驅動,要么都是用模型驅動。

          (2)如果你的DB中的持久層的對象與表單中的屬性都是一一對應的話,那么就使用模型驅動吧,畢竟看起來代碼要整潔得多。

          (3)如果表單的屬性不是一一對應的話,那么就應該使用屬性驅動,否則,你的系統就必須提供兩個Bean,一個對應表單提交的數據,另一個用與持久層。

           


          看上面的例子,其實密碼確認rpass是不需要放到DB中去的,而僅僅是用于校驗密碼的,不是嗎?那么如果使用模型驅動的話,就存在這個問題了,而使用屬性驅動的話又有些繁瑣,現在我們就來調整一個看我的解決方法:

           


          4.完整的例子

          (1)表單提交的JSP頁面index.jsp

          <%@ page language="java" contentType="text/html; charset=UTF-8"
              pageEncoding="UTF-8"%>
          <%@ taglib uri="/struts-tags" prefix="s"%>
          <%
              String path = request.getContextPath();
              String basePath = request.getScheme() + "://"
                      + request.getServerName() + ":" + request.getServerPort()
                      + path + "/";
          %>

          <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
          <html>
              <head>
                  <base href="<%=basePath%>">
                  <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
                  <title>CSDN首頁</title>
              </head>
              <body>
                  <s:a href="userManager/userRegister.jsp">用戶注冊</s:a>
                 
                  <form action="register.do" name="SampleForm" method="post">
                      Username:<input type="text" name="uname"><br>
                      Password:<input type="password" name="upass"><br>
                      Confirm: <input type="password" name="rpass"><br>
                      <input type="submit" value="Submit">
                  </form>
              </body>
          </html>

           


          (2)User的定義

           


          package org.abu.csdn.action.user;

          import com.opensymphony.xwork2.ActionSupport;

          /**
           * Struts2屬性驅動演示用的Java Bean
           * @author 阿布
           *
           */
          public class User {

              private String uname;
              private String upass; 

              public String getUname() {
                  return uname;
              }

              public void setUname(String uname) {
                  this.uname = uname;
              }

              public String getUpass() {
                  return upass;
              }

              public void setUpass(String upass) {
                  this.upass = upass;
              }  
            
          }

           


          (3)RegisterAction的定義

           


          package org.abu.csdn.action.user;

          import com.opensymphony.xwork2.ActionSupport;

          /**
           * Struts2屬性驅動演示用的Action
           * @author 阿布
           *
           */
          public class RegisterAction extends ActionSupport {

           

           

              // 用來給spring注入,及屬性拷貝


              private User user;

           

           

              private String uname;
              private String upass;
              private String rpass;

              public String getUname() {
                  return uname;
              }

              public void setUname(String uname) {
                  this.uname = uname;
              }

              public String getUpass() {
                  return upass;
              }

              public void setUpass(String upass) {
                  this.upass = upass;
              }

              public String getRpass() {
                  return rpass;
              }

              public void setRpass(String rpass) {
                  this.rpass = rpass;
              }
             
              @Override
              public String execute() throws Exception {

                  // 調用方法將屬性copy到user中去,便于后續的service方法


                  copyAttribute();

                  // TODO:編寫自己的user業務代碼
                  return ActionSupport.SUCCESS;
              }

           


              /**
               * 注意這是一個action全局的校驗
               */
              @Override
              public void validate() {
                  // 進行密碼的校驗
                  if (!(upass.trim()).equals((rpass.trim()))) {
                      // 注意這里addFieldError的fieldName參數必須用引號引起來,
                      // 不能這樣使用addFieldError(rpass,"XXXXXX"),而必須是addFieldError("rpass","XXXXX")
                      this.addFieldError("rpass", this
                              .getText("csdn.action.user.register.validate.verify"));
                  }
              }

           

           

           


              /**
               * 將表單屬性中需要持久化的屬性拷貝到user中去
               * @author 阿布
               *
              */
              private void copyAttributes () {

                      user.setUname(uname);

                      user.setUpass(upass);


              }


          }

           

           

           

          (4)Struts.xml配置

          <?xml version="1.0" encoding="UTF-8" ?>
          <!DOCTYPE struts PUBLIC
              "-//Apache Software Foundation//DTD Struts Configuration 2.1//EN"
              "http://struts.apache.org/dtds/struts-2.1.dtd">
          <struts>
              <package name="root" extends="struts-default" namespace="/userManager">
                  <action name="userRegister" class="org.abu.csdn.action.user.RegisterAction">
                      <result name="success">/index.jsp</result>
                      <result name="input">/userManager/userRegister.jsp</result>
                  </action>               
              </package>
          </struts>

           

           

           

          本文來自CSDN博客,轉載請標明出處:http://blog.csdn.net/csuliky/archive/2009/05/30/4226917.aspx

          posted @ 2010-06-17 21:05 Eric_jiang 閱讀(9215) | 評論 (1)編輯 收藏

          對Tomcat部署web應用的方式總結,常見的有以下四種:
           

          1,使用控制臺部署

               訪問Http://localhost:8080,并通過Tomcat Manager登錄,進入部署界面即可。

          2,利用Tomcat自動部署

               將應用程序復制到Tomcat的 webapps路徑下,Tomcat啟動時將自動加載。

          3,修改Server.xml文件部署

               用UE或EditPlus打開Tomcat位于conf/server.xml的配置文件,找到以下內容:

          Xml代碼
          <Host name="localhost" debug="0" appBase="webapps"  
                unpackWARs="true" autoDeploy="true"  
                xmlValidation="false" xmlNamespaceAware="false">  
              .....   
            
          </Host>  
           .....
             在Host之間添加如下內容:

          來源:(http://blog.sina.com.cn/s/blog_658fbfbb0100i3sa.html) - tomcat自動部署_eric_新浪博客
          Xml代碼
          <Context path="/Mywebapps" reloadable="true" docBase="d:\Mywebapps" workDir="d:\Mywebapps\emp"/>  

          path:表示訪問的路徑;如上述例子中,訪問該應用程序為:http://localhost:8080/Mywebapps

          reloadable:表示可以在運行時在classes與lib文件夾下自動加載類包

          docbase:表示應用程序的地址,注意斜杠的方向“\”

          workdir:表示緩存文件的放置地址

           

          4,增加自定義web部署文件(推薦使用,不需要重啟Tomcat)

              在Tomcat安裝目錄conf\Catalina\localhost下,里面有Tomcat自帶的三個應用,隨意復制其中的一個XML文件,然后修改 docbase指向你自己的應用程序,并把path改名,各參數參見上第三種方法。或者你也可以自己新建一個XML文件(注意此文件名將作為 Context中的path,不管文件里的path怎么設置也無效),將以下內容復制過去,修改相應路徑即可。

          Xml代碼
          <Context path="/test" docBase="F:/J2EE/yazd_war_3_0"  
                  debug="0" privileged="true" reloadable="true" >  
          </Context>  

           

                部署完畢后,通過http://localhost:8080/你的path名 就可以訪問。
           

          posted @ 2010-06-16 14:43 Eric_jiang 閱讀(3773) | 評論 (0)編輯 收藏

          <host appBase="d:/aaa">
          <Context path="/smswap" reloadable="true" docBase="D:\workspace\smswap\WebRoot"></Context>
          </host>

          我們先看appBase,這個目錄表示:
          1 這個目錄下面的子目錄將自動被部署為應用。
          2 這個目錄下面的.war文件將被自動解壓縮并部署為應用

          而docBase只是指向了你某個應用的目錄,這個可以和appBase沒有任何關系。

          總結:
          如果你想自己指定路徑,那么應該在docBase里面
          如果你想簡單,那么直接把他們復制到appBase下面就行了

          如果你把他們弄重復了,也就是2個指向了一個目錄,看上去也能運行,但你的應用下面的每個子目錄,其實是被部署為單獨的應用的。
          比如你的應用為

          myApp, 放在了
          d:\project\myApp
          里面有2個子目錄
          d:\project\myApp\images
          d:\project\myApp\js

          你可以通過
          1 設置 appBase 指向 d:\project 來讓系統自動部署
          2 你可以手工指定docBase到 d:\project\myApp
          3 如果你指定了 appBase到 d:\project\myApp 那么
          d:\project\myApp\images這個將不再是普通的子目錄,而是一個單獨的虛擬目錄,或者叫應用了。因為其被自動部署
          d:\project\myApp\js 也一樣的后果
          posted @ 2010-06-16 14:41 Eric_jiang 閱讀(26500) | 評論 (1)編輯 收藏

              cookie雖然是由一個網頁所創建,但并不只是創建cookie的網頁才能讀 取該cookie。在默認情況下,與創建cookie的網頁在同一目錄或子目錄下的所有網頁都可以讀取該cookie。但如果在這個目錄下還有子目錄,要 使在子目錄中也可以訪問,則需要使用path參數設置cookie,語法如下:
          document.cookie="name=value; path=cookieDir";
             如果要使cookie在整個網站下可用,可以將cookieDir指定為根目錄,示例如下:
          document.cookie="userId=320; path=/";
             上面所說都指的是在同一個目錄中的訪問,可是要想在不同虛擬目錄中訪問則要另外想辦法來解決這個問題。但是path不能解決在不同域中訪問cookie的 問題。在默認情況下,只有和設置cookie的網頁在同一個Web服務器的網頁才能訪問該網頁創建的cookie。但可以通過domain參數來實現對其 的控制,其語法格式如下:
          document.cookie="name=value; domain=cookieDomain";

          具體代碼如下,直接運行即可:

          設置路徑:

          <html>
          <head>
              <title>設置cookie的路徑</title>
          <script language="javascript" type="text/javascript">
             <!--

              var now=new Date();
             now.setDate(now.getDate()+1);
             var cookies="userName="+escape("哈哈")+";expires="+now.toString()+";path=/";
             document.cookie=cookies;
             document.write("cookie文件中的內容為:<br>",unescape(document.cookie));
             -->
          </script>

          </head>
          <body></body>

          </html>

          設置域:

          <html>
          <head>
              <title>設置cookie的路徑</title>
          <script language="javascript" type="text/javascript">
             <!--

             

             var now=new Date();
             now.setDate(now.getDate()+1);
             var cookies="userName="+escape("哈哈")+";expires="+now.toString()+";path=/; domain=.baidu.com";
             document.cookie=cookies;
             document.write("cookie文件中的內容為:<br>",unescape(document.cookie));
             -->
          </script>

          </head>
          <body></body>

          </html>

          posted @ 2010-06-13 15:02 Eric_jiang 閱讀(10215) | 評論 (1)編輯 收藏

          1、什么是泛域名解析? 
             
          泛域名解析是指將*.域名解析到同一IP。 
          在域名前添加任何子域名,均可訪問到所指向的WEB地址。也就是客戶的域名a.com之下所設的*.a.com全部解析到同一個IP地址上去。 
          比如客戶設b.a.com就會自已自動解析到與a.com同一個IP地址上去。 
             
          2、泛域名解析域名域名解析的區別? 
             
          泛域名解析是:*.域名解析到同一IP。 
          域名解析是:子域名.域名解析到同一IP。 
          注意:只有客戶的空間是獨立IP的時候泛域名才有意義。而域名解析則沒有此要求。 

             
          3、怎樣設置域名泛解析? 
             
          您可按以下的步驟辦理: 

          (1)用您的用戶名和密碼登陸本公司站點。 
          (2)域名管理--MYDNS功能--主機記錄列表--在域名處輸入*,在類型處選擇A,順序處不必填寫保持默認值,在指向處填寫服務器的ip地址,然后點擊“增加新紀錄”即可。
          (3)如果您需要解析2級域名的泛解析比如xxx.05.abc.com,那么在上面的域名處輸入*.05即可。 
          (4)等半個小時到1個小時您的解析就可生效(新注冊的域名24小時內生效)。 
          注:請參考MYDNS功能頁面內的使用幫助。 

          4、相關記錄說明: 
          增加IP:對應IP里只能填寫IP,不能填寫如:http://以及:881等字符。 
          修改域名DNS:該記錄輕易不要設置,如果您確實懂,您可以添加新的NS記錄。
          posted @ 2010-06-13 10:24 Eric_jiang 閱讀(372) | 評論 (0)編輯 收藏

          僅列出標題
          共57頁: First 上一頁 48 49 50 51 52 53 54 55 56 下一頁 Last 
          主站蜘蛛池模板: 泗水县| 明光市| 环江| 武冈市| 藁城市| 石楼县| 黑龙江省| 屏东县| 广昌县| 苍溪县| 和林格尔县| 泰州市| 普宁市| 西吉县| 大同市| 南昌县| 双峰县| 乐昌市| 南丰县| 青州市| 南岸区| 武冈市| 闸北区| 黑山县| 靖宇县| 和政县| 屯昌县| 韶山市| 阜阳市| 周至县| 天台县| 曲水县| 舒城县| 庄浪县| 治县。| 江安县| 沿河| 金乡县| 塔城市| 丹东市| 芜湖市|