The database is seeded by adding statements to the PerformInitialSetup method of the IdentityDbInit class, which is the application-specific Entity Framework database setup class. Listing 14-20 shows the changes I made to create an administration user.
ÖÖÖ²Êý¾Ý¿âµÄ°ì·¨ÊÇÔÚIdentityDbInitÀàµÄPerformInitialSetup·½·¨ÖÐÌí¼ÓһЩÓï¾ä£¬IdentityDbInitÊÇÓ¦ÓóÌÐòרÓõÄEntity FrameworkÊý¾Ý¿âÉèÖÃÀà¡£Çåµ¥14-20ÊÇΪÁË´´½¨¹ÜÀíÓû§Ëù×öµÄÐÞ¸Ä
Listing 14-20. Seeding the Database in the AppIdentityDbContext.cs File
Çåµ¥14-20. ÔÚAppIdentityDbContext.csÎļþÖÐÖÖÖ²Êý¾Ý¿â
namespace Users.Infrastructure { public class AppIdentityDbContext : IdentityDbContext<AppUser> {
public AppIdentityDbContext() : base("IdentityDb") { }
static AppIdentityDbContext() { Database.SetInitializer<AppIdentityDbContext>(new IdentityDbInit()); }
public static AppIdentityDbContext Create() { return new AppIdentityDbContext(); } }
public class IdentityDbInit : DropCreateDatabaseIfModelChanges<AppIdentityDbContext> { protected override void Seed(AppIdentityDbContext context) { PerformInitialSetup(context); base.Seed(context); }
public void PerformInitialSetup(AppIdentityDbContext context) { AppUserManager userMgr = new AppUserManager(new UserStore<AppUser>(context)); AppRoleManager roleMgr = new AppRoleManager(new RoleStore<AppRole>(context));
string roleName = "Administrators"; string userName = "Admin"; string password = "MySecret"; string email = "admin@example.com";
if (!roleMgr.RoleExists(roleName)) { roleMgr.Create(new AppRole(roleName)); }
AppUser user = userMgr.FindByName(userName); if (user == null) { userMgr.Create(new AppUser { UserName = userName, Email = email }, password); user = userMgr.FindByName(userName); }
if (!userMgr.IsInRole(user.Id, roleName)) { userMgr.AddToRole(user.Id, roleName); } } } }
Tip For this example, I used the synchronous extension methods to locate and manage the role and user. As I explained in Chapter 13, I prefer the asynchronous methods by default, but the synchronous methods can be useful when you need to perform a sequence of related operations.
Ìáʾ£ºÔÚÉÏÊöʾÀýÖУ¬ÎÒʹÓÃÁËͬ²½µÄÀ©Õ¹·½·¨À´¶¨Î»ºÍ¹ÜÀí½ÇÉ«ºÍÓû§¡£ÕýÈçµÚ13ÕÂËù½âÊ͵ÄÄÇÑù£¬Ò»°ãÇé¿öÏÂÎÒ¸üϲ»¶Òì²½·½·¨£¬µ«ÊÇ£¬µ±ÐèÒªÖ´ÐÐһϵÁÐÏà¹Ø²Ù×÷ʱ£¬Í¬²½·½·¨¿ÉÄÜÊÇÓÐÓõġ£
I have to create instances of AppUserManager and AppRoleManager directly because the PerformInitialSetup method is called before the OWIN configuration is complete. I use the RoleManager and AppManager objects to create a role called Administrators and a user called Admin and add the user to the role.
ÎÒ±ØÐëÖ±½Ó´´½¨AppUserManagerºÍAppRoleManagerµÄʵÀý£¬ÒòΪPerformInitialSetup·½·¨ÊÇÔÚOWINÅäÖÃÍê³É֮ǰ¾Í±»µ÷Óõġ£ÎÒʹÓÃRoleManagerºÍAppManager¶ÔÏó´´½¨Ò»¸öÃû³ÆΪAdministratorsµÄ½ÇÉ«£¬ºÍÒ»¸öÃû³ÆΪµÄAdminµÄÓû§£¬²¢½«´ËÓû§Ìí¼Óµ½¸Ã½ÇÉ«¡£
Tip Read Chapter 15 before you add database seeding to your project. I describe database migrations, which allow you to take control of schema changes in the database and which put the seeding logic in a different place.
Ìáʾ£ºÔÚÏîÄ¿ÖÐÌí¼ÓÊý¾Ý¿âÖÖֲ֮ǰ£¬ÇëÏÈÔĶÁµÚ15Õ¡£ÎÒÔÚÆäÖÐÃèÊöÁËÊý¾Ý¿âǨÒÆ£¬ÕâÈÃÄãÄܹ»¶ÔÊý¾Ý¿âÖеļܹ¹±ä»¯½øÐпØÖÆ£¬²¢¿ÉÒÔ½«ÖÖÖ²Âß¼·ÅÔÚ²»Í¬µÄµØ·½¡£
With this change, I can use the Authorize attribute to protect the Admin and RoleAdmin controllers. Listing 14-21 shows the change I made to the Admin controller.
¾¹ýÕâÖÖÐ޸ģ¬ÎÒ¿ÉÒÔʹÓÃAuthorize×¢½âÊôÐÔÀ´±£»¤AdminºÍRoleAdmin¿ØÖÆÆ÷¡£Çåµ¥14-21ÏÔʾÁ˶ÔAdmin¿ØÖÆÆ÷Ëù×öµÄÐ޸ġ£
Listing 14-21. Restricting Access in the AdminController.cs File
Çåµ¥14-21. ÔÚAdminController.csÎļþÖеÄÏÞÖÆ·ÃÎÊ
namespace Users.Controllers {
[Authorize(Roles = "Administrators")] public class AdminController : Controller { // ...statements omitted for brevity... // ...³öÓÚ¼ò»¯£¬ºöÂÔÁËÕâÀïµÄÓï¾ä... } }
Listing 14-22 shows the corresponding change I made to the RoleAdmin controller.
Çåµ¥14-22ÊǶÔRoleAdmin¿ØÖÆÆ÷Ëù×öµÄÏàÓ¦Ð޸ġ£
¡¡