ASP.NET を使用して作成する XML Web サービスのデザイン ガイドライン

XML Web サービスは、インターネット経由でプログラムによってアクセスできるサービスを提供する強力な技術です。高度な XML Web サービスの作成に役立つ推奨事項を次に示します。

  • XML Web サービスは、クライアントと XML Web サービスを管理するサーバー間の同期通信および非同期通信の両方をサポートしています。同期通信では、クライアントはサービスに対する要求をホスト サーバーに送信し、その応答を待機します。これにより、クライアントは応答を待機している間、その他の操作を実行できなくなります。ただし、非同期通信では、クライアントは応答の待機中に他のタスクの処理を続行します。クライアントは、サービス要求の結果が使用可能になると、その結果に応答します。

    Web サービス記述言語ツール (Wsdl.exe) を使用してプロキシ クラスを作成すると、そのプロキシ クラスには標準的な同期バーションのメソッドと非同期バージョンのメソッドが生成されます。非同期バージョンは、Begin および End の 2 つのメソッドです。Begin メソッドを使用して XML Web サービスを開始し、End メソッドを使用してその結果を取得します。

    非同期通信を使用すると、システムの使用効率の向上を図り、XML Web サービスの結果を待機している間のクライアントでの遅延を回避できます。

    クライアント アプリケーションから XML Web サービスを非同期に呼び出す方法を次のコード例に示します。

    <%@ Page Language="C#" %>
    <%@ Import Namespace="System.Net" %>
    <html>
       <script language="C#" runat="server">
          void EnterBtn_Click(Object Src, EventArgs E) 
          {
             MyMath.Math math = new MyMath.Math();
             // Call to Add XML Web service method asynchronously 
             // and then wait for it to complete.
             IAsyncResult result =
                             math.BeginAdd(Convert.ToInt32(Num1.Text),
                                           Convert.ToInt32(Num2.Text),
                                           null,
                                           null);
             // Wait for asynchronous call to complete.
             result.AsyncWaitHandle.WaitOne();
             // Complete the asynchronous call to Add XML Web service method.
             float total = math.EndAdd(result);
             // Display results in a Label control.
             Total.Text = "Total: " + total.ToString();
          }
       </script>
    <body>
       <form action="MathClient.aspx" runat=server>
          <font face="Verdana"> 
             Enter the two numbers you want to add and then press 
             the Total button.
             <p>
             Number 1: 
             <asp:textbox id="Num1" 
             runat=server/>  
             +
             Number 2: 
             <asp:textbox id="Num2" 
                  runat=server/> 
             =
             <asp:button id="Total_Button"
                  text="Total" 
                  OnClick="EnterBtn_Click" 
                  runat=server/>
             <p>
             <asp:label id="Total" runat=server/>
          </font>
        </form>
    </body>
    </html>
    [Visual Basic]
    <%@ Page Language="VB" %>
    <%@ Import Namespace="System.Net" %>
    <html>
       <script language="VB" runat="server">
          Sub EnterBtn_Click(Src As Object, E As EventArgs) 
             Dim math As New MyMath.Math()
             ' Call to Add XML Web service method asynchronously 
             ' and then wait for it to complete.
             Dim result As IAsyncResult = _
                             math.BeginAdd(Convert.ToInt32(Num1.Text), _
                                           Convert.ToInt32(Num2.Text), _
                                           Nothing, _
                                           Nothing)
    
             ' Wait for asynchronous call to complete.
             result.AsyncWaitHandle.WaitOne()
             ' Complete the asynchronous call to Add XML Web service method.
             Dim addtotal As Single = math.EndAdd(result)
             ' Display results in a Label control.
             Total.Text = "Total: " & addtotal.ToString()
          End Sub
       </script>
    <body>
       <form action="MathClient.aspx" runat=server>
          <font face="Verdana"> 
             Enter the two numbers you want to add and then press 
             the Total button.
             <p>
             Number 1: 
             <asp:textbox id="Num1" 
             runat=server/>  
             +
             Number 2: 
             <asp:textbox id="Num2" 
                  runat=server/> 
             =
             <asp:button id="Total_Button"
                  text="Total" 
                  OnClick="EnterBtn_Click" 
                  runat=server/>
             <p>
             <asp:label id="Total" runat=server/>
          </font>
        </form>
    </body>
    </html>
    

    非同期通信の追加情報については、「XML Web サービスとの非同期通信」を参照してください。

  • インターネット経由で数多くのサービスを要求すると、クライアント アプリケーションのパフォーマンスに影響します。XML Web サービスのデザイン時に、関連する情報をまとめるメソッドを作成することで、サービスの要求を効果的に処理できます。たとえば、書籍情報を取得する XML Web サービスをデザインするとします。書籍のタイトル、作者、および出版元を取得するメソッドを個別に作成するのではなく、1 回のサービス要求ですべての情報を返すメソッドを作成します。情報のブロックを小さくして複数回に分けて転送するよりも、大きな情報ブロックを 1 回で転送した方が効率的です。

    関連する情報を 1 つの XML Web サービス メソッドにまとめる方法を次のコード例に示します。

    <%@ WebService Language="C#" Class="DataService" %>
    using System;
    using System.Data;
    using System.Data.SqlClient;
    using System.Web.Services;
    public class DataService {
       [WebMethod]
       public DataSet GetTitleAuthors() {
            SqlConnection myConnection = new SqlConnection("Persist Security Info=False;Integrated Security=SSPI;server=localhost;database=pubs");
            SqlDataAdapter myCommand1 = new SqlDataAdapter ("select * from Authors", myConnection);
            SqlDataAdapter myCommand2 = new SqlDataAdapter("select * from Titles", myConnection);
            DataSet ds = new DataSet();
            myCommand1.Fill(ds, "Authors");
            myCommand2.Fill(ds, "Titles");
            return ds;
       }
    }
    [Visual Basic]
    <%@ WebService Language="VB" Class="DataService" %>
    Imports System
    Imports System.Data
    Imports System.Data.SqlClient
    Imports System.Web.Services
    Public Class DataService   
        <WebMethod> _
        Public Function GetTitleAuthors() As DataSet
            Dim myConnection As New SqlConnection("Persist Security Info=False;Integrated Security=SSPI;server=localhost;database=pubs")
            Dim myCommand1 As New SqlDataAdapter("select * from Authors", myConnection)
            Dim myCommand2 As New SqlDataAdapter("select * from Titles", myConnection)
            Dim ds As New DataSet()
            myCommand1.Fill(ds, "Authors")
            myCommand2.Fill(ds, "Titles")
            Return ds
        End Function
    End Class
    
  • XML Web サービスのデザイン時には、必ず標準のオブジェクト指向プログラミング手法を使用してください。カプセル化を使用して実装の詳細を隠ぺいします。より複雑な XML Web サービスの場合、継承およびポリモーフィズムを使用してコード再利用し、デザインを簡潔化できます。

    継承を使用して数値計算を実行する XML Web サービスを作成する方法を次のコード例に示します。

    <%@ WebService Language="C#" Class="Add" %>
    using System;
    using System.Web.Services;
    abstract public class MathService : WebService 
    {
       [WebMethod]
       abstract public float CalculateTotal(float a, float b);
    }
    public class Add : MathService 
    {
       [WebMethod]
       override public float CalculateTotal(float a, float b)
       {
           return a + b;
       }
    }
    public class Subtract : MathService 
    {
       [WebMethod]
       override public float CalculateTotal(float a, float b)
       {
           return a - b;
       }
    }
    public class Multiply : MathService 
    {
       [WebMethod]
       override public float CalculateTotal(float a, float b)
       {
           return a * b;
       }
    }
    public class Divide : MathService 
    {
       [WebMethod]
       override public float CalculateTotal(float a, float b)
       {
           if (b==0) 
              return -1;
           else
              return a / b;
       }
    }
    [Visual Basic]
    <%@ WebService Language="VB" Class="Add" %>
    Imports System
    Imports System.Web.Services
    MustInherit Public Class MathService : Inherits WebService    
        <WebMethod> _
        Public MustOverride Function CalculateTotal(a As Single, _
                            b As Single) As Single
    End Class
    Public Class Add : Inherits MathService    
        <WebMethod> _
        Public Overrides Function CalculateTotal(a As Single, _
                         b As Single) As Single
            Return a + b
        End Function
    End Class 
    Public Class Subtract : Inherits MathService
        <WebMethod> _
        Public Overrides Function CalculateTotal(a As Single, _
                         b As Single) As Single
            Return a - b
        End Function
    End Class 
    Public Class Multiply : Inherits MathService
        <WebMethod> _
        Public Overrides Function CalculateTotal(a As Single, _
                         b As Single) As Single
            Return a * b
        End Function
    End Class 
    Public Class Divide : Inherits MathService
        <WebMethod> _
        Public Overrides Function CalculateTotal(a As Single, _
                         b As Single) As Single
            If b = 0 Then
                Return - 1
            Else
                Return a / b
            End If
        End Function
    End Class
    
  • 出力キャッシュを使用して XML Web サービスのパフォーマンスを向上させます。出力キャッシュを有効にすると、指定した期間中、サービス要求の結果が出力キャッシュに格納されます。したがって、同様の XML Web サービス要求が行われた場合、その結果を再計算するのではなく、出力キャッシュから取得できます。そのため、XML Web サービス サーバーで行う必要がある処理が減ることで XML Web サービスの反応時間が改善されます。クライアントとサーバーの両方でキャッシュを実行できます。Duration プロパティを使用して、XML Web サービスの出力をキャッシュしておく時間を指定できます。

    クライアントで出力キャッシュを有効にするディレクティブは次のとおりです。

    <%@ OutputCache Duration="60" %>
    

    クライアント アプリケーションで Duration プロパティを使用して出力キャッシュ時間を 60 秒間に指定する方法を次のコード例に示します。

    <%@ Page Language="C#" %>
    <%@ Import Namespace="System.Net" %>
    <%@ OutputCache Duration="60" VaryByParam="none" %>
    <html>
       <script language="C#" runat="server">
          void EnterBtn_Click(Object Src, EventArgs e) 
          {
             MyMath.Math math = new MyMath.Math();
             // Call the XML Web service.
             float total = math.Add(Convert.ToInt32(Num1.Text),
                                  Convert.ToInt32(Num2.Text));
             // Display the results in a Label control.
             Total.Text = "Total: " + total.ToString();
          }
       </script>
    <body>
       <form action="MathClient.aspx" runat=server>
          <font face="Verdana"> 
             Enter the two numbers you want to add and press 
             the Total button.
             <p>
             Number 1: 
             <asp:textbox id="Num1" 
             runat=server/>  
             +
             Number 2: 
             <asp:textbox id="Num2" 
                  runat=server/> 
             =
             <asp:button id="Total_Button"
                  text="Total" 
                  OnClick="EnterBtn_Click" 
                  runat=server/>
             <p>
             <asp:label id="Total" runat=server/>
          </font>
        </form>
    </body>
    </html>
    [Visual Basic]
    <%@ Page Language="VB" %>
    <%@ Import Namespace="System.Net" %>
    <%@ OutputCache Duration="60" VaryByParam="none" %>
    <html>
       <script language="VB" runat="server">
          Sub EnterBtn_Click(Src As Object, e As EventArgs) 
             Dim math As New MyMath.Math()
             ' Call the XML Web service.
             Dim addtotal As Single = math.Add(Convert.ToInt32(Num1.Text), _
                                  Convert.ToInt32(Num2.Text))
             ' Display the results in a Label control.
             Total.Text = "Total: " & addtotal.ToString()
          End Sub
       </script>
    <body>
       <form action="MathClient.aspx" runat=server>
          <font face="Verdana"> 
             Enter the two numbers you want to add and press 
             the Total button.
             <p>
             Number 1: 
             <asp:textbox id="Num1" 
             runat=server/>  
             +
             Number 2: 
             <asp:textbox id="Num2" 
                  runat=server/> 
             =
             <asp:button id="Total_Button"
                  text="Total" 
                  OnClick="EnterBtn_Click" 
                  runat=server/>
             <p>
             <asp:label id="Total" runat=server/>
          </font>
        </form>
    </body>
    </html>
    

    また、WebMethod 属性クラスの CacheDuration プロパティを使用して、サーバーでキャッシュを有効にすることもできます。XML Web サービス メソッドで CacheDuration プロパティを使用して出力キャッシュ時間を 60 秒間に指定する方法を次のコード例に示します。

    <%@ WebService Language="C#" Class="MathService" %>
    using System;
    using System.Web.Services;
    public class MathService : WebService {
       [WebMethod(CacheDuration=60)]
       public float Add(float a, float b)
       {
           return a + b;
       }
       [WebMethod(CacheDuration=60)]
       public float Subtract(float a, float b)
       {
           return a - b;
       }
       [WebMethod(CacheDuration=60)]
       public float Multiply(float a, float b)
       {
           return a * b;
       }
       [WebMethod(CacheDuration=60)]
       public float Divide(float a, float b)
       {
           if (b==0) return -1;
           return a / b;
       }
    }  
    [Visual Basic]
    <%@ WebService Language="VB" Class="MathService" %>
    Imports System
    Imports System.Web.Services
    Public Class MathService
        Inherits WebService 
        <WebMethod(CacheDuration := 60)> _
        Public Function Add(a As Single, b As Single) As Single
            Return a + b
        End Function
    
        <WebMethod(CacheDuration := 60)> _
        Public Function Subtract(a As Single, b As Single) As Single
            Return a - b
        End Function
    
        <WebMethod(CacheDuration := 60)> _
        Public Function Multiply(a As Single, b As Single) As Single
            Return a * b
        End Function
    
        <WebMethod(CacheDuration := 60)> _
        Public Function Divide(a As Single, b As Single) As Single
            If b = 0 Then
                Return - 1
            End If
            Return a / b
        End Function
    End Class
    
  • XML Web サービスのデザイン時には、スキーマの書式指定の構造に従ってください。

  • XML Web サービスは、主要なトランスポート プロトコルおよびシリアル化プロトコルとして SOAP を使用します。SOAP メッセージは、省略可能なヘッダーのセットとメッセージの本文で構成されます。ヘッダー セクションには、Web サーバー上のインフラストラクチャによって処理できる情報が含まれています。SOAP は、ヘッダーの定義は行いません。本文セクションには、XML Web サービスのパラメータや戻り値など、アプリケーションによって処理される情報が含まれています。

    SOAP ヘッダーの使用方法の追加情報については、「SOAP ヘッダーの使用」を参照してください。

  • XML Web サービスについて、そのサービスの操作やデータ構造について記述する静的 HTML ファイルなどのドキュメントを用意します。また、XML Web サービスの使用方法の例も含めるようにします。サービスの説明またはサービス ヘルプ ページだけをユーザーに提供するドキュメントとすることは避けてください。

参照

ASP.NET を使用した XML Web サービスの作成 | XML Web サービスとの非同期通信 | SOAP ヘッダーの使用