I want to show you how to “upload” data to a OData Service, that is make a Http POST from client to your service. For this example I started a new Project by adding an AdventureWorks Entity Model and configuring it to a Wcf Data Service. How to you can read at:msdn (Don’t worry, this is about the Northwind DB, instead choose the AdventureWorks DB, if you not yet downloaded: check this!
Somehow the wcf data service will look like:
using System.Collections.Generic;
using System.Data.Services;
using System.Linq;
using System.ServiceModel.Web;
using System.Web;
using System.Linq.Expressions;
using System.Data.Services.Common;
namespace TestAdventureWorksDataServices
{
public class AdventureService : DataService<AdventureWorksEntities>
{
// This method is called only once to initialize service-wide policies.
public static void InitializeService(DataServiceConfiguration config)
{
// TODO: set rules to indicate which entity sets and service operations are visible, updatable, etc.
// Examples:
config.SetEntitySetAccessRule("*", EntitySetRights.All);
// config.SetServiceOperationAccessRule("MyServiceOperation", ServiceOperationRights.All);
config.DataServiceBehavior.MaxProtocolVersion = DataServiceProtocolVersion.V2;
config.UseVerboseErrors = false;
}
protected override void HandleException(HandleExceptionArgs args)
{
throw new DataServiceException(args.Exception.InnerException.Message, args.Exception);
}
}
}
Once we’ve setup our service, it’s time for a client that makes some calls to it. First add a new project to the solution (ConsoleApplication for now) and make a ServiceReference to the service.
In this example we want to add 3 new products and persist them in the DB producttable. For the last part we don’t have to worry, since the Entity Framework will handle this all.
Take a look at the client:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.Services.Client;
namespace Client
{
using Client.AdventureWorksServiceReference;
class Program
{
private static AdventureWorksEntities _context = null;
static void Main(string[] args)
{
_context = new AdventureWorksEntities(new Uri("http://ipv4.fiddler:51824/AdventureService.svc"));
var product1 = Product.CreateProduct(0, "My Test Product 1", "1234", true, true, 1, 1, 100, 200, 3,
DateTime.Now, new Guid("E29C16AE-908A-4F53-8E19-DC2CFDDF08A0"), DateTime.Now);
var product2 = Product.CreateProduct(0, "My Test Product 2", "5678", true, true, 1, 1, 200, 300, 3,
DateTime.Now, new Guid("1B9689D6-CCFF-40C3-AA0F-1AC3C5951738"), DateTime.Now);
var product3 = Product.CreateProduct(0, "My Test Product 3", "9876", true, true, 1, 1, 300, 400, 3,
DateTime.Now, new Guid("{0B677FB4-890E-4FAF-AD6A-7477D5703E6E}"), DateTime.Now);
var collection = new DataServiceCollection<Product>(_context);
collection.Add(product1);
collection.Add(product2);
collection.Add(product3);
_context.SaveChanges();
Console.Read();
//remove products to omit unique constraint next time running this app:
collection.Remove(product1);
collection.Remove(product2);
collection.Remove(product3);
_context.SaveChanges();
Console.WriteLine("Deleted. Sorry, changed my mind!");
Console.Read();
}
}
}
A short walkthrough of what is happening here.
First, take note of instead of setting up the context by calling “http://localhost:51824/AdventureService.svc” we include “http://ipv4.fiddler:51824/AdventureService.svc”. This is done so that later on we can monitor our calls in Fiddler.
When the application fires, a context of our service is setup, which will track all changes. In the end, if we agree with those changes we can call “context.SaveChanges()”;
By calling SaveChanges() requests are finally made to store the products. Let’s take a look in Fiddler:

As you see, there are 3 requests made to the service. Note!: by calling SaveChanges() only once.
Now let’s do it again, but change some code:
change following line:
_context.SaveChanges();
into:
_context.SaveChanges(SaveChangesOptions.Batch);
check this out in fiddler and you’ll notify the call is only made once:
