fix: 平台订阅管理支持跨租户查询
This commit is contained in:
@@ -14,19 +14,31 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
#region 订阅查询
|
||||
|
||||
/// <inheritdoc />
|
||||
public async Task<TenantSubscription?> FindByIdAsync(long subscriptionId, CancellationToken cancellationToken = default)
|
||||
public async Task<TenantSubscription?> FindByIdAsync(
|
||||
long subscriptionId,
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
return await dbContext.TenantSubscriptions
|
||||
var query = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
return await query
|
||||
.FirstOrDefaultAsync(s => s.Id == subscriptionId, cancellationToken);
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public async Task<IReadOnlyList<TenantSubscription>> FindByIdsAsync(
|
||||
IEnumerable<long> subscriptionIds,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
var ids = subscriptionIds.ToList();
|
||||
return await dbContext.TenantSubscriptions
|
||||
var query = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
return await query
|
||||
.Where(s => ids.Contains(s.Id))
|
||||
.ToListAsync(cancellationToken);
|
||||
}
|
||||
@@ -34,10 +46,15 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
/// <inheritdoc />
|
||||
public async Task<(IReadOnlyList<SubscriptionWithRelations> Items, int Total)> SearchPagedAsync(
|
||||
SubscriptionSearchFilter filter,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
// 1. 构建基础查询
|
||||
var query = dbContext.TenantSubscriptions
|
||||
var subscriptionQuery = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
var query = subscriptionQuery
|
||||
.AsNoTracking()
|
||||
.Join(
|
||||
dbContext.Tenants,
|
||||
@@ -113,9 +130,16 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
}
|
||||
|
||||
/// <inheritdoc />
|
||||
public async Task<SubscriptionDetailInfo?> GetDetailAsync(long subscriptionId, CancellationToken cancellationToken = default)
|
||||
public async Task<SubscriptionDetailInfo?> GetDetailAsync(
|
||||
long subscriptionId,
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
var result = await dbContext.TenantSubscriptions
|
||||
var subscriptionQuery = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
var result = await subscriptionQuery
|
||||
.AsNoTracking()
|
||||
.Where(s => s.Id == subscriptionId)
|
||||
.Select(s => new
|
||||
@@ -147,10 +171,16 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
/// <inheritdoc />
|
||||
public async Task<IReadOnlyList<SubscriptionWithTenant>> FindByIdsWithTenantAsync(
|
||||
IEnumerable<long> subscriptionIds,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
var ids = subscriptionIds.ToList();
|
||||
return await dbContext.TenantSubscriptions
|
||||
|
||||
var query = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
return await query
|
||||
.Where(s => ids.Contains(s.Id))
|
||||
.Join(
|
||||
dbContext.Tenants,
|
||||
@@ -169,10 +199,15 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
public async Task<IReadOnlyList<AutoRenewalCandidate>> FindAutoRenewalCandidatesAsync(
|
||||
DateTime now,
|
||||
DateTime renewalThreshold,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
// 1. 查询开启自动续费且即将到期的活跃订阅
|
||||
var query = dbContext.TenantSubscriptions
|
||||
var subscriptionQuery = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
var query = subscriptionQuery
|
||||
.Where(s => s.Status == SubscriptionStatus.Active
|
||||
&& s.AutoRenew
|
||||
&& s.EffectiveTo <= renewalThreshold
|
||||
@@ -195,10 +230,15 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
public async Task<IReadOnlyList<RenewalReminderCandidate>> FindRenewalReminderCandidatesAsync(
|
||||
DateTime startOfDay,
|
||||
DateTime endOfDay,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
// 1. 查询到期落在指定区间的订阅(且未开启自动续费)
|
||||
var query = dbContext.TenantSubscriptions
|
||||
var subscriptionQuery = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
var query = subscriptionQuery
|
||||
.Where(s => s.Status == SubscriptionStatus.Active
|
||||
&& !s.AutoRenew
|
||||
&& s.EffectiveTo >= startOfDay
|
||||
@@ -226,10 +266,15 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
/// <inheritdoc />
|
||||
public async Task<IReadOnlyList<TenantSubscription>> FindExpiredActiveSubscriptionsAsync(
|
||||
DateTime now,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
var query = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
// 1. 查询已到期仍为 Active 的订阅
|
||||
return await dbContext.TenantSubscriptions
|
||||
return await query
|
||||
.Where(s => s.Status == SubscriptionStatus.Active && s.EffectiveTo < now)
|
||||
.ToListAsync(cancellationToken);
|
||||
}
|
||||
@@ -238,10 +283,15 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
public async Task<IReadOnlyList<TenantSubscription>> FindGracePeriodExpiredSubscriptionsAsync(
|
||||
DateTime now,
|
||||
int gracePeriodDays,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
var query = ignoreTenantFilter
|
||||
? dbContext.TenantSubscriptions.IgnoreQueryFilters()
|
||||
: dbContext.TenantSubscriptions;
|
||||
|
||||
// 1. 查询宽限期已结束的订阅
|
||||
return await dbContext.TenantSubscriptions
|
||||
return await query
|
||||
.Where(s => s.Status == SubscriptionStatus.GracePeriod
|
||||
&& s.EffectiveTo.AddDays(gracePeriodDays) < now)
|
||||
.ToListAsync(cancellationToken);
|
||||
@@ -312,9 +362,14 @@ public sealed class EfSubscriptionRepository(TakeoutAppDbContext dbContext) : IS
|
||||
/// <inheritdoc />
|
||||
public async Task<IReadOnlyList<TenantQuotaUsage>> GetQuotaUsagesAsync(
|
||||
long tenantId,
|
||||
CancellationToken cancellationToken = default)
|
||||
CancellationToken cancellationToken = default,
|
||||
bool ignoreTenantFilter = false)
|
||||
{
|
||||
return await dbContext.TenantQuotaUsages
|
||||
var query = ignoreTenantFilter
|
||||
? dbContext.TenantQuotaUsages.IgnoreQueryFilters()
|
||||
: dbContext.TenantQuotaUsages;
|
||||
|
||||
return await query
|
||||
.AsNoTracking()
|
||||
.Where(q => q.TenantId == tenantId)
|
||||
.ToListAsync(cancellationToken);
|
||||
|
||||
Reference in New Issue
Block a user