1. ホーム
  2. c#

[解決済み] ASP.NET Web APIのカスタムメソッド名

2022-10-09 03:03:20

質問

WCF Web APIから新しいASP.NET MVC 4 Web APIに変換しているところです。私はUsersControllerを持っており、Authenticateという名前のメソッドを持ちたいと思っています。GetAll、GetOne、Post、Deleteの例を見ましたが、これらのサービスに追加のメソッドを追加したい場合はどうすればよいでしょうか。例えば、私のUsersServiceにはAuthenticateというメソッドがあり、ユーザ名とパスワードを渡すはずですが、うまくいきません。

public class UsersController : BaseApiController
{
    public string GetAll()
    {
        return "getall!";
    }

    public string Get(int id)
    {
        return "get 1! " + id;
    }

    public User GetAuthenticate(string userName, string password, string applicationName)
    {
        LogWriter.Write(String.Format("Received authenticate request for username {0} and password {1} and application {2}",
            userName, password, applicationName));

        //check if valid leapfrog login.
        var decodedUsername = userName.Replace("%40", "@");
        var encodedPassword = password.Length > 0 ? Utility.HashString(password) : String.Empty;
        var leapFrogUsers = LeapFrogUserData.FindAll(decodedUsername, encodedPassword);

        if (leapFrogUsers.Count > 0)
        {
            return new User
            {
                Id = (uint)leapFrogUsers[0].Id,
                Guid = leapFrogUsers[0].Guid
            };
        }
        else
            throw new HttpResponseException("Invalid login credentials");
    }
}

myapi/api/users/をブラウズするとGetAllが、myapi/api/users/1をブラウズするとGetが呼ばれますが、myapi/api/users/authenticate?username={0}&password={1}とすると、Get (NOT Authenticate) とエラーが発生します。

Navtrak.Services.WCF.NavtrakAPI.Controllers.UsersController' の 'System.String Get(Int32)' メソッドのパラメータ 'id' が NULL でない型 'System.Int32' のため、パラメータ辞書に null エントリが含まれています。オプションのパラメータは、参照型、NULL可能な型、またはオプションのパラメータとして宣言されている必要があります。

Authenticateのようなカスタムメソッド名を呼び出すにはどうしたらよいですか?

どのように解決するのですか?

デフォルトでは、ルート設定はRESTFulの規約に従っており、Get、Post、Put、Deleteのアクション名のみを受け付けます(global.asaxのルートを見てください => デフォルトではアクション名を指定できません => HTTP動詞を使用してディスパッチされます)。つまり、GET リクエストを /api/users/authenticate に GET リクエストを送ると、基本的に Get(int id) アクションを呼び出し id=authenticate を渡すと、Getアクションが整数を期待するため、明らかにクラッシュします。

もし標準的なものと異なるアクション名を持ちたいなら、ルート定義を global.asax :

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

これで /api/users/getauthenticate に移動してユーザーを認証します。