您無法在 InfoPath 2003 中自動送出結構化 XML 資料給 Web 服務

文章翻譯 文章翻譯
文章編號: 826989 - 檢視此文章適用的產品。
全部展開 | 全部摺疊

在此頁中

徵狀

當您使用內建的 InfoPath 送出功能從 InfoPath 表單將資料送出至 Web 服務時,可能會遭遇下列其中一個徵狀:
  • 您可能會收到錯誤訊息。根據要送出之資訊以及在該 Web 服務叫用的編碼方法而定,您收到的錯誤訊息會有所不同。
  • 您可能會發現,未預期的資料被送出給 Web 服務。
本文也討論下列主題:
  • InfoPath 如何送出資料給 Web 服務。
  • 兩種送出 InfoPath 表單內容給 Web 服務的方法。

發生的原因

當 InfoPath 送出資料給 Web 服務時,會送出選做為參數之 XML 節點的內容,但不會送出 XML 節點本身。這種方法通常運作順利。例如,您的 Web 服務方法可能如下:
[WebMethod]
   public void SendSampleString( string sampleString )
   {
      //Do something interesting with the sample string.
   } 
如果您送出下列 XML 項目給這個 Web 服務方法,則 sampleString 參數會填入 Hello, World!(如您所預期)。
<sampleElement>"Hello, World!"</sampleElement>
遺憾的是,這個行為可能導致難以將 XML 節點或整個 InfoPath 表單送出給 Web 服務。例如,您的 Web 服務方法可能如下:
[WebMethod]
   public string SendXMLElement( System.Xml.XmlElement theElement )
   {
      //Report how many children the submitted node had.
      return "Node with " + theElement.ChildNodes.Count + " children submitted.";
   }
如果您使用內建的 InfoPath 送出功能將範例 XML 項目送出給此方法,則 theElement 參數的內容會產生錯誤。這個錯誤發生的原因,是因為只有 XML 項目的內容 (Hello, World!) 會傳送給 Web 服務方法。因為該字串不是有效的 XML 項目,所以 .NET Framework 會產生錯誤;錯誤訊息會顯示在 InfoPath 中。

當您嘗試送出整個 InfoPath 表單給範例 Web 服務方法時,也會發生類似的問題。在這種情況下,InfoPath 會送出 InfoPath 表單的所有子節點,但不會送出根節點。這樣會導致送出多個頂層 XML 節點。因為這也不是有效的 XML,所以 .NET Framework 會選取第一個頂層 XML 節點,並使用它做為 theElement 參數。所有其他節點則會被略過,看起來就像是這些節點都未送出。

解決方案

這個問題已經在 Microsoft Office 2003 Service Pack 1 中獲得修正。如果要解決這個問題,請取得 Microsoft Office 2003 的最新版 Service Pack。

如需詳細資訊,請按一下下面的文件編號,檢視「Microsoft 知識庫」中的文件:
870924 如何取得 Office 2003 的最新 Service Pack

其他可行方案

如果需要替代的解決方案,請在指令碼中寫入自訂的送出動作。您可以使用下列其中一種方法:
  • 使用次要資料來源來執行送出作業。
  • 撰寫程式碼,該程式碼可建立自訂的 SOAP 訊息,並將該訊息傳送給 Web 服務。

使用次要資料來源

  1. [工具] 功能表上,按一下 [次要資料來源]
  2. [次要資料來源] 對話方塊中,按一下 [新增]
  3. [資料來源安裝精靈] 的第一個頁面中,按一下 [Web 服務],然後按一下 [下一步]
  4. 輸入您要送出之 Web 服務的位置,然後按一下 [下一步]
  5. 選取您要使用的 Web 服務方法,然後按一下 [下一步]
  6. 當 InfoPath 提示您選取表單欄位或群組,以用於填入 Web 服務方法的參數時,請將參數保留空白,然後按一下 [下一步]
  7. 按一下以清除 [開啟表單時,連線到這個次要資料來源] 核取方塊,按一下 [完成],然後按一下 [確定],以關閉 [次要資料來源] 對話方塊。
  8. [工具] 功能表上,按一下 [送出表單]
  9. [送出表單] 對話方塊中,按一下 [啟用送出]
  10. [送出] 清單中,按一下 [使用自訂指令碼送出],然後按一下 [確定],以開啟 Microsoft Script Editor。
  11. XDocument::OnSubmitRequest 方法中,使用類似下列指令碼來送出整個表單。

    注意 您也可以送出該表單中的個別項目。
    try{
          //Get a reference to the SendXMLElement secondary data source.
          var objSendXMLElement = XDocument.GetDOM("SendXMLElement");
          objSendXMLElement.setProperty( "SelectionNamespaces",
             'xmlns:s1="http://joelallxp.microsoft.com/schema" ' +
             'xmlns:s0="http://tempuri.org/" ' +
             'xmlns:dfs="http://schemas.microsoft.com/office/infopath/2003/dataFormSolution"' );
     
          //Remove any data from the SendXMLElement secondary data source.
          var objData = objSendXMLElement.selectSingleNode(
             "/dfs:myFields/dfs:queryFields/s0:SendXMLElement/s0:theElement");
          var objCurrentData = objData.selectNodes("@* | node()");
          objCurrentData.removeAll();
     
          //Clone the XDocument.
          var objClonedDocument = XDocument.DOM.documentElement.cloneNode(true );
          objData.appendChild( objClonedDocument );
       
          //Call the "Query" method of the secondary data source to send the data.
          XDocument.DataObjects("SendXMLElement").Query();
       
          //Report the results of the submit.
          XDocument.UI.Alert( 
             objSendXMLElement.selectSingleNode(
                "/dfs:myFields/dfs:dataFields/s0:SendXMLElementResponse/s0:SendXMLElementResult").text );
          eventObj.ReturnStatus = true;
       }
       catch(ex)
       {
          eventObj.ReturnStatus = false;
       }

撰寫程式碼

  1. [工具] 功能表上,按一下 [送出表單]
  2. [送出表單] 對話方塊中,按一下 [啟用送出]
  3. [送出] 清單中,按一下 [使用自訂指令碼送出],然後按一下 [確定],以開啟 Microsoft Script Editor。
  4. XDocument::OnSubmitRequest 方法中,使用類似下列指令碼來送出整個表單。

    注意 您也可以送出該表單中的個別項目。
    try
       { 
          //Create a SOAP object.
          var objSOAPConnector = new ActiveXObject("MSOSOAP.HttpConnector30");
       
          //Set the EndPointURL property to point to the Web service.
          objSOAPConnector.Property("EndPointURL") = "http://server/WebService1/Submit.asmx";
     
          //Set the SoapAction property to point to the Web service method. You can find this URI 
          //in the WSDL file of the Web service.
          objSOAPConnector.Property("SoapAction") = "http://tempuri.org/SendXMLElement";
          objSOAPConnector.Connect();
          
          //Begin construction of a SOAP message to send to the Web service.
          objSOAPConnector.BeginMessage();
     
          var objSOAPSerializer = new ActiveXObject("MSOSoap.SoapSerializer30");
          objSOAPSerializer.Init( objSOAPConnector.InputStream );
          objSOAPSerializer.startEnvelope();
          objSOAPSerializer.startBody();
     
          //Construct the structure that marks the method name and the parameter name 
          //that you are sending.
          objSOAPSerializer.StartElement( "SendXMLElement", "http://tempuri.org/" );
          objSOAPSerializer.StartElement( "theNode", "http://tempuri.org/" );
     
          //Write out the XML of the document.
          objSOAPSerializer.WriteXml( XDocument.DOM.documentElement.xml );
     
          //Finish each element.
          objSOAPSerializer.EndElement();
          objSOAPSerializer.EndElement();
     
          //Call EndMessage to complete the SOAP message and send it to the Web service method.
          //This results in the Web service method being called.
          objSOAPSerializer.endBody();
          objSOAPSerializer.endEnvelope(); 
          objSOAPConnector.EndMessage();
     
          //Use a SoapReader to read the response from the Web service method .
          var ResponseReader = new ActiveXObject("MSOSOAP.SoapReader30");
          ResponseReader.Load( objSOAPConnector.OutputStream );
     
          //If there was no error, return true.
          if (ResponseReader.Fault != null)
          {
             eventObj.ReturnStatus = false;
             throw "Error submitting data: " + ResponseReader.Fault.xml;
          }
          eventObj.ReturnStatus = true;
       } 
       catch (ex)
       { 
          XDocument.UI.Alert("Failed to submit document: " + ex.description); 
       }

狀況說明

這是原本設計的作法。

這是 Microsoft Office InfoPath 2003 中原本設計的作法,而在 Microsoft Office InfoPath 2003 Service Pack 1 中已有所變更。

其他相關資訊

重現問題的步驟

  1. 建立包含下列兩個方法的 Web 服務:
    • 方法 1
      [WebMethod]
         public void SendSampleString( string sampleString )
         {
            //Do something interesting with the sample string.
         } 
    • 方法 2
      [WebMethod]
         public string SendXMLElement( System.Xml.XmlElement theElement )
         {
            //Report how many children the submitted node had.
            return "Node with " + theElement.ChildNodes.Count + " children submitted.";
         }
  2. 選取 [新資料來源],以設計新的 InfoPath 表單。
  3. [資料來源安裝精靈] 中,選取 [Web 服務],然後按一下 [下一步]
  4. 按一下 [接收和送出資料],然後按一下 [下一步]
  5. 針對接收資料 Web 服務方法,請依照下列步驟執行:
    1. 輸入您先前建立之 Web 服務的 URL,然後按一下 [下一步]
    2. [選取作業] 清單中,按一下 [SendXMLElement],然後按一下 [下一步]
  6. 針對送出資料 Web 服務方法,請依照下列步驟執行:
    1. 輸入您先前建立之 Web 服務的 URL,然後按一下 [下一步]
    2. [選取作業] 清單中,按一下 [SendXMLElement],然後按一下 [下一步]
  7. 按一下 [修改] 按鈕,以選擇送出作業的參數。
  8. [dataFields] 清單中,按一下 [SendXMLElementResult],按一下 [確定],然後按一下 [下一步]
  9. 選取 [先設計資料檢視],然後按一下 [完成],以關閉 [資料來源安裝精靈] 對話方塊。
  10. 新增 [SendXMLElementResult] 欄位到表單中。
  11. 預覽表單。
  12. [傳送 XML 節點結果] 控制項中,輸入 Hello, World!
  13. [檔案] 功能表上,按一下 [送出]

    您會收到下列錯誤訊息:
    InfoPath 無法送出表單。
    表單送出時發生錯誤。

    顯示詳細資料:
    SOAP 回應指出有錯誤發生:
    伺服器無法讀取要求。--> XML 文件 1,409 中有錯誤。-->指定的轉換無效。
  14. 關閉 [預覽] 視窗,然後返回表單「設計」模式。
如果要解決這個問題,請使用本文<解決方案>一節所述的其中一種方法。

屬性

文章編號: 826989 - 上次校閱: 2006年4月11日 - 版次: 4.0
這篇文章中的資訊適用於:
  • Microsoft Office InfoPath 2003
  • Microsoft Office InfoPath 2003, Service Pack 1 (SP1)
關鍵字:?
kbtshoot kbprb kbbug KB826989
Microsoft及(或)其供應商不就任何在本伺服器上發表的文字資料及其相關圖表資訊的恰當性作任何承諾。所有文字資料及其相關圖表均以「現狀」供應,不負任何擔保責任。Microsoft及(或)其供應商謹此聲明,不負任何對與此資訊有關之擔保責任,包括關於適售性、適用於某一特定用途、權利或不侵權的明示或默示擔保責任。Microsoft及(或)其供應商無論如何不對因或與使用本伺服器上資訊或與資訊的實行有關而引起的契約、過失或其他侵權行為之訴訟中的特別的、間接的、衍生性的損害或任何因使用而喪失所導致的之損害、資料或利潤負任何責任。

提供意見

 

Contact us for more help

Contact us for more help
Connect with Answer Desk for expert help.
Get more support from smallbusiness.support.microsoft.com