Как создать URL-адрес веб-API ASP.NET?

120

В ASP.NET MVC у нас есть @Url.Actionдействия. Есть ли что-то похожее, например @Url.Api, на / api / controller?

Шейн Кортриль
источник

Ответы:

139

ApiController имеет свойство Url который имеет тип System.Web.Http.Routing.UrlHelper , который позволяет построить URLs для контроллеров API.

Пример:

public class ValuesController : ApiController
{
    // GET /api/values
    public IEnumerable<string> Get()
    {
        // returns /api/values/123
        string url = Url.Route("DefaultApi", new { controller = "values", id = "123" });
        return new string[] { "value1", "value2" };
    }

    // GET /api/values/5
    public string Get(int id)
    {
        return "value";
    }

    ...
}

Этого UrlHelper нет ни в ваших представлениях, ни в стандартных контроллерах.


ОБНОВИТЬ:

А чтобы выполнять маршрутизацию вне ApiController, вы можете сделать следующее:

public class HomeController : Controller
{
    public ActionResult Index()
    {
        string url = Url.RouteUrl(
            "DefaultApi", 
            new { httproute = "", controller = "values", id = "123" }
        );
        return View();
    }
}

или внутри представления:

<script type="text/javascript">
    var url = '@Url.RouteUrl("DefaultApi", new { httproute = "", controller = "values", id = "123" })';
    $.ajax({
       url: url,
       type: 'GET',
       success: function(result) {
           // ...
       }
    });
</script>

Обратите внимание на httproute = ""маркер маршрута, который важен.

Очевидно, это предполагает, что ваш маршрут Api вызывается DefaultApiв вашем методе RegisterRoutes в Global.asax:

routes.MapHttpRoute(
    name: "DefaultApi",
    routeTemplate: "api/{controller}/{id}",
    defaults: new { id = RouteParameter.Optional }
);
Дарин Димитров
источник
Это ... на самом деле мне не очень помогает, так как мне нужно, чтобы мой View мог безопасно генерировать URL-адреса. Если есть лицензия Go Live, какой способ «Go Live» создавать URL-адреса в просмотре?
Шейн Кортриль
Что еще более важно, это не сработает, если вы используете ASP.Net Development Server, поскольку он все время меняет порты, поэтому вы даже не можете жестко указать URL-адрес в представлении.
Шейн Кортриль
@ShaneCourtrille, я обновил свой ответ, чтобы проиллюстрировать, как вы можете использовать нормальный System.Web.Mvc.UrlHelperалгоритм для генерации маршрутов Api вне HttpControllerContext.
Дарин Димитров
Огромное спасибо! Я пытался использовать RouteUrl, но не знал о требованиях httproute param.
Шейн Кортриль
2
Я понимаю цель образца; Я говорю, что это был бы более полезный образец, если бы вы добавили одну строку кода ViewBag, потому что вы продемонстрировали бы, что это значение - это то, к чему мы пытались добраться в вероятном сценарии, а не просто при выполнении некоторого произвольного кода. Опять же, я бы не стал комментировать, если бы не потратил пару минут, не осознавая, что я упустил, прежде чем я наконец осознал, что конкретная строка кода была соответствующей.
Джон Дэвис,
43

Он работает с более простой формой, Url.Actionпоэтому вам не нужно ссылаться на какие-либо имена маршрутизации:

Url.Action("ActionName", "ControllerName", new { httproute = "DefaultApi" })

Вы можете добавить, area = ""если URL-адрес требуется в пределах области. (Контроллеры Api по умолчанию находятся за пределами областей.) Я использую MVC 4.

Габор Имре
источник
7
UrlHelper в Web Api - это msdn.microsoft.com/en-us/library/… , у него нет метода действия.
Юрий Факторович
8
@YuriyFaktorovich Этот пост подразумевает, Url.Actionчто используется из View. Urlотносится к типу System.Web.Mvc.UrlHelperи не соответствует WebApiмаршрутам. Вот почему вам нужен дополнительный параметр: new { httproute = "" }.
Джесси
3
Я добавил, httproute""но это не отображение = /
Маслоу
Мне пришлось добавить ссылку с пустой областью и нулевыми атрибутами html, @Html.ActionLink("link", "Get", "Servers", new { id = r.idServer, area = "", httproute = "" }, null) но это сработало отлично
Кристофер Г. Льюис,
2
Это отлично работает из представления, однако я не уверен, почему он генерирует имя действия в виде строки запроса, например: / api / dashboard? Action = getdata. Я ожидал этого: / api / dashboard / getdata
umutesen
7

Хотите иметь возможность генерировать ссылки безопасным способом, без жестко заданных строк (имен контроллеров)?

Для этого есть nuget! (и это написано Марком Симаном)

https://github.com/ploeh/Hyprlinkr

Работает так:

Маршруты, как обычно:

name: "API Default",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }

Получите URL:

var linker = new RouteLinker(request);
var uri = linker.GetUri<FooController>(r => r.GetById(1337));

Результат:

http://localhost/api/foo/1337
Кристиан Диаконеску
источник
3

Вот метод KISS для ответа на вопрос:

Если это код, который вы использовали бы для создания URL-адреса контроллера MVC

@Url.Action("Edit", "MyController")

Чтобы получить URL-адрес версии API контроллера (при условии, что вы используете то же имя контроллера), вы можете использовать

@Url.Action("Edit", "api/MyController")

Все, что делает метод Url.Action, - это добавление корневого пути приложения с именем контроллера, за которым следует имя действия (если это не «Индекс», и в этом случае он не добавляется. Если объект значений маршрута имеет идентификатор свойство значение также добавляется к URL-адресу.

Джеймс Банч
источник
Спасибо! Мне не хватало имени api/перед моим контроллером.
Дэниел Конгроув