mirror of https://github.com/abpframework/abp.git
committed by
GitHub
71 changed files with 1882 additions and 126 deletions
@ -0,0 +1,3 @@ |
|||
<Weavers xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="FodyWeavers.xsd"> |
|||
<ConfigureAwait ContinueOnCapturedContext="false" /> |
|||
</Weavers> |
|||
@ -0,0 +1,30 @@ |
|||
<?xml version="1.0" encoding="utf-8"?> |
|||
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"> |
|||
<!-- This file was generated by Fody. Manual changes to this file will be lost when your project is rebuilt. --> |
|||
<xs:element name="Weavers"> |
|||
<xs:complexType> |
|||
<xs:all> |
|||
<xs:element name="ConfigureAwait" minOccurs="0" maxOccurs="1"> |
|||
<xs:complexType> |
|||
<xs:attribute name="ContinueOnCapturedContext" type="xs:boolean" /> |
|||
</xs:complexType> |
|||
</xs:element> |
|||
</xs:all> |
|||
<xs:attribute name="VerifyAssembly" type="xs:boolean"> |
|||
<xs:annotation> |
|||
<xs:documentation>'true' to run assembly verification (PEVerify) on the target assembly after all weavers have been executed.</xs:documentation> |
|||
</xs:annotation> |
|||
</xs:attribute> |
|||
<xs:attribute name="VerifyIgnoreCodes" type="xs:string"> |
|||
<xs:annotation> |
|||
<xs:documentation>A comma-separated list of error codes that can be safely ignored in assembly verification.</xs:documentation> |
|||
</xs:annotation> |
|||
</xs:attribute> |
|||
<xs:attribute name="GenerateXsd" type="xs:boolean"> |
|||
<xs:annotation> |
|||
<xs:documentation>'false' to turn off automatic generation of the XML Schema file.</xs:documentation> |
|||
</xs:annotation> |
|||
</xs:attribute> |
|||
</xs:complexType> |
|||
</xs:element> |
|||
</xs:schema> |
|||
@ -0,0 +1,23 @@ |
|||
<Project Sdk="Microsoft.NET.Sdk"> |
|||
|
|||
<Import Project="..\..\..\configureawait.props" /> |
|||
<Import Project="..\..\..\common.props" /> |
|||
|
|||
<PropertyGroup> |
|||
<TargetFrameworks>netstandard2.0;netstandard2.1;net8.0</TargetFrameworks> |
|||
<Nullable>enable</Nullable> |
|||
<WarningsAsErrors>Nullable</WarningsAsErrors> |
|||
<AssemblyName>Volo.Abp.AspNetCore.Abstractions</AssemblyName> |
|||
<PackageId>Volo.Abp.AspNetCore.Abstractions</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.Core\Volo.Abp.Core.csproj" /> |
|||
</ItemGroup> |
|||
|
|||
</Project> |
|||
@ -0,0 +1,15 @@ |
|||
using Microsoft.Extensions.DependencyInjection; |
|||
using Volo.Abp.AspNetCore.VirtualFileSystem; |
|||
using Volo.Abp.AspNetCore.WebClientInfo; |
|||
using Volo.Abp.Modularity; |
|||
|
|||
namespace Volo.Abp.AspNetCore; |
|||
|
|||
public class AbpAspNetCoreAbstractionsModule : AbpModule |
|||
{ |
|||
public override void ConfigureServices(ServiceConfigurationContext context) |
|||
{ |
|||
context.Services.AddSingleton<IWebContentFileProvider, NullWebContentFileProvider>(); |
|||
context.Services.AddSingleton<IWebClientInfoProvider, NullWebClientInfoProvider>();; |
|||
} |
|||
} |
|||
@ -0,0 +1,22 @@ |
|||
using Microsoft.Extensions.FileProviders; |
|||
using Microsoft.Extensions.Primitives; |
|||
|
|||
namespace Volo.Abp.AspNetCore.VirtualFileSystem; |
|||
|
|||
public class NullWebContentFileProvider : IWebContentFileProvider |
|||
{ |
|||
public virtual IFileInfo GetFileInfo(string subpath) |
|||
{ |
|||
return new NotFoundFileInfo(subpath); |
|||
} |
|||
|
|||
public virtual IDirectoryContents GetDirectoryContents(string subpath) |
|||
{ |
|||
return new NotFoundDirectoryContents(); |
|||
} |
|||
|
|||
public virtual IChangeToken Watch(string filter) |
|||
{ |
|||
return NullChangeToken.Singleton; |
|||
} |
|||
} |
|||
@ -0,0 +1,10 @@ |
|||
namespace Volo.Abp.AspNetCore.WebClientInfo; |
|||
|
|||
public class NullWebClientInfoProvider : IWebClientInfoProvider |
|||
{ |
|||
public virtual string? BrowserInfo { get; } |
|||
|
|||
public virtual string? ClientIpAddress { get; } |
|||
|
|||
public virtual string? DeviceInfo { get; } |
|||
} |
|||
@ -0,0 +1,17 @@ |
|||
using System.Collections.Generic; |
|||
using Volo.Abp.Security.Claims; |
|||
|
|||
namespace Volo.Abp.Identity.AspNetCore; |
|||
|
|||
public class AbpRefreshingPrincipalOptions |
|||
{ |
|||
public List<string> CurrentPrincipalKeepClaimTypes { get; set; } |
|||
|
|||
public AbpRefreshingPrincipalOptions() |
|||
{ |
|||
CurrentPrincipalKeepClaimTypes = new List<string> |
|||
{ |
|||
AbpClaimTypes.SessionId |
|||
}; |
|||
} |
|||
} |
|||
@ -0,0 +1,14 @@ |
|||
namespace Volo.Abp.Identity; |
|||
|
|||
public class IdentitySessionConsts |
|||
{ |
|||
public static int MaxSessionIdLength { get; set; } = 128; |
|||
|
|||
public static int MaxDeviceLength { get; set; } = 64; |
|||
|
|||
public static int MaxDeviceInfoLength { get; set; } = 64; |
|||
|
|||
public static int MaxClientIdLength { get; set; } = 64; |
|||
|
|||
public static int MaxIpAddressesLength { get; set; } = 256; |
|||
} |
|||
@ -0,0 +1,10 @@ |
|||
namespace Volo.Abp.Identity; |
|||
|
|||
public static class IdentitySessionDevices |
|||
{ |
|||
public const string Web = "Web"; |
|||
|
|||
public const string OAuth = "OAuth"; |
|||
|
|||
public const string Mobile = "Mobile"; |
|||
} |
|||
@ -0,0 +1,35 @@ |
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.Threading; |
|||
using System.Threading.Tasks; |
|||
using Volo.Abp.Domain.Repositories; |
|||
|
|||
namespace Volo.Abp.Identity; |
|||
|
|||
public interface IIdentitySessionRepository : IBasicRepository<IdentitySession, Guid> |
|||
{ |
|||
Task<IdentitySession> FindAsync(string sessionId, CancellationToken cancellationToken = default); |
|||
|
|||
Task<IdentitySession> GetAsync(string sessionId, CancellationToken cancellationToken = default); |
|||
|
|||
Task<List<IdentitySession>> GetListAsync( |
|||
string sorting = null, |
|||
int maxResultCount = int.MaxValue, |
|||
int skipCount = 0, |
|||
Guid? userId = null, |
|||
string device = null, |
|||
string clientId = null, |
|||
CancellationToken cancellationToken = default); |
|||
|
|||
Task<long> GetCountAsync( |
|||
Guid? userId = null, |
|||
string device = null, |
|||
string clientId = null, |
|||
CancellationToken cancellationToken = default); |
|||
|
|||
Task DeleteAllAsync(Guid userId, Guid? exceptSessionId = null, CancellationToken cancellationToken = default); |
|||
|
|||
Task DeleteAllAsync(Guid userId, string device, Guid? exceptSessionId = null, CancellationToken cancellationToken = default); |
|||
|
|||
Task DeleteAllAsync(TimeSpan inactiveTimeSpan, CancellationToken cancellationToken = default); |
|||
} |
|||
@ -0,0 +1,90 @@ |
|||
using System; |
|||
using System.Collections.Generic; |
|||
using Volo.Abp.Domain.Entities; |
|||
using Volo.Abp.MultiTenancy; |
|||
|
|||
namespace Volo.Abp.Identity; |
|||
|
|||
public class IdentitySession : BasicAggregateRoot<Guid>, IMultiTenant |
|||
{ |
|||
public virtual string SessionId { get; protected set; } |
|||
|
|||
/// <summary>
|
|||
/// Web, Mobile ...
|
|||
/// </summary>
|
|||
public virtual string Device { get; protected set; } |
|||
|
|||
public virtual string DeviceInfo { get; protected set; } |
|||
|
|||
public virtual Guid? TenantId { get; protected set; } |
|||
|
|||
public virtual Guid UserId { get; protected set; } |
|||
|
|||
public virtual string ClientId { get; set; } |
|||
|
|||
public virtual string IpAddresses { get; protected set; } |
|||
|
|||
public virtual DateTime SignedIn { get; protected set; } |
|||
|
|||
public virtual DateTime? LastAccessed { get; protected set; } |
|||
|
|||
protected IdentitySession() |
|||
{ |
|||
|
|||
} |
|||
|
|||
public IdentitySession( |
|||
Guid id, |
|||
string sessionId, |
|||
string device, |
|||
string deviceInfo, |
|||
Guid userId, |
|||
Guid? tenantId, |
|||
string clientId, |
|||
string ipAddresses, |
|||
DateTime signedIn, |
|||
DateTime? lastAccessed = null) |
|||
{ |
|||
Id = id; |
|||
SessionId = sessionId; |
|||
Device = device; |
|||
DeviceInfo = deviceInfo; |
|||
UserId = userId; |
|||
TenantId = tenantId; |
|||
ClientId = clientId; |
|||
IpAddresses = ipAddresses; |
|||
SignedIn = signedIn; |
|||
LastAccessed = lastAccessed; |
|||
} |
|||
|
|||
public void SetSignedInTime(DateTime signedIn) |
|||
{ |
|||
SignedIn = signedIn; |
|||
} |
|||
|
|||
public void UpdateLastAccessedTime(DateTime? lastAccessed) |
|||
{ |
|||
LastAccessed = lastAccessed; |
|||
} |
|||
|
|||
public void SetIpAddresses(IEnumerable<string> ipAddresses) |
|||
{ |
|||
IpAddresses = JoinAsString(ipAddresses); |
|||
} |
|||
|
|||
public IEnumerable<string> GetIpAddresses() |
|||
{ |
|||
return GetArrayFromString(IpAddresses); |
|||
} |
|||
|
|||
private static string JoinAsString(IEnumerable<string> list) |
|||
{ |
|||
var serialized = string.Join(",", list); |
|||
return serialized.IsNullOrWhiteSpace() ? null : serialized; |
|||
} |
|||
|
|||
private string[] GetArrayFromString(string str) |
|||
{ |
|||
return str?.Split(",", StringSplitOptions.RemoveEmptyEntries) ?? Array.Empty<string>(); |
|||
} |
|||
} |
|||
@ -0,0 +1,85 @@ |
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.Linq; |
|||
using System.Linq.Dynamic.Core; |
|||
using System.Threading; |
|||
using System.Threading.Tasks; |
|||
using Microsoft.EntityFrameworkCore; |
|||
using Volo.Abp.Domain.Entities; |
|||
using Volo.Abp.Domain.Repositories.EntityFrameworkCore; |
|||
using Volo.Abp.EntityFrameworkCore; |
|||
using Volo.Abp.Timing; |
|||
|
|||
namespace Volo.Abp.Identity.EntityFrameworkCore; |
|||
|
|||
public class EfCoreIdentitySessionRepository : EfCoreRepository<IIdentityDbContext, IdentitySession, Guid>, IIdentitySessionRepository |
|||
{ |
|||
public EfCoreIdentitySessionRepository(IDbContextProvider<IIdentityDbContext> dbContextProvider) |
|||
: base(dbContextProvider) |
|||
{ |
|||
|
|||
} |
|||
|
|||
public virtual async Task<IdentitySession> FindAsync(string sessionId, CancellationToken cancellationToken = default) |
|||
{ |
|||
return await (await GetDbSetAsync()).FirstOrDefaultAsync(x => x.SessionId == sessionId, GetCancellationToken(cancellationToken)); |
|||
} |
|||
|
|||
public virtual async Task<IdentitySession> GetAsync(string sessionId, CancellationToken cancellationToken = default) |
|||
{ |
|||
var session = await FindAsync(sessionId, cancellationToken); |
|||
if (session == null) |
|||
{ |
|||
throw new EntityNotFoundException(typeof(IdentitySession)); |
|||
} |
|||
|
|||
return session; |
|||
} |
|||
|
|||
public virtual async Task<List<IdentitySession>> GetListAsync( |
|||
string sorting = null, |
|||
int maxResultCount = int.MaxValue, |
|||
int skipCount = 0, |
|||
Guid? userId = null, |
|||
string device = null, |
|||
string clientId = null, |
|||
CancellationToken cancellationToken = default) |
|||
{ |
|||
return await (await GetDbSetAsync()) |
|||
.WhereIf(userId.HasValue, x => x.UserId == userId) |
|||
.WhereIf(!device.IsNullOrWhiteSpace(), x => x.Device == device) |
|||
.WhereIf(!clientId.IsNullOrWhiteSpace(), x => x.ClientId == clientId) |
|||
.OrderBy(sorting.IsNullOrWhiteSpace() ? $"{nameof(IdentitySession.LastAccessed)} desc" : sorting) |
|||
.PageBy(skipCount, maxResultCount) |
|||
.ToListAsync(GetCancellationToken(cancellationToken)); |
|||
} |
|||
|
|||
public virtual async Task<long> GetCountAsync( |
|||
Guid? userId = null, |
|||
string device = null, |
|||
string clientId = null, |
|||
CancellationToken cancellationToken = default) |
|||
{ |
|||
return await (await GetDbSetAsync()) |
|||
.WhereIf(userId.HasValue, x => x.UserId == userId) |
|||
.WhereIf(!device.IsNullOrWhiteSpace(), x => x.Device == device) |
|||
.WhereIf(!clientId.IsNullOrWhiteSpace(), x => x.ClientId == clientId) |
|||
.LongCountAsync(GetCancellationToken(cancellationToken)); |
|||
} |
|||
|
|||
public virtual async Task DeleteAllAsync(Guid userId, Guid? exceptSessionId = null, CancellationToken cancellationToken = default) |
|||
{ |
|||
await DeleteAsync(x => x.UserId == userId && x.Id != exceptSessionId, cancellationToken: cancellationToken); |
|||
} |
|||
|
|||
public virtual async Task DeleteAllAsync(Guid userId, string device, Guid? exceptSessionId = null, CancellationToken cancellationToken = default) |
|||
{ |
|||
await DeleteAsync(x => x.UserId == userId && x.Device == device && x.Id != exceptSessionId, cancellationToken: cancellationToken); |
|||
} |
|||
|
|||
public virtual async Task DeleteAllAsync(TimeSpan inactiveTimeSpan, CancellationToken cancellationToken = default) |
|||
{ |
|||
var now = LazyServiceProvider.LazyGetRequiredService<IClock>().Now; |
|||
await DeleteDirectAsync(x => x.LastAccessed == null || x.LastAccessed < now.Subtract(inactiveTimeSpan), cancellationToken: cancellationToken); |
|||
} |
|||
} |
|||
@ -0,0 +1,90 @@ |
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.Linq; |
|||
using System.Linq.Dynamic.Core; |
|||
using System.Threading; |
|||
using System.Threading.Tasks; |
|||
using MongoDB.Driver; |
|||
using MongoDB.Driver.Linq; |
|||
using Volo.Abp.Domain.Entities; |
|||
using Volo.Abp.Domain.Repositories.MongoDB; |
|||
using Volo.Abp.MongoDB; |
|||
using Volo.Abp.Timing; |
|||
|
|||
namespace Volo.Abp.Identity.MongoDB; |
|||
|
|||
public class MongoIdentitySessionRepository : MongoDbRepository<IAbpIdentityMongoDbContext, IdentitySession, Guid>, IIdentitySessionRepository |
|||
{ |
|||
public MongoIdentitySessionRepository(IMongoDbContextProvider<IAbpIdentityMongoDbContext> dbContextProvider) |
|||
: base(dbContextProvider) |
|||
{ |
|||
|
|||
} |
|||
|
|||
public virtual async Task<IdentitySession> FindAsync(string sessionId, CancellationToken cancellationToken = default) |
|||
{ |
|||
return await (await GetMongoQueryableAsync(GetCancellationToken(cancellationToken))) |
|||
.As<IMongoQueryable<IdentitySession>>() |
|||
.FirstOrDefaultAsync(x => x.SessionId == sessionId, GetCancellationToken(cancellationToken)); |
|||
} |
|||
|
|||
public virtual async Task<IdentitySession> GetAsync(string sessionId, CancellationToken cancellationToken = default) |
|||
{ |
|||
var session = await FindAsync(sessionId, cancellationToken); |
|||
if (session == null) |
|||
{ |
|||
throw new EntityNotFoundException(typeof(IdentitySession)); |
|||
} |
|||
|
|||
return session; |
|||
} |
|||
|
|||
public virtual async Task<List<IdentitySession>> GetListAsync( |
|||
string sorting = null, |
|||
int maxResultCount = int.MaxValue, |
|||
int skipCount = 0, |
|||
Guid? userId = null, |
|||
string device = null, |
|||
string clientId = null, |
|||
CancellationToken cancellationToken = default) |
|||
{ |
|||
return await (await GetMongoQueryableAsync(GetCancellationToken(cancellationToken))) |
|||
.WhereIf(userId.HasValue, x => x.UserId == userId) |
|||
.WhereIf(!device.IsNullOrWhiteSpace(), x => x.Device == device) |
|||
.WhereIf(!clientId.IsNullOrWhiteSpace(), x => x.ClientId == clientId) |
|||
.OrderBy(sorting.IsNullOrWhiteSpace() ? $"{nameof(IdentitySession.LastAccessed)} desc" : sorting) |
|||
.PageBy(skipCount, maxResultCount) |
|||
.As<IMongoQueryable<IdentitySession>>() |
|||
.ToListAsync(GetCancellationToken(cancellationToken)); |
|||
} |
|||
|
|||
public virtual async Task<long> GetCountAsync( |
|||
Guid? userId = null, |
|||
string device = null, |
|||
string clientId = null, |
|||
CancellationToken cancellationToken = default) |
|||
{ |
|||
return await (await GetMongoQueryableAsync(GetCancellationToken(cancellationToken))) |
|||
.WhereIf(userId.HasValue, x => x.UserId == userId) |
|||
.WhereIf(!device.IsNullOrWhiteSpace(), x => x.Device == device) |
|||
.WhereIf(!clientId.IsNullOrWhiteSpace(), x => x.ClientId == clientId) |
|||
.As<IMongoQueryable<IdentitySession>>() |
|||
.LongCountAsync(GetCancellationToken(cancellationToken)); |
|||
} |
|||
|
|||
public virtual async Task DeleteAllAsync(Guid userId, Guid? exceptSessionId = null, CancellationToken cancellationToken = default) |
|||
{ |
|||
await DeleteAsync(x => x.UserId == userId && x.Id != exceptSessionId, cancellationToken: cancellationToken); |
|||
} |
|||
|
|||
public virtual async Task DeleteAllAsync(Guid userId, string device, Guid? exceptSessionId = null, CancellationToken cancellationToken = default) |
|||
{ |
|||
await DeleteAsync(x => x.UserId == userId && x.Device == device && x.Id != exceptSessionId, cancellationToken: cancellationToken); |
|||
} |
|||
|
|||
public virtual async Task DeleteAllAsync(TimeSpan inactiveTimeSpan, CancellationToken cancellationToken = default) |
|||
{ |
|||
var now = LazyServiceProvider.LazyGetRequiredService<IClock>().Now; |
|||
await DeleteDirectAsync(x => x.LastAccessed == null || x.LastAccessed < now.Subtract(inactiveTimeSpan), cancellationToken: cancellationToken); |
|||
} |
|||
} |
|||
Loading…
Reference in new issue