耐心無止境 成功一瞬間

          BlogJava 聯(lián)系 聚合 管理
            31 Posts :: 5 Stories :: 25 Comments :: 0 Trackbacks
          本文描述了一個用Java編寫的不使用專門SOAP庫的簡單通用SOAP客戶機(jī)。該客戶機(jī)可以讓您用任何 XML 編輯器(或文本編輯器)創(chuàng)建自己的請求, 而不是在暗中為您創(chuàng)建 SOAP 請求 XML 文檔。 該客戶機(jī)向您顯示實(shí)際的 SOAP 響應(yīng) XML 文檔,而不是僅僅提供遠(yuǎn)程方法的返回值。 這個簡短的 Java 程序精確顯示了什么是 SOAP:打開 HTTP 連接、發(fā)送適當(dāng) XML 以調(diào)用遠(yuǎn)程方法、接著讀取服務(wù)器返回的 XML 響應(yīng)。


          通用 Java SOAP 客戶機(jī)


          SOAP(簡單對象訪問協(xié)議)是 IBM、Microsoft、DevelopMentor 和 UserLand Software 為在網(wǎng)絡(luò)上交換信息而開發(fā)的一種已在發(fā)展的 W3C 標(biāo)準(zhǔn)。 隨著Web上可以公開使用的SOAP服務(wù)器的不斷增加,SOAP幾乎對用任何語言編寫的程序——即使是用流行的簡單語言(如 Visual Basic、JavaScript 和 perl)編寫的非常短小的程序——執(zhí)行著HTML對Web瀏覽器所做的事:它為這些程序提供一個簡單的方法來利用萬維網(wǎng)上不斷增加的可用信息源。

          與 HTML 類似,SOAP 提供一套標(biāo)記來表示在Web上使用HTTP傳輸協(xié)議(從 SOAP 1.1 以來,SMTP 也可以)發(fā)送的不同信息塊的作用。但是,SOAP向您提供的能力遠(yuǎn)遠(yuǎn)強(qiáng)于HTML。使用SOAP,您的程序向 SOAP服務(wù)器發(fā)送“SOAP請求”(一個簡短的XML文檔,描述在遠(yuǎn)程機(jī)器上要調(diào)用的方法和所有要傳遞給它的參數(shù))。SOAP服務(wù)器將嘗試用那些參數(shù)執(zhí)行該方法,并將SOAP響應(yīng)發(fā)回程序。響應(yīng)可以是執(zhí)行的結(jié)果,也可以是相應(yīng)的錯誤消息。可以使用公共SOAP服務(wù)器為提出請求的客戶機(jī)提供股票價格、最新的貨幣兌換率、FedEx 包裹跟蹤信息、代數(shù)表達(dá)式的解決方案以及其它各類信息。

          在SOAP存在之前,嘗試使用這種信息的程序必須先捕獲Web頁面,然后“刮下”HTML,以查找適當(dāng)?shù)奈谋尽?對這些Web頁面進(jìn)行可視的重新設(shè)計(jì)(例如,將當(dāng)前股票價格放到表中第三列而不是第二列中)就可以使這些程序無用。SOAP規(guī)范以及它所攜帶的簡要的SOAP請求和響應(yīng)模式為客戶機(jī)和服務(wù)器之間的聯(lián)絡(luò)提供了一個框架,該框架是那些強(qiáng)健得多的信息收集工具的基礎(chǔ)。

          有許多SOAP客戶機(jī)可用于大多數(shù)的流行編程語言;有關(guān)詳盡列表,請參閱 SOAP::Lite for Perl 主頁上的 SOAP Toolkits 部分(請參閱參考資料)。大多數(shù) SOAP 客戶機(jī)都提供類庫、COM 對象或從您自己程序調(diào)用的等同對象。通常,使用這些客戶機(jī)庫遵循以下模式:

          · 程序傳遞要調(diào)用的遠(yuǎn)程方法的名稱和所有必需參數(shù)。

          · 庫組裝 SOAP 請求的適當(dāng) XML 文檔以將這一信息打包。

          · 庫將這一 XML 文檔傳遞給 SOAP 端點(diǎn) URL 標(biāo)識的 SOAP 服務(wù)器,這與通過指定服務(wù)器的 URL 將瀏覽器指向 Web 服務(wù)器地址很類似。

          · SOAP 服務(wù)器嘗試執(zhí)行方法后,它組裝包含執(zhí)行結(jié)果的 SOAP 響應(yīng) XML 文檔,并將它發(fā)回 SOAP 客戶機(jī)。

          · 接收SOAP響應(yīng)時,客戶機(jī)庫對XML進(jìn)行語法分析以獲得方法調(diào)用的結(jié)果,并將結(jié)果傳遞給使用庫的程序。


          SOAPClient4XG


          SOAP 的介紹(請參閱 developerWorks 上 Graham Glass 編寫得極佳的“ Web 服務(wù)革命”專欄)總是討論用于 SOAP 請求和響應(yīng)的 XML 的結(jié)構(gòu),但是我接觸到的 SOAP 客戶機(jī)總是會暗中進(jìn)行 XML 組裝和語法分析,所以我從來不用知道。 作為使用 XML 的人員,我曾想自己執(zhí)行 XML 部分;我認(rèn)為如果 SOAP 這樣簡單,那么我應(yīng)該能夠編寫一個簡單的 SOAP 客戶機(jī)來讀取 SOAP 請求的 XML 文檔、將它發(fā)送到命令行上指定的 SOAP 端點(diǎn) URL、讀回響應(yīng)文檔并輸出該響應(yīng)。這將使它成為一個真正的通用 SOAP 客戶機(jī),因?yàn)樗{(diào)用任何 SOAP 服務(wù)器上的任何方法。

          清單1中顯示的 SoapClient4XG(“SOAP Client for XML Geeks”)Java類執(zhí)行該任務(wù),而不使用早先提到的 SOAP Toolkits 頁面上列出的任何專用 Java SOAP 類(請參閱參考資料)。 檢查了必需的 SOAP 端點(diǎn) URL 和 SOAP XML 文檔文件名參數(shù)及可選的 SOAP 操作參數(shù)后,讀入文件,將它發(fā)送到 SOAP 服務(wù)器,讀回響應(yīng),然后將其輸出到標(biāo)準(zhǔn)出口。

          清單1

          Listing 1. The complete SOAP client
          /**
          * SOAPClient4XG. Read the SOAP envelope file passed as the second
          * parameter, pass it to the SOAP endpoint passed as the first parameter, and
          * print out the SOAP envelope passed as a response.  with help from Michael
          * Brennan 03/09/01
          *
          *
          * @author  Bob DuCharme
          * @version 1.1
          * @param   SOAPUrl      URL of SOAP Endpoint to send request.
          * @param   xmlFile2Send A file with an XML document of the request.  
          *
          * 5/23/01 revision: SOAPAction added
          */
          import java.io.*;
          import java.net.*;
          public class SOAPClient4XG {
              public static void main(String[] args) throws Exception {
                  if (args.length  < 2) {
                      System.err.println("Usage:  java SOAPClient4XG " +
                                         "http://soapURL soapEnvelopefile.xml" +
                                         " [SOAPAction]");
                                          System.err.println("SOAPAction is optional.");
                      System.exit(1);
                  }
                  String SOAPUrl      = args[0];
                  String xmlFile2Send = args[1];
                            String SOAPAction = "";
                  if (args.length  > 2)
                                          SOAPAction = args[2];
                  // Create the connection where we&#39;re going to send the file.
                  URL url = new URL(SOAPUrl);
                  URLConnection connection = url.openConnection();
                  HttpURLConnection httpConn = (HttpURLConnection) connection;
                  // Open the input file. After we copy it to a byte array, we can see
                  // how big it is so that we can set the HTTP Cotent-Length
                  // property. (See complete e-mail below for more on this.)
                  FileInputStream fin = new FileInputStream(xmlFile2Send);
                  ByteArrayOutputStream bout = new ByteArrayOutputStream();    
                  // Copy the SOAP file to the open connection.
                  copy(fin,bout);
                  fin.close();
                  byte[] b = bout.toByteArray();
                  // Set the appropriate HTTP parameters.
                  httpConn.setRequestProperty( "Content-Length",
                                               String.valueOf( b.length ) );
                  httpConn.setRequestProperty("Content-Type","text/xml; charset=utf-8");
                            httpConn.setRequestProperty("SOAPAction",SOAPAction);
                  httpConn.setRequestMethod( "POST" );
                  httpConn.setDoOutput(true);
                  httpConn.setDoInput(true);
                  // Everything&#39;s set up; send the XML that was read in to b.
                  OutputStream out = httpConn.getOutputStream();
                  out.write( b );    
                  out.close();
                  // Read the response and write it to standard out.
                  InputStreamReader isr =
                      new InputStreamReader(httpConn.getInputStream());
                  BufferedReader in = new BufferedReader(isr);
                  String inputLine;
                  while ((inputLine = in.readLine()) != null)
                      System.out.println(inputLine);
                  in.close();
              }
            // copy method from From E.R. Harold&#39;s book "Java I/O"
            public static void copy(InputStream in, OutputStream out)
             throws IOException {
              // do not allow other threads to read from the
              // input or write to the output while copying is
              // taking place
              synchronized (in) {
                synchronized (out) {
                  byte[] buffer = new byte[256];
                  while (true) {
                    int bytesRead = in.read(buffer);
                    if (bytesRead == -1) break;
                    out.write(buffer, 0, bytesRead);
                  }
                }
              }
            }
          }


          posted on 2005-10-28 13:26 Joshua Yan 閱讀(587) 評論(0)  編輯  收藏 所屬分類: JavaWeb
          主站蜘蛛池模板: 石景山区| 弥勒县| 香港| 阜平县| 镇安县| 汉沽区| 广汉市| 临澧县| 宜宾市| 闽侯县| 虹口区| 高邑县| 黄陵县| 合川市| 木兰县| 青龙| 治县。| 乌兰察布市| 温泉县| 常熟市| 巴塘县| 温宿县| 靖江市| 长垣县| 电白县| 星座| 突泉县| 宜黄县| 福安市| 高要市| 重庆市| 玉树县| 军事| 昌吉市| 乡城县| 临沭县| 北宁市| 葵青区| 桃江县| 霍城县| 德庆县|