97 lines
2.7 KiB
C#
97 lines
2.7 KiB
C#
namespace MyOffice.Services.Users;
|
|
|
|
using Domain;
|
|
using Core;
|
|
using Data.Models.Users;
|
|
using Data.Repositories.Users;
|
|
|
|
public class UserService
|
|
{
|
|
private readonly IUserRepository _userRepository;
|
|
private readonly IUserExternalRepository _userExternalRepository;
|
|
private readonly SemaphoreSlim _addExternalLock = new(1, 1);
|
|
|
|
public UserService(
|
|
IUserRepository userRepository,
|
|
IUserExternalRepository userExternalRepository
|
|
)
|
|
{
|
|
_userRepository = userRepository;
|
|
_userExternalRepository = userExternalRepository;
|
|
}
|
|
|
|
public async Task<User?> Get(Guid id)
|
|
{
|
|
return await _userRepository.GetUserAsync(id);
|
|
}
|
|
|
|
public async Task<List<UserExternal>> GetUserExternals(Guid userId)
|
|
{
|
|
return await _userExternalRepository.GetUserExternalsByUserIdAsync(userId);
|
|
}
|
|
|
|
public async Task<UserExternal?> GetUserExternal(Guid userId, string provider)
|
|
{
|
|
return await _userExternalRepository.GetByUserIdAsync(userId, provider);
|
|
}
|
|
|
|
public async Task<Exec<UserExternal>> RemoveUserExternal(
|
|
Guid userId,
|
|
string provider,
|
|
CancellationToken cancellationToken = default)
|
|
{
|
|
var result = new Exec<UserExternal>();
|
|
|
|
var userExternal = await _userExternalRepository.GetByUserIdAsync(userId, provider);
|
|
if (userExternal == null) return result.Set(GeneralExecStatus.not_found);
|
|
|
|
await _userExternalRepository.RemoveUserExternalAsync(userExternal, cancellationToken);
|
|
|
|
return result.Set(userExternal);
|
|
}
|
|
|
|
public async Task<Exec<UserExternal, AddUserExternalStatusEnum>> AddUserExternalAsync(
|
|
Guid userId,
|
|
string provider,
|
|
string externalId,
|
|
string email,
|
|
CancellationToken cancellationToken = default
|
|
)
|
|
{
|
|
var result = new Exec<UserExternal, AddUserExternalStatusEnum>(AddUserExternalStatusEnum.success);
|
|
|
|
var externalLogin = await _userExternalRepository.GetByUserIdAsync(userId, provider);
|
|
|
|
if (externalLogin != null) return result.Set(externalLogin);
|
|
|
|
await _addExternalLock.WaitAsync(cancellationToken);
|
|
try
|
|
{
|
|
externalLogin = await _userExternalRepository.GetByUserIdAsync(userId, provider);
|
|
if (externalLogin != null) return result.Set(externalLogin);
|
|
|
|
externalLogin = await _userExternalRepository.GetByExternalIdAsync(externalId, provider);
|
|
if (externalLogin != null) return result.Set(AddUserExternalStatusEnum.externalid_used);
|
|
|
|
var user = await _userRepository.GetByUserUserNameAsync(email);
|
|
if (user?.Id != userId) return result.Set(AddUserExternalStatusEnum.user_not_valid);
|
|
|
|
externalLogin = new UserExternal
|
|
{
|
|
UserId = userId,
|
|
CreatedOn = DateTime.UtcNow,
|
|
Provider = provider.ToLower(),
|
|
ExternalId = externalId,
|
|
Email = email
|
|
};
|
|
await _userExternalRepository.AddUserExternalAsync(externalLogin, cancellationToken);
|
|
}
|
|
finally
|
|
{
|
|
_addExternalLock.Release();
|
|
}
|
|
|
|
return result;
|
|
}
|
|
}
|