JSONP с ASP.NET Web API - PullRequest
       32

JSONP с ASP.NET Web API

135 голосов
/ 24 февраля 2012

Я работаю над созданием нового набора сервисов в ASP.MVC MVC 4 с использованием Web API.Пока это здорово.Я создал сервис и заставил его работать, и теперь я пытаюсь использовать его с помощью JQuery.Я могу вернуть строку JSON с помощью Fiddler, и, похоже, все в порядке, но поскольку служба существует на отдельном сайте, я пытаюсь вызвать ее с ошибками JQuery с помощью «Not Allowed».Таким образом, это явно тот случай, когда мне нужно использовать JSONP.

Я знаю, что веб-API является новым, но я надеюсь, что кто-то там может мне помочь.сделать вызов метода Web API с использованием JSONP?

Ответы [ 15 ]

1 голос
/ 11 июля 2012

Йохперл, Томас. Ответ, данный Питером Мобергом выше, должен быть верным для RC-версии, поскольку JsonMediaTypeFormatter, от которого он наследует, уже использует сериализатор NewtonSoft Json, и поэтому то, что у него есть, должно работать без изменений.

Однако, почему люди все еще используют параметры, когда вы можете просто сделать следующее

public override Task WriteToStreamAsync(Type type, object value, Stream stream, HttpContentHeaders contentHeaders, TransportContext transportContext)
        {
            var isJsonpRequest = IsJsonpRequest();

            if(isJsonpRequest.Item1)
            {
                return Task.Factory.StartNew(() =>
                {
                    var writer = new StreamWriter(stream);
                    writer.Write(isJsonpRequest.Item2 + "(");
                    writer.Flush();
                    base.WriteToStreamAsync(type, value, stream, contentHeaders, transportContext).Wait();
                    writer.Write(")");
                    writer.Flush();
                });
            }

            return base.WriteToStreamAsync(type, value, stream, contentHeaders, transportContext);
        }

        private Tuple<bool, string> IsJsonpRequest()
        {
            if(HttpContext.Current.Request.HttpMethod != "GET")
                return new Tuple<bool, string>(false, null);

            var callback = HttpContext.Current.Request.QueryString[CallbackQueryParameter];

            return new Tuple<bool, string>(!string.IsNullOrEmpty(callback), callback);
        }
0 голосов
/ 15 марта 2018

Мы можем решить проблему CORS (совместного использования ресурсов из разных источников) двумя способами,

1) Использование Jsonp 2) Включение Cors

1) Использование Jsonp- для использования Jsonp нам нужно установить пакет nuget WebApiContrib.Formatting.Jsonp и нужно добавить JsonpFormmater в WebApiConfig.cs см. скриншоты, enter image description here

Код Jquery enter image description here

2) Включение Cors -

, чтобы включить cors, нам нужно добавить пакет nuget Microsoft.AspNet.WebApi.Cors, и нам нужно включить cors в WebApiConfig.cs, смотрите скриншот

enter image description here

Для получения дополнительной информации, вы можете обратиться к моему примеру репозитория на GitHub, используя следующую ссылку. https://github.com/mahesh353/Ninject.WebAPi/tree/develop

0 голосов
/ 13 февраля 2015

Если контекст Web Api, благодаря и ссылаясь на ответ 010227leo, вы должны учитывать WebContext.Current значение, которое будет null.

Поэтому я обновил его кодэто:

public class JsonCallbackAttribute
    : ActionFilterAttribute
{
    private const string CallbackQueryParameter = "callback";

    public override void OnActionExecuted(HttpActionExecutedContext context)
    {
        var callback = context.Request.GetQueryNameValuePairs().Where(item => item.Key == CallbackQueryParameter).Select(item => item.Value).SingleOrDefault();

        if (!string.IsNullOrEmpty(callback))
        {
            var jsonBuilder = new StringBuilder(callback);

            jsonBuilder.AppendFormat("({0})", context.Response.Content.ReadAsStringAsync().Result);

            context.Response.Content = new StringContent(jsonBuilder.ToString());
        }

        base.OnActionExecuted(context);
    }
}
0 голосов
/ 12 августа 2013

Проверьте это.Посмотрите, поможет ли это.

JSONP с веб-API

0 голосов
/ 14 января 2013

Для тех из вас, кто использует HttpSelfHostServer, этот раздел кода не будет работать на HttpContext.Current, так как он не существует на самом хост-сервере.

private Tuple<bool, string> IsJsonpRequest()
{
if(HttpContext.Current.Request.HttpMethod != "GET")
 return new Tuple<bool, string>(false, null);
 var callback = HttpContext.Current.Request.QueryString[CallbackQueryParameter];
 return new Tuple<bool, string>(!string.IsNullOrEmpty(callback), callback);
 }

Однако вы можете перехватить само«контекст» хоста через это переопределение.

public override MediaTypeFormatter GetPerRequestFormatterInstance(Type type, HttpRequestMessage request, MediaTypeHeaderValue mediaType)
        {
            _method = request.Method;
            _callbackMethodName =
                request.GetQueryNameValuePairs()
                       .Where(x => x.Key == CallbackQueryParameter)
                       .Select(x => x.Value)
                       .FirstOrDefault();

            return base.GetPerRequestFormatterInstance(type, request, mediaType);
        }

Request.Method выдаст вам «GET», «POST» и т. д., а GetQueryNameValuePairs может получить параметр? callback.Таким образом, мой пересмотренный код выглядит так:

private Tuple<bool, string> IsJsonpRequest()
 {
     if (_method.Method != "GET")
     return new Tuple<bool, string>(false, null);

     return new Tuple<bool, string>(!string.IsNullOrEmpty(_callbackMethodName), _callbackMethodName);
}

Надеюсь, это поможет некоторым из вас.Таким образом, вам не обязательно нужен HttpContext shim.

C.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...