137 lines
4.8 KiB
Go
137 lines
4.8 KiB
Go
package internal
|
|
|
|
import (
|
|
"context"
|
|
|
|
"github.com/tech/sendico/pkg/auth"
|
|
"github.com/tech/sendico/pkg/db/account"
|
|
"github.com/tech/sendico/pkg/db/organization"
|
|
"github.com/tech/sendico/pkg/db/policy"
|
|
"github.com/tech/sendico/pkg/mlogger"
|
|
"github.com/tech/sendico/pkg/mutil/mzap"
|
|
"go.mongodb.org/mongo-driver/bson/primitive"
|
|
"go.uber.org/zap"
|
|
)
|
|
|
|
// AccountManager provides helper methods for account management operations
|
|
type AccountManager struct {
|
|
logger mlogger.Logger
|
|
accountDB account.DB
|
|
orgDB organization.DB
|
|
policyDB policy.DB
|
|
authManager auth.Manager
|
|
}
|
|
|
|
// NewAccountManager creates a new AccountManager instance
|
|
func NewAccountManager(
|
|
logger mlogger.Logger,
|
|
accountDB account.DB,
|
|
orgDB organization.DB,
|
|
policyDB policy.DB,
|
|
authManager auth.Manager,
|
|
) *AccountManager {
|
|
var namedLogger mlogger.Logger
|
|
if logger != nil {
|
|
namedLogger = logger.Named("account_manager")
|
|
}
|
|
return &AccountManager{
|
|
logger: namedLogger,
|
|
accountDB: accountDB,
|
|
orgDB: orgDB,
|
|
policyDB: policyDB,
|
|
authManager: authManager,
|
|
}
|
|
}
|
|
|
|
// DeleteOrganization deletes an organization and all its associated data
|
|
// The caller is responsible for wrapping this in a transaction
|
|
func (m *AccountManager) DeleteOrganization(ctx context.Context, orgRef primitive.ObjectID) error {
|
|
m.logger.Debug("Deleting organization", mzap.ObjRef("org_ref", orgRef))
|
|
|
|
// Delete organization roles
|
|
if err := m.deleteOrganizationRoles(ctx, orgRef); err != nil {
|
|
m.logger.Warn("Failed to delete organization roles", zap.Error(err), mzap.ObjRef("org_ref", orgRef))
|
|
return err
|
|
}
|
|
|
|
// Delete organization policies
|
|
if err := m.deleteOrganizationPolicies(ctx, orgRef); err != nil {
|
|
m.logger.Warn("Failed to delete organization policies", zap.Error(err), mzap.ObjRef("org_ref", orgRef))
|
|
return err
|
|
}
|
|
|
|
// Finally delete the organization itself
|
|
if err := m.orgDB.Delete(ctx, primitive.NilObjectID, orgRef); err != nil {
|
|
m.logger.Warn("Failed to delete organization", zap.Error(err), mzap.ObjRef("org_ref", orgRef))
|
|
return err
|
|
}
|
|
|
|
m.logger.Info("Successfully deleted organization", mzap.ObjRef("org_ref", orgRef))
|
|
return nil
|
|
}
|
|
|
|
// DeleteAccount deletes an account and all its associated data
|
|
// The caller is responsible for wrapping this in a transaction
|
|
func (m *AccountManager) DeleteAccount(ctx context.Context, accountRef primitive.ObjectID) error {
|
|
m.logger.Debug("Deleting account", mzap.ObjRef("account_ref", accountRef))
|
|
|
|
// Delete the account
|
|
if err := m.accountDB.Delete(ctx, accountRef); err != nil {
|
|
m.logger.Warn("Failed to delete account", zap.Error(err), mzap.ObjRef("account_ref", accountRef))
|
|
return err
|
|
}
|
|
|
|
m.logger.Info("Successfully deleted account", mzap.ObjRef("account_ref", accountRef))
|
|
return nil
|
|
}
|
|
|
|
// DeleteAll deletes all data for a given account and organization
|
|
// The caller is responsible for wrapping this in a transaction
|
|
func (m *AccountManager) DeleteAll(ctx context.Context, accountRef, organizationRef primitive.ObjectID) error {
|
|
m.logger.Debug("Deleting all data", mzap.ObjRef("account_ref", accountRef), mzap.ObjRef("organization_ref", organizationRef))
|
|
|
|
// Delete organization first (which will cascade delete all related data)
|
|
if err := m.DeleteOrganization(ctx, organizationRef); err != nil {
|
|
m.logger.Warn("Failed to delete organization", zap.Error(err), mzap.ObjRef("organization_ref", organizationRef))
|
|
return err
|
|
}
|
|
|
|
// Delete account
|
|
if err := m.DeleteAccount(ctx, accountRef); err != nil {
|
|
m.logger.Warn("Failed to delete account", zap.Error(err), mzap.ObjRef("account_ref", accountRef))
|
|
return err
|
|
}
|
|
|
|
m.logger.Info("Successfully deleted all data", mzap.ObjRef("account_ref", accountRef), mzap.ObjRef("organization_ref", organizationRef))
|
|
return nil
|
|
}
|
|
|
|
// deleteOrganizationRoles deletes all roles for an organization
|
|
func (m *AccountManager) deleteOrganizationRoles(ctx context.Context, orgRef primitive.ObjectID) error {
|
|
// Get all roles for the organization
|
|
roles, err := m.authManager.Role().List(ctx, orgRef)
|
|
if err != nil {
|
|
m.logger.Warn("Failed to list organization roles", zap.Error(err), mzap.ObjRef("org_ref", orgRef))
|
|
return err
|
|
}
|
|
|
|
// Delete each role
|
|
for _, role := range roles {
|
|
if err := m.authManager.Role().Delete(ctx, role.ID); err != nil {
|
|
m.logger.Warn("Failed to delete role", zap.Error(err), mzap.ObjRef("role_ref", role.ID), mzap.ObjRef("org_ref", orgRef))
|
|
return err
|
|
}
|
|
}
|
|
|
|
m.logger.Info("Successfully deleted organization roles", zap.Int("count", len(roles)), mzap.ObjRef("org_ref", orgRef))
|
|
return nil
|
|
}
|
|
|
|
// deleteOrganizationPolicies deletes all policies for an organization
|
|
func (m *AccountManager) deleteOrganizationPolicies(_ context.Context, _ primitive.ObjectID) error {
|
|
// Note: PolicyDB is used for both roles and policies, but the interface is unclear
|
|
// This would need to be implemented differently or skipped for now
|
|
m.logger.Warn("Policy deletion not implemented - interface unclear")
|
|
return nil
|
|
}
|