DataProvider

2024-03-07 18:26 更新

DataProvider用于從Server端轉(zhuǎn)載數(shù)據(jù)到瀏覽器中,包含異步和同步兩種執(zhí)行模式。

Pure Client

在Pure Client的開發(fā)模式中,我們主要需要關(guān)注的是Dorado.AjaxDataProvider這個類。該類內(nèi)部通過Dorado的Ajax引擎向服務(wù)端請求數(shù)據(jù),返回的數(shù)據(jù)格式默認應(yīng)為JSON形式。 下面的命令定義了一個DataSet,同時設(shè)置該DataSet通過AjaxDataProvider來提取數(shù)據(jù),數(shù)據(jù)事實上被保存在服務(wù)端data/phones.js文件中。

  1. var dataSet = new Dorado.widget.DataSet({
  2. dataProvider: new Dorado.AjaxDataProvider("data/phones.js"),
  3. dataType: "Phone"
  4. });

Dorado.AjaxDataProvider在發(fā)送Ajax請求時往往還會在請求中附帶一些其他的信息,這取決與相應(yīng)DataSet和DataType的設(shè)置。 例如我們?yōu)镈ataSet的parameter屬性定義了內(nèi)容,或者我們聲明了DataSet按照分頁的方式裝載數(shù)據(jù)。那么這些額外的參數(shù)和分頁的信息都會附帶在請求中被一同發(fā)送到服務(wù)器端。目前AjaxDataProvider所支持的額外信息包括:

  • parameter - 一組額外的屬性。一般是通過DataSet的parameter屬性定義的。
  • pageSize - 數(shù)據(jù)分頁裝載時每頁的記錄數(shù)。如果不支持數(shù)據(jù)分頁裝載,此參數(shù)將是0。
  • pageNo - 數(shù)據(jù)分頁裝載時當前請求的頁號。

Dorado.AjaxDataProvider默認以POST方式發(fā)起請求,同時將上述的這些額外信息放置在POST請求的content中。這樣,我們在服務(wù)器端必須擁有一些相應(yīng)的支持才能讀到這些JSON信息。以Java為例,下面給出了一個可以解析并得到這些JSON信息的Servlet的實例。

  1. import java.io.IOException;
  2. import javax.servlet.ServletException;
  3. import javax.servlet.ServletInputStream;
  4. import javax.servlet.http.HttpServlet;
  5. import javax.servlet.http.HttpServletRequest;
  6. import javax.servlet.http.HttpServletResponse;
  7. import net.sf.json.JSONObject;
  8. public class ExampleServiceServlet extends HttpServlet {
  9. private static final String JAVASCRIPT_TOKEN = "javascript";
  10. private static final int BUFFER_SIZE = 4096;
  11. protected void doPost(HttpServletRequest request,
  12. HttpServletResponse response) throws ServletException, IOException {
  13. ServletInputStream in = request.getInputStream();
  14. try {
  15. String contentType = request.getContentType();
  16. if (contentType.contains(JAVASCRIPT_TOKEN)) { // 判斷contentType以確認客戶端是否是以JSON的信息發(fā)送POST信息
  17. StringBuffer buf = new StringBuffer();
  18. byte[] b = new byte[BUFFER_SIZE];
  19. for (int n; (n = in.read(b)) != -1;) {
  20. buf.append(new String(b, 0, n));
  21. }
  22. JSONObject json = JSONObject.fromObject(buf.toString()); // 利用JSONObject工具類解析并得到了客戶端發(fā)送的JSON信息
  23. // 此處就可以利用這些JSON信息編寫自己的業(yè)務(wù)邏輯了
  24. }
  25. }
  26. finally {
  27. in.close();
  28. }
  29. }
  30. }

當然,在有些情況下我們可以希望自己來定義這些額外的信息應(yīng)該如何被傳遞到Server。這時最好的辦法就是派生出一個新的DataProvider,并且復(fù)寫其中的getLoadOptions方法。 假設(shè)我們希望將parameter中的個參數(shù)以及pageSize、pageNo全部放到請求的URL參數(shù)中,那么我們可以這樣來定義派生類:

  1. Dorado.MyDataProvider = $extend(Dorado.AjaxDataProvider, {
  2. getLoadOptions: function(arg) {
  3. /* 調(diào)用父類中的處理邏輯
  4. * 由于我們知道原先的邏輯將額外數(shù)據(jù)都放置在jsonData中。因此我們可以從返回的options的jsonData屬性中取得這些信息。
  5. */
  6. var options = $invokeSuper.call(this, arguments);
  7. var jsonData = options.jsonData;
  8. var parameter = Dorado.Object.apply({}, jsonData.parameter); // 將jsonData中定義的子屬性復(fù)制到parameter中
  9. parameter.pageSize = jsonData.pageSize; // 將pageSize設(shè)置到parameter中
  10. parameter.pageNo = jsonData.pageNo; // 將pageNo設(shè)置到parameter中
  11. options.parameter = parameter;
  12. delete options.jsonData; // 清除原先的jsonData
  13. return options;
  14. }
  15. });

非Pure Client模式

該模式是指和dorado服務(wù)端的代碼整合開發(fā)的場景。在這種場景下,后臺的Ajax請求是由dorado后端的攔截器攔截并轉(zhuǎn)發(fā)請求的。 在這種模式下我們可以在view設(shè)計器的model節(jié)點下看到多種類型的DataProvider: 其中最常用的是DirectDataProvider。 例如我們在Java后臺通過annotation技術(shù)定義了一個DataProvider:

  1. @Component
  2. public class SimpleCRUD {
  3. @Resource
  4. private ProductDao productDao;
  5. @DataProvider
  6. public Collection<Product> getAll() throws Exception {
  7. return productDao.getAll();
  8. }
  9. ...

接下來就可以在model中添加一個DirectDataProvider,并設(shè)置其interceptor屬性: 這樣這個Provider就知道通過interceptor攔截器去獲取數(shù)據(jù)。 該處使用的是spring:的表達式,表示要從后臺的spring服務(wù)中獲取beanId為simpleCRUD的對象中通過getAll方法獲取數(shù)據(jù)。 設(shè)置好之后我們再設(shè)置DataSet的dataProvider為這個自定義的dataProvider即完成了DataProvider的定義和使用。 當然在日常使用中,可以再度簡化這個開發(fā)過程,在view中我們可以不用添加DirectDataProvider對象。而是直接在DataSet的dataProvider對象上定義: 這種方式會在dorado的內(nèi)部自動創(chuàng)建DirectDataProvider對象,這種使用方式更為簡潔一些。 當然你在dorado的sample-center中還能看到這種定義方式: 看,這個地方連spring的id都可以省略。這是基于約定由于配置的一種使用方式,即假設(shè)當前View的名稱和對應(yīng)Spring的id的名稱一樣的情況下,例如本例view的名稱為SimpleCRUD.view.xml,而對應(yīng)的服務(wù)bean的名稱為"simpleCURD",這種情況下我們就可以直接省略dataProvider屬性配置中beanId的編寫,直接寫#+對應(yīng)的方法名就可以。

以上內(nèi)容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號