21

Web.APIルーティングに問題があります。次の2つのルートがあります。

config.Routes.MapHttpRoute(
    name: "MethodOne",
    routeTemplate: "api/{controller}/{action}/{id}/{type}",
    defaults: new { id = RouteParameter.Optional, type = RouteParameter.Optional }
);

config.Routes.MapHttpRoute(
    name: "MethodTwo",
    routeTemplate: "api/{controller}/{action}/{directory}/{report}",
    defaults: new { directory = RouteParameter.Optional, report = RouteParameter.Optional }
);

そして私のコントローラーでは、これら2つの方法があります。

[HttpGet]
[ActionName("methodone")]
public string MethodOne(string id, string type)
{
    return string.Empty;
}

[HttpGet]
[ActionName("methodtwo")]
public string MethodTwo(string directory, string report)
{
    return string.Empty;
}

これらの2つは一見共存することはできません。WebApiConfigでMethodOneルートをコメントアウトすると、MethodTwoルートが機能します。MethodTwoルートにコメントを付けると、MethodOneが機能します。両方をコメントなしのままにしておくと、MethodOneは機能しますが、MethodTwoは機能しません。

私はこれらの両方に1つのルートを使用することを望んでいたので、同じパラメーター名を使用する必要があるようです。ジェネリックパラメーター名でメソッドを作成するのは誰ですか?悪い。メソッドに同じパラメーター名(p1、p2、p3など)を付けたくないので、新しいメソッド専用のルートを作成できると思いました。しかし、これでもうまくいかないようです。

WebGet(UriTemplate="")WCFの残りの部分が本当に恋しいです。

1つのコントローラーに多くのメソッドがあり、1つ、2つ、3つ、またはそれ以上のパラメーターを持つものもあります。MapHttpRouteアプローチで意味のあるパラメーター名を使用できないとは信じられません。

私はそれを完全にコメントして使用することができましたWebGet()…しかし、そこに着く前に、何かが足りないかどうかを確認したかったのです。

4

3 に答える 3

17

この問題が発生する理由は、最初のルートが両方のリクエストに一致するためです。URL の id と type トークンは両方のリクエストに一致します。これは、ルートが実行されているときに URL を解析し、各セグメントを URL と照合しようとするためです。

したがって、最初のルートは次のように両方のリクエストにうまく一致します。

~/methodone/1/mytype => action = methodone, id = 1, and type = mytype
~/methodtwo/directory/report => action = methodtwo, id = directory, and type = report

これを回避するには、次のようなルートを使用する必要があります

config.Routes.MapHttpRoute(
    name: "MethodOne",
    routeTemplate: "api/{controller}/methodone/{id}/{type}",
    defaults: new { id = RouteParameter.Optional, type = RouteParameter.Optional }
);

config.Routes.MapHttpRoute(
    name: "MethodTwo",
    routeTemplate: "api/{controller}/methodtwo/{directory}/{report}",
    defaults: new { directory = RouteParameter.Optional, report = RouteParameter.Optional }
);

WebGet を使用している場合でも、私が信じているこれら 2 つのメソッドのあいまいさを解消するために、同様のことを行う必要があるかもしれません。

于 2013-02-08T02:12:19.300 に答える
4

/MethodTwo?directory=a&report=b のようにクエリ文字列でパラメーターを渡すことを選択できますが、パスにパラメーターを表示したい場合は、属性ベースのルーティングに適しているように見えます。フィリップはそれについての素晴らしい投稿をここに持っています:

http://www.strathweb.com/2012/05/attribute-based-routing-in-asp-net-web-api/

于 2013-02-08T02:12:11.613 に答える
4

http://www.asp.net/web-api/overview/web-api-routing-and-actions/routing-and-action-selectionから

URI セグメントがプレースホルダーと一致する方法を制限する制約を指定することもできます。

Constraint: new { id = @"\d+" } // "id" が 1 桁以上の場合にのみ一致します。

この制約を「MethodOne」(api/{controller}/{action}/{id}/{type}) に追加すると、{id} が数値の場合にのみ一致する数値、それ以外の場合は「MethodTwo」("api /{コントローラ}/{アクション}/{ディレクトリ}/{レポート}")。

于 2013-08-07T13:43:08.417 に答える