The use of Mvc WebApi and cross-domain problems, mvcwebapi
I often use webservice to call interfaces in my company, but it is always a web service. I think it is too heavy. Although some people feel very comfortable and awesome. For example, the company needs to connect to another group of interfaces during development, and then it can only specify the port and ip address to its computer. For various problems, he is modifying the Code or the computer is not enabled, and we cannot develop it here. I hope to use the api next time
Then, Many api articles in the garden did not go down to the Cross-origin solution, demonstrating that the project was successfully created, and then the api method was successfully obtained in the current project. It's successful? Are you kidding us? No error. It's just teasing us.
Next, let's go to webapi to create a WebApi project.
Here I have created two sites, one api and one mvc project in advance. Then add them to IIS (iis8 here). If you do not know how to add them to iis, I will briefly describe them.
Open iis manager --> website, right-click to add a website --> enter a name for the website name, select the path of your project web --> then the application pool, and select defaappapppool --> Host Name: obtain the name of your website (Note: The name here requires configuring the host file) --> OK
Then configure the host file,C: \ Windows \ System32 \ Drivers \ etcSome computers can directly modify the hosts file under the path. If not, copy the file to the desktop and put it in the folder. The configuration is as follows:
127.0.0.1 myWeb. loca/
127.0.0.1 myApi. loca/
My web host name: myWeb. loca/(same as configuring iis to name your website)
My api Host Name: myApi. loca/(same as configuring iis to name your website)
Remember to add the http://myWeb.loca/
Start api journey
Next, I started to implement the project. The above configurations are ready.
First, we need to modify the route of the webapi, because the default method is to determine the access method based on parameter transmission. Here I set it to the mvc habit App_Start --> WebApiConfig. cs
config.Routes.MapHttpRoute( name: "DefaultApi", routeTemplate: "api/{controller}/{action}/{id}", defaults: new { id = RouteParameter.Optional } );
Then there is a method for writing the api.
Public class ValuesController: ApiController {private LX. EFOPT. BLL. IBLL. IUser_InfoBLL User_InfoBLL = new User_InfoBLL (); // GET api/values public string GetList () {List <LX. EFOPT. model. user_Info> modelUser_InfoList = User_InfoBLL.GetUser_InfoList (); string jsonList = JsonUtils. serializeToJson (modelUser_InfoList); return JsonUtils. serializeToJson (new {code = "1", msg = "success", data = modelUser_InfoList });}View Code
Then, we access this api directly in the browser, verify that our data is correct output, direct access address: http://myapi.loca/api/values/GetList
The result is as follows:
Oh, Mom, good, kensen! Of course, this is not over yet. I have not played with you. Next, I access the api at myWeb. loca/this web site. Walk you ~
Similarly, I have created a user controller on the web site, and now I want to create an apitest page.
<Input type = "button" id = "getlist" value = "get data list"/> <br/>
function getlist() { var url = "http://myapi.loca/api/values/GetList?callback=?";
Console. log ("getJSON: start ");
$. GetJSON (url,
Function (data ){
// Process data
Console. log ("getJSON: end ");
Console. log ($. parseJSON (data ));
});
}
Returned result: the callback function is not executed.
It is difficult to find the cause of this problem for the first time. Ajax has been executed and the status is 200. You can also see the string returned by Response in the Network. In short, no returned results are executed in the callback function of $. getJSON.
Solution 1
1. Let's start with a low-cost (lower version) solution. This version only requires Framework 4.0.
We add a JsonCallbackAttribute class under the App_Start folder to inherit from ActionFilterAttribute. Pay attention to the Code. This code is determined based on the passed callback parameter.
Public class JsonCallbackAttribute: ActionFilterAttribute {private const string CallbackQueryParameter = "callback"; public override void OnActionExecuted (HttpActionExecutedContext context) {var callback = string. empty; if (IsJsonp (out callback) {var jsonBuilder = new StringBuilder (callback); jsonBuilder. appendFormat ("({0})", context. response. content. readAsStringAsync (). result); context. respon Se. content = new StringContent (jsonBuilder. toString ();} base. onActionExecuted (context);} private bool IsJsonp (out string callback) {callback = HttpContext. current. request. queryString [CallbackQueryParameter]; return! String. IsNullOrEmpty (callback );}}View Code
Then, you can add this [JsonCallback] attribute to the api method or controller.
[JsonCallback] public class ValuesController: ApiController // or [JsonCallback] public string GetList (){}
Next, let's take a look at the results after ajax execution?
After the [JsonCallback] is added, the result shows that the callback is successful. Json is also printed, indicating that our solution is successful. Oh, good ~
Solution 2
The cost of this method is high, at least the version of Framework 4.5 or later. What are you afraid. Just install one. Yes, but does the average server have 4.5 of them? We don't have one.
Step 1: Add a JsonpMediaTypeFormatter class under the App_Start folder of the api site
Public class JsonpMediaTypeFormatter: JsonMediaTypeFormatter {public string Callback {get; private set;} public JsonpMediaTypeFormatter (string callback = null) {this. callback = callback;} public override Task WriteToStreamAsync (Type type, object value, Stream writeStream, HttpContent content, System. net. transportContext transportContext) {if (string. isNullOrEmpty (this. callback) {return bas E. writeToStreamAsync (type, value, writeStream, content, transportContext);} try {this. writeToStream (type, value, writeStream, content); return Task. fromResult <AsyncVoid> (new AsyncVoid ();} catch (Exception exception) {TaskCompletionSource <AsyncVoid> source = new TaskCompletionSource <AsyncVoid> (); source. setException (exception); return source. task;} private void WriteToStream (Type type, obje Ct value, Stream writeStream, HttpContent content) {JsonSerializer serializer = JsonSerializer. create (this. serializerSettings); using (StreamWriter streamWriter = new StreamWriter (writeStream, this. supportedEncodings. first () using (JsonTextWriter jsonTextWriter = new JsonTextWriter (streamWriter) {CloseOutput = false}) {jsonTextWriter. writeRaw (this. callback + "("); serializer. serialize (jsonTe XtWriter, value); jsonTextWriter. WriteRaw (")") ;}} public override MediaTypeFormatter GetPerRequestFormatterInstance (Type type, HttpRequestMessage request, required mediaType) {if (request. Method! = HttpMethod. get) {return this;} string callback; if (request. getQueryNameValuePairs (). toDictionary (pair => pair. key, pair => pair. value ). tryGetValue ("callback", out callback) {return new JsonpMediaTypeFormatter (callback) ;}return this ;}}View Code
Step 2: Register Global in Application_Start of Global. asax
GlobalConfiguration.Configuration.Formatters.Insert(0, new JsonpMediaTypeFormatter());
In fact, there are solutions in the third and fourth phases, but I still haven't succeeded in the test. I don't know the specific reason.
Summary
Here we solve the ajax get method. As for post, the client submits ajax to its own Handler. ashx or controller first. The same is true for APIS submitted using httppost.
Thank you! I hope you can leave some suggestions and comments. This person will write articles. Give some encouragement.
Thank you for your article.
Reference: http://www.cnblogs.com/artech/p/cors-4-asp-net-web-api-03.html
Http://stackoverflow.com/questions/9421312/jsonp-with-asp-net-web-api/18206518#18206518
From: http://www.cnblogs.com/lxsweat/