Create a Read-Only OData Endpoint with ASP.NET Web API
The Open Data Protocol (OData) is a data access protocol for the web. OData provides a uniform way to structure data, query the data, and manipulate the data set through CRUD operations (create, read, update, and delete).
OData supports both AtomPub (XML) and JSON formats. OData also defines a way to expose metadata about the data. Clients can use the metadata to discover the type information and relationships for the data set.
ASP.NET Web API OData makes it easy to create an OData endpoint for a data set. You can control exactly which OData operations the endpoint supports. You can host multiple OData endpoints, alongside non-OData endpoints. You have full control over your data model, back-end business logic, and data layer.
You can find more information about OData at http://www.odata.org/.
In this tutorial, you will create a simple OData endpoint that clients can query. You will also create a C# client for the endpoint. After you complete this tutorial, the next set of tutorials show how to add more functionality, such as CRUD operations and entity relations.
Download the completed project.
- Requirements
- Create the Visual Studio Project
- Add an Entity Model
- Add an OData Controller
- Configure the Endpoint
Requirements
- Visual Studio 2012 or Visual Studio Express 2012 for Web
- ASP.NET and Web Tools 2012.2 Update or the Microsoft ASP.NET Web API OData NuGet package.
Create the Visual Studio Project
In this tutorial, you will create a simple OData endpoint that is read-only. The endpoint will expose a single resource, a set of products. Later tutorials will add more features, including the ability to create, update, or delete entities.
Start Visual Studio and select New Project from the Start page. Or, from the File menu, select New and then Project.
In the Templates pane, select Installed Templates and expand the Visual C# node. Under Visual C#, select Web. In the list of project templates, select ASP.NET MVC 4 Web Application.
In the New ASP.NET MVC 4 Project dialog, select Web API and click OK.
If you installed ASP.NET and Web Tools 2012.2 Update, then the Web API project template automatically includes the OData packages. Otherwise, use NuGet Package Manager to install them:
- From the Tools menu, select Library Package Manager and then Package Manager Console.
- In the Package Manager Console window, enter the following:
Install-Package Microsoft.AspNet.WebApi.OData
Add an Entity Model
A model is an object that represents the data in your application. For this tutorial, we need a model that represents a product. The model corresponds to our OData entity type.
In Solution Explorer, right-click the Models folder. From the context menu, select Add then select Class.
In the Add New Item dialog, name the class "Product".
By convention, model classes are placed in the Models folder. You don’t have to follow this convention in your own projects, but we’ll use it for this tutorial.
In the Product.cs file, add the following class definition:
public class Product { public int ID { get; set; } public string Name { get; set; } public decimal Price { get; set; } public string Category { get; set; } }
The ID property will be the entity key. Clients can query products by ID. This field would also be the primary key in the back-end database.
Add an OData Controller
A controller is a class that handles HTTP requests. You define a separate controller for each entity set in you OData service. (In this tutorial, we’ll create a single controller.) In Solution Explorer, right-click the the Controllers folder. Select Add and then select Controller.
In the Add Controller wizard, name the controller "ProductsController". In the Template drop-down list, select Empty API Controller. Then click Add.
The Add Controller wizard creates a file named ProductsController.cs in the Controllers folder. Open this file. Notice that the controller inherits from ApiController. Modify the class to inherit from EntitySetController:
public class ProductsController : EntitySetController<Product, int> { }
The EntitySetController class derives from ODataController, which itself derives from ApiController.
Although you can create an OData endpoint using the ODataController class directly, EntitySetController handles the details of creating the correct OData-compliant HTTP response. This lets you focus on the code that is specific to your application. The EntitySetController class takes two generic type parameters: The first is the type for the entity (Product
) and the second is the type for the entity key (int).
The EntitySetController class is defined in the System.Web.Http.OData namespace. In Visual Studio, you can resolve a namespace by right-clicking the type name and selecting Resolve:
Next, add a list of products to the controller:
public class ProductsController : EntitySetController<Product, int> { static List<Product> products = new List<Product>() { new Product() { ID = 1, Name = "Hat", Price = 15, Category = "Apparel" }, new Product() { ID = 2, Name = "Socks", Price = 5, Category = "Apparel" }, new Product() { ID = 3, Name = "Scarf", Price = 12, Category = "Apparel" }, new Product() { ID = 4, Name = "Yo-yo", Price = 4.95M, Category = "Toys" }, new Product() { ID = 5, Name = "Puzzle", Price = 8, Category = "Toys" }, }; }
Of course, in a real application, you would probably store the product list in a database. Here, I’m storing them in memory for simplicity.
To support GET (read) requests, override these two methods of the EntitySetController class:
- Get
- GetEntityByKey
The Get method returns the product list as an IQueryable:
public override IQueryable<Product> Get() { return products.AsQueryable(); }
The GetEntityByKey method looks up a product by its key:
protected override Product GetEntityByKey(int key) { return products.FirstOrDefault(p => p.ID == key); }
Configure the Endpoint
The last step is to hook everything up. In Solution Explorer, expand the App_Start folder and open the file named WebApiConfig.cs. This class holds configuration code for Web API. Add the following code to the Register method:
ODataModelBuilder modelBuilder = new ODataConventionModelBuilder(); modelBuilder.EntitySet<Product>("Products"); Microsoft.Data.Edm.IEdmModel model = modelBuilder.GetEdmModel(); config.Routes.MapODataRoute("ODataRoute", "odata", model);
This code does two things:
- Creates an Entity Data Model (EDM) for the OData endpoint.
- Configures the endpoint.
An EDM is an abstract model of the data. The EDM is used to create the metadata document and define the URIs for the service. The ODataConventionModelBuilder creates an EDM by using a set of default naming conventions EDM. This approach requires the least code. If you want more control over the EDM, you can use the ODataModelBuilder class to create the EDM by adding properties, keys, and navigation properties explicitly.
The EntitySet method adds an entity set to the EDM:
modelBuilder.EntitySet<Product>("Products");
The string “Products” defines the name of the entity set. The name of the controller must match the name of the entity set. In this tutorial, the entity set is named “Products” and the controller is named ProductsController
. If you named the entity set “ProductSet”, you would name the controller ProductSetController
. Note that an endpoint can have multiple entity sets. Call EntitySet<T> for each entity set, and then define a corresponding controller.
The MapODataRoute method sets up the OData URIs and configures the endpoint.
config.Routes.MapODataRoute("ODataRoute", "odata", model);
The first parameter is the route name. This value is not used by clients. The second parameter is the URI prefix for the endpoint. Given this code, the URI for the Products entity set is http:/hostname/odata/Products. Your application can have more than one OData endpoint. For each endpoint, call MapODataRoute and provide a unique route name and a unique URI prefix.
Comments (0) RSS Feed