ABP VNext种子数据按顺序插入

文章详细介绍了在ABPVNext框架中如何按顺序插入种子数据,包括新增Author和Book实体,定义CustomDataSeedDbMigrationService以插入自定义数据,实现ISowSeed接口来控制种子数据的执行顺序,以及使用EntityFramework进行数据库操作和迁移。通过这些步骤,确保了作者和图书信息的正确插入。
摘要由CSDN通过智能技术生成

1.Domain层

1.1 新加Author和Book实体

 public class Author : FullAuditedAggregateRoot<Guid>
    {
        public string Name { get; private set; }
        public DateTime BirthDate { get; set; }
        public string ShortBio { get; set; }

        private Author()
        {
            /* This constructor is for deserialization / ORM purpose */
        }

        internal Author(
            Guid id,
            [NotNull] string name,
            DateTime birthDate,
            [CanBeNull] string shortBio = null)
            : base(id)
        {
            SetName(name);
            BirthDate = birthDate;
            ShortBio = shortBio;
        }

        internal Author ChangeName([NotNull] string name)
        {
            SetName(name);
            return this;
        }

        private void SetName([NotNull] string name)
        {
            Name = Check.NotNullOrWhiteSpace(
                name,
                nameof(name),
                maxLength: 100
            );
        }
    }
public class Book : AuditedAggregateRoot<Guid>, IMultiTenant
    {
        public string Name { get; set; }

        public BookType Type { get; set; }

        public DateTime PublishDate { get; set; }

        public float Price { get; set; }

        public Guid AuthorId { get; set; }

        public Guid? TenantId { get; set; }
    }

1.2 CustomDataSeedDbMigrationService新加方法

CustomDataSeedDbMigrationService中的MigrateAsync方法中添加自定义的种子数据插入方法:

    private async Task CustomSeedDataAsync(bool isUseCustomRank = true)
    {
        var dataSeedContext = new DataSeedContext()
            .WithProperty(IdentityDataSeedContributor.AdminEmailPropertyName, "admin@ycims.com")
            .WithProperty(IdentityDataSeedContributor.AdminPasswordPropertyName, "ycqwe123")
            .WithProperty("IsUseCustomRank", isUseCustomRank);

        await _dataSeeder.SeedAsync(dataSeedContext);
    }

MigrateAsync完整代码:

public async Task MigrateAsync()
    {
        var initialMigrationAdded = AddInitialMigrationIfNotExist();

        if (initialMigrationAdded)
        {
            return;
        }

        Logger.LogInformation("Started database migrations...");

        await MigrateDatabaseSchemaAsync();
        await SeedDataAsync();
        //自定义顺序插入种子数据
        await CustomSeedDataAsync();
        Logger.LogInformation($"Successfully completed host database migrations.");

        var tenants = await _tenantRepository.GetListAsync(includeDetails: true);

        var migratedDatabaseSchemas = new HashSet<string>();
        foreach (var tenant in tenants)
        {
            using (_currentTenant.Change(tenant.Id))
            {
                if (tenant.ConnectionStrings.Any())
                {
                    var tenantConnectionStrings = tenant.ConnectionStrings
                        .Select(x => x.Value)
                        .ToList();

                    if (!migratedDatabaseSchemas.IsSupersetOf(tenantConnectionStrings))
                    {
                        await MigrateDatabaseSchemaAsync(tenant);

                        migratedDatabaseSchemas.AddIfNotContains(tenantConnectionStrings);
                    }
                }

                await SeedDataAsync(tenant);
            }

            Logger.LogInformation($"Successfully completed {tenant.Name} tenant database migrations.");
        }

        Logger.LogInformation("Successfully completed all database migrations.");
        Logger.LogInformation("You can safely end this process...");
    }

1.3新加ISowSeed接口

 public interface ISowSeed
    {
        /// <summary>
        /// 种子执行顺序(从小到大执行)
        /// </summary>
        int Sort { get; set; }

        Task ExecAsync(DataSeedContext context);
    }

1.4 作者和图书种子数据逻辑

这里作者的数据顺序为1,图书为2

 public class AuthorSowSeed : ISowSeed, ITransientDependency
    {
        private readonly IRepository<Author, Guid> _authorRepository;
        private readonly IGuidGenerator _guidGenerator;

        public AuthorSowSeed(IRepository<Author, Guid> authorRepository, IGuidGenerator guidGenerator)
        {
            _authorRepository = authorRepository;
            _guidGenerator = guidGenerator;
        }

        public int Sort { get; set; } = 1;

        public async Task ExecAsync(DataSeedContext context)
        {
            await this.MockData();
        }

        private async ValueTask MockData()
        {
            var author1 = await _authorRepository.FindAsync(s => s.Name == "George Orwell");
            if (author1 == null)
            {
                await _authorRepository.InsertAsync(new Author(_guidGenerator.Create(), "George Orwell", new DateTime(1903, 06, 25), "Orwell produced literary criticism and poetry, fiction and polemical journalism; and is best known for the allegorical novella Animal Farm (1945) and the dystopian novel Nineteen Eighty-Four (1949)."), autoSave: true);
            }

            var author2 = await _authorRepository.FindAsync(s => s.Name == "Douglas Adams");
            if (author2 == null)
            {
                var douglas = await _authorRepository.InsertAsync(new Author(_guidGenerator.Create(), "Douglas Adams", new DateTime(1952, 03, 11), "Douglas Adams was an English author, screenwriter, essayist, humorist, satirist and dramatist. Adams was an advocate for environmentalism and conservation, a lover of fast cars, technological innovation and the Apple Macintosh, and a self-proclaimed 'radical atheist'."), autoSave: true);
            }

        }
    }

    public class BookSowSeed : ISowSeed, ITransientDependency
    {
        private readonly IRepository<Book, Guid> _bookRepository;
        private readonly IRepository<Author, Guid> _authorRepository;

        public BookSowSeed(IRepository<Book, Guid> bookRepository, IRepository<Author, Guid> authorRepository)
        {
            _bookRepository = bookRepository;
            _authorRepository = authorRepository;
        }

        public int Sort { get; set; } = 2;

        public async Task ExecAsync(DataSeedContext context)
        {
            await this.MockData();
        }

        private async ValueTask MockData()
        {
            var book1 = await _bookRepository.FindAsync(s => s.Name == "1984");
            if (book1 == null)
            {
                await _bookRepository.InsertAsync(
               new Book
               {
                   AuthorId = (await _authorRepository.FindAsync(s => s.Name == "George Orwell")).Id, // SET THE AUTHOR
                   Name = "1984",
                   Type = BookType.Dystopia,
                   PublishDate = new DateTime(1949, 6, 8),
                   Price = 19.84f

               },
               autoSave: true
           );
            }

            var book2 = await _bookRepository.FindAsync(s => s.Name == "The Hitchhiker's Guide to the Galaxy");
            if (book2 == null)
            {
                await _bookRepository.InsertAsync(
              new Book
              {
                  AuthorId = (await _authorRepository.FindAsync(s => s.Name == "Douglas Adams")).Id, // SET THE AUTHOR
                  Name = "The Hitchhiker's Guide to the Galaxy",
                  Type = BookType.ScienceFiction,
                  PublishDate = new DateTime(1995, 9, 27),
                  Price = 42.0f
              },
              autoSave: true
          );
            }

        }
    }

1.5 新加CustomDataSeedDataSeederContributor

    internal class CustomDataSeedDataSeederContributor : IDataSeedContributor, ITransientDependency
    {
        private readonly IEnumerable<ISowSeed> _dataSowSeeds;

        public CustomDataSeedDataSeederContributor(IEnumerable<ISowSeed> dataSowSeeds)
        {
            this._dataSowSeeds = dataSowSeeds;
        }

        public async Task SeedAsync(DataSeedContext context)
        {
            if (!context.Properties.ContainsKey("IsUseCustomRank"))
            {
                return;
            }

            var items = _dataSowSeeds.OrderBy(p => p.Sort);
            foreach (var item in items)
            {
                await item.ExecAsync(context);
            }
        }
    }

2.EntityFrameworkCore

2.1 CustomDataSeedDbContext

    public DbSet<Book> Books { get; set; }
    public DbSet<Author> Authors { get; set; }

    builder.Entity<Book>(b =>
        {
            b.ToTable(CustomDataSeedConsts.DbTablePrefix + "Books",
                CustomDataSeedConsts.DbSchema);
            b.ConfigureByConvention(); //auto configure for the base class props
            b.Property(x => x.Name).IsRequired().HasMaxLength(128);
            b.HasOne<Author>().WithMany().HasForeignKey(x => x.AuthorId).IsRequired();
        });

        builder.Entity<Author>(b =>
        {
            b.ToTable(CustomDataSeedConsts.DbTablePrefix + "Authors",
                CustomDataSeedConsts.DbSchema);

            b.ConfigureByConvention();

            b.Property(x => x.Name)
                .IsRequired()
                .HasMaxLength(100);

            b.HasIndex(x => x.Name);
        });

2.2 生成迁移脚本

dotnet ef migrations add AddBooks

2.3 应用到数据库

应用到数据库之后,启动CustomDataSeed.DbMigrator项目可以打断点查看种子数据生成顺序

dotnet ef database update

3.源码

源代码

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值