8

DNN の MVC ベースのサービス フレームワークを利用して、DotNetNuke 6 Web サイト用の REST API を構築しています。ただし、認証のバックグラウンドがないため、どこから始めればよいかさえわかりません。

基本的に、クライアントがポータルのデータに対して GET リクエストを作成できるようにし、一部のクライアント (すべてではない) がユーザー データの簡単な更新を POST できるようにしたいと考えています。

情報を検索しようとしていますが、何を検索しているのかわからないのが問題です。DNN にはさまざまなログインとロールがありますが、それらが考慮されているかどうか、またはどのように考慮されているかはわかりません。oAuth などについては聞いたことがありますが、それについての私の理解は最も基本的なレベルです。それが必要なものかどうか、またそれが DNN にどのように適用されるかはわかりません。誰かが私を正しい方向に向けることができますか?

更新:モジュールとの結び付けとさらなる調査に関する以下の回答に基づいて、私が行ったことは次のとおりです。

このサービス専用のモジュールを作成し、「APIGET」と「APIPOST」という 2 つの特別なアクセス許可を追加しました。これらを DNN のいくつかのテスト ロール/テスト アカウントに割り当てました。モジュール ID を指定して、現在のユーザーが必要なアクセス許可を持っているかどうかを確認するカスタムの authorize 属性を作成しました (ロールを介して、または直接)。私の知る限り、タブ ID は私の場合は関係ありません。

Web ブラウザー (ログインしている DNN アカウントに基づく) と、アカウントのユーザー名/パスワードを使用して HTTP 要求を送信する php スクリプトの両方で動作しているようです。

認証属性:

using DotNetNuke.Entities.Modules;
using DotNetNuke.Entities.Portals;
using DotNetNuke.Security;
using DotNetNuke.Security.Permissions;
using System.Web;

public class MyAuthorize : DotNetNuke.Web.Services.AuthorizeAttributeBase
{
    public const string AuthModuleFriendlyName = "MyAuthModule";
    public const string GETPermission = "APIGET";
    public const string POSTPermission = "APIPOST";

    public string Permission { get; set; }

    protected override bool AuthorizeCore(HttpContextBase context)
    {
        ModuleController mc = new ModuleController();

        ModuleInfo mi = mc.GetModuleByDefinition(PortalController.GetCurrentPortalSettings().PortalId, AuthModuleFriendlyName);

        ModulePermissionCollection permCollection = mi.ModulePermissions;

        return ModulePermissionController.HasModulePermission(permCollection, Permission);
    }
}

コントローラー: (「mytest」は GET と POST の両方のエンドポイントです)

public class MyController : DnnController
{
    [ActionName("mytest")]
    [AcceptVerbs(HttpVerbs.Get)]
    [DnnAuthorize(AllowAnonymous = true)]
    [MyAuthorize(Permission = MyAuthorize.GETPermission)]
    public string myget(string id = "")
    {
        return "You have my permission to GET";
    }

    [ActionName("mytest")]
    [AcceptVerbs(HttpVerbs.Post)]
    [DnnAuthorize(AllowAnonymous = true)]
    [MyAuthorize(Permission = MyAuthorize.POSTPermission)]
    public string mypost(string id = "")
    {
        return "You have my permission to POST";
    }
}
4

4 に答える 4

8

DNN サービス フレームワークのサービスを DNN アクセス許可に関連付ける主な方法は、アクセス許可をモジュール インスタンスに関連付けることです。つまり、サービスのユーザーがどのモジュールから/について呼び出しているかを特定する必要があります (リクエスト [ヘッダー、クエリ文字列、Cookie、フォーム] で ModuleId と TabId を送信することにより)。次に、どのアクセス許可を指定できますか?サービスに対して特定のアクションを実行するには、そのモジュールが必要です。

サービスで属性を使用し、SupportedModulesモジュール名のコンマ区切りリストを渡して、独自のモジュールのみが許可されるようにすることができます。DnnModuleAuthorize次に、サービスまたは個々のアクション レベルで属性を追加して、そのモジュールでユーザーが必要とする権限を示します。インスタンスでは、アクションにAllowAnonymous属性を追加し、メソッド (およびその他のもの)に対してサービスに属性を追加することもできます。コントローラに属性を設定できないことに注意してください。アクションに設定された承認を上書きするため、アクションをより制限することができなくなります。GETDnnModuleAuthorizePOSTAllowAnonymous

また、CSRF 攻撃から保護するためValidateAntiForgeryTokenに、アクションに属性を追加する必要があります。POST

パーミッションをサービスに自然に関連付けるモジュールがない場合は、パーミッション管理ユーティリティとして公開するためだけに、その目的のためだけにモジュールを作成できます。

上記の承認部分を把握すると、DNN はフォーム Cookie を使用して認証を処理するか (つまり、AJAX シナリオは自動的に処理されます)、または基本認証またはダイジェスト認証を介して (非 AJAX シナリオの場合) 処理します。とはいえ、非 AJAX を使用している場合は、偽造防止トークンが適用される場合にのみ、偽造防止トークンを検証する方法を見つける必要があります。

于 2013-04-17T13:19:19.720 に答える
2

[DnnModuleAuthorize(PermissionKey = "DELETEDATA")]カスタム権限を使用するための @Richards コメントに追加したかっただけです。

完全な属性は次のとおりです。

[DnnModuleAuthorize(PermissionKey = "DELETEDATA", AccessLevel = SecurityAccessLevel.Edit)]

ここに示すように、空白のままにしても何も起こりません:

于 2015-06-03T23:03:01.893 に答える
2

DnnModuleAuthorize 属性は、カスタム アクセス許可の PermissionKey パラメータを受け取るため、次のようなことができることに注意してください。

    [DnnModuleAuthorize(PermissionKey = "DELETEDATA")]
    [HttpPost]
    public HttpResponseMessage DeleteData(FormDataCollection data)

これで独自のエラー メッセージを提供できるようには見えないため、代わりに次のようにメソッド本体をラップし、カスタム許可属性を除外することができます。

    [DnnModuleAuthorize(AccessLevel = SecurityAccessLevel.View)]
    [HttpPost]
    public HttpResponseMessage DeleteData(FormDataCollection data)
    {
        var errorMessage = "Could not delete data";

        if (ModulePermissionController.HasModulePermission(ActiveModule.ModulePermissions,"DELETEDATA"))
        {
            // do stuff here
        }
        else
        {
            errorMessage = "User does not have delete permission";
        }

        var error = new HttpResponseMessage(HttpStatusCode.BadRequest)
        {
            Content =
                new StringContent(
                errorMessage)
        };
        return error;
    }
于 2014-09-16T17:55:15.110 に答える