forked from baron/baron-sso
chore: consolidate local integration changes
This commit is contained in:
@@ -16,6 +16,7 @@ type UserProjectionRepository interface {
|
||||
IsReady(ctx context.Context) (bool, error)
|
||||
GetStatus(ctx context.Context) (domain.UserProjectionStatus, error)
|
||||
CountTenantMembers(ctx context.Context, tenants []domain.Tenant) (map[string]int64, error)
|
||||
CountTenantMembersRecursive(ctx context.Context, tenants []domain.Tenant) (map[string]int64, error)
|
||||
ReplaceAllFromKratos(ctx context.Context, users []domain.User) error
|
||||
MarkFailed(ctx context.Context, syncErr error) error
|
||||
}
|
||||
@@ -108,10 +109,63 @@ func (r *userProjectionRepository) CountTenantMembers(ctx context.Context, tenan
|
||||
return counts, nil
|
||||
}
|
||||
|
||||
func (r *userProjectionRepository) CountTenantMembersRecursive(ctx context.Context, tenants []domain.Tenant) (map[string]int64, error) {
|
||||
counts := make(map[string]int64, len(tenants))
|
||||
for _, tenant := range tenants {
|
||||
counts[tenant.ID] = 0
|
||||
}
|
||||
if len(tenants) == 0 {
|
||||
return counts, nil
|
||||
}
|
||||
|
||||
valuePlaceholders := make([]string, 0, len(tenants))
|
||||
args := make([]any, 0, len(tenants))
|
||||
for _, tenant := range tenants {
|
||||
valuePlaceholders = append(valuePlaceholders, "(?)")
|
||||
args = append(args, strings.TrimSpace(tenant.ID))
|
||||
}
|
||||
|
||||
query := fmt.Sprintf(`
|
||||
WITH RECURSIVE requested(tenant_id) AS (
|
||||
VALUES %s
|
||||
),
|
||||
descendants(root_tenant_id, tenant_id) AS (
|
||||
SELECT requested.tenant_id, requested.tenant_id
|
||||
FROM requested
|
||||
UNION ALL
|
||||
SELECT descendants.root_tenant_id, child.id::text
|
||||
FROM descendants
|
||||
JOIN tenants child
|
||||
ON child.parent_id::text = descendants.tenant_id
|
||||
AND child.deleted_at IS NULL
|
||||
)
|
||||
SELECT requested.tenant_id, COUNT(DISTINCT users.id) AS count
|
||||
FROM requested
|
||||
LEFT JOIN descendants
|
||||
ON descendants.root_tenant_id = requested.tenant_id
|
||||
LEFT JOIN users
|
||||
ON users.deleted_at IS NULL
|
||||
AND users.tenant_id::text = descendants.tenant_id
|
||||
GROUP BY requested.tenant_id
|
||||
`, strings.Join(valuePlaceholders, ","))
|
||||
|
||||
type result struct {
|
||||
TenantID string
|
||||
Count int64
|
||||
}
|
||||
var rows []result
|
||||
if err := r.db.WithContext(ctx).Raw(query, args...).Scan(&rows).Error; err != nil {
|
||||
return nil, err
|
||||
}
|
||||
for _, row := range rows {
|
||||
counts[row.TenantID] = row.Count
|
||||
}
|
||||
return counts, nil
|
||||
}
|
||||
|
||||
func (r *userProjectionRepository) ReplaceAllFromKratos(ctx context.Context, users []domain.User) error {
|
||||
now := time.Now()
|
||||
return r.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
|
||||
ids := make([]string, 0, len(users))
|
||||
for i := range users {
|
||||
users[i].DeletedAt = gorm.DeletedAt{}
|
||||
if users[i].CreatedAt.IsZero() {
|
||||
@@ -120,7 +174,6 @@ func (r *userProjectionRepository) ReplaceAllFromKratos(ctx context.Context, use
|
||||
if users[i].UpdatedAt.IsZero() {
|
||||
users[i].UpdatedAt = now
|
||||
}
|
||||
ids = append(ids, users[i].ID)
|
||||
}
|
||||
|
||||
if len(users) > 0 {
|
||||
@@ -138,11 +191,6 @@ func (r *userProjectionRepository) ReplaceAllFromKratos(ctx context.Context, use
|
||||
}).Create(&users).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
if err := tx.Where("id NOT IN ?", ids).Delete(&domain.User{}).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
} else if err := tx.Where("1 = 1").Delete(&domain.User{}).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return upsertUserProjectionState(tx, domain.UserProjectionStatusReady, &now, "")
|
||||
|
||||
Reference in New Issue
Block a user