チュートリアル : 型プロバイダーを使用した OData サービスへのアクセス (F#)

OData (Open Data Protocol) は、インターネットでデータを転送するためのプロトコルです。多くのデータ プロバイダーが、OData Web サービスを公開してデータへのアクセスを提供しています。F# 3.0 では、ODataService 型プロバイダーによって自動生成されるデータ型を使用して、どの OData ソースからでもデータにアクセスできます。OData の詳細については、「Introducing OData」を参照してください。

このチュートリアルでは、F# ODataService 型プロバイダーを使用して、OData サービスのクライアント型を生成し、サービスが提供するデータ フィードを照会する方法を示します。

このチュートリアルでは以下の作業について説明します。このチュートリアルを正しく行うには、これらの作業を順に行ってください。

  • Configuring a client project for an OData service

  • Accessing OData types

  • Querying an OData service

  • Verifying the OData requests

OData サービスのクライアント プロジェクトの構成

この手順では、OData 型プロバイダーを使用するようにプロジェクトを設定します。

OData サービスのクライアント プロジェクトを構成するには

  • F# コンソール アプリケーション プロジェクトを開き、System.Data.Services.Client Framework アセンブリへの参照を追加します。

  • [拡張機能] の下で、FSharp.Data.TypeProviders アセンブリへの参照を追加します。

OData 型へのアクセス

この手順では、OData サービスの型とデータへのアクセスを提供する型プロバイダーを作成します。

OData 型にアクセスするには

  • コード エディターで、F# ソース ファイルを開いて次のコードを入力します。

    open Microsoft.FSharp.Data.TypeProviders
    
    
    type Northwind = ODataService<"http://services.odata.org/Northwind/Northwind.svc/">
    
    let db = Northwind.GetDataContext()
    let fullContext = Northwind.ServiceTypes.NorthwindEntities()
    

    この例では、F# 型プロバイダーを呼び出し、指定した OData URI に基づく一連の型を生成するように指示しました。データに関する情報を含む 2 つのオブジェクトを使用できます。この例では、1 つは簡易データ コンテキストの db です。このオブジェクトには、テーブルやフィードの型を含む、データベースに関連付けられているデータ型だけが含まれています。この例の、もう 1 つのオブジェクト fullContext は DataContext のインスタンスで、追加のプロパティ、メソッド、イベントなどが多数含まれています。

OData サービスの照会

この手順では、F# クエリ式を使用して OData サービスを照会します。

OData サービスに照会するには

  1. 型プロバイダーを設定したので、OData サービスを照会できます。

    OData は、使用可能なクエリ操作の一部のみをサポートしています。次の操作と対応するキーワードがサポートされています。

    • プロジェクション (select)

    • フィルター処理 (where、文字列演算と日付演算を使用)

    • ページング (skip、take)

    • 順序付け (orderBy、thenBy)

    • AddQueryOption および Expand (OData 固有の演算)

    詳細については、「LINQ Considerations」を参照してください。

    フィードまたはテーブルのすべてのエントリが必要な場合は、次のコードのように、クエリ式の最も単純な形式を使用してください。

    query { for customer in db.Customers do
            select customer }
    |> Seq.iter (fun customer ->
        printfn "ID: %s\nCompany: %s" customer.CustomerID customer.CompanyName
        printfn "Contact: %s\nAddress: %s" customer.ContactName customer.Address
        printfn "         %s, %s %s" customer.City customer.Region customer.PostalCode
        printfn "%s\n" customer.Phone)
    
  2. select キーワードの後にタプルを使用して、必要なフィールドまたは列を指定します。

    query { for cat in db.Categories do
            select (cat.CategoryID, cat.CategoryName, cat.Description) }
    |> Seq.iter (fun (id, name, description) ->
        printfn "ID: %d\nCategory: %s\nDescription: %s\n" id name description)
    
  3. where 句を使用して、条件を指定します。

    query { for employee in db.Employees do
            where (employee.EmployeeID = 9)
            select employee }
    |> Seq.iter (fun employee ->
        printfn "Name: %s ID: %d" (employee.FirstName + " " + employee.LastName) (employee.EmployeeID))                         
    
  4. Contains メソッドを使用して、クエリに部分文字列の条件を指定します。次のクエリは、名前に "Chef" を含むすべての製品を返します。また、GetValueOrDefault の使い方にも注目してください。UnitPrice は null 許容値であるため、Value プロパティを使用して値を取得するか、GetValueOrDefault を呼び出す必要があります。

    query { for product in db.Products do
            where (product.ProductName.Contains("Chef"))
            select product }
    |> Seq.iter (fun product ->
        printfn "ID: %d Product: %s" product.ProductID product.ProductName
        printfn "Price: %M\n" (product.UnitPrice.GetValueOrDefault()))
    
  5. 文字列が特定の部分文字列で終わるように指定するには、EndsWith メソッドを使用します。

    query { for product in db.Products do
            where (product.ProductName.EndsWith("u"))
            select product }
    |> Seq.iter (fun product ->
        printfn "ID: %d Product: %s" product.ProductID product.ProductName
        printfn "Price: %M\n" (product.UnitPrice.GetValueOrDefault()))
    
  6. && 演算子を使用して、where 句で条件を組み合わせます。

    // Open this module to use the nullable operators ?> and ?<.
    open Microsoft.FSharp.Linq.NullableOperators
    
    let salesIn1997 = query { for sales in db.Category_Sales_for_1997 do
                              where (sales.CategorySales ?> 50000.00M && sales.CategorySales ?< 60000.0M)
                              select sales }
    salesIn1997
    |> Seq.iter (fun sales ->
        printfn "Category: %s Sales: %M" sales.CategoryName (sales.CategorySales.GetValueOrDefault()))
    

    演算子 ?> と ?< は null 許容の演算子です。null 許容の等価演算子と比較演算子をすべて使用できます。詳細については、「Linq.NullableOperators モジュール (F#)」を参照してください。

  7. 順序付けを指定するには sortBy クエリ演算子を使用し、さらにもう 1 レベル順序付けを指定するには thenBy を使用します。クエリの select 部分にタプルが使用されている点にも注目してください。したがって、クエリには要素型としてタプルが含まれています。

    printfn "Freight for some orders: "
    query { for order in db.Orders do
            sortBy (order.OrderDate.Value)
            thenBy (order.OrderID)
            select (order.OrderDate, order.OrderID, order.Customer.CompanyName)
             }
    |> Seq.iter (fun (orderDate, orderID, company) ->
        printfn "OrderDate: %s" (orderDate.GetValueOrDefault().ToString())
        printfn "OrderID: %d Company: %s\n" orderID company)
    
  8. skip 演算子を使用して、指定した数のレコードを無視し、take 演算子を使用して、返すレコードの数を指定します。この方法で、データ フィードにページングを実装できます。

    printfn "Get the first page of 2 employees."
    query { for employee in db.Employees do
            take 2
            select employee }
    |> Seq.iter (fun employee ->
        printfn "Name: %s ID: %d" (employee.FirstName + " " + employee.LastName) (employee.EmployeeID)) 
    
    printfn "Get the next 2 employees."
    query { for employee in db.Employees do
            skip 2
            take 2
            select employee }
    |> Seq.iter (fun employee ->
        printfn "Name: %s ID: %d" (employee.FirstName + " " + employee.LastName) (employee.EmployeeID)) 
    

OData 要求の確認

OData のすべてのクエリは、特定の OData 要求 URI に変換されます。完全なデータ コンテキスト オブジェクトの SendingRequest イベントにイベント ハンドラーを追加することによって、デバッグなどを行うためにその URI を確認できます。

OData 要求を確認するには

  • OData 要求 URI を確認するには、次のコードを使用します。

        // The DataContext property returns the full data context.
        db.DataContext.SendingRequest.Add (fun eventArgs -> printfn "Requesting %A" eventArgs.Request.RequestUri)
    

    前のコードの出力は次のようになります。

requesting http://services.odata.org/Northwind/Northwind.svc/Orders()?$orderby=ShippedDate&$select=OrderID,ShippedDate

参照

処理手順

クエリ式 (F#)

関連項目

ODataService 型プロバイダー (F#)

その他の技術情報

LINQ Considerations