Browse Source

Removed IdentityServer

pull/174/head
Galip Tolga Erdem 3 years ago
parent
commit
05503c6697
  1. 1
      services/identity/src/EShopOnAbp.IdentityService.Domain.Shared/EShopOnAbp.IdentityService.Domain.Shared.csproj
  2. 5
      services/identity/src/EShopOnAbp.IdentityService.Domain.Shared/IdentityServiceDomainSharedModule.cs
  3. 5
      services/identity/src/EShopOnAbp.IdentityService.Domain.Shared/IdentityServiceModuleExtensionConfigurator.cs
  4. 1
      services/identity/src/EShopOnAbp.IdentityService.Domain/EShopOnAbp.IdentityService.Domain.csproj
  5. 4
      services/identity/src/EShopOnAbp.IdentityService.Domain/IdentityServiceDomainModule.cs
  6. 1
      services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EShopOnAbp.IdentityService.EntityFrameworkCore.csproj
  7. 34
      services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EntityFrameworkCore/IdentityServiceDbContext.cs
  8. 5
      services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EntityFrameworkCore/IdentityServiceEfCoreEntityExtensionMappings.cs
  9. 5
      services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EntityFrameworkCore/IdentityServiceEntityFrameworkCoreModule.cs
  10. 424
      services/identity/src/EShopOnAbp.IdentityService.HttpApi.Host/DbMigrations/IdentityServerDataSeeder.cs
  11. 2
      services/identity/src/EShopOnAbp.IdentityService.HttpApi.Host/DbMigrations/IdentityServiceDatabaseMigrationChecker.cs

1
services/identity/src/EShopOnAbp.IdentityService.Domain.Shared/EShopOnAbp.IdentityService.Domain.Shared.csproj

@ -11,7 +11,6 @@
<ItemGroup>
<PackageReference Include="Volo.Abp.Identity.Domain.Shared" Version="7.0.0" />
<PackageReference Include="Volo.Abp.IdentityServer.Domain.Shared" Version="7.0.0" />
</ItemGroup>
<ItemGroup>

5
services/identity/src/EShopOnAbp.IdentityService.Domain.Shared/IdentityServiceDomainSharedModule.cs

@ -1,8 +1,6 @@
using EShopOnAbp.IdentityService.Localization;
using Volo.Abp.Identity;
using Volo.Abp.IdentityServer;
using Volo.Abp.Localization;
using Volo.Abp.Localization.ExceptionHandling;
using Volo.Abp.Modularity;
using Volo.Abp.Validation.Localization;
using Volo.Abp.VirtualFileSystem;
@ -10,8 +8,7 @@ using Volo.Abp.VirtualFileSystem;
namespace EShopOnAbp.IdentityService
{
[DependsOn(
typeof(AbpIdentityDomainSharedModule),
typeof(AbpIdentityServerDomainSharedModule)
typeof(AbpIdentityDomainSharedModule)
)]
public class IdentityServiceDomainSharedModule : AbpModule
{

5
services/identity/src/EShopOnAbp.IdentityService.Domain.Shared/IdentityServiceModuleExtensionConfigurator.cs

@ -1,7 +1,4 @@
using System.ComponentModel.DataAnnotations;
using Volo.Abp.Identity;
using Volo.Abp.ObjectExtending;
using Volo.Abp.Threading;
using Volo.Abp.Threading;
namespace EShopOnAbp.IdentityService
{

1
services/identity/src/EShopOnAbp.IdentityService.Domain/EShopOnAbp.IdentityService.Domain.csproj

@ -11,7 +11,6 @@
<ItemGroup>
<PackageReference Include="Volo.Abp.Identity.Domain" Version="7.0.0" />
<PackageReference Include="Volo.Abp.IdentityServer.Domain" Version="7.0.0" />
</ItemGroup>
</Project>

4
services/identity/src/EShopOnAbp.IdentityService.Domain/IdentityServiceDomainModule.cs

@ -1,13 +1,11 @@
using Volo.Abp.Identity;
using Volo.Abp.IdentityServer;
using Volo.Abp.Modularity;
namespace EShopOnAbp.IdentityService
{
[DependsOn(
typeof(IdentityServiceDomainSharedModule),
typeof(AbpIdentityDomainModule),
typeof(AbpIdentityServerDomainModule)
typeof(AbpIdentityDomainModule)
)]
public class IdentityServiceDomainModule : AbpModule
{

1
services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EShopOnAbp.IdentityService.EntityFrameworkCore.csproj

@ -18,7 +18,6 @@
<ItemGroup>
<PackageReference Include="Volo.Abp.EntityFrameworkCore.PostgreSql" Version="7.0.0" />
<PackageReference Include="Volo.Abp.Identity.EntityFrameworkCore" Version="7.0.0" />
<PackageReference Include="Volo.Abp.IdentityServer.EntityFrameworkCore" Version="7.0.0" />
</ItemGroup>
</Project>

34
services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EntityFrameworkCore/IdentityServiceDbContext.cs

@ -3,13 +3,6 @@ using Volo.Abp.Data;
using Volo.Abp.EntityFrameworkCore;
using Volo.Abp.Identity;
using Volo.Abp.Identity.EntityFrameworkCore;
using Volo.Abp.IdentityServer.ApiResources;
using Volo.Abp.IdentityServer.ApiScopes;
using Volo.Abp.IdentityServer.Clients;
using Volo.Abp.IdentityServer.Devices;
using Volo.Abp.IdentityServer.EntityFrameworkCore;
using Volo.Abp.IdentityServer.Grants;
using Volo.Abp.IdentityServer.IdentityResources;
namespace EShopOnAbp.IdentityService.EntityFrameworkCore
{
@ -23,8 +16,7 @@ namespace EShopOnAbp.IdentityService.EntityFrameworkCore
* used modules (as explained above). See IdentityServiceMigrationsDbContext for migrations.
*/
[ConnectionStringName(IdentityServiceDbProperties.ConnectionStringName)]
public class IdentityServiceDbContext : AbpDbContext<IdentityServiceDbContext>, IIdentityDbContext,
IIdentityServerDbContext
public class IdentityServiceDbContext : AbpDbContext<IdentityServiceDbContext>, IIdentityDbContext
{
public DbSet<IdentityUser> Users { get; set; }
public DbSet<IdentityRole> Roles { get; set; }
@ -32,29 +24,6 @@ namespace EShopOnAbp.IdentityService.EntityFrameworkCore
public DbSet<OrganizationUnit> OrganizationUnits { get; set; }
public DbSet<IdentitySecurityLog> SecurityLogs { get; set; }
public DbSet<IdentityLinkUser> LinkUsers { get; set; }
public DbSet<ApiResource> ApiResources { get; set; }
public DbSet<ApiResourceSecret> ApiResourceSecrets { get; set; }
public DbSet<ApiResourceClaim> ApiResourceClaims { get; set; }
public DbSet<ApiResourceScope> ApiResourceScopes { get; set; }
public DbSet<ApiResourceProperty> ApiResourceProperties { get; set; }
public DbSet<ApiScope> ApiScopes { get; set; }
public DbSet<ApiScopeClaim> ApiScopeClaims { get; set; }
public DbSet<ApiScopeProperty> ApiScopeProperties { get; set; }
public DbSet<IdentityResource> IdentityResources { get; set; }
public DbSet<IdentityResourceClaim> IdentityClaims { get; set; }
public DbSet<IdentityResourceProperty> IdentityResourceProperties { get; set; }
public DbSet<Client> Clients { get; set; }
public DbSet<ClientGrantType> ClientGrantTypes { get; set; }
public DbSet<ClientRedirectUri> ClientRedirectUris { get; set; }
public DbSet<ClientPostLogoutRedirectUri> ClientPostLogoutRedirectUris { get; set; }
public DbSet<ClientScope> ClientScopes { get; set; }
public DbSet<ClientSecret> ClientSecrets { get; set; }
public DbSet<ClientClaim> ClientClaims { get; set; }
public DbSet<ClientIdPRestriction> ClientIdPRestrictions { get; set; }
public DbSet<ClientCorsOrigin> ClientCorsOrigins { get; set; }
public DbSet<ClientProperty> ClientProperties { get; set; }
public DbSet<PersistedGrant> PersistedGrants { get; set; }
public DbSet<DeviceFlowCodes> DeviceFlowCodes { get; set; }
public IdentityServiceDbContext(DbContextOptions<IdentityServiceDbContext> options)
: base(options)
@ -66,7 +35,6 @@ namespace EShopOnAbp.IdentityService.EntityFrameworkCore
base.OnModelCreating(builder);
builder.ConfigureIdentity();
builder.ConfigureIdentityServer();
}
}
}

5
services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EntityFrameworkCore/IdentityServiceEfCoreEntityExtensionMappings.cs

@ -1,7 +1,4 @@
using Microsoft.EntityFrameworkCore;
using Volo.Abp.Identity;
using Volo.Abp.ObjectExtending;
using Volo.Abp.Threading;
using Volo.Abp.Threading;
namespace EShopOnAbp.IdentityService.EntityFrameworkCore
{

5
services/identity/src/EShopOnAbp.IdentityService.EntityFrameworkCore/EntityFrameworkCore/IdentityServiceEntityFrameworkCoreModule.cs

@ -3,7 +3,6 @@ using Microsoft.Extensions.DependencyInjection;
using Volo.Abp.EntityFrameworkCore;
using Volo.Abp.EntityFrameworkCore.PostgreSql;
using Volo.Abp.Identity.EntityFrameworkCore;
using Volo.Abp.IdentityServer.EntityFrameworkCore;
using Volo.Abp.Modularity;
namespace EShopOnAbp.IdentityService.EntityFrameworkCore
@ -11,8 +10,7 @@ namespace EShopOnAbp.IdentityService.EntityFrameworkCore
[DependsOn(
typeof(IdentityServiceDomainModule),
typeof(AbpEntityFrameworkCorePostgreSqlModule),
typeof(AbpIdentityEntityFrameworkCoreModule),
typeof(AbpIdentityServerEntityFrameworkCoreModule)
typeof(AbpIdentityEntityFrameworkCoreModule)
)]
public class IdentityServiceEntityFrameworkCoreModule : AbpModule
{
@ -26,7 +24,6 @@ namespace EShopOnAbp.IdentityService.EntityFrameworkCore
context.Services.AddAbpDbContext<IdentityServiceDbContext>(options =>
{
options.ReplaceDbContext<IIdentityDbContext>();
options.ReplaceDbContext<IIdentityServerDbContext>();
options.AddDefaultRepositories(includeAllEntities: true);
});

424
services/identity/src/EShopOnAbp.IdentityService.HttpApi.Host/DbMigrations/IdentityServerDataSeeder.cs

@ -1,424 +0,0 @@
using IdentityServer4.Models;
using Microsoft.Extensions.Configuration;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Volo.Abp.Authorization.Permissions;
using Volo.Abp.Data;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Guids;
using Volo.Abp.Identity;
using Volo.Abp.IdentityServer.ApiResources;
using Volo.Abp.IdentityServer.ApiScopes;
using Volo.Abp.IdentityServer.Clients;
using Volo.Abp.IdentityServer.IdentityResources;
using Volo.Abp.MultiTenancy;
using Volo.Abp.PermissionManagement;
using Volo.Abp.Uow;
using ApiResource = Volo.Abp.IdentityServer.ApiResources.ApiResource;
using ApiScope = Volo.Abp.IdentityServer.ApiScopes.ApiScope;
using Client = Volo.Abp.IdentityServer.Clients.Client;
namespace EShopOnAbp.IdentityService.DbMigrations;
public class IdentityServerDataSeeder : IDataSeedContributor, ITransientDependency
{
private readonly IApiResourceRepository _apiResourceRepository;
private readonly IApiScopeRepository _apiScopeRepository;
private readonly IClientRepository _clientRepository;
private readonly IIdentityResourceDataSeeder _identityResourceDataSeeder;
private readonly IGuidGenerator _guidGenerator;
private readonly IPermissionDataSeeder _permissionDataSeeder;
private readonly IConfiguration _configuration;
private readonly ICurrentTenant _currentTenant;
public IdentityServerDataSeeder(
IClientRepository clientRepository,
IApiResourceRepository apiResourceRepository,
IApiScopeRepository apiScopeRepository,
IIdentityResourceDataSeeder identityResourceDataSeeder,
IGuidGenerator guidGenerator,
IPermissionDataSeeder permissionDataSeeder,
IConfiguration configuration,
ICurrentTenant currentTenant)
{
_clientRepository = clientRepository;
_apiResourceRepository = apiResourceRepository;
_apiScopeRepository = apiScopeRepository;
_identityResourceDataSeeder = identityResourceDataSeeder;
_guidGenerator = guidGenerator;
_permissionDataSeeder = permissionDataSeeder;
_configuration = configuration;
_currentTenant = currentTenant;
}
public virtual Task SeedAsync(DataSeedContext context)
{
return SeedAsync();
}
[UnitOfWork]
public virtual async Task SeedAsync()
{
using (_currentTenant.Change(null))
{
await _identityResourceDataSeeder.CreateStandardResourcesAsync();
await CreateApiResourcesAsync();
await CreateApiScopesAsync();
await CreateSwaggerClientsAsync();
await CreateClientsAsync();
}
}
private async Task CreateApiResourcesAsync()
{
var commonApiUserClaims = new[]
{
"email",
"email_verified",
"name",
"phone_number",
"phone_number_verified",
"role"
};
await CreateApiResourceAsync("AccountService", commonApiUserClaims);
await CreateApiResourceAsync("IdentityService", commonApiUserClaims);
await CreateApiResourceAsync("AdministrationService", commonApiUserClaims);
await CreateApiResourceAsync("CatalogService", commonApiUserClaims);
await CreateApiResourceAsync("BasketService", commonApiUserClaims);
await CreateApiResourceAsync("OrderingService", commonApiUserClaims);
await CreateApiResourceAsync("PaymentService", commonApiUserClaims);
await CreateApiResourceAsync("CmskitService", commonApiUserClaims);
}
private async Task CreateApiScopesAsync()
{
await CreateApiScopeAsync("AccountService");
await CreateApiScopeAsync("IdentityService");
await CreateApiScopeAsync("AdministrationService");
await CreateApiScopeAsync("CatalogService");
await CreateApiScopeAsync("BasketService");
await CreateApiScopeAsync("OrderingService");
await CreateApiScopeAsync("PaymentService");
await CreateApiScopeAsync("CmskitService");
}
private async Task CreateSwaggerClientsAsync()
{
await CreateWebGatewaySwaggerClientAsync("WebGateway",
new[]
{
"AccountService",
"IdentityService",
"AdministrationService",
"CatalogService",
"BasketService",
"PaymentService",
"OrderingService",
"CmskitService"
});
}
private async Task CreateWebGatewaySwaggerClientAsync(string name, string[] scopes = null)
{
var commonScopes = new[]
{
"email",
"openid",
"profile",
"role",
"phone",
"address"
};
scopes ??= new[] { name };
// Swagger Client
var swaggerClientId = $"{name}_Swagger";
if (!swaggerClientId.IsNullOrWhiteSpace())
{
var webGatewaySwaggerRootUrl = _configuration[$"IdentityServerClients:{name}:RootUrl"].TrimEnd('/');
var publicWebGatewayRootUrl = _configuration[$"IdentityServerClients:PublicWebGateway:RootUrl"].TrimEnd('/');
var accountServiceRootUrl = _configuration[$"IdentityServerClients:AccountService:RootUrl"].TrimEnd('/');
var identityServiceRootUrl = _configuration[$"IdentityServerClients:IdentityService:RootUrl"].TrimEnd('/');
var administrationServiceRootUrl = _configuration[$"IdentityServerClients:AdministrationService:RootUrl"].TrimEnd('/');
var catalogServiceRootUrl = _configuration[$"IdentityServerClients:CatalogService:RootUrl"].TrimEnd('/');
var basketServiceRootUrl = _configuration[$"IdentityServerClients:BasketService:RootUrl"].TrimEnd('/');
var orderingServiceRootUrl = _configuration[$"IdentityServerClients:OrderingService:RootUrl"].TrimEnd('/');
var paymentServiceRootUrl = _configuration[$"IdentityServerClients:PaymentService:RootUrl"].TrimEnd('/');
var cmskitServiceRootUrl = _configuration[$"IdentityServerClients:CmskitService:RootUrl"].TrimEnd('/');
await CreateClientAsync(
name: swaggerClientId,
scopes: commonScopes.Union(scopes),
grantTypes: new[] { "authorization_code" },
secret: "1q2w3e*".Sha256(),
requireClientSecret: false,
redirectUris: new List<string>
{
$"{webGatewaySwaggerRootUrl}/swagger/oauth2-redirect.html", // WebGateway redirect uri
$"{publicWebGatewayRootUrl}/swagger/oauth2-redirect.html", // PublicWebGateway redirect uri
$"{accountServiceRootUrl}/swagger/oauth2-redirect.html", // AccountService redirect uri
$"{identityServiceRootUrl}/swagger/oauth2-redirect.html", // IdentityService redirect uri
$"{administrationServiceRootUrl}/swagger/oauth2-redirect.html", // AdministrationService redirect uri
$"{catalogServiceRootUrl}/swagger/oauth2-redirect.html", // CatalogService redirect uri
$"{basketServiceRootUrl}/swagger/oauth2-redirect.html", // BasketService redirect uri
$"{orderingServiceRootUrl}/swagger/oauth2-redirect.html", // OrderingService redirect uri
$"{paymentServiceRootUrl}/swagger/oauth2-redirect.html", // PaymentService redirect uri
$"{cmskitServiceRootUrl}/swagger/oauth2-redirect.html" // CmskitService redirect uri
},
corsOrigins: new[]
{
webGatewaySwaggerRootUrl.RemovePostFix("/"),
publicWebGatewayRootUrl.RemovePostFix("/"),
accountServiceRootUrl.RemovePostFix("/"),
identityServiceRootUrl.RemovePostFix("/"),
administrationServiceRootUrl.RemovePostFix("/"),
catalogServiceRootUrl.RemovePostFix("/"),
basketServiceRootUrl.RemovePostFix("/"),
orderingServiceRootUrl.RemovePostFix("/"),
paymentServiceRootUrl.RemovePostFix("/"),
cmskitServiceRootUrl.RemovePostFix("/")
}
);
}
}
private async Task<ApiResource> CreateApiResourceAsync(string name, IEnumerable<string> claims)
{
var apiResource = await _apiResourceRepository.FindByNameAsync(name);
if (apiResource == null)
{
apiResource = await _apiResourceRepository.InsertAsync(
new ApiResource(
_guidGenerator.Create(),
name,
name + " API"
),
autoSave: true
);
}
foreach (var claim in claims)
{
if (apiResource.FindClaim(claim) == null)
{
apiResource.AddUserClaim(claim);
}
}
return await _apiResourceRepository.UpdateAsync(apiResource);
}
private async Task<ApiScope> CreateApiScopeAsync(string name)
{
var apiScope = await _apiScopeRepository.FindByNameAsync(name);
if (apiScope == null)
{
apiScope = await _apiScopeRepository.InsertAsync(
new ApiScope(
_guidGenerator.Create(),
name,
name + " API"
),
autoSave: true
);
}
return apiScope;
}
private async Task CreateClientsAsync()
{
var commonScopes = new[]
{
"email",
"openid",
"profile",
"role",
"phone",
"address"
};
//Public Web Client
var publicWebClientRootUrl = _configuration["IdentityServerClients:PublicWeb:RootUrl"]
.EnsureEndsWith('/');
await CreateClientAsync(
name: "PublicWeb",
scopes: commonScopes.Union(new[]
{
"AccountService",
"AdministrationService",
"CatalogService",
"BasketService",
"PaymentService",
"OrderingService",
"CmskitService"
}),
grantTypes: new[] { "hybrid" },
secret: "1q2w3e*".Sha256(),
redirectUris: new List<string> { $"{publicWebClientRootUrl}signin-oidc" },
postLogoutRedirectUri: $"{publicWebClientRootUrl}signout-callback-oidc",
frontChannelLogoutUri: $"{publicWebClientRootUrl}Account/FrontChannelLogout",
corsOrigins: new[] { publicWebClientRootUrl.RemovePostFix("/") }
);
//Angular Client
var angularClientRootUrl =
_configuration["IdentityServerClients:Web:RootUrl"].TrimEnd('/');
await CreateClientAsync(
name: "Web",
scopes: commonScopes.Union(new[]
{
"AccountService",
"IdentityService",
"AdministrationService",
"CatalogService",
"OrderingService",
"CmskitService"
}),
grantTypes: new[] { "authorization_code", "LinkLogin", "password" },
secret: "1q2w3e*".Sha256(),
requirePkce: true,
requireClientSecret: false,
redirectUris: new List<string> { $"{angularClientRootUrl}" },
postLogoutRedirectUri: $"{angularClientRootUrl}",
corsOrigins: new[] { angularClientRootUrl }
);
//Administration Service Client
await CreateClientAsync(
name: "EShopOnAbp_AdministrationService",
scopes: commonScopes.Union(new[]
{
"IdentityService"
}),
grantTypes: new[] { "client_credentials" },
secret: "1q2w3e*".Sha256(),
permissions: new[] { IdentityPermissions.Users.Default }
);
//Cmskit Service Client
await CreateClientAsync(
name: "EShopOnAbp_CmskitService",
scopes: commonScopes.Union(new[]
{
"IdentityService"
}),
grantTypes: new[] { "client_credentials" },
secret: "1q2w3e*".Sha256(),
permissions: new[] { IdentityPermissions.UserLookup.Default }
);
}
private async Task<Client> CreateClientAsync(
string name,
IEnumerable<string> scopes,
IEnumerable<string> grantTypes,
string secret = null,
List<string> redirectUris = null,
string postLogoutRedirectUri = null,
string frontChannelLogoutUri = null,
bool requireClientSecret = true,
bool requirePkce = false,
IEnumerable<string> permissions = null,
IEnumerable<string> corsOrigins = null)
{
var client = await _clientRepository.FindByClientIdAsync(name);
if (client == null)
{
client = await _clientRepository.InsertAsync(
new Client(
_guidGenerator.Create(),
name
)
{
ClientName = name,
ProtocolType = "oidc",
Description = name,
AlwaysIncludeUserClaimsInIdToken = true,
AllowOfflineAccess = true,
AbsoluteRefreshTokenLifetime = 31536000, //365 days
AccessTokenLifetime = 31536000, //365 days
AuthorizationCodeLifetime = 300,
IdentityTokenLifetime = 300,
RequireConsent = false,
FrontChannelLogoutUri = frontChannelLogoutUri,
RequireClientSecret = requireClientSecret,
RequirePkce = requirePkce
},
autoSave: true
);
}
foreach (var scope in scopes)
{
if (client.FindScope(scope) == null)
{
client.AddScope(scope);
}
}
foreach (var grantType in grantTypes)
{
if (client.FindGrantType(grantType) == null)
{
client.AddGrantType(grantType);
}
}
if (!secret.IsNullOrEmpty())
{
if (client.FindSecret(secret) == null)
{
client.AddSecret(secret);
}
}
if (redirectUris != null)
{
foreach (var redirectUri in redirectUris)
{
if (redirectUri != null)
{
if (client.FindRedirectUri(redirectUri) == null)
{
client.AddRedirectUri(redirectUri);
}
}
}
}
if (postLogoutRedirectUri != null)
{
if (client.FindPostLogoutRedirectUri(postLogoutRedirectUri) == null)
{
client.AddPostLogoutRedirectUri(postLogoutRedirectUri);
}
}
if (permissions != null)
{
await _permissionDataSeeder.SeedAsync(
ClientPermissionValueProvider.ProviderName,
name,
permissions,
null
);
}
if (corsOrigins != null)
{
foreach (var origin in corsOrigins)
{
if (!origin.IsNullOrWhiteSpace() && client.FindCorsOrigin(origin) == null)
{
client.AddCorsOrigin(origin);
}
}
}
return await _clientRepository.UpdateAsync(client);
}
}

2
services/identity/src/EShopOnAbp.IdentityService.HttpApi.Host/DbMigrations/IdentityServiceDatabaseMigrationChecker.cs

@ -1,9 +1,7 @@
using EShopOnAbp.IdentityService.EntityFrameworkCore;
using System;
using System.Threading.Tasks;
using EShopOnAbp.Shared.Hosting.Microservices.DbMigrations.EfCore;
using Volo.Abp.EventBus.Distributed;
using Volo.Abp.EventBus.Local;
using Volo.Abp.MultiTenancy;
using Volo.Abp.Uow;
using Volo.Abp.DistributedLocking;

Loading…
Cancel
Save