我试图在WebApi2中创建两个方法,将数据转换为对象并返回一个标记。
Get Command完美运行。
[HttpGet]
[Route("refresh")]
public HttpResponseMessage refresh([FromUri] oAuthTokenRequest tokenItem)
{
var device = new ConnectedDevices();
var AuthString = device.getAuthorization(Request.Headers.Authorization.Parameter);
var serviceKey = new ServiceKeyManagement();
var accessToken = new oAuthAccessResponse();
var response = Request.CreateResponse(HttpStatusCode.Forbidden, "Unknown", "application/json");
var clientID = AuthString[0];
var errorResponse = new oAuthErrorResponse();
var oauth = new oAuthAuthenticationCode();
String email = String.Empty;
var tokenRequest = new oAuthTokenRequest();
Log.Debug("oAuth REST API GET: Refresh: Authorization Parameter: " + Request.Headers.Authorization.Parameter, this);
Log.Debug("oAuth REST API GET: Refresh: clientID: " + clientID, this);
Log.Debug("oAuth REST API GET: Refresh: Request: " + Request.RequestUri, this);
if (!serviceKey.isValidServiceKey(clientID, AuthString[1]))
{
errorResponse.error = oAuthCodes.ErrorCodes.unauthorized_client.ToString();
errorResponse.error_description = "Invalid Service Key";
errorResponse.error_uri = String.Empty;
response = Request.CreateResponse(HttpStatusCode.Forbidden, errorResponse, "application/json");
response.ReasonPhrase = "refresh: Invalid Login Request.";
} // end of if (!serviceKey.isValidServiceKey(clientID, AuthString[1]))
else
{
Log.Debug("oAuth REST API GET: Refresh: NameValuePairs: " + tokenItem.grant_type, this);
tokenRequest.redirect_url = tokenItem.redirect_url;
tokenRequest.code = tokenItem.code;
tokenRequest.grant_type = tokenItem.grant_type;
tokenRequest.clientID = clientID;
response = tokenValidation(tokenRequest, clientID);
} // end else for if (!serviceKey.isValidServiceKey(clientID, AuthString[1]))
return response;
} // end of public HttpResponseMessage Login(ConnectedDeviceViewModel login)
这将从URI中读取变量,然后将它们解析为对象。
Post命令没有这样做:
[HttpPost]
[Route("refresh")]
public HttpResponseMessage refreshPost([FromBody] oAuthTokenRequest tokenItem)
{
var device = new ConnectedDevices();
var AuthString = device.getAuthorization(Request.Headers.Authorization.Parameter);
var serviceKey = new ServiceKeyManagement();
var accessToken = new oAuthAccessResponse();
var response = Request.CreateResponse(HttpStatusCode.Forbidden, "Unknown", "application/json");
var clientID = AuthString[0];
var errorResponse = new oAuthErrorResponse();
var oauth = new oAuthAuthenticationCode();
String email = String.Empty;
var tokenRequest = new oAuthTokenRequest();
Log.Debug("oAuth REST API: Refresh POST: Authorization Parameter: " + Request.Headers.Authorization.Parameter, this);
Log.Debug("oAuth REST API: Refresh POST: clientID: " + clientID, this);
Log.Debug("oAuth REST API: Refresh POST: Request: " + Request.RequestUri, this);
if (!serviceKey.isValidServiceKey(clientID, AuthString[1]))
{
errorResponse.error = oAuthCodes.ErrorCodes.unauthorized_client.ToString();
errorResponse.error_description = "Invalid Service Key";
errorResponse.error_uri = String.Empty;
response = Request.CreateResponse(HttpStatusCode.Forbidden, errorResponse, "application/json");
response.ReasonPhrase = "refresh: Invalid Login Request.";
} // end of if (!serviceKey.isValidServiceKey(clientID, AuthString[1]))
else
{
Log.Debug("oAuth REST API POST: Refresh: NameValuePairs: " + String.Join(" : ", Request.GetQueryNameValuePairs().ToList()), this);
tokenRequest.redirect_url = tokenItem.redirect_url;
tokenRequest.code = tokenItem.code;
tokenRequest.grant_type = tokenItem.grant_type;
tokenRequest.clientID = clientID;
response = tokenValidation(tokenRequest, clientID);
} // end else for if (!serviceKey.isValidServiceKey(clientID, AuthString[1]))
return response;
}
如果这是正在发送的JSON,帖子将完美运行。我尝试了各种方式的签名:
[HttpPost]
[Route("refresh")]
public HttpResponseMessage refreshPost([FromBody] oAuthTokenRequest tokenItem)
[HttpPost]
[Route("refresh")]
public HttpResponseMessage refreshPost(oAuthTokenRequest tokenItem)
[HttpPost]
[Route("refresh")]
public HttpResponseMessage refreshPost(FormDataFormat oAuthTokenRequest tokenItem)
在每种情况下,如果我尝试发送以下请求:
POST /api/TokenAuthorization/refresh HTTP/1.1
Host: localhost.www.bissell.com
Authorization: Basic U21hcnRDbGVhbkFsZXhhOlJOWFpfaEFQWUhBVHpVTTc1STVrdDVQcmlEUkkzV0VtdG5FX1dCS0ZiaUEtVGRBVXZtMWZzNldKRV9ZOFJXajVicEVnbmxpdmp2eWJsNkRYelhEYmR1SXB0d0VGV2IwbDRWbXpBWFI3d1VxX2twaklzLTQ4SDRfTnc2Q2YtNy1ZaVpWcU9RSGlBNjFmUWI0MWJoNU1vUjVFd0hMMExZam8tVkszWXJRa3RabWlPb0pTSXVNdWtRazJ2Tjl3MFFmdF9YTWRuUHY5eDNXRFBtMlB0TURSV2VhMVZOUXpDeVFzd0xJRFhtaU1ZbmVhNFBQZ2V3cHp0UmNFU2RjVVlMY0puQVZ5SF90TS01TUg5ZVcwOWRFNmtjMV9BSWRDc3FUcHQwTHB5V1ltVFpjVEVGcGtkdlBwSWJ1N21Od3ZWb0tCU2hZZ0RabEdpQ1dzNVVoM25DbGVVVE5FdXVNaVJiVUdsUWJIVEJKdmtWUmNQbk9qZzJSRHA5ZjBwTml3ZU1fOEthazlQRU1pNXNuSkFMaFo5bWFQTmRVTVNMaXQ1T1VkbVZYVDhuckU5eVdWN1cyS1J2bDh0ZnFsX0Z0OVVNWWFfRjI3TTlGV2dFdm9FbndZV3RyVlgxYkxPdWk1QUlFNVU3OGhzd3loYk5TMkJzRnN2Sk5YaU9icExRa2NESWNrN3g4OWVCaUdsUGNSbGkxdDRBbEVfWER6ZDFzcVNwcURWdjR2NGJwRklYUFRaWXh6MzlhSFl1akdaXzhmMW5QRjYzN3d4WFNDcU52SkpublZYRWR1T1Ey
Content-Type: application/x-www-form-urlencoded
Cache-Control: no-cache
Postman-Token: 434aa7f2-a3d2-ce43-d300-001d61be4562
grant_type=authorization_code&code=20620A62853B45B9BEEA6E67C7587BC1%3AC0DB652683B5ACB67797A42D3DDB4D03ABA0561100137DB812602C57E17736E72D6E1E35D5A56C7F67B1760EA33A539D932C7A96A1853E4E103118F41D004D7E&redirect_url=abc&clientID=abc&clientSecret=abc
我收到以下错误
"ExceptionMessage": "This method or property is not supported after HttpRequest.Form, Files, InputStream, or BinaryRead has been invoked.
我的WebApiConfig.cs看起来像这样:
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
var json = config.Formatters.JsonFormatter;
json.SerializerSettings.PreserveReferencesHandling = Newtonsoft.Json.PreserveReferencesHandling.Objects;
config.Formatters.Remove(config.Formatters.XmlFormatter);
}
}
我在互联网上看起来很高低,他们所说的一切都是我正在做的事情。所以,我猜我错过了一些基本的东西,很可能是在WebApiConfig中。任何帮助将不胜感激。
更新 所以,这不是我想要做代码的方式,但是,我确实找到了这个解决方案: Is there a way to handle form post data in a Web Api controller?
var httpctx = (HttpContextWrapper)Request.Properties["MS_HttpContext"];
tokenRequest.redirect_url = httpctx.Request.Form["redirect_url"] ?? null;
tokenRequest.code = httpctx.Request.Form["code"] ?? null;
tokenRequest.grant_type = httpctx.Request.Form["grant_type"] ?? null;
tokenRequest.clientID = clientID;
答案 0 :(得分:1)
如果你仍然在寻找标准的方法,你必须扩展IModelBinder类
以下是示例
public class CustomModelBinder : IModelBinder
{
public bool BindModel(HttpActionContext actionContext, ModelBindingContext bindingContext)
{
ObjToPass obj = new ObjToPass();
var parameter =HttpUtility.ParseQueryString(HttpUtility.UrlDecode(actionContext.Request.Content.ReadAsStringAsync().Result).Remove(0,4));
var res = parameter.ToString().Split('&');
obj.Id = Convert.ToInt32(res[0].Split('=')[1]);
obj.Name = res[1].Split('=')[1];
bindingContext.Model = obj;
//obj.Id = Convert.ToInt32(bindingContext.PropertyMetadata.Values[0]);
return true;
}
}
public class CustomerOrderModelBinderProvider : ModelBinderProvider
{
public override IModelBinder GetBinder(System.Web.Http.HttpConfiguration configuration, Type modelType)
{
return new CustomModelBinder();
}
}
在您的控制器中添加此
[HttpPost]
public void PostValues([ModelBinder(typeof(CustomerOrderModelBinderProvider))] ObjToPass obj)
{ }
我在请求正文中传递值。如果您采用此方法,则必须根据需要更改BindModel。我有硬编码和使用分割和数组值。
答案 1 :(得分:0)
使用[FromUri]
POST api/default?Id=1&Name=Boopathy HTTP/1.1
Host: localhost:51715
Connection: keep-alive
Content-Length: 0
Postman-Token: 86a69035-eea6-16fe-8ecd-86421336f46d
Cache-Control: no-cache
Origin: chrome-extension://aicmkgpgakddgnaphhhpliifpcfhicfo
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/56.0.2924.87 Safari/537.36
Content-Type: application/x-www-form-urlencoded
Accept: */*
Accept-Encoding: gzip, deflate, br
Accept-Language: en-GB,en-US;q=0.8,en;q=0.6
答案 2 :(得分:0)
所以,我不喜欢这个答案,但确实有效:
var httpctx = (HttpContextWrapper)Request.Properties["MS_HttpContext"];
if (Request.Content.Headers.ContentType.MediaType == "application/x-www-form-urlencoded")
{
tokenRequest.redirect_url = httpctx.Request.Form["redirect_url"] ?? null;
tokenRequest.code = httpctx.Request.Form["code"] ?? null;
tokenRequest.grant_type = httpctx.Request.Form["grant_type"] ?? null;
}
else
{
var bodyText = Request.Content.ReadAsAsync<oAuthTokenRequest>().Result;
tokenRequest.redirect_url = bodyText.redirect_url;
tokenRequest.code = bodyText.code;
tokenRequest.grant_type = bodyText.grant_type;
}
它拆分了form-urlencoded和json的请求。