I have two methods named Post* in my Web API server:
Controller
public void PostNoBills(int accountid, string name)
{
duckbillsRepository.Post(accountid, name);
}
public void Post(NoBills noBills)
{
duckbillsRepository.Post(noBills);
}
Repository:
public void PostNoBills(int accountid, string name)
{
int maxId = noBills.Max(d => d.Id);
NoBills duckbill = new NoBills();
duckbill.Id = maxId + 1;
duckbill.AccountId = accountid;
duckbill.Name = name;
NoBills.Add(duckbill);
}
public void Post(NoBills noBills)
{
int maxId = NoBills.Max(d => d.Id);
NoBills.Id = maxId + 1;
NoBills.Add(noBills);
}
So when I call a Post method from the client, passing an int and a string:
string uri = String.Format("http://platypi:28642/api/NoBills/{0}/{1}", onAccountOfWally, moniker);
var request = System.Net.WebRequest.Create(uri);
request.Method = "POST";
string postData = String.Format("{0}/{1}", onAccountOfWally, moniker);
byte[] byteArray = System.Text.Encoding.UTF8.GetBytes(postData);
request.ContentType = "application/json";
request.ContentLength = byteArray.Length;
using (var requestStream = request.GetRequestStream())
{
requestStream.Write(byteArray, 0, byteArray.Length);
}
using (var response = request.GetResponse())
...I expect the method with the "int accountid, string name" arguments to be the one that gets called, but it's not - the other one (the one accepting "NoBills noBills" as its argument) is. Why?
(BTW, I'm not at all sure the client code above is "right")
UPDATE
In acquiescence to the invitation/demand of Kian Challa, here is WebApiConfig:
public static class WebApiConfig { public static void Register(HttpConfiguration config) { // Web API configuration and services
// Web API routes
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
config.Routes.MapHttpRoute(
name: "DefaultApiWithParameters",
routeTemplate: "api/{controller}/{ID}/{CountToFetch}"
//defaults: new { ID = RouteParameter.Optional, CountToFetch = RouteParameter.Optional }
);
config.Routes.MapHttpRoute(
name: "DefaultApiWith3Parameters",
routeTemplate: "api/{controller}/{ID}/{packSize}/{CountToFetch}"
//defaults: new { ID = RouteParameter.Optional, packSize = RouteParameter.Optional, CountToFetch = RouteParameter.Optional }
);
As a bonus, here is RouteConfig.cs:
public class RouteConfig
{
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
);
}
}
...and the perhaps pertinent piece of Global.asax.cs:
protected void Application_Start()
{
AreaRegistration.RegisterAllAreas();
GlobalConfiguration.Configure(WebApiConfig.Register);
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
}
UPDATE 2
In reply to Kian Challa's comment below containing "on the action public void PostNoBills(int accountid, string name)"
Okay, so that is (if you're talking about the Controller code):
public void PostNoBills(int accountid, string name)
{
duckbillsRepository.Post(accountid, name);
}
How should it be changed with:
[Route("api/nobills/{accountid}/{name}")]
? You imply that I need add nothing to WebApiConfig ("...instead of creating a new route in WebApiConfig.cs...") so...precisely what do I need to add, and where do I need to add it?