3
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

ASP.NET CoreでIDスキャフォールディング後にRoleを追加する話。

Posted at

概要

ASP.NET Coreで、認証無しのテンプレートにID スキャフォールディングで追加した後に、IdentityRoleを追加するサンプルです。
IDスキャフォールディングで追加すると、UserのみでRoleは使わないテンプレートが作られます。

たとえば、

  • "Administrator"グループのユーザにだけ制限したページを作りたい

ときにRoleを使うと便利なのですが、意外とここからどうすればいいかよくわかりません。

Razor Pageベースのモノが見当たらず、あっても今度はUserStoreやらRoleStoreやらをフルに実装するモノしかなく大変ややこしかったので一から作ってみました。

環境

  • Visual Studio 2017 Professional( Build Toolsでもたぶん大丈夫)
  • .NET Core 2.1
  • ASP.NET Core 2.1
  • Razor Pages

ソース

完全なソースは、
https://github.com/imudak/IdRoleSample
にあります。

追加手順

以下の手順で変更を加えていきます。
リンクはgithubのcommitに対応しています。

1. ASP.NET Core WEbアプリケーションの作成
2. ID スキャフォールディング Login, Logout, AccessDenied, Registerを実装。
3. NuGetパッケージ更新。
4. app.UseAuthentication()追加。
5. Loginメニュー追加。
6. EmailをUserNameに変更。外部ログイン認証へのリンク削除。
7. 簡単のため、UseInMemoryDatabase()を使用。
8. Contactを認証が必要なページとする。
9. IdentityRoleを追加。
10. 起動時にAdministrator Roleを生成。
11. Register時にRoleの項目(IsAdministrator)追加。
12. Policy = "RequireAdministratorRole"追加。

詳細は、リンク先のgithub を見ていただくとして:sweat_smile:肝心なとこだけ書きます。

9. IdentityRoleを追加。

IdentityDbContextの書き換え

/Areas/Identity/Data/IdRoleSampleContext.cs の親クラスを変更します。

 namespace IdRoleSample.Models
 {
-    public class IdRoleSampleContext : IdentityDbContext<IdentityUser>
+    public class IdRoleSampleContext : IdentityDbContext<IdentityUser, IdentityRole, string>
     {
         public IdRoleSampleContext(DbContextOptions<IdRoleSampleContext> options)
             : base(options)

AddDefaultIdentityをAddIdentityに変更

/Areas/Identity/IdentityHostingStartup.csにて、

  • AddDefaultIdentityからAddIdentityにして、IdentityRoleを追加
  • AddDefaultUI()を追加。
namespace IdRoleSample.Areas.Identity
{
    public class IdentityHostingStartup : IHostingStartup
    {
        public void Configure(IWebHostBuilder builder)
        {
            builder.ConfigureServices((context, services) =>
            {
                services.AddDbContext<IdRoleSampleContext>(options =>
                    options.UseInMemoryDatabase("IdRoleSampleContext"));
                //options.UseSqlServer(
                //    context.Configuration.GetConnectionString("IdRoleSampleContextConnection")));

-                services.AddDefaultIdentity<IdentityUser>()
-                    .AddEntityFrameworkStores<IdRoleSampleContext>();
+                services.AddIdentity<IdentityUser, IdentityRole>()
+                    .AddEntityFrameworkStores<IdRoleSampleContext>()
+                    .AddDefaultUI();
            });
        }
    }
}

AddDefaultUI()追加ですが、これしないと認証失敗したときになぜか/Identity/Account/Login/に飛んでくれませんでした。

12. Policy = "RequireAdministratorRole"追加。

/Areas/Identity/IdentityHostingStartup.csにて"RequireAdministratorRole"というPolicyを追加しています。

    public class IdentityHostingStartup : IHostingStartup
    {
        public void Configure(IWebHostBuilder builder)
        {
            builder.ConfigureServices((context, services) =>
            {
                services.AddDbContext<IdRoleSampleContext>(options =>
                    options.UseInMemoryDatabase("IdRoleSampleContext"));
                //options.UseSqlServer(
                //    context.Configuration.GetConnectionString("IdRoleSampleContextConnection")));

                services.AddIdentity<IdentityUser, IdentityRole>()
                    .AddEntityFrameworkStores<IdRoleSampleContext>()
                    .AddDefaultUI();
+
+                services.AddAuthorization(options =>
+                {
+                    options.AddPolicy("RequireAdministratorRole", policy => policy.RequireRole("Administrator"));
+                });
            });
        }
    }

この"RequireAdministratorRole"ポリシーを使って、/Contact/ページには"Administrator"Roleのユーザーでないとアクセスできないようにしています。

namespace IdRoleSample.Pages
{
    [Authorize(Policy = "RequireAdministratorRole")]
    public class ContactModel : PageModel
    {
        public string Message { get; set; }

        public void OnGet()
        {
            Message = "Your contact page.";
        }
    }
}

参考

3
5
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?