mirror of https://github.com/abpframework/abp.git
104 changed files with 3259 additions and 52 deletions
@ -1,2 +1,3 @@ |
|||||
# abp-blog |
# Blogging Module |
||||
ABP Blogging Module |
|
||||
|
This module is used for ABP blog: https://abp.io/blog/abp/ |
||||
|
|||||
@ -0,0 +1,17 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Text; |
||||
|
|
||||
|
namespace Volo.Abp.Identity |
||||
|
{ |
||||
|
public class IdentityClaimTypeConsts |
||||
|
{ |
||||
|
public const int MaxNameLength = 128; |
||||
|
|
||||
|
public const int MaxRegexLength = 512; |
||||
|
|
||||
|
public const int MaxRegexDescriptionLength = 128; |
||||
|
|
||||
|
public const int MaxDescriptionLength = 256; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,14 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Text; |
||||
|
|
||||
|
namespace Volo.Abp.Identity |
||||
|
{ |
||||
|
public enum IdentityClaimValueType |
||||
|
{ |
||||
|
String, |
||||
|
Int, |
||||
|
Boolean, |
||||
|
DateTime |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,13 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Text; |
||||
|
using System.Threading.Tasks; |
||||
|
using Volo.Abp.Domain.Repositories; |
||||
|
|
||||
|
namespace Volo.Abp.Identity |
||||
|
{ |
||||
|
public interface IIdentityClaimTypeRepository : IBasicRepository<IdentityClaimType, Guid> |
||||
|
{ |
||||
|
Task<bool> DoesNameExist(string name, Guid? claimTypeId = null); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,51 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Text; |
||||
|
using System.Threading.Tasks; |
||||
|
using Volo.Abp.Domain.Services; |
||||
|
using Volo.Abp.Guids; |
||||
|
|
||||
|
namespace Volo.Abp.Identity |
||||
|
{ |
||||
|
public class IdenityClaimTypeManager : IDomainService |
||||
|
{ |
||||
|
private readonly IIdentityClaimTypeRepository _identityClaimTypeRepository; |
||||
|
private readonly IGuidGenerator _guidGenerator; |
||||
|
|
||||
|
public IdenityClaimTypeManager(IIdentityClaimTypeRepository identityClaimTypeRepository, IGuidGenerator guidGenerator) |
||||
|
{ |
||||
|
_identityClaimTypeRepository = identityClaimTypeRepository; |
||||
|
_guidGenerator = guidGenerator; |
||||
|
} |
||||
|
|
||||
|
public async Task<IdentityClaimType> GetAsync(Guid id) |
||||
|
{ |
||||
|
return await _identityClaimTypeRepository.GetAsync(id); |
||||
|
} |
||||
|
|
||||
|
public async Task<IdentityClaimType> CreateAsync(IdentityClaimType claimType) |
||||
|
{ |
||||
|
if (await _identityClaimTypeRepository.DoesNameExist(claimType.Name)) |
||||
|
{ |
||||
|
throw new AbpException($"Name Exist: {claimType.Name}"); |
||||
|
} |
||||
|
|
||||
|
return await _identityClaimTypeRepository.InsertAsync(claimType); |
||||
|
} |
||||
|
|
||||
|
public async Task<IdentityClaimType> UpdateAsync(IdentityClaimType claimType) |
||||
|
{ |
||||
|
if (await _identityClaimTypeRepository.DoesNameExist(claimType.Name, claimType.Id)) |
||||
|
{ |
||||
|
throw new AbpException($"Name Exist: {claimType.Name}"); |
||||
|
} |
||||
|
|
||||
|
return await _identityClaimTypeRepository.UpdateAsync(claimType); |
||||
|
} |
||||
|
|
||||
|
public async Task DeleteAsync(Guid id) |
||||
|
{ |
||||
|
await _identityClaimTypeRepository.DeleteAsync(id); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,44 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Text; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.Identity |
||||
|
{ |
||||
|
public class IdentityClaimType : Entity<Guid> |
||||
|
{ |
||||
|
public virtual string Name { get; protected set; } |
||||
|
|
||||
|
public virtual bool Required { get; protected set; } |
||||
|
|
||||
|
public virtual bool IsStatic { get; protected set; } |
||||
|
|
||||
|
public virtual string Regex { get; protected set; } |
||||
|
|
||||
|
public virtual string RegexDescription { get; protected set; } |
||||
|
|
||||
|
public virtual string Description { get; protected set; } |
||||
|
|
||||
|
public virtual IdentityClaimValueType ValueType { get; protected set; } |
||||
|
|
||||
|
protected IdentityClaimType() |
||||
|
{ |
||||
|
} |
||||
|
|
||||
|
public IdentityClaimType(Guid id, [NotNull] string name, bool required, bool isStatic, [CanBeNull]string regex, [CanBeNull]string regexDescription, [CanBeNull] string description, IdentityClaimValueType valueType = IdentityClaimValueType.String) |
||||
|
{ |
||||
|
Check.NotNull(name, nameof(name)); |
||||
|
|
||||
|
Name = name; |
||||
|
Required = required; |
||||
|
IsStatic = isStatic; |
||||
|
Regex = regex; |
||||
|
RegexDescription = regexDescription; |
||||
|
Description = description; |
||||
|
ValueType = valueType; |
||||
|
} |
||||
|
|
||||
|
|
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,24 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Text; |
||||
|
using System.Threading.Tasks; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Microsoft.EntityFrameworkCore.Internal; |
||||
|
using Volo.Abp.Domain.Repositories.EntityFrameworkCore; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
|
||||
|
namespace Volo.Abp.Identity.EntityFrameworkCore |
||||
|
{ |
||||
|
public class EfCoreIdentityClaimTypeRepository : EfCoreRepository<IIdentityDbContext, IdentityClaimType, Guid>, IIdentityClaimTypeRepository |
||||
|
{ |
||||
|
public EfCoreIdentityClaimTypeRepository(IDbContextProvider<IIdentityDbContext> dbContextProvider) : base(dbContextProvider) |
||||
|
{ |
||||
|
} |
||||
|
|
||||
|
public async Task<bool> DoesNameExist(string name, Guid? claimTypeId = null) |
||||
|
{ |
||||
|
return await DbSet.WhereIf(claimTypeId != null, ct => ct.Id == claimTypeId).CountAsync(ct => ct.Name == name) > 0; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,23 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Text; |
||||
|
using System.Threading.Tasks; |
||||
|
using MongoDB.Driver.Linq; |
||||
|
using Volo.Abp.Domain.Repositories.MongoDB; |
||||
|
using Volo.Abp.MongoDB; |
||||
|
|
||||
|
namespace Volo.Abp.Identity.MongoDB |
||||
|
{ |
||||
|
public class MongoIdentityClaimTypeRepository : MongoDbRepository<IAbpIdentityMongoDbContext, IdentityClaimType, Guid>, IIdentityClaimTypeRepository |
||||
|
{ |
||||
|
public MongoIdentityClaimTypeRepository(IMongoDbContextProvider<IAbpIdentityMongoDbContext> dbContextProvider) : base(dbContextProvider) |
||||
|
{ |
||||
|
} |
||||
|
|
||||
|
public async Task<bool> DoesNameExist(string name, Guid? claimTypeId = null) |
||||
|
{ |
||||
|
return GetMongoQueryable().WhereIf(claimTypeId != null, ct => ct.Id == claimTypeId).Count(ct => ct.Name == name) > 0; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,9 @@ |
|||||
|
using Volo.Abp.Identity.EntityFrameworkCore; |
||||
|
|
||||
|
namespace Volo.Abp.Identity.MongoDB |
||||
|
{ |
||||
|
public class IdentityClaimTypeRepository_Tests : IdentityClaimTypeRepository_Tests<AbpIdentityEntityFrameworkCoreTestModule> |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.Identity.MongoDB |
||||
|
{ |
||||
|
public class IdentityClaimTypeRepository_Tests : IdentityClaimTypeRepository_Tests<AbpIdentityMongoDbTestModule> |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,40 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Text; |
||||
|
using System.Threading.Tasks; |
||||
|
using Microsoft.Extensions.DependencyInjection; |
||||
|
using Shouldly; |
||||
|
using Volo.Abp.Guids; |
||||
|
using Volo.Abp.Modularity; |
||||
|
using Xunit; |
||||
|
|
||||
|
namespace Volo.Abp.Identity |
||||
|
{ |
||||
|
public abstract class IdentityClaimTypeRepository_Tests<TStartupModule> : AbpIdentityTestBase<TStartupModule> |
||||
|
where TStartupModule : IAbpModule |
||||
|
{ |
||||
|
protected IIdentityClaimTypeRepository ClaimTypeRepository { get; } |
||||
|
protected IGuidGenerator GuidGenerator { get; } |
||||
|
|
||||
|
public IdentityClaimTypeRepository_Tests() |
||||
|
{ |
||||
|
ClaimTypeRepository = ServiceProvider.GetRequiredService<IIdentityClaimTypeRepository>(); |
||||
|
GuidGenerator = ServiceProvider.GetRequiredService<IGuidGenerator>(); |
||||
|
} |
||||
|
|
||||
|
[Fact] |
||||
|
public async Task Should_Check_Name_If_It_Is_Uniquee() |
||||
|
{ |
||||
|
var claim = (await ClaimTypeRepository.GetListAsync()).FirstOrDefault(); |
||||
|
|
||||
|
var result1 = await ClaimTypeRepository.DoesNameExist(claim.Name); |
||||
|
|
||||
|
result1.ShouldBe(true); |
||||
|
|
||||
|
var result2 = await ClaimTypeRepository.DoesNameExist(Guid.NewGuid().ToString()); |
||||
|
|
||||
|
result2.ShouldBe(false); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,53 @@ |
|||||
|
|
||||
|
Microsoft Visual Studio Solution File, Format Version 12.00 |
||||
|
# Visual Studio 15 |
||||
|
VisualStudioVersion = 15.0.27703.2047 |
||||
|
MinimumVisualStudioVersion = 10.0.40219.1 |
||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{59A0FC0F-EA6D-477B-84A7-3B1E41B4C858}" |
||||
|
EndProject |
||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Volo.Abp.IdentityServer.Domain", "src\Volo.Abp.IdentityServer.Domain\Volo.Abp.IdentityServer.Domain.csproj", "{A3B81AEE-EE96-4F75-856B-55B25D8822E2}" |
||||
|
EndProject |
||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Volo.Abp.IdentityServer.Domain.Shared", "src\Volo.Abp.IdentityServer.Domain.Shared\Volo.Abp.IdentityServer.Domain.Shared.csproj", "{FC035412-78AD-424C-BECE-B19D04C7B5A6}" |
||||
|
EndProject |
||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Volo.Abp.IdentityServer.EntityFrameworkCore", "src\Volo.Abp.IdentityServer.EntityFrameworkCore\Volo.Abp.IdentityServer.EntityFrameworkCore.csproj", "{F352D620-1CBF-4658-953F-70BA73B458F1}" |
||||
|
EndProject |
||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "test", "test", "{2C792EC1-BA27-44ED-B7CC-D0939553F1B2}" |
||||
|
EndProject |
||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Volo.Abp.IdentityServer.EntityFrameworkCore.Tests", "test\Volo.Abp.IdentityServer.EntityFrameworkCore.Tests\Volo.Abp.IdentityServer.EntityFrameworkCore.Tests.csproj", "{8B8FBA95-4FA2-4438-A387-7C5EC7A89E82}" |
||||
|
EndProject |
||||
|
Global |
||||
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution |
||||
|
Debug|Any CPU = Debug|Any CPU |
||||
|
Release|Any CPU = Release|Any CPU |
||||
|
EndGlobalSection |
||||
|
GlobalSection(ProjectConfigurationPlatforms) = postSolution |
||||
|
{A3B81AEE-EE96-4F75-856B-55B25D8822E2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU |
||||
|
{A3B81AEE-EE96-4F75-856B-55B25D8822E2}.Debug|Any CPU.Build.0 = Debug|Any CPU |
||||
|
{A3B81AEE-EE96-4F75-856B-55B25D8822E2}.Release|Any CPU.ActiveCfg = Release|Any CPU |
||||
|
{A3B81AEE-EE96-4F75-856B-55B25D8822E2}.Release|Any CPU.Build.0 = Release|Any CPU |
||||
|
{FC035412-78AD-424C-BECE-B19D04C7B5A6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU |
||||
|
{FC035412-78AD-424C-BECE-B19D04C7B5A6}.Debug|Any CPU.Build.0 = Debug|Any CPU |
||||
|
{FC035412-78AD-424C-BECE-B19D04C7B5A6}.Release|Any CPU.ActiveCfg = Release|Any CPU |
||||
|
{FC035412-78AD-424C-BECE-B19D04C7B5A6}.Release|Any CPU.Build.0 = Release|Any CPU |
||||
|
{F352D620-1CBF-4658-953F-70BA73B458F1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU |
||||
|
{F352D620-1CBF-4658-953F-70BA73B458F1}.Debug|Any CPU.Build.0 = Debug|Any CPU |
||||
|
{F352D620-1CBF-4658-953F-70BA73B458F1}.Release|Any CPU.ActiveCfg = Release|Any CPU |
||||
|
{F352D620-1CBF-4658-953F-70BA73B458F1}.Release|Any CPU.Build.0 = Release|Any CPU |
||||
|
{8B8FBA95-4FA2-4438-A387-7C5EC7A89E82}.Debug|Any CPU.ActiveCfg = Debug|Any CPU |
||||
|
{8B8FBA95-4FA2-4438-A387-7C5EC7A89E82}.Debug|Any CPU.Build.0 = Debug|Any CPU |
||||
|
{8B8FBA95-4FA2-4438-A387-7C5EC7A89E82}.Release|Any CPU.ActiveCfg = Release|Any CPU |
||||
|
{8B8FBA95-4FA2-4438-A387-7C5EC7A89E82}.Release|Any CPU.Build.0 = Release|Any CPU |
||||
|
EndGlobalSection |
||||
|
GlobalSection(SolutionProperties) = preSolution |
||||
|
HideSolutionNode = FALSE |
||||
|
EndGlobalSection |
||||
|
GlobalSection(NestedProjects) = preSolution |
||||
|
{A3B81AEE-EE96-4F75-856B-55B25D8822E2} = {59A0FC0F-EA6D-477B-84A7-3B1E41B4C858} |
||||
|
{FC035412-78AD-424C-BECE-B19D04C7B5A6} = {59A0FC0F-EA6D-477B-84A7-3B1E41B4C858} |
||||
|
{F352D620-1CBF-4658-953F-70BA73B458F1} = {59A0FC0F-EA6D-477B-84A7-3B1E41B4C858} |
||||
|
{8B8FBA95-4FA2-4438-A387-7C5EC7A89E82} = {2C792EC1-BA27-44ED-B7CC-D0939553F1B2} |
||||
|
EndGlobalSection |
||||
|
GlobalSection(ExtensibilityGlobals) = postSolution |
||||
|
SolutionGuid = {45562023-C330-4060-A583-2BA10F472D3D} |
||||
|
EndGlobalSection |
||||
|
EndGlobal |
||||
@ -0,0 +1,16 @@ |
|||||
|
<Project> |
||||
|
<PropertyGroup> |
||||
|
<LangVersion>latest</LangVersion> |
||||
|
<Version>0.3.0</Version> |
||||
|
<NoWarn>$(NoWarn);CS1591</NoWarn> |
||||
|
<PackageIconUrl>http://www.aspnetboilerplate.com/images/abp_nupkg.png</PackageIconUrl> |
||||
|
<PackageProjectUrl>http://abp.io</PackageProjectUrl> |
||||
|
<RepositoryType>git</RepositoryType> |
||||
|
<RepositoryUrl>https://github.com/volosoft/abp/</RepositoryUrl> |
||||
|
</PropertyGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<PackageReference Include="SourceLink.Create.CommandLine" Version="2.8.1" PrivateAssets="All" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
</Project> |
||||
@ -0,0 +1,20 @@ |
|||||
|
<Project Sdk="Microsoft.NET.Sdk"> |
||||
|
|
||||
|
<Import Project="..\..\common.props" /> |
||||
|
|
||||
|
<PropertyGroup> |
||||
|
<TargetFramework>netstandard2.0</TargetFramework> |
||||
|
<AssemblyName>Volo.Abp.IdentityServer.Domain.Shared</AssemblyName> |
||||
|
<PackageId>Volo.Abp.IdentityServer.Domain.Shared</PackageId> |
||||
|
<AssetTargetFallback>$(AssetTargetFallback);portable-net45+win8+wp8+wpa81;</AssetTargetFallback> |
||||
|
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute> |
||||
|
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute> |
||||
|
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute> |
||||
|
<RootNamespace /> |
||||
|
</PropertyGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<ProjectReference Include="..\..\..\..\..\abp\framework\src\Volo.Abp.Core\Volo.Abp.Core.csproj" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
</Project> |
||||
@ -0,0 +1,9 @@ |
|||||
|
using Volo.Abp.Modularity; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class AbpIdentityServerDomainSharedModule : AbpModule |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,9 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiResourceConsts |
||||
|
{ |
||||
|
public const int NameMaxLength = 200; |
||||
|
public const int DisplayNameMaxLength = 200; |
||||
|
public const int DescriptionMaxLength = 1000; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,9 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiScopeConsts |
||||
|
{ |
||||
|
public const int NameMaxLength = 196; |
||||
|
public const int DisplayNameMaxLength = 128; |
||||
|
public const int DescriptionMaxLength = 256; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,8 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientClaimConsts |
||||
|
{ |
||||
|
public const int TypeMaxLength = 250; |
||||
|
public const int ValueMaxLength = 250; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,25 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientConsts |
||||
|
{ |
||||
|
public const int ClientIdMaxLength = 200; |
||||
|
|
||||
|
public const int ProtocolTypeMaxLength = 200; |
||||
|
|
||||
|
public const int ClientNameMaxLength = 200; |
||||
|
|
||||
|
public const int ClientUriMaxLength = 2000; |
||||
|
|
||||
|
public const int LogoUriMaxLength = 2000; |
||||
|
|
||||
|
public const int DescriptionMaxLength = 1000; |
||||
|
|
||||
|
public const int FrontChannelLogoutUriMaxLength = 2000; |
||||
|
|
||||
|
public const int BackChannelLogoutUriMaxLength = 2000; |
||||
|
|
||||
|
public const int ClientClaimsPrefixMaxLength = 200; |
||||
|
|
||||
|
public const int PairWiseSubjectSaltMaxLength = 200; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientCorsOriginConsts |
||||
|
{ |
||||
|
public const int OriginMaxLength = 150; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientGrantTypeConsts |
||||
|
{ |
||||
|
public const int GrantTypeMaxLength = 196; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientIdPRestrictionConsts |
||||
|
{ |
||||
|
public const int ProviderMaxLength = 64; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientPostLogoutRedirectUriConsts |
||||
|
{ |
||||
|
public const int PostLogoutRedirectUriMaxLength = 2000; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,8 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientPropertyConsts |
||||
|
{ |
||||
|
public const int KeyMaxLength = 250; |
||||
|
public const int ValueMaxLength = 2000; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientRedirectUriConsts |
||||
|
{ |
||||
|
public const int RedirectUriMaxLength = 2000; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientScopeConsts |
||||
|
{ |
||||
|
public const int ScopeMaxLength = 196; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,10 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Grants |
||||
|
{ |
||||
|
public class PersistedGrantConsts |
||||
|
{ |
||||
|
public const int KeyMaxLength = 200; |
||||
|
public const int TypeMaxLength = 50; |
||||
|
public const int SubjectIdMaxLength = 200; |
||||
|
public const int ClientIdMaxLength = 200; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,9 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.IdentityResources |
||||
|
{ |
||||
|
public class IdentityResourceConsts |
||||
|
{ |
||||
|
public const int NameMaxLength = 200; |
||||
|
public const int DisplayNameMaxLength = 200; |
||||
|
public const int DescriptionMaxLength = 1000; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,9 @@ |
|||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class SecretConsts |
||||
|
{ |
||||
|
public const int TypeMaxLength = 32; |
||||
|
public const int ValueMaxLength = 196; |
||||
|
public const int DescriptionMaxLength = 256; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,7 @@ |
|||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class UserClaimConsts |
||||
|
{ |
||||
|
public const int TypeMaxLength = 196; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,28 @@ |
|||||
|
<Project Sdk="Microsoft.NET.Sdk"> |
||||
|
|
||||
|
<Import Project="..\..\common.props" /> |
||||
|
|
||||
|
<PropertyGroup> |
||||
|
<TargetFramework>netstandard2.0</TargetFramework> |
||||
|
<AssemblyName>Volo.Abp.IdentityServer.Domain</AssemblyName> |
||||
|
<PackageId>Volo.Abp.IdentityServer.Domain</PackageId> |
||||
|
<AssetTargetFallback>$(AssetTargetFallback);portable-net45+win8+wp8+wpa81;</AssetTargetFallback> |
||||
|
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute> |
||||
|
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute> |
||||
|
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute> |
||||
|
<RootNamespace /> |
||||
|
</PropertyGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<ProjectReference Include="..\Volo.Abp.IdentityServer.Domain.Shared\Volo.Abp.IdentityServer.Domain.Shared.csproj" /> |
||||
|
<ProjectReference Include="..\..\..\..\..\abp\modules\identity\src\Volo.Abp.Identity.Domain\Volo.Abp.Identity.Domain.csproj" /> |
||||
|
<ProjectReference Include="..\..\..\..\..\abp\framework\src\Volo.Abp.AutoMapper\Volo.Abp.AutoMapper.csproj" /> |
||||
|
<ProjectReference Include="..\..\..\..\..\abp\framework\src\Volo.Abp.Security\Volo.Abp.Security.csproj" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<PackageReference Include="IdentityServer4" Version="2.2.0" /> |
||||
|
<PackageReference Include="IdentityServer4.AspNetIdentity" Version="2.1.0" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
</Project> |
||||
@ -0,0 +1,2 @@ |
|||||
|
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation"> |
||||
|
<s:String x:Key="/Default/CodeInspection/CSharpLanguageProject/LanguageLevel/@EntryValue">CSharp71</s:String></wpf:ResourceDictionary> |
||||
@ -0,0 +1,28 @@ |
|||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Security.Claims; |
||||
|
using IdentityServer4.Services; |
||||
|
using Microsoft.Extensions.Logging; |
||||
|
using Volo.Abp.Security.Claims; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class AbpClaimsService : DefaultClaimsService |
||||
|
{ |
||||
|
public AbpClaimsService(IProfileService profile, ILogger<DefaultClaimsService> logger) |
||||
|
: base(profile, logger) |
||||
|
{ |
||||
|
} |
||||
|
|
||||
|
protected override IEnumerable<Claim> GetOptionalClaims(ClaimsPrincipal subject) |
||||
|
{ |
||||
|
var tenantClaim = subject.FindFirst(AbpClaimTypes.TenantId); |
||||
|
if (tenantClaim == null) |
||||
|
{ |
||||
|
return base.GetOptionalClaims(subject); |
||||
|
} |
||||
|
|
||||
|
return base.GetOptionalClaims(subject).Union(new[] { tenantClaim }); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,48 @@ |
|||||
|
using System; |
||||
|
using System.IdentityModel.Tokens.Jwt; |
||||
|
using IdentityModel; |
||||
|
using IdentityServer4.Services; |
||||
|
using Microsoft.Extensions.DependencyInjection; |
||||
|
using Microsoft.Extensions.DependencyInjection.Extensions; |
||||
|
using Volo.Abp.Identity; |
||||
|
using Volo.Abp.IdentityServer.AspNetIdentity; |
||||
|
using Volo.Abp.Security.Claims; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public static class AbpIdentityServerBuilderExtensions |
||||
|
{ |
||||
|
public static IIdentityServerBuilder AddAbpIdentityServer( |
||||
|
this IIdentityServerBuilder builder, |
||||
|
Action<AbpIdentityServerOptions> optionsAction = null) |
||||
|
{ |
||||
|
var options = new AbpIdentityServerOptions(); |
||||
|
optionsAction?.Invoke(options); |
||||
|
|
||||
|
//TODO: AspNet Identity integration lines. Can be extracted to a extension method
|
||||
|
builder.AddAspNetIdentity<IdentityUser>(); |
||||
|
builder.AddProfileService<AbpProfileService>(); |
||||
|
builder.AddResourceOwnerValidator<AbpResourceOwnerPasswordValidator>(); |
||||
|
|
||||
|
builder.Services.Replace(ServiceDescriptor.Transient<IClaimsService, AbpClaimsService>()); |
||||
|
|
||||
|
if (options.UpdateAbpClaimTypes) |
||||
|
{ |
||||
|
AbpClaimTypes.UserId = JwtClaimTypes.Subject; |
||||
|
AbpClaimTypes.UserName = JwtClaimTypes.Name; |
||||
|
AbpClaimTypes.Role = JwtClaimTypes.Role; |
||||
|
AbpClaimTypes.Email = JwtClaimTypes.Email; |
||||
|
} |
||||
|
|
||||
|
if (options.UpdateJwtSecurityTokenHandlerDefaultInboundClaimTypeMap) |
||||
|
{ |
||||
|
JwtSecurityTokenHandler.DefaultInboundClaimTypeMap[AbpClaimTypes.UserId] = AbpClaimTypes.UserId; |
||||
|
JwtSecurityTokenHandler.DefaultInboundClaimTypeMap[AbpClaimTypes.UserName] = AbpClaimTypes.UserName; |
||||
|
JwtSecurityTokenHandler.DefaultInboundClaimTypeMap[AbpClaimTypes.Role] = AbpClaimTypes.Role; |
||||
|
JwtSecurityTokenHandler.DefaultInboundClaimTypeMap[AbpClaimTypes.Email] = AbpClaimTypes.Email; |
||||
|
} |
||||
|
|
||||
|
return builder; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,9 @@ |
|||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public static class AbpIdentityServerConsts |
||||
|
{ |
||||
|
public const string DefaultDbTablePrefix = "IdentityServer"; |
||||
|
|
||||
|
public const string DefaultDbSchema = null; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,47 @@ |
|||||
|
using Microsoft.Extensions.DependencyInjection; |
||||
|
using Volo.Abp.AutoMapper; |
||||
|
using Volo.Abp.Domain; |
||||
|
using Volo.Abp.Identity; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.Modularity; |
||||
|
using Volo.Abp.Security; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
[DependsOn(typeof(AbpIdentityServerDomainSharedModule))] |
||||
|
[DependsOn(typeof(AbpDddDomainModule))] |
||||
|
[DependsOn(typeof(AbpAutoMapperModule))] |
||||
|
[DependsOn(typeof(AbpIdentityDomainModule))] |
||||
|
[DependsOn(typeof(AbpSecurityModule))] |
||||
|
public class AbpIdentityServerDomainModule : AbpModule |
||||
|
{ |
||||
|
public override void ConfigureServices(ServiceConfigurationContext context) |
||||
|
{ |
||||
|
context.Services.Configure<AbpAutoMapperOptions>(options => |
||||
|
{ |
||||
|
options.AddProfile<ClientAutoMapperProfile>(validate: true); |
||||
|
}); |
||||
|
|
||||
|
AddIdentityServer(context.Services); |
||||
|
} |
||||
|
|
||||
|
private static void AddIdentityServer(IServiceCollection services) |
||||
|
{ |
||||
|
var identityServerBuilder = services.AddIdentityServer(options => |
||||
|
{ |
||||
|
options.Events.RaiseErrorEvents = true; |
||||
|
options.Events.RaiseInformationEvents = true; |
||||
|
options.Events.RaiseFailureEvents = true; |
||||
|
options.Events.RaiseSuccessEvents = true; |
||||
|
}); |
||||
|
|
||||
|
identityServerBuilder |
||||
|
.AddDeveloperSigningCredential() //TODO: Should be able to change this!
|
||||
|
.AddClientStore<ClientStore>() |
||||
|
.AddResourceStore<ResourceStore>() |
||||
|
.AddAbpIdentityServer(); |
||||
|
|
||||
|
services.ExecutePreConfiguredActions(identityServerBuilder); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,17 @@ |
|||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class AbpIdentityServerOptions |
||||
|
{ |
||||
|
/// <summary>
|
||||
|
/// Updates <see cref="JwtSecurityTokenHandler.DefaultInboundClaimTypeMap"/> to be compatible with identity server claims.
|
||||
|
/// Default: true.
|
||||
|
/// </summary>
|
||||
|
public bool UpdateJwtSecurityTokenHandlerDefaultInboundClaimTypeMap { get; set; } = true; |
||||
|
|
||||
|
/// <summary>
|
||||
|
/// Updates <see cref="AbpClaimTypes"/> to be compatible with identity server claims.
|
||||
|
/// Default: true.
|
||||
|
/// </summary>
|
||||
|
public bool UpdateAbpClaimTypes { get; set; } = true; |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,76 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using IdentityServer4; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiResource : AggregateRoot<Guid> |
||||
|
{ |
||||
|
[NotNull] |
||||
|
public virtual string Name { get; protected set; } |
||||
|
|
||||
|
public virtual string DisplayName { get; set; } |
||||
|
|
||||
|
public virtual string Description { get; set; } |
||||
|
|
||||
|
public virtual bool Enabled { get; set; } |
||||
|
|
||||
|
public virtual List<ApiSecret> Secrets { get; protected set; } |
||||
|
|
||||
|
public virtual List<ApiScope> Scopes { get; protected set; } |
||||
|
|
||||
|
public virtual List<ApiResourceClaim> UserClaims { get; protected set; } |
||||
|
|
||||
|
protected ApiResource() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public ApiResource(Guid id, [NotNull] string name, string displayName = null, string description = null) |
||||
|
{ |
||||
|
Check.NotNull(name, nameof(name)); |
||||
|
|
||||
|
Id = id; |
||||
|
|
||||
|
Name = name; |
||||
|
|
||||
|
DisplayName = displayName; |
||||
|
Description = description; |
||||
|
|
||||
|
Enabled = true; |
||||
|
|
||||
|
Secrets = new List<ApiSecret>(); |
||||
|
Scopes = new List<ApiScope>(); |
||||
|
UserClaims = new List<ApiResourceClaim>(); |
||||
|
|
||||
|
Scopes.Add(new ApiScope(id, name, displayName, description)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddSecret( |
||||
|
[NotNull] string value, |
||||
|
DateTime? expiration = null, |
||||
|
string type = IdentityServerConstants.SecretTypes.SharedSecret, |
||||
|
string description = null) |
||||
|
{ |
||||
|
Secrets.Add(new ApiSecret(Id, value, expiration, type, description)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddScope( |
||||
|
[NotNull] string name, |
||||
|
string displayName = null, |
||||
|
string description = null, |
||||
|
bool required = false, |
||||
|
bool emphasize = false, |
||||
|
bool showInDiscoveryDocument = true) |
||||
|
{ |
||||
|
Scopes.Add(new ApiScope(Id, name, displayName, description, required, emphasize, showInDiscoveryDocument)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddUserClaim([NotNull] string type) |
||||
|
{ |
||||
|
UserClaims.Add(new ApiResourceClaim(Id, type)); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,26 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiResourceClaim : UserClaim |
||||
|
{ |
||||
|
public virtual Guid ApiResourceId { get; set; } |
||||
|
|
||||
|
protected ApiResourceClaim() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ApiResourceClaim(Guid apiResourceId, [NotNull] string type) |
||||
|
: base(type) |
||||
|
{ |
||||
|
ApiResourceId = apiResourceId; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] {ApiResourceId, Type}; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,64 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiScope : Entity |
||||
|
{ |
||||
|
public virtual Guid ApiResourceId { get; protected set; } |
||||
|
|
||||
|
[NotNull] |
||||
|
public virtual string Name { get; protected set; } |
||||
|
|
||||
|
public virtual string DisplayName { get; set; } |
||||
|
|
||||
|
public virtual string Description { get; set; } |
||||
|
|
||||
|
public virtual bool Required { get; set; } |
||||
|
|
||||
|
public virtual bool Emphasize { get; set; } |
||||
|
|
||||
|
public virtual bool ShowInDiscoveryDocument { get; set; } |
||||
|
|
||||
|
public virtual List<ApiScopeClaim> UserClaims { get; protected set; } |
||||
|
|
||||
|
protected ApiScope() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ApiScope( |
||||
|
Guid apiResourceId, |
||||
|
[NotNull] string name, |
||||
|
string displayName = null, |
||||
|
string description = null, |
||||
|
bool required = false, |
||||
|
bool emphasize = false, |
||||
|
bool showInDiscoveryDocument = true) |
||||
|
{ |
||||
|
Check.NotNull(name, nameof(name)); |
||||
|
|
||||
|
ApiResourceId = apiResourceId; |
||||
|
Name = name; |
||||
|
DisplayName = displayName ?? name; |
||||
|
Description = description; |
||||
|
Required = required; |
||||
|
Emphasize = emphasize; |
||||
|
ShowInDiscoveryDocument = showInDiscoveryDocument; |
||||
|
|
||||
|
UserClaims = new List<ApiScopeClaim>(); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddUserClaim([NotNull] string type) |
||||
|
{ |
||||
|
UserClaims.Add(new ApiScopeClaim(ApiResourceId, Name, type)); |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ApiResourceId, Name }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,32 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiScopeClaim : UserClaim |
||||
|
{ |
||||
|
public Guid ApiResourceId { get; protected set; } |
||||
|
|
||||
|
[NotNull] |
||||
|
public string Name { get; protected set; } |
||||
|
|
||||
|
protected ApiScopeClaim() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ApiScopeClaim(Guid apiResourceId, [NotNull] string name, [NotNull] string type) |
||||
|
: base(type) |
||||
|
{ |
||||
|
Check.NotNull(name, nameof(name)); |
||||
|
|
||||
|
ApiResourceId = apiResourceId; |
||||
|
Name = name; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ApiResourceId, Name, Type }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,36 @@ |
|||||
|
using System; |
||||
|
using IdentityServer4; |
||||
|
using JetBrains.Annotations; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiSecret : Secret |
||||
|
{ |
||||
|
public virtual Guid ApiResourceId { get; protected set; } |
||||
|
|
||||
|
protected ApiSecret() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ApiSecret( |
||||
|
Guid apiResourceId, |
||||
|
[NotNull] string value, |
||||
|
DateTime? expiration = null, |
||||
|
string type = IdentityServerConstants.SecretTypes.SharedSecret, |
||||
|
string description = null |
||||
|
) : base( |
||||
|
value, |
||||
|
expiration, |
||||
|
type, |
||||
|
description) |
||||
|
{ |
||||
|
ApiResourceId = apiResourceId; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ApiResourceId, Type, Value }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,28 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Volo.Abp.Domain.Repositories; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public interface IApiResourceRepository : IBasicRepository<ApiResource, Guid> |
||||
|
{ |
||||
|
Task<ApiResource> FindByNameAsync( |
||||
|
string name, |
||||
|
bool includeDetails = true, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
|
||||
|
Task<List<ApiResource>> GetListByScopesAsync( |
||||
|
string[] scopeNames, |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
|
||||
|
Task<List<ApiResource>> GetListAsync( |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,42 @@ |
|||||
|
using System.Threading.Tasks; |
||||
|
using System.Security.Principal; |
||||
|
using IdentityServer4.AspNetIdentity; |
||||
|
using IdentityServer4.Models; |
||||
|
using Microsoft.AspNetCore.Identity; |
||||
|
using Volo.Abp.Identity; |
||||
|
using Volo.Abp.MultiTenancy; |
||||
|
using Volo.Abp.Uow; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.AspNetIdentity |
||||
|
{ |
||||
|
public class AbpProfileService : ProfileService<IdentityUser> |
||||
|
{ |
||||
|
private readonly ICurrentTenant _currentTenant; |
||||
|
public AbpProfileService( |
||||
|
IdentityUserManager userManager, |
||||
|
IUserClaimsPrincipalFactory<IdentityUser> claimsFactory, |
||||
|
ICurrentTenant currentTenant) |
||||
|
: base(userManager, claimsFactory) |
||||
|
{ |
||||
|
_currentTenant = currentTenant; |
||||
|
} |
||||
|
|
||||
|
[UnitOfWork] |
||||
|
public override async Task GetProfileDataAsync(ProfileDataRequestContext context) |
||||
|
{ |
||||
|
using (_currentTenant.Change(context.Subject.FindTenantId())) |
||||
|
{ |
||||
|
await base.GetProfileDataAsync(context); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
[UnitOfWork] |
||||
|
public override async Task IsActiveAsync(IsActiveContext context) |
||||
|
{ |
||||
|
using (_currentTenant.Change(context.Subject.FindTenantId())) |
||||
|
{ |
||||
|
await base.IsActiveAsync(context); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,33 @@ |
|||||
|
using System.Threading.Tasks; |
||||
|
using IdentityServer4.AspNetIdentity; |
||||
|
using IdentityServer4.Services; |
||||
|
using IdentityServer4.Validation; |
||||
|
using Microsoft.AspNetCore.Identity; |
||||
|
using Microsoft.Extensions.Logging; |
||||
|
using Volo.Abp.Identity; |
||||
|
using Volo.Abp.Uow; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.AspNetIdentity |
||||
|
{ |
||||
|
public class AbpResourceOwnerPasswordValidator : ResourceOwnerPasswordValidator<IdentityUser> |
||||
|
{ |
||||
|
public AbpResourceOwnerPasswordValidator( |
||||
|
IdentityUserManager userManager, |
||||
|
SignInManager<IdentityUser> signInManager, |
||||
|
IEventService events, |
||||
|
ILogger<ResourceOwnerPasswordValidator<IdentityUser>> logger |
||||
|
) : base( |
||||
|
userManager, |
||||
|
signInManager, |
||||
|
events, |
||||
|
logger) |
||||
|
{ |
||||
|
} |
||||
|
|
||||
|
[UnitOfWork] |
||||
|
public override async Task ValidateAsync(ResourceOwnerPasswordValidationContext context) |
||||
|
{ |
||||
|
await base.ValidateAsync(context); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,196 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using IdentityServer4; |
||||
|
using IdentityServer4.Models; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
using Volo.Abp.Guids; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class Client : AggregateRoot<Guid> |
||||
|
{ |
||||
|
public virtual string ClientId { get; set; } |
||||
|
|
||||
|
public virtual string ClientName { get; set; } |
||||
|
|
||||
|
public virtual string Description { get; set; } |
||||
|
|
||||
|
public virtual string ClientUri { get; set; } |
||||
|
|
||||
|
public virtual string LogoUri { get; set; } |
||||
|
|
||||
|
public virtual bool Enabled { get; set; } = true; |
||||
|
|
||||
|
public virtual string ProtocolType { get; set; } |
||||
|
|
||||
|
public virtual bool RequireClientSecret { get; set; } |
||||
|
|
||||
|
public virtual bool RequireConsent { get; set; } |
||||
|
|
||||
|
public virtual bool AllowRememberConsent { get; set; } |
||||
|
|
||||
|
public virtual bool AlwaysIncludeUserClaimsInIdToken { get; set; } |
||||
|
|
||||
|
public virtual bool RequirePkce { get; set; } |
||||
|
|
||||
|
public virtual bool AllowPlainTextPkce { get; set; } |
||||
|
|
||||
|
public virtual bool AllowAccessTokensViaBrowser { get; set; } |
||||
|
|
||||
|
public virtual string FrontChannelLogoutUri { get; set; } |
||||
|
|
||||
|
public virtual bool FrontChannelLogoutSessionRequired { get; set; } |
||||
|
|
||||
|
public virtual string BackChannelLogoutUri { get; set; } |
||||
|
|
||||
|
public virtual bool BackChannelLogoutSessionRequired { get; set; } |
||||
|
|
||||
|
public virtual bool AllowOfflineAccess { get; set; } |
||||
|
|
||||
|
public virtual int IdentityTokenLifetime { get; set; } |
||||
|
|
||||
|
public virtual int AccessTokenLifetime { get; set; } |
||||
|
|
||||
|
public virtual int AuthorizationCodeLifetime { get; set; } |
||||
|
|
||||
|
public virtual int? ConsentLifetime { get; set; } |
||||
|
|
||||
|
public virtual int AbsoluteRefreshTokenLifetime { get; set; } |
||||
|
|
||||
|
public virtual int SlidingRefreshTokenLifetime { get; set; } |
||||
|
|
||||
|
public virtual int RefreshTokenUsage { get; set; } |
||||
|
|
||||
|
public virtual bool UpdateAccessTokenClaimsOnRefresh { get; set; } |
||||
|
|
||||
|
public virtual int RefreshTokenExpiration { get; set; } |
||||
|
|
||||
|
public virtual int AccessTokenType { get; set; } |
||||
|
|
||||
|
public virtual bool EnableLocalLogin { get; set; } |
||||
|
|
||||
|
public virtual bool IncludeJwtId { get; set; } |
||||
|
|
||||
|
public virtual bool AlwaysSendClientClaims { get; set; } |
||||
|
|
||||
|
public virtual string ClientClaimsPrefix { get; set; } |
||||
|
|
||||
|
public virtual string PairWiseSubjectSalt { get; set; } |
||||
|
|
||||
|
public virtual List<ClientScope> AllowedScopes { get; set; } |
||||
|
|
||||
|
public virtual List<ClientSecret> ClientSecrets { get; set; } |
||||
|
|
||||
|
public virtual List<ClientGrantType> AllowedGrantTypes { get; set; } |
||||
|
|
||||
|
public virtual List<ClientCorsOrigin> AllowedCorsOrigins { get; set; } |
||||
|
|
||||
|
public virtual List<ClientRedirectUri> RedirectUris { get; set; } |
||||
|
|
||||
|
public virtual List<ClientPostLogoutRedirectUri> PostLogoutRedirectUris { get; set; } |
||||
|
|
||||
|
public virtual List<ClientIdPRestriction> IdentityProviderRestrictions { get; set; } |
||||
|
|
||||
|
public virtual List<ClientClaim> Claims { get; set; } |
||||
|
|
||||
|
public virtual List<ClientProperty> Properties { get; set; } |
||||
|
|
||||
|
protected Client() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public Client(Guid id, [NotNull] string clientId) |
||||
|
{ |
||||
|
Check.NotNull(clientId, nameof(clientId)); |
||||
|
|
||||
|
Id = id; |
||||
|
ClientId = clientId; |
||||
|
|
||||
|
//TODO: Replace magics with constants?
|
||||
|
|
||||
|
ProtocolType = IdentityServerConstants.ProtocolTypes.OpenIdConnect; |
||||
|
RequireClientSecret = true; |
||||
|
RequireConsent = true; |
||||
|
AllowRememberConsent = true; |
||||
|
FrontChannelLogoutSessionRequired = true; |
||||
|
BackChannelLogoutSessionRequired = true; |
||||
|
IdentityTokenLifetime = 300; |
||||
|
AccessTokenLifetime = 3600; |
||||
|
AuthorizationCodeLifetime = 300; |
||||
|
AbsoluteRefreshTokenLifetime = 2592000; |
||||
|
SlidingRefreshTokenLifetime = 1296000; |
||||
|
RefreshTokenUsage = (int)TokenUsage.OneTimeOnly; |
||||
|
RefreshTokenExpiration = (int)TokenExpiration.Absolute; |
||||
|
AccessTokenType = (int)IdentityServer4.Models.AccessTokenType.Jwt; |
||||
|
EnableLocalLogin = true; |
||||
|
ClientClaimsPrefix = "client_"; |
||||
|
|
||||
|
AllowedScopes = new List<ClientScope>(); |
||||
|
ClientSecrets = new List<ClientSecret>(); |
||||
|
AllowedGrantTypes = new List<ClientGrantType>(); |
||||
|
AllowedCorsOrigins = new List<ClientCorsOrigin>(); |
||||
|
RedirectUris = new List<ClientRedirectUri>(); |
||||
|
PostLogoutRedirectUris = new List<ClientPostLogoutRedirectUri>(); |
||||
|
IdentityProviderRestrictions = new List<ClientIdPRestriction>(); |
||||
|
Claims = new List<ClientClaim>(); |
||||
|
Properties = new List<ClientProperty>(); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddGrantType([NotNull] string grantType) |
||||
|
{ |
||||
|
AllowedGrantTypes.Add(new ClientGrantType(Id, grantType)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddGrantTypes(IEnumerable<string> grantTypes) |
||||
|
{ |
||||
|
AllowedGrantTypes.AddRange( |
||||
|
grantTypes.Select( |
||||
|
grantType => new ClientGrantType(Id, grantType) |
||||
|
) |
||||
|
); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddSecret([NotNull] string value, DateTime? expiration = null, string type = IdentityServerConstants.SecretTypes.SharedSecret, string description = null) |
||||
|
{ |
||||
|
ClientSecrets.Add(new ClientSecret(Id, value, expiration, type, description)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddScope([NotNull] string scope) |
||||
|
{ |
||||
|
AllowedScopes.Add(new ClientScope(Id, scope)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddCorsOrigin([NotNull] string origin) |
||||
|
{ |
||||
|
AllowedCorsOrigins.Add(new ClientCorsOrigin(Id, origin)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddRedirectUri([NotNull] string redirectUri) |
||||
|
{ |
||||
|
RedirectUris.Add(new ClientRedirectUri(Id, redirectUri)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddPostLogoutRedirectUri([NotNull] string postLogoutRedirectUri) |
||||
|
{ |
||||
|
PostLogoutRedirectUris.Add(new ClientPostLogoutRedirectUri(Id, postLogoutRedirectUri)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddIdentityProviderRestriction([NotNull] string provider) |
||||
|
{ |
||||
|
IdentityProviderRestrictions.Add(new ClientIdPRestriction(Id, provider)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddProperty([NotNull] string key) |
||||
|
{ |
||||
|
Properties.Add(new ClientProperty(Id, key)); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddClaim(IGuidGenerator guidGenerator, [NotNull] string type, string value) |
||||
|
{ |
||||
|
Claims.Add(new ClientClaim(guidGenerator.Create(), Id, type, value)); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,86 @@ |
|||||
|
using System.Collections.Generic; |
||||
|
using System.Security.Claims; |
||||
|
using AutoMapper; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Grants; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientAutoMapperProfile : Profile |
||||
|
{ |
||||
|
public ClientAutoMapperProfile() |
||||
|
{ |
||||
|
//TODO: Reverse maps will not used probably. Remove those will not used
|
||||
|
|
||||
|
CreateMap<Client, IdentityServer4.Models.Client>(); |
||||
|
|
||||
|
CreateMap<ClientCorsOrigin, string>() |
||||
|
.ConstructUsing(src => src.Origin) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.Origin, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ApiResource, IdentityServer4.Models.ApiResource>() |
||||
|
.ForMember(dest => dest.ApiSecrets, opt => opt.MapFrom(src => src.Secrets)); |
||||
|
|
||||
|
//TODO: Why PersistedGrant mapping is in this profile?
|
||||
|
CreateMap<PersistedGrant, IdentityServer4.Models.PersistedGrant>().ReverseMap(); |
||||
|
|
||||
|
CreateMap<IdentityResource, IdentityServer4.Models.IdentityResource>(); |
||||
|
|
||||
|
CreateMap<UserClaim, string>() |
||||
|
.ConstructUsing(src => src.Type) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.Type, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ApiSecret, IdentityServer4.Models.Secret>(); |
||||
|
|
||||
|
CreateMap<ApiScope, IdentityServer4.Models.Scope>(); |
||||
|
|
||||
|
CreateMap<ClientProperty, KeyValuePair<string, string>>() |
||||
|
.ReverseMap(); |
||||
|
|
||||
|
CreateMap<Client, IdentityServer4.Models.Client>() |
||||
|
.ForMember(dest => dest.ProtocolType, opt => opt.Condition(srs => srs != null)) |
||||
|
.ReverseMap(); |
||||
|
|
||||
|
CreateMap<ClientCorsOrigin, string>() |
||||
|
.ConstructUsing(src => src.Origin) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.Origin, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ClientIdPRestriction, string>() |
||||
|
.ConstructUsing(src => src.Provider) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.Provider, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ClientClaim, Claim>(MemberList.None) |
||||
|
.ConstructUsing(src => new Claim(src.Type, src.Value)) |
||||
|
.ReverseMap(); |
||||
|
|
||||
|
CreateMap<ClientScope, string>() |
||||
|
.ConstructUsing(src => src.Scope) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.Scope, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ClientPostLogoutRedirectUri, string>() |
||||
|
.ConstructUsing(src => src.PostLogoutRedirectUri) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.PostLogoutRedirectUri, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ClientRedirectUri, string>() |
||||
|
.ConstructUsing(src => src.RedirectUri) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.RedirectUri, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ClientGrantType, string>() |
||||
|
.ConstructUsing(src => src.GrantType) |
||||
|
.ReverseMap() |
||||
|
.ForMember(dest => dest.GrantType, opt => opt.MapFrom(src => src)); |
||||
|
|
||||
|
CreateMap<ClientSecret, IdentityServer4.Models.Secret>(MemberList.Destination) |
||||
|
.ForMember(dest => dest.Type, opt => opt.Condition(srs => srs != null)) |
||||
|
.ReverseMap(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,30 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientClaim : Entity<Guid> |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; set; } |
||||
|
|
||||
|
public virtual string Type { get; set; } |
||||
|
|
||||
|
public virtual string Value { get; set; } |
||||
|
|
||||
|
protected ClientClaim() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientClaim(Guid id, Guid clientId, [NotNull] string type, string value) |
||||
|
{ |
||||
|
Check.NotNull(type, nameof(type)); |
||||
|
|
||||
|
Id = id; |
||||
|
ClientId = clientId; |
||||
|
Type = type; |
||||
|
Value = value; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,31 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientCorsOrigin : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; protected set; } |
||||
|
|
||||
|
public virtual string Origin { get; protected set; } |
||||
|
|
||||
|
protected ClientCorsOrigin() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientCorsOrigin(Guid clientId, [NotNull] string origin) |
||||
|
{ |
||||
|
Check.NotNull(origin, nameof(origin)); |
||||
|
|
||||
|
ClientId = clientId; |
||||
|
Origin = origin; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, Origin }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,31 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientGrantType : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; protected set; } |
||||
|
|
||||
|
public virtual string GrantType { get; protected set; } |
||||
|
|
||||
|
protected ClientGrantType() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientGrantType(Guid clientId, [NotNull] string grantType) |
||||
|
{ |
||||
|
Check.NotNull(grantType, nameof(grantType)); |
||||
|
|
||||
|
ClientId = clientId; |
||||
|
GrantType = grantType; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, GrantType }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,31 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientIdPRestriction : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; set; } |
||||
|
|
||||
|
public virtual string Provider { get; set; } |
||||
|
|
||||
|
protected ClientIdPRestriction() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientIdPRestriction(Guid clientId, [NotNull] string provider) |
||||
|
{ |
||||
|
Check.NotNull(provider, nameof(provider)); |
||||
|
|
||||
|
ClientId = clientId; |
||||
|
Provider = provider; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, Provider }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,31 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientPostLogoutRedirectUri : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; protected set; } |
||||
|
|
||||
|
public virtual string PostLogoutRedirectUri { get; protected set; } |
||||
|
|
||||
|
protected ClientPostLogoutRedirectUri() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientPostLogoutRedirectUri(Guid clientId, [NotNull] string postLogoutRedirectUri) |
||||
|
{ |
||||
|
Check.NotNull(postLogoutRedirectUri, nameof(postLogoutRedirectUri)); |
||||
|
|
||||
|
ClientId = clientId; |
||||
|
PostLogoutRedirectUri = postLogoutRedirectUri; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, PostLogoutRedirectUri }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,33 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientProperty : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; set; } |
||||
|
|
||||
|
public virtual string Key { get; set; } |
||||
|
|
||||
|
public virtual string Value { get; set; } |
||||
|
|
||||
|
protected ClientProperty() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientProperty(Guid clientId, [NotNull] string key) |
||||
|
{ |
||||
|
Check.NotNull(key, nameof(key)); |
||||
|
|
||||
|
ClientId = clientId; |
||||
|
Key = key; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, Key }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,31 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientRedirectUri : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; protected set; } |
||||
|
|
||||
|
public virtual string RedirectUri { get; protected set; } |
||||
|
|
||||
|
protected ClientRedirectUri() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientRedirectUri(Guid clientId, [NotNull] string redirectUri) |
||||
|
{ |
||||
|
Check.NotNull(redirectUri, nameof(redirectUri)); |
||||
|
|
||||
|
ClientId = clientId; |
||||
|
RedirectUri = redirectUri; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, RedirectUri }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,28 @@ |
|||||
|
using System; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientScope : Entity |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; protected set; } |
||||
|
|
||||
|
public virtual string Scope { get; protected set; } |
||||
|
|
||||
|
protected ClientScope() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientScope(Guid clientId, string scope) |
||||
|
{ |
||||
|
ClientId = clientId; |
||||
|
Scope = scope; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, Scope }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,36 @@ |
|||||
|
using System; |
||||
|
using IdentityServer4; |
||||
|
using JetBrains.Annotations; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientSecret : Secret |
||||
|
{ |
||||
|
public virtual Guid ClientId { get; protected set; } |
||||
|
|
||||
|
protected ClientSecret() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal ClientSecret( |
||||
|
Guid clientId, |
||||
|
[NotNull] string value, |
||||
|
DateTime? expiration = null, |
||||
|
string type = IdentityServerConstants.SecretTypes.SharedSecret, |
||||
|
string description = null |
||||
|
) : base( |
||||
|
value, |
||||
|
expiration, |
||||
|
type, |
||||
|
description) |
||||
|
{ |
||||
|
ClientId = clientId; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { ClientId, Type, Value }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,24 @@ |
|||||
|
using System.Threading.Tasks; |
||||
|
using IdentityServer4.Stores; |
||||
|
using Volo.Abp.ObjectMapping; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientStore : IClientStore |
||||
|
{ |
||||
|
private readonly IClientRepository _clientRepository; |
||||
|
private readonly IObjectMapper _objectMapper; |
||||
|
|
||||
|
public ClientStore(IClientRepository clientRepository, IObjectMapper objectMapper) |
||||
|
{ |
||||
|
_clientRepository = clientRepository; |
||||
|
_objectMapper = objectMapper; |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<IdentityServer4.Models.Client> FindClientByIdAsync(string clientId) |
||||
|
{ |
||||
|
var client = await _clientRepository.FindByCliendIdAsync(clientId); |
||||
|
return _objectMapper.Map<Client, IdentityServer4.Models.Client>(client); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,17 @@ |
|||||
|
using System; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Repositories; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public interface IClientRepository : IBasicRepository<Client, Guid> |
||||
|
{ |
||||
|
Task<Client> FindByCliendIdAsync( |
||||
|
[NotNull] string clientId, |
||||
|
bool includeDetails = true, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,34 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Volo.Abp.Domain.Repositories; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Grants |
||||
|
{ |
||||
|
public interface IPersistentGrantRepository : IBasicRepository<PersistedGrant, Guid> |
||||
|
{ |
||||
|
Task<PersistedGrant> FindByKeyAsync( |
||||
|
string key, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
|
||||
|
Task<List<PersistedGrant>> GetListBySubjectIdAsync( |
||||
|
string key, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
|
||||
|
Task DeleteAsync( |
||||
|
string subjectId, |
||||
|
string clientId, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
|
||||
|
Task DeleteAsync( |
||||
|
string subjectId, |
||||
|
string clientId, |
||||
|
string type, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,32 @@ |
|||||
|
using System; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Grants |
||||
|
{ |
||||
|
public class PersistedGrant : AggregateRoot<Guid> |
||||
|
{ |
||||
|
public virtual string Key { get; set; } |
||||
|
|
||||
|
public virtual string Type { get; set; } |
||||
|
|
||||
|
public virtual string SubjectId { get; set; } |
||||
|
|
||||
|
public virtual string ClientId { get; set; } |
||||
|
|
||||
|
public virtual DateTime CreationTime { get; set; } |
||||
|
|
||||
|
public virtual DateTime? Expiration { get; set; } |
||||
|
|
||||
|
public virtual string Data { get; set; } |
||||
|
|
||||
|
protected PersistedGrant() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public PersistedGrant(Guid id) |
||||
|
{ |
||||
|
Id = id; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,72 @@ |
|||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading.Tasks; |
||||
|
using IdentityServer4.Stores; |
||||
|
using Volo.Abp.DependencyInjection; |
||||
|
using Volo.Abp.Guids; |
||||
|
using Volo.Abp.ObjectMapping; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Grants |
||||
|
{ |
||||
|
public class PersistedGrantStore : IPersistedGrantStore, ITransientDependency |
||||
|
{ |
||||
|
private readonly IPersistentGrantRepository _persistentGrantRepository; |
||||
|
private readonly IObjectMapper _objectMapper; |
||||
|
private readonly IGuidGenerator _guidGenerator; |
||||
|
|
||||
|
public PersistedGrantStore(IPersistentGrantRepository persistentGrantRepository, IObjectMapper objectMapper, IGuidGenerator guidGenerator) |
||||
|
{ |
||||
|
_persistentGrantRepository = persistentGrantRepository; |
||||
|
_objectMapper = objectMapper; |
||||
|
_guidGenerator = guidGenerator; |
||||
|
} |
||||
|
|
||||
|
public virtual async Task StoreAsync(IdentityServer4.Models.PersistedGrant grant) |
||||
|
{ |
||||
|
var entity = _objectMapper.Map<IdentityServer4.Models.PersistedGrant, PersistedGrant>(grant); |
||||
|
var existing = await _persistentGrantRepository.FindByKeyAsync(grant.Key); |
||||
|
if (existing == null) |
||||
|
{ |
||||
|
entity.Id = _guidGenerator.Create(); |
||||
|
await _persistentGrantRepository.InsertAsync(entity); |
||||
|
} |
||||
|
else |
||||
|
{ |
||||
|
await _persistentGrantRepository.UpdateAsync(entity); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<IdentityServer4.Models.PersistedGrant> GetAsync(string key) |
||||
|
{ |
||||
|
var persistedGrant = await _persistentGrantRepository.FindByKeyAsync(key); |
||||
|
return _objectMapper.Map<PersistedGrant, IdentityServer4.Models.PersistedGrant>(persistedGrant); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<IEnumerable<IdentityServer4.Models.PersistedGrant>> GetAllAsync(string subjectId) |
||||
|
{ |
||||
|
var persistedGrants = await _persistentGrantRepository.GetListBySubjectIdAsync(subjectId); |
||||
|
return persistedGrants.Select(x => _objectMapper.Map<PersistedGrant, IdentityServer4.Models.PersistedGrant>(x)); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task RemoveAsync(string key) |
||||
|
{ |
||||
|
var persistedGrant = await _persistentGrantRepository.FindByKeyAsync(key); |
||||
|
if (persistedGrant == null) |
||||
|
{ |
||||
|
return; |
||||
|
} |
||||
|
|
||||
|
await _persistentGrantRepository.DeleteAsync(persistedGrant); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task RemoveAllAsync(string subjectId, string clientId) |
||||
|
{ |
||||
|
await _persistentGrantRepository.DeleteAsync(subjectId, clientId); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task RemoveAllAsync(string subjectId, string clientId, string type) |
||||
|
{ |
||||
|
await _persistentGrantRepository.DeleteAsync(subjectId, clientId, type); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,22 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Volo.Abp.Domain.Repositories; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.IdentityResources |
||||
|
{ |
||||
|
public interface IIdentityResourceRepository : IBasicRepository<IdentityResource, Guid> |
||||
|
{ |
||||
|
Task<List<IdentityResource>> GetListByScopesAsync( |
||||
|
string[] scopeNames, |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
|
||||
|
Task<List<IdentityResource>> GetListAsync( |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default |
||||
|
); |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,26 @@ |
|||||
|
using System; |
||||
|
using JetBrains.Annotations; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.IdentityResources |
||||
|
{ |
||||
|
public class IdentityClaim : UserClaim |
||||
|
{ |
||||
|
public virtual Guid IdentityResourceId { get; set; } |
||||
|
|
||||
|
protected IdentityClaim() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected internal IdentityClaim(Guid identityResourceId, [NotNull] string type) |
||||
|
: base(type) |
||||
|
{ |
||||
|
IdentityResourceId = identityResourceId; |
||||
|
} |
||||
|
|
||||
|
public override object[] GetKeys() |
||||
|
{ |
||||
|
return new object[] { IdentityResourceId, Type }; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,60 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.IdentityResources |
||||
|
{ |
||||
|
public class IdentityResource : AggregateRoot<Guid> |
||||
|
{ |
||||
|
public virtual string Name { get; set; } |
||||
|
|
||||
|
public virtual string DisplayName { get; set; } |
||||
|
|
||||
|
public virtual string Description { get; set; } |
||||
|
|
||||
|
public virtual bool Enabled { get; set; } |
||||
|
|
||||
|
public virtual bool Required { get; set; } |
||||
|
|
||||
|
public virtual bool Emphasize { get; set; } |
||||
|
|
||||
|
public virtual bool ShowInDiscoveryDocument { get; set; } |
||||
|
|
||||
|
public virtual List<IdentityClaim> UserClaims { get; set; } |
||||
|
|
||||
|
protected IdentityResource() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public IdentityResource( |
||||
|
Guid id, |
||||
|
[NotNull] string name, |
||||
|
string displayName = null, |
||||
|
string description = null, |
||||
|
bool enabled = true, |
||||
|
bool required = false, |
||||
|
bool emphasize = false, |
||||
|
bool showInDiscoveryDocument = true) |
||||
|
{ |
||||
|
Check.NotNull(name, nameof(name)); |
||||
|
|
||||
|
Id = id; |
||||
|
Name = name; |
||||
|
DisplayName = displayName; |
||||
|
Description = description; |
||||
|
Enabled = enabled; |
||||
|
Required = required; |
||||
|
Emphasize = emphasize; |
||||
|
ShowInDiscoveryDocument = showInDiscoveryDocument; |
||||
|
|
||||
|
UserClaims = new List<IdentityClaim>(); |
||||
|
} |
||||
|
|
||||
|
public virtual void AddUserClaim([NotNull] string type) |
||||
|
{ |
||||
|
UserClaims.Add(new IdentityClaim(Id, type)); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,27 @@ |
|||||
|
using Microsoft.AspNetCore.Authentication; |
||||
|
using Microsoft.AspNetCore.Builder; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Jwt |
||||
|
{ |
||||
|
//TODO: Should we move this to another package..?
|
||||
|
|
||||
|
public static class JwtTokenMiddleware |
||||
|
{ |
||||
|
public static IApplicationBuilder UseJwtTokenMiddleware(this IApplicationBuilder app, string schema) |
||||
|
{ |
||||
|
return app.Use(async (ctx, next) => |
||||
|
{ |
||||
|
if (ctx.User.Identity?.IsAuthenticated != true) |
||||
|
{ |
||||
|
var result = await ctx.AuthenticateAsync(schema); |
||||
|
if (result.Succeeded && result.Principal != null) |
||||
|
{ |
||||
|
ctx.User = result.Principal; |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
await next(); |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,59 @@ |
|||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading.Tasks; |
||||
|
using IdentityServer4.Models; |
||||
|
using IdentityServer4.Stores; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
using Volo.Abp.ObjectMapping; |
||||
|
using ApiResource = IdentityServer4.Models.ApiResource; |
||||
|
using IdentityResource = Volo.Abp.IdentityServer.IdentityResources.IdentityResource; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class ResourceStore : IResourceStore |
||||
|
{ |
||||
|
private readonly IIdentityResourceRepository _identityResourceRepository; |
||||
|
private readonly IApiResourceRepository _apiResourceRepository; |
||||
|
private readonly IObjectMapper _objectMapper; |
||||
|
|
||||
|
public ResourceStore( |
||||
|
IIdentityResourceRepository identityResourceRepository, |
||||
|
IObjectMapper objectMapper, |
||||
|
IApiResourceRepository apiResourceRepository) |
||||
|
{ |
||||
|
_identityResourceRepository = identityResourceRepository; |
||||
|
_objectMapper = objectMapper; |
||||
|
_apiResourceRepository = apiResourceRepository; |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<IEnumerable<IdentityServer4.Models.IdentityResource>> FindIdentityResourcesByScopeAsync(IEnumerable<string> scopeNames) |
||||
|
{ |
||||
|
var resource = await _identityResourceRepository.GetListByScopesAsync(scopeNames.ToArray(), includeDetails: true); |
||||
|
return _objectMapper.Map<List<IdentityResource>, List<IdentityServer4.Models.IdentityResource>>(resource); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<IEnumerable<ApiResource>> FindApiResourcesByScopeAsync(IEnumerable<string> scopeNames) |
||||
|
{ |
||||
|
var resources = await _apiResourceRepository.GetListByScopesAsync(scopeNames.ToArray(), includeDetails: true); |
||||
|
return resources.Select(x => _objectMapper.Map<ApiResources.ApiResource, ApiResource>(x)); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<ApiResource> FindApiResourceAsync(string name) |
||||
|
{ |
||||
|
var resource = await _apiResourceRepository.FindByNameAsync(name); |
||||
|
return _objectMapper.Map<ApiResources.ApiResource, ApiResource>(resource); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<Resources> GetAllResourcesAsync() |
||||
|
{ |
||||
|
var identityResources = await _identityResourceRepository.GetListAsync(includeDetails: true); |
||||
|
var apiResources = await _apiResourceRepository.GetListAsync(includeDetails: true); |
||||
|
|
||||
|
return new Resources( |
||||
|
_objectMapper.Map<List<IdentityResource>, IdentityServer4.Models.IdentityResource[]>(identityResources), |
||||
|
_objectMapper.Map<List<ApiResources.ApiResource>, ApiResource[]>(apiResources) |
||||
|
); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,37 @@ |
|||||
|
using System; |
||||
|
using IdentityServer4; |
||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public abstract class Secret : Entity |
||||
|
{ |
||||
|
public virtual string Type { get; protected set; } |
||||
|
|
||||
|
public virtual string Value { get; set; } |
||||
|
|
||||
|
public virtual string Description { get; set; } |
||||
|
|
||||
|
public virtual DateTime? Expiration { get; set; } |
||||
|
|
||||
|
protected Secret() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected Secret( |
||||
|
[NotNull] string value, |
||||
|
DateTime? expiration = null, |
||||
|
string type = IdentityServerConstants.SecretTypes.SharedSecret, |
||||
|
string description = null) |
||||
|
{ |
||||
|
Check.NotNull(value, nameof(value)); |
||||
|
|
||||
|
Value = value; |
||||
|
Expiration = expiration; |
||||
|
Type = type; |
||||
|
Description = description; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,37 @@ |
|||||
|
namespace Volo.Abp.IdentityServer.Temp |
||||
|
{ |
||||
|
//TODO: Remove!
|
||||
|
//internal static class IdentityServerConfig
|
||||
|
//{
|
||||
|
// public static IEnumerable<ApiResource> GetApiResources()
|
||||
|
// {
|
||||
|
// return new List<ApiResource>
|
||||
|
// {
|
||||
|
// new ApiResource("api1", "My API")
|
||||
|
// };
|
||||
|
// }
|
||||
|
|
||||
|
// public static IEnumerable<IdentityServer4.Models.Client> GetClients()
|
||||
|
// {
|
||||
|
// return new List<Client>
|
||||
|
// {
|
||||
|
// new Client
|
||||
|
// {
|
||||
|
// ClientId = "client",
|
||||
|
|
||||
|
// // no interactive user, use the clientid/secret for authentication
|
||||
|
// AllowedGrantTypes = GrantTypes.ClientCredentials,
|
||||
|
|
||||
|
// // secret for authentication
|
||||
|
// ClientSecrets =
|
||||
|
// {
|
||||
|
// new IdentityServer4.Models.Secret("secret".Sha256())
|
||||
|
// },
|
||||
|
|
||||
|
// // scopes that client has access to
|
||||
|
// AllowedScopes = { "api1" }
|
||||
|
// }
|
||||
|
// };
|
||||
|
// }
|
||||
|
//}
|
||||
|
} |
||||
@ -0,0 +1,22 @@ |
|||||
|
using JetBrains.Annotations; |
||||
|
using Volo.Abp.Domain.Entities; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public abstract class UserClaim : Entity |
||||
|
{ |
||||
|
public virtual string Type { get; protected set; } |
||||
|
|
||||
|
protected UserClaim() |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected UserClaim([NotNull] string type) |
||||
|
{ |
||||
|
Check.NotNull(type, nameof(type)); |
||||
|
|
||||
|
Type = type; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,22 @@ |
|||||
|
<Project Sdk="Microsoft.NET.Sdk"> |
||||
|
|
||||
|
<Import Project="..\..\common.props" /> |
||||
|
|
||||
|
<PropertyGroup> |
||||
|
<TargetFramework>netstandard2.0</TargetFramework> |
||||
|
<AssemblyName>Volo.Abp.IdentityServer.EntityFrameworkCore</AssemblyName> |
||||
|
<PackageId>Volo.Abp.IdentityServer.EntityFrameworkCore</PackageId> |
||||
|
<AssetTargetFallback>$(AssetTargetFallback);portable-net45+win8+wp8+wpa81;</AssetTargetFallback> |
||||
|
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute> |
||||
|
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute> |
||||
|
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute> |
||||
|
<RootNamespace /> |
||||
|
</PropertyGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<ProjectReference Include="..\Volo.Abp.IdentityServer.Domain\Volo.Abp.IdentityServer.Domain.csproj" /> |
||||
|
|
||||
|
<ProjectReference Include="..\..\..\..\..\abp\framework\src\Volo.Abp.EntityFrameworkCore\Volo.Abp.EntityFrameworkCore.csproj" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
</Project> |
||||
@ -0,0 +1,2 @@ |
|||||
|
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation"> |
||||
|
<s:String x:Key="/Default/CodeInspection/CSharpLanguageProject/LanguageLevel/@EntryValue">CSharp71</s:String></wpf:ResourceDictionary> |
||||
@ -0,0 +1,55 @@ |
|||||
|
using System.Linq; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public static class AbpIdentityServerEfCoreQueryableExtensions |
||||
|
{ |
||||
|
public static IQueryable<ApiResource> IncludeDetails(this IQueryable<ApiResource> queryable, bool include = true) |
||||
|
{ |
||||
|
if (!include) |
||||
|
{ |
||||
|
return queryable; |
||||
|
} |
||||
|
|
||||
|
return queryable |
||||
|
.Include(x => x.Secrets) |
||||
|
.Include(x => x.UserClaims) |
||||
|
.Include(x => x.Scopes) |
||||
|
.ThenInclude(s => s.UserClaims); |
||||
|
} |
||||
|
|
||||
|
public static IQueryable<IdentityResource> IncludeDetails(this IQueryable<IdentityResource> queryable, bool include = true) |
||||
|
{ |
||||
|
if (!include) |
||||
|
{ |
||||
|
return queryable; |
||||
|
} |
||||
|
|
||||
|
return queryable |
||||
|
.Include(x => x.UserClaims); |
||||
|
} |
||||
|
|
||||
|
public static IQueryable<Client> IncludeDetails(this IQueryable<Client> queryable, bool include = true) |
||||
|
{ |
||||
|
if (!include) |
||||
|
{ |
||||
|
return queryable; |
||||
|
} |
||||
|
|
||||
|
return queryable |
||||
|
.Include(x => x.AllowedGrantTypes) |
||||
|
.Include(x => x.RedirectUris) |
||||
|
.Include(x => x.PostLogoutRedirectUris) |
||||
|
.Include(x => x.AllowedScopes) |
||||
|
.Include(x => x.ClientSecrets) |
||||
|
.Include(x => x.Claims) |
||||
|
.Include(x => x.IdentityProviderRestrictions) |
||||
|
.Include(x => x.AllowedCorsOrigins) |
||||
|
.Include(x => x.Properties); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,59 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.Domain.Repositories.EntityFrameworkCore; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.EntityFrameworkCore; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.ApiResources |
||||
|
{ |
||||
|
public class ApiResourceRepository : EfCoreRepository<IIdentityServerDbContext, ApiResource, Guid>, IApiResourceRepository |
||||
|
{ |
||||
|
public ApiResourceRepository(IDbContextProvider<IIdentityServerDbContext> dbContextProvider) : base(dbContextProvider) |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public virtual async Task<ApiResource> FindByNameAsync( |
||||
|
string name, |
||||
|
bool includeDetails = true, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
var query = from apiResource in DbSet.IncludeDetails(includeDetails) |
||||
|
where apiResource.Name == name |
||||
|
select apiResource; |
||||
|
|
||||
|
return await query |
||||
|
.FirstOrDefaultAsync(GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<List<ApiResource>> GetListByScopesAsync( |
||||
|
string[] scopeNames, |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
var query = from api in DbSet.IncludeDetails(includeDetails) |
||||
|
where api.Scopes.Any(x => scopeNames.Contains(x.Name)) |
||||
|
select api; |
||||
|
|
||||
|
return await query.ToListAsync(GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<List<ApiResource>> GetListAsync( |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
return await DbSet |
||||
|
.IncludeDetails(includeDetails) |
||||
|
.ToListAsync(GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public override IQueryable<ApiResource> WithDetails() |
||||
|
{ |
||||
|
return GetQueryable().IncludeDetails(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,34 @@ |
|||||
|
using System; |
||||
|
using System.Linq; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.Domain.Repositories.EntityFrameworkCore; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.EntityFrameworkCore; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Clients |
||||
|
{ |
||||
|
public class ClientRepository : EfCoreRepository<IIdentityServerDbContext, Client, Guid>, IClientRepository |
||||
|
{ |
||||
|
public ClientRepository(IDbContextProvider<IIdentityServerDbContext> dbContextProvider) : base(dbContextProvider) |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public virtual async Task<Client> FindByCliendIdAsync( |
||||
|
string clientId, |
||||
|
bool includeDetails = true, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
return await DbSet |
||||
|
.IncludeDetails(includeDetails) |
||||
|
.FirstOrDefaultAsync(x => x.ClientId == clientId, GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public override IQueryable<Client> WithDetails() |
||||
|
{ |
||||
|
return GetQueryable().IncludeDetails(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,28 @@ |
|||||
|
using Microsoft.Extensions.DependencyInjection; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.IdentityServer.Grants; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
using Volo.Abp.Modularity; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.EntityFrameworkCore |
||||
|
{ |
||||
|
[DependsOn(typeof(AbpIdentityServerDomainModule))] |
||||
|
[DependsOn(typeof(AbpEntityFrameworkCoreModule))] |
||||
|
public class AbpIdentityServerEntityFrameworkCoreModule : AbpModule |
||||
|
{ |
||||
|
public override void ConfigureServices(ServiceConfigurationContext context) |
||||
|
{ |
||||
|
context.Services.AddAbpDbContext<IdentityServerDbContext>(options => |
||||
|
{ |
||||
|
options.AddDefaultRepositories<IIdentityServerDbContext>(); |
||||
|
|
||||
|
options.AddRepository<Client, ClientRepository>(); |
||||
|
options.AddRepository<ApiResource, ApiResourceRepository>(); |
||||
|
options.AddRepository<IdentityResource, IdentityResourceRepository>(); |
||||
|
options.AddRepository<PersistedGrant, PersistentGrantRepository>(); |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,50 @@ |
|||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.Data; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.IdentityServer.Grants; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.EntityFrameworkCore |
||||
|
{ |
||||
|
[ConnectionStringName("AbpIdentityServer")] |
||||
|
public interface IIdentityServerDbContext : IEfCoreDbContext |
||||
|
{ |
||||
|
DbSet<ApiResource> ApiResources { get; set; } |
||||
|
|
||||
|
DbSet<ApiSecret> ApiSecrets { get; set; } |
||||
|
|
||||
|
DbSet<ApiResourceClaim> ApiResourceClaims { get; set; } |
||||
|
|
||||
|
DbSet<ApiScope> ApiScopes { get; set; } |
||||
|
|
||||
|
DbSet<ApiScopeClaim> ApiScopeClaims { get; set; } |
||||
|
|
||||
|
DbSet<IdentityResource> IdentityResources { get; set; } |
||||
|
|
||||
|
DbSet<IdentityClaim> IdentityClaims { get; set; } |
||||
|
|
||||
|
DbSet<Client> Clients { get; set; } |
||||
|
|
||||
|
DbSet<ClientGrantType> ClientGrantTypes { get; set; } |
||||
|
|
||||
|
DbSet<ClientRedirectUri> ClientRedirectUris { get; set; } |
||||
|
|
||||
|
DbSet<ClientPostLogoutRedirectUri> ClientPostLogoutRedirectUris { get; set; } |
||||
|
|
||||
|
DbSet<ClientScope> ClientScopes { get; set; } |
||||
|
|
||||
|
DbSet<ClientSecret> ClientSecrets { get; set; } |
||||
|
|
||||
|
DbSet<ClientClaim> ClientClaims { get; set; } |
||||
|
|
||||
|
DbSet<ClientIdPRestriction> ClientIdPRestrictions { get; set; } |
||||
|
|
||||
|
DbSet<ClientCorsOrigin> ClientCorsOrigins { get; set; } |
||||
|
|
||||
|
DbSet<ClientProperty> ClientProperties { get; set; } |
||||
|
|
||||
|
DbSet<PersistedGrant> PersistedGrants { get; set; } |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,66 @@ |
|||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.Data; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.IdentityServer.Grants; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.EntityFrameworkCore |
||||
|
{ |
||||
|
[ConnectionStringName("AbpIdentityServer")] |
||||
|
public class IdentityServerDbContext : AbpDbContext<IdentityServerDbContext>, IIdentityServerDbContext |
||||
|
{ |
||||
|
public static string TablePrefix { get; set; } = AbpIdentityServerConsts.DefaultDbTablePrefix; |
||||
|
|
||||
|
public static string Schema { get; set; } = AbpIdentityServerConsts.DefaultDbSchema; |
||||
|
|
||||
|
public DbSet<ApiResource> ApiResources { get; set; } |
||||
|
|
||||
|
public DbSet<ApiSecret> ApiSecrets { get; set; } |
||||
|
|
||||
|
public DbSet<ApiResourceClaim> ApiResourceClaims { get; set; } |
||||
|
|
||||
|
public DbSet<ApiScope> ApiScopes { get; set; } |
||||
|
|
||||
|
public DbSet<ApiScopeClaim> ApiScopeClaims { get; set; } |
||||
|
|
||||
|
public DbSet<IdentityResource> IdentityResources { get; set; } |
||||
|
|
||||
|
public DbSet<IdentityClaim> IdentityClaims { 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 IdentityServerDbContext(DbContextOptions<IdentityServerDbContext> options) |
||||
|
: base(options) |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
protected override void OnModelCreating(ModelBuilder builder) |
||||
|
{ |
||||
|
base.OnModelCreating(builder); |
||||
|
builder.ConfigureIdentityServer(TablePrefix, Schema); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,228 @@ |
|||||
|
using JetBrains.Annotations; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.IdentityServer.Grants; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.EntityFrameworkCore |
||||
|
{ |
||||
|
public static class IdentityServerDbContextModelCreatingExtensions |
||||
|
{ |
||||
|
public static void ConfigureIdentityServer( |
||||
|
this ModelBuilder builder, |
||||
|
[CanBeNull] string tablePrefix = AbpIdentityServerConsts.DefaultDbTablePrefix, |
||||
|
[CanBeNull] string schema = AbpIdentityServerConsts.DefaultDbSchema) |
||||
|
{ |
||||
|
Check.NotNull(builder, nameof(builder)); |
||||
|
|
||||
|
if (tablePrefix == null) |
||||
|
{ |
||||
|
tablePrefix = ""; |
||||
|
} |
||||
|
|
||||
|
builder.Entity<Client>(client => |
||||
|
{ |
||||
|
client.ToTable(tablePrefix + "Clients", schema); |
||||
|
|
||||
|
client.Property(x => x.ClientId).HasMaxLength(ClientConsts.ClientIdMaxLength).IsRequired(); |
||||
|
client.Property(x => x.ProtocolType).HasMaxLength(ClientConsts.ProtocolTypeMaxLength).IsRequired(); |
||||
|
client.Property(x => x.ClientName).HasMaxLength(ClientConsts.ClientNameMaxLength); |
||||
|
client.Property(x => x.ClientUri).HasMaxLength(ClientConsts.ClientUriMaxLength); |
||||
|
client.Property(x => x.LogoUri).HasMaxLength(ClientConsts.LogoUriMaxLength); |
||||
|
client.Property(x => x.Description).HasMaxLength(ClientConsts.DescriptionMaxLength); |
||||
|
client.Property(x => x.FrontChannelLogoutUri).HasMaxLength(ClientConsts.FrontChannelLogoutUriMaxLength); |
||||
|
client.Property(x => x.BackChannelLogoutUri).HasMaxLength(ClientConsts.BackChannelLogoutUriMaxLength); |
||||
|
client.Property(x => x.ClientClaimsPrefix).HasMaxLength(ClientConsts.ClientClaimsPrefixMaxLength); |
||||
|
client.Property(x => x.PairWiseSubjectSalt).HasMaxLength(ClientConsts.PairWiseSubjectSaltMaxLength); |
||||
|
|
||||
|
client.HasMany(x => x.AllowedScopes).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.ClientSecrets).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.AllowedGrantTypes).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.AllowedCorsOrigins).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.RedirectUris).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.PostLogoutRedirectUris).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.IdentityProviderRestrictions).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.Claims).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
client.HasMany(x => x.Properties).WithOne().HasForeignKey(x => x.ClientId).IsRequired(); |
||||
|
|
||||
|
client.HasIndex(x => x.ClientId).IsUnique(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientGrantType>(grantType => |
||||
|
{ |
||||
|
grantType.ToTable(tablePrefix + "ClientGrantTypes", schema); |
||||
|
|
||||
|
grantType.HasKey(x => new { x.ClientId, x.GrantType }); |
||||
|
|
||||
|
grantType.Property(x => x.GrantType).HasMaxLength(ClientGrantTypeConsts.GrantTypeMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientRedirectUri>(redirectUri => |
||||
|
{ |
||||
|
redirectUri.ToTable(tablePrefix + "ClientRedirectUris", schema); |
||||
|
|
||||
|
redirectUri.HasKey(x => new { x.ClientId, x.RedirectUri }); |
||||
|
|
||||
|
redirectUri.Property(x => x.RedirectUri).HasMaxLength(ClientRedirectUriConsts.RedirectUriMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientPostLogoutRedirectUri>(postLogoutRedirectUri => |
||||
|
{ |
||||
|
postLogoutRedirectUri.ToTable(tablePrefix + "ClientPostLogoutRedirectUris", schema); |
||||
|
|
||||
|
postLogoutRedirectUri.HasKey(x => new { x.ClientId, x.PostLogoutRedirectUri }); |
||||
|
|
||||
|
postLogoutRedirectUri.Property(x => x.PostLogoutRedirectUri).HasMaxLength(ClientPostLogoutRedirectUriConsts.PostLogoutRedirectUriMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientScope>(scope => |
||||
|
{ |
||||
|
scope.ToTable(tablePrefix + "ClientScopes", schema); |
||||
|
|
||||
|
scope.HasKey(x => new { x.ClientId, x.Scope }); |
||||
|
|
||||
|
scope.Property(x => x.Scope).HasMaxLength(ClientScopeConsts.ScopeMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientSecret>(secret => |
||||
|
{ |
||||
|
secret.ToTable(tablePrefix + "ClientSecrets", schema); |
||||
|
|
||||
|
secret.HasKey(x => new { x.ClientId, x.Type, x.Value }); |
||||
|
|
||||
|
secret.Property(x => x.Type).HasMaxLength(SecretConsts.TypeMaxLength).IsRequired(); |
||||
|
secret.Property(x => x.Value).HasMaxLength(SecretConsts.ValueMaxLength).IsRequired(); |
||||
|
secret.Property(x => x.Description).HasMaxLength(SecretConsts.DescriptionMaxLength); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientClaim>(claim => |
||||
|
{ |
||||
|
claim.ToTable(tablePrefix + "ClientClaims", schema); |
||||
|
|
||||
|
claim.Property(x => x.Type).HasMaxLength(ClientClaimConsts.TypeMaxLength).IsRequired(); |
||||
|
claim.Property(x => x.Value).HasMaxLength(ClientClaimConsts.ValueMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientIdPRestriction>(idPRestriction => |
||||
|
{ |
||||
|
idPRestriction.ToTable(tablePrefix + "ClientIdPRestrictions", schema); |
||||
|
|
||||
|
idPRestriction.HasKey(x => new { x.ClientId, x.Provider }); |
||||
|
|
||||
|
idPRestriction.Property(x => x.Provider).HasMaxLength(ClientIdPRestrictionConsts.ProviderMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientCorsOrigin>(corsOrigin => |
||||
|
{ |
||||
|
corsOrigin.ToTable(tablePrefix + "ClientCorsOrigins", schema); |
||||
|
|
||||
|
corsOrigin.HasKey(x => new { x.ClientId, x.Origin }); |
||||
|
|
||||
|
corsOrigin.Property(x => x.Origin).HasMaxLength(ClientCorsOriginConsts.OriginMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ClientProperty>(property => |
||||
|
{ |
||||
|
property.ToTable(tablePrefix + "ClientProperties", schema); |
||||
|
|
||||
|
property.HasKey(x => new { x.ClientId, x.Key }); |
||||
|
|
||||
|
property.Property(x => x.Key).HasMaxLength(ClientPropertyConsts.KeyMaxLength).IsRequired(); |
||||
|
property.Property(x => x.Value).HasMaxLength(ClientPropertyConsts.ValueMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<PersistedGrant>(grant => |
||||
|
{ |
||||
|
grant.ToTable(tablePrefix + "PersistedGrants", schema); |
||||
|
|
||||
|
grant.Property(x => x.Key).HasMaxLength(PersistedGrantConsts.KeyMaxLength).ValueGeneratedNever(); |
||||
|
grant.Property(x => x.Type).HasMaxLength(PersistedGrantConsts.TypeMaxLength).IsRequired(); |
||||
|
grant.Property(x => x.SubjectId).HasMaxLength(PersistedGrantConsts.SubjectIdMaxLength); |
||||
|
grant.Property(x => x.ClientId).HasMaxLength(PersistedGrantConsts.ClientIdMaxLength).IsRequired(); |
||||
|
grant.Property(x => x.CreationTime).IsRequired(); |
||||
|
grant.Property(x => x.Data).IsRequired(); |
||||
|
|
||||
|
grant.HasKey(x => x.Key); //TODO: What about Id!!!
|
||||
|
|
||||
|
grant.HasIndex(x => new { x.SubjectId, x.ClientId, x.Type }); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<IdentityResource>(identityResource => |
||||
|
{ |
||||
|
identityResource.ToTable(tablePrefix + "IdentityResources", schema); |
||||
|
|
||||
|
identityResource.Property(x => x.Name).HasMaxLength(IdentityResourceConsts.NameMaxLength).IsRequired(); |
||||
|
identityResource.Property(x => x.DisplayName).HasMaxLength(IdentityResourceConsts.DisplayNameMaxLength); |
||||
|
identityResource.Property(x => x.Description).HasMaxLength(IdentityResourceConsts.DescriptionMaxLength); |
||||
|
|
||||
|
identityResource.HasMany(x => x.UserClaims).WithOne().HasForeignKey(x => x.IdentityResourceId).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<IdentityClaim>(claim => |
||||
|
{ |
||||
|
claim.ToTable(tablePrefix + "IdentityClaims", schema); |
||||
|
|
||||
|
claim.HasKey(x => new { x.IdentityResourceId, x.Type }); |
||||
|
|
||||
|
claim.Property(x => x.Type).HasMaxLength(UserClaimConsts.TypeMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ApiResource>(apiResource => |
||||
|
{ |
||||
|
apiResource.ToTable(tablePrefix + "ApiResources", schema); |
||||
|
|
||||
|
apiResource.Property(x => x.Name).HasMaxLength(ApiResourceConsts.NameMaxLength).IsRequired(); |
||||
|
apiResource.Property(x => x.DisplayName).HasMaxLength(ApiResourceConsts.DisplayNameMaxLength); |
||||
|
apiResource.Property(x => x.Description).HasMaxLength(ApiResourceConsts.DescriptionMaxLength); |
||||
|
|
||||
|
apiResource.HasMany(x => x.Secrets).WithOne().HasForeignKey(x => x.ApiResourceId).IsRequired(); |
||||
|
apiResource.HasMany(x => x.Scopes).WithOne().HasForeignKey(x => x.ApiResourceId).IsRequired(); |
||||
|
apiResource.HasMany(x => x.UserClaims).WithOne().HasForeignKey(x => x.ApiResourceId).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ApiSecret>(apiSecret => |
||||
|
{ |
||||
|
apiSecret.ToTable(tablePrefix + "ApiSecrets", schema); |
||||
|
|
||||
|
apiSecret.HasKey(x => new { x.ApiResourceId, x.Type, x.Value }); |
||||
|
|
||||
|
apiSecret.Property(x => x.Type).HasMaxLength(SecretConsts.TypeMaxLength).IsRequired(); |
||||
|
apiSecret.Property(x => x.Value).HasMaxLength(SecretConsts.ValueMaxLength).IsRequired(); |
||||
|
apiSecret.Property(x => x.Description).HasMaxLength(SecretConsts.DescriptionMaxLength); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ApiResourceClaim>(apiClaim => |
||||
|
{ |
||||
|
apiClaim.ToTable(tablePrefix + "ApiClaims", schema); |
||||
|
|
||||
|
apiClaim.HasKey(x => new { x.ApiResourceId, x.Type }); |
||||
|
|
||||
|
apiClaim.Property(x => x.Type).HasMaxLength(UserClaimConsts.TypeMaxLength).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ApiScope>(apiScope => |
||||
|
{ |
||||
|
apiScope.ToTable(tablePrefix + "ApiScopes", schema); |
||||
|
|
||||
|
apiScope.HasKey(x => new { x.ApiResourceId, x.Name }); |
||||
|
|
||||
|
apiScope.Property(x => x.Name).HasMaxLength(ApiScopeConsts.NameMaxLength).IsRequired(); |
||||
|
apiScope.Property(x => x.DisplayName).HasMaxLength(ApiScopeConsts.DisplayNameMaxLength); |
||||
|
apiScope.Property(x => x.Description).HasMaxLength(ApiScopeConsts.DescriptionMaxLength); |
||||
|
|
||||
|
apiScope.HasMany(x => x.UserClaims).WithOne().HasForeignKey(x => new { x.ApiResourceId, x.Name }).IsRequired(); |
||||
|
}); |
||||
|
|
||||
|
builder.Entity<ApiScopeClaim>(apiScopeClaim => |
||||
|
{ |
||||
|
apiScopeClaim.ToTable(tablePrefix + "ApiScopeClaims", schema); |
||||
|
|
||||
|
apiScopeClaim.HasKey(x => new { x.ApiResourceId, x.Name, x.Type }); |
||||
|
|
||||
|
apiScopeClaim.Property(x => x.Type).HasMaxLength(UserClaimConsts.TypeMaxLength).IsRequired(); |
||||
|
apiScopeClaim.Property(x => x.Name).HasMaxLength(ApiScopeConsts.NameMaxLength).IsRequired(); |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,60 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.Domain.Repositories.EntityFrameworkCore; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.EntityFrameworkCore; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.Grants |
||||
|
{ |
||||
|
public class PersistentGrantRepository : EfCoreRepository<IIdentityServerDbContext, PersistedGrant, Guid>, IPersistentGrantRepository |
||||
|
{ |
||||
|
public PersistentGrantRepository(IDbContextProvider<IIdentityServerDbContext> dbContextProvider) : base(dbContextProvider) |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public Task<PersistedGrant> FindByKeyAsync( |
||||
|
string key, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
return DbSet |
||||
|
.FirstOrDefaultAsync(x => x.Key == key, GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public Task<List<PersistedGrant>> GetListBySubjectIdAsync( |
||||
|
string subjectId, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
return DbSet |
||||
|
.Where(x => x.SubjectId == subjectId) |
||||
|
.ToListAsync(GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public async Task DeleteAsync( |
||||
|
string subjectId, |
||||
|
string clientId, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
await DeleteAsync( |
||||
|
x => x.SubjectId == subjectId && x.ClientId == clientId, |
||||
|
cancellationToken: GetCancellationToken(cancellationToken) |
||||
|
); |
||||
|
} |
||||
|
|
||||
|
public async Task DeleteAsync( |
||||
|
string subjectId, |
||||
|
string clientId, |
||||
|
string type, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
await DeleteAsync( |
||||
|
x => x.SubjectId == subjectId && x.ClientId == clientId && x.Type == type, |
||||
|
cancellationToken: GetCancellationToken(cancellationToken) |
||||
|
); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,47 @@ |
|||||
|
using System; |
||||
|
using System.Collections.Generic; |
||||
|
using System.Linq; |
||||
|
using System.Threading; |
||||
|
using System.Threading.Tasks; |
||||
|
using Microsoft.EntityFrameworkCore; |
||||
|
using Volo.Abp.Domain.Repositories.EntityFrameworkCore; |
||||
|
using Volo.Abp.EntityFrameworkCore; |
||||
|
using Volo.Abp.IdentityServer.EntityFrameworkCore; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer.IdentityResources |
||||
|
{ |
||||
|
public class IdentityResourceRepository : EfCoreRepository<IIdentityServerDbContext, IdentityResource, Guid>, IIdentityResourceRepository |
||||
|
{ |
||||
|
public IdentityResourceRepository(IDbContextProvider<IIdentityServerDbContext> dbContextProvider) |
||||
|
: base(dbContextProvider) |
||||
|
{ |
||||
|
|
||||
|
} |
||||
|
|
||||
|
public virtual async Task<List<IdentityResource>> GetListByScopesAsync( |
||||
|
string[] scopeNames, |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
var query = from identityResource in DbSet.IncludeDetails(includeDetails) |
||||
|
where scopeNames.Contains(identityResource.Name) |
||||
|
select identityResource; |
||||
|
|
||||
|
return await query.ToListAsync(GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public virtual async Task<List<IdentityResource>> GetListAsync( |
||||
|
bool includeDetails = false, |
||||
|
CancellationToken cancellationToken = default) |
||||
|
{ |
||||
|
return await DbSet |
||||
|
.IncludeDetails(includeDetails) |
||||
|
.ToListAsync(GetCancellationToken(cancellationToken)); |
||||
|
} |
||||
|
|
||||
|
public override IQueryable<IdentityResource> WithDetails() |
||||
|
{ |
||||
|
return GetQueryable().IncludeDetails(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,33 @@ |
|||||
|
<Project Sdk="Microsoft.NET.Sdk"> |
||||
|
|
||||
|
<PropertyGroup> |
||||
|
<TargetFramework>netcoreapp2.0</TargetFramework> |
||||
|
<AssemblyName>Volo.Abp.IdentityServer.EntityFrameworkCore.Tests</AssemblyName> |
||||
|
<PackageId>Volo.Abp.IdentityServer.EntityFrameworkCore.Tests</PackageId> |
||||
|
<GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles> |
||||
|
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute> |
||||
|
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute> |
||||
|
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute> |
||||
|
<RootNamespace /> |
||||
|
</PropertyGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<ProjectReference Include="..\..\src\Volo.Abp.IdentityServer.EntityFrameworkCore\Volo.Abp.IdentityServer.EntityFrameworkCore.csproj" /> |
||||
|
|
||||
|
<ProjectReference Include="..\..\..\..\..\abp\modules\identity\src\Volo.Abp.Identity.EntityFrameworkCore\Volo.Abp.Identity.EntityFrameworkCore.csproj" /> |
||||
|
|
||||
|
<ProjectReference Include="..\..\..\..\..\abp\framework\src\Volo.Abp.Autofac\Volo.Abp.Autofac.csproj" /> |
||||
|
<ProjectReference Include="..\..\..\..\..\abp\framework\src\Volo.Abp.TestBase\Volo.Abp.TestBase.csproj" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
<ItemGroup> |
||||
|
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.7.2" /> |
||||
|
<PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="2.1.0" /> |
||||
|
<PackageReference Include="NSubstitute" Version="3.1.0" /> |
||||
|
<PackageReference Include="Shouldly" Version="3.0.0" /> |
||||
|
<PackageReference Include="xunit" Version="2.3.1" /> |
||||
|
<PackageReference Include="xunit.extensibility.execution" Version="2.3.1" /> |
||||
|
<PackageReference Include="xunit.runner.visualstudio" Version="2.3.1" /> |
||||
|
</ItemGroup> |
||||
|
|
||||
|
</Project> |
||||
@ -0,0 +1,10 @@ |
|||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class AbpIdentityServerTestBase : AbpIntegratedTest<AbpIdentityServerTestEntityFrameworkCoreModule> |
||||
|
{ |
||||
|
protected override void SetAbpApplicationCreationOptions(AbpApplicationCreationOptions options) |
||||
|
{ |
||||
|
options.UseAutofac(); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
@ -0,0 +1,129 @@ |
|||||
|
using IdentityServer4.Models; |
||||
|
using Volo.Abp.DependencyInjection; |
||||
|
using Volo.Abp.Guids; |
||||
|
using Volo.Abp.IdentityServer.ApiResources; |
||||
|
using Volo.Abp.IdentityServer.Clients; |
||||
|
using Volo.Abp.IdentityServer.Grants; |
||||
|
using Volo.Abp.IdentityServer.IdentityResources; |
||||
|
using ApiResource = Volo.Abp.IdentityServer.ApiResources.ApiResource; |
||||
|
using Client = Volo.Abp.IdentityServer.Clients.Client; |
||||
|
using IdentityResource = Volo.Abp.IdentityServer.IdentityResources.IdentityResource; |
||||
|
using PersistedGrant = Volo.Abp.IdentityServer.Grants.PersistedGrant; |
||||
|
|
||||
|
namespace Volo.Abp.IdentityServer |
||||
|
{ |
||||
|
public class AbpIdentityServerTestDataBuilder : ITransientDependency |
||||
|
{ |
||||
|
private readonly IGuidGenerator _guidGenerator; |
||||
|
private readonly IClientRepository _clientRepository; |
||||
|
private readonly IPersistentGrantRepository _persistentGrantRepository; |
||||
|
private readonly IApiResourceRepository _apiResourceRepository; |
||||
|
private readonly IIdentityResourceRepository _identityResourceRepository; |
||||
|
|
||||
|
public AbpIdentityServerTestDataBuilder( |
||||
|
IClientRepository clientRepository, |
||||
|
IGuidGenerator guidGenerator, |
||||
|
IPersistentGrantRepository persistentGrantRepository, |
||||
|
IApiResourceRepository apiResourceRepository, |
||||
|
IIdentityResourceRepository identityResourceRepository) |
||||
|
{ |
||||
|
_clientRepository = clientRepository; |
||||
|
_guidGenerator = guidGenerator; |
||||
|
_persistentGrantRepository = persistentGrantRepository; |
||||
|
_apiResourceRepository = apiResourceRepository; |
||||
|
_identityResourceRepository = identityResourceRepository; |
||||
|
} |
||||
|
|
||||
|
public void Build() |
||||
|
{ |
||||
|
AddClients(); |
||||
|
AddPersistentGrants(); |
||||
|
AddApiResources(); |
||||
|
AddIdentityResources(); |
||||
|
} |
||||
|
|
||||
|
private void AddClients() |
||||
|
{ |
||||
|
var client42 = new Client(_guidGenerator.Create(), "42") |
||||
|
{ |
||||
|
ProtocolType = "TestProtocol-42" |
||||
|
}; |
||||
|
|
||||
|
client42.AddCorsOrigin("Origin1"); |
||||
|
|
||||
|
client42.AddScope("api1"); |
||||
|
|
||||
|
_clientRepository.Insert(client42); |
||||
|
} |
||||
|
|
||||
|
private void AddPersistentGrants() |
||||
|
{ |
||||
|
_persistentGrantRepository.Insert(new PersistedGrant(_guidGenerator.Create()) |
||||
|
{ |
||||
|
Key = "38", |
||||
|
ClientId = "TestClientId-38", |
||||
|
Type = "TestType-38", |
||||
|
SubjectId = "TestSubject", |
||||
|
Data = "TestData-38" |
||||
|
}); |
||||
|
|
||||
|
_persistentGrantRepository.Insert(new PersistedGrant(_guidGenerator.Create()) |
||||
|
{ |
||||
|
Key = "37", |
||||
|
ClientId = "TestClientId-37", |
||||
|
Type = "TestType-37", |
||||
|
SubjectId = "TestSubject", |
||||
|
Data = "TestData-37" |
||||
|
}); |
||||
|
|
||||
|
_persistentGrantRepository.Insert(new PersistedGrant(_guidGenerator.Create()) |
||||
|
{ |
||||
|
Key = "36", |
||||
|
ClientId = "TestClientId-X", |
||||
|
Type = "TestType-36", |
||||
|
SubjectId = "TestSubject-X", |
||||
|
Data = "TestData-36" |
||||
|
}); |
||||
|
|
||||
|
_persistentGrantRepository.Insert(new PersistedGrant(_guidGenerator.Create()) |
||||
|
{ |
||||
|
Key = "35", |
||||
|
ClientId = "TestClientId-X", |
||||
|
Type = "TestType-35", |
||||
|
SubjectId = "TestSubject-X", |
||||
|
Data = "TestData-35" |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
private void AddApiResources() |
||||
|
{ |
||||
|
var apiResource = new ApiResource(_guidGenerator.Create(), "Test-ApiResource-Name-1") |
||||
|
{ |
||||
|
Enabled = true, |
||||
|
Description = "Test-ApiResource-Description-1", |
||||
|
DisplayName = "Test-ApiResource-DisplayName-1" |
||||
|
}; |
||||
|
|
||||
|
apiResource.AddSecret("secret".Sha256()); |
||||
|
apiResource.AddScope("Test-ApiResource-ApiScope-Name-1", "Test-ApiResource-ApiScope-DisplayName-1"); |
||||
|
apiResource.AddUserClaim("Test-ApiResource-Claim-Type-1"); |
||||
|
|
||||
|
_apiResourceRepository.Insert(apiResource); |
||||
|
} |
||||
|
|
||||
|
private void AddIdentityResources() |
||||
|
{ |
||||
|
var identityResource = new IdentityResource(_guidGenerator.Create(), "Test-Identity-Resource-Name-1") |
||||
|
{ |
||||
|
Description = "Test-Identity-Resource-Description-1", |
||||
|
DisplayName = "Test-Identity-Resource-DisplayName-1", |
||||
|
Required = true, |
||||
|
Emphasize = true |
||||
|
}; |
||||
|
|
||||
|
identityResource.AddUserClaim("Test-Identity-Resource-1-IdentityClaim-Type-1"); |
||||
|
|
||||
|
_identityResourceRepository.Insert(identityResource); |
||||
|
} |
||||
|
} |
||||
|
} |
||||
Some files were not shown because too many files changed in this diff
Loading…
Reference in new issue