presence/Presence.Desktop/ViewModels/GroupViewModel.cs

259 lines
8.7 KiB
C#
Raw Normal View History

2024-12-05 08:26:58 +00:00
using Presence.Desktop.Models;
using ReactiveUI;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Reactive;
using System.Reactive.Linq;
2025-04-30 01:13:44 +00:00
using System.Threading.Tasks;
2024-12-05 08:26:58 +00:00
using Avalonia.Controls;
using System.IO;
2025-04-30 01:13:44 +00:00
using presence_client.ApiClients.Interfaces;
2024-12-05 08:26:58 +00:00
using Demo.Domain.Models;
2025-04-30 01:13:44 +00:00
using Microsoft.Extensions.DependencyInjection;
using Presence.Desktop.DI;
2024-12-05 08:26:58 +00:00
namespace Presence.Desktop.ViewModels
{
public class GroupViewModel : ViewModelBase, IRoutableViewModel
{
2025-04-30 01:13:44 +00:00
private readonly IGroupApiClient _groupApiClient;
private readonly IUserApiClient _userApiClient;
private readonly List<GroupPresenter> _groupPresentersDataSource = new();
2024-12-05 08:26:58 +00:00
private ObservableCollection<GroupPresenter> _groups;
2025-04-30 01:13:44 +00:00
private ObservableCollection<UserPresenter> _users;
private string? _newFIO;
2024-12-05 08:26:58 +00:00
private GroupPresenter? _selectedGroupItem;
2025-04-30 01:13:44 +00:00
private UserPresenter? _selectedUser;
2024-12-22 16:52:52 +00:00
private string? _selectedSecondItem;
2025-04-30 01:13:44 +00:00
public ObservableCollection<GroupPresenter> Groups => _groups;
public ObservableCollection<UserPresenter> Users => _users;
public ObservableCollection<string> SecondComboBoxItems { get; } =
new ObservableCollection<string> { "no sort", "name sort", "name sort rev" };
2024-12-22 16:52:52 +00:00
2025-04-30 01:13:44 +00:00
public GroupPresenter? SelectedGroupItem
2024-12-22 16:52:52 +00:00
{
2025-04-30 01:13:44 +00:00
get => _selectedGroupItem;
set => this.RaiseAndSetIfChanged(ref _selectedGroupItem, value);
2024-12-22 16:52:52 +00:00
}
public UserPresenter? SelectedUser
{
get => _selectedUser;
set => this.RaiseAndSetIfChanged(ref _selectedUser, value);
}
2025-04-30 01:13:44 +00:00
public string? SelectedSecondItem
{
get => _selectedSecondItem;
set => this.RaiseAndSetIfChanged(ref _selectedSecondItem, value);
}
2024-12-22 16:52:52 +00:00
public string? NewFIO
{
get => _newFIO;
set => this.RaiseAndSetIfChanged(ref _newFIO, value);
}
2025-04-30 01:13:44 +00:00
public ReactiveCommand<Unit, Unit> DeleteUsersByGroupCommand { get; }
public ReactiveCommand<Unit, Unit> ImportStudentsCommand { get; }
2024-12-22 16:52:52 +00:00
public ReactiveCommand<UserPresenter, Unit> DeleteUserCommand { get; }
public ReactiveCommand<UserPresenter, Unit> UpdateUserFIOCommand { get; }
2025-04-30 01:13:44 +00:00
public ReactiveCommand<Unit, Unit> GoBackCommand { get; }
2024-12-05 08:26:58 +00:00
2025-04-30 01:13:44 +00:00
public GroupViewModel(IGroupApiClient groupApiClient, IUserApiClient userApiClient, IScreen hostScreen)
2024-12-05 08:26:58 +00:00
{
2025-04-30 01:13:44 +00:00
_groupApiClient = groupApiClient;
_userApiClient = userApiClient;
_groups = new ObservableCollection<GroupPresenter>();
2024-12-05 08:26:58 +00:00
_users = new ObservableCollection<UserPresenter>();
2025-04-30 01:13:44 +00:00
DeleteUsersByGroupCommand = ReactiveCommand.CreateFromTask(DeleteUsersByGroupAsync);
ImportStudentsCommand = ReactiveCommand.CreateFromTask(ImportStudentsAsync);
DeleteUserCommand = ReactiveCommand.CreateFromTask<UserPresenter>(DeleteUserAsync);
UpdateUserFIOCommand = ReactiveCommand.CreateFromTask<UserPresenter>(UpdateUserFIOAsync);
HostScreen = hostScreen;
GoBackCommand = ReactiveCommand.Create(() =>
{
HostScreen.Router.Navigate.Execute(new StartViewModel(HostScreen));
});
SelectedSecondItem = SecondComboBoxItems.First();
2024-12-05 08:26:58 +00:00
this.WhenAnyValue(vm => vm.SelectedGroupItem)
2025-04-30 01:13:44 +00:00
.WhereNotNull()
.Subscribe(_ => SetUsers());
2024-12-22 16:52:52 +00:00
this.WhenAnyValue(vm => vm.SelectedSecondItem)
2025-04-30 01:13:44 +00:00
.WhereNotNull()
2024-12-05 08:26:58 +00:00
.Subscribe(_ => SetUsers());
2025-04-30 01:13:44 +00:00
LoadDataAsync().ConfigureAwait(false);
}
2024-12-05 08:26:58 +00:00
2025-04-30 01:13:44 +00:00
private async Task LoadDataAsync()
{
await RefreshGroupsAsync();
2024-12-22 16:52:52 +00:00
}
2025-04-30 01:13:44 +00:00
private async Task RefreshGroupsAsync()
2024-12-22 16:52:52 +00:00
{
2025-04-30 01:13:44 +00:00
var groupsFromApi = await _groupApiClient.GetGroupsWithUsersAsync();
2024-12-22 16:52:52 +00:00
_groupPresentersDataSource.Clear();
2025-04-30 01:13:44 +00:00
foreach (var group in groupsFromApi)
2024-12-05 08:26:58 +00:00
{
2024-12-22 16:52:52 +00:00
var groupPresenter = new GroupPresenter
2024-12-05 08:26:58 +00:00
{
2024-12-22 16:52:52 +00:00
Id = group.ID,
Name = group.Name,
users = group.Users?.Select(user => new UserPresenter
2024-12-05 08:26:58 +00:00
{
2024-12-22 16:52:52 +00:00
Name = user.FIO,
Guid = user.Guid,
Group = new GroupPresenter { Id = group.ID, Name = group.Name }
2025-04-30 01:13:44 +00:00
}).ToList() ?? new List<UserPresenter>()
2024-12-05 08:26:58 +00:00
};
2024-12-22 16:52:52 +00:00
_groupPresentersDataSource.Add(groupPresenter);
}
2024-12-05 08:26:58 +00:00
2024-12-22 16:52:52 +00:00
_groups = new ObservableCollection<GroupPresenter>(_groupPresentersDataSource);
2025-04-30 01:13:44 +00:00
this.RaisePropertyChanged(nameof(Groups));
if (_groups.Any())
{
SelectedGroupItem = _groups.First();
}
}
private void SetUsers()
{
Users.Clear();
if (SelectedGroupItem == null)
{
this.RaisePropertyChanged(nameof(Users));
return;
}
var group = _groupPresentersDataSource.FirstOrDefault(it => it.Id == SelectedGroupItem.Id);
if (group?.users == null)
{
this.RaisePropertyChanged(nameof(Users));
return;
}
var sortedUsers = SelectedSecondItem switch
{
"name sort" => group.users.OrderBy(user => user.Name),
"name sort rev" => group.users.OrderByDescending(user => user.Name),
_ => group.users
};
foreach (var user in sortedUsers)
{
Users.Add(user);
}
this.RaisePropertyChanged(nameof(Users));
2024-12-05 08:26:58 +00:00
}
2025-04-30 01:13:44 +00:00
private async Task ImportStudentsAsync()
2024-12-05 08:26:58 +00:00
{
2024-12-22 16:52:52 +00:00
if (SelectedGroupItem == null || SelectedGroupItem.Id == null) return;
2024-12-05 08:26:58 +00:00
2024-12-22 16:52:52 +00:00
var openFileDialog = new OpenFileDialog
2024-12-05 08:26:58 +00:00
{
2024-12-22 16:52:52 +00:00
Filters = new List<FileDialogFilter>
2024-12-05 08:26:58 +00:00
{
2025-04-30 01:13:44 +00:00
new() { Name = "CSV Files", Extensions = { "csv" } }
2024-12-22 16:52:52 +00:00
},
AllowMultiple = false
};
2024-12-05 08:26:58 +00:00
2024-12-22 16:52:52 +00:00
var result = await openFileDialog.ShowAsync(new Window());
if (result?.Length > 0)
{
var filePath = result[0];
var lines = File.ReadAllLines(filePath);
2025-04-30 01:13:44 +00:00
var createdUsers = new List<ImportStudents>();
2024-12-05 08:26:58 +00:00
2024-12-22 16:52:52 +00:00
foreach (var line in lines.Skip(1))
2024-12-05 08:26:58 +00:00
{
2025-04-30 01:13:44 +00:00
var columns = line.Split(';');
if (columns.Length < 2) continue;
2024-12-22 16:52:52 +00:00
var fio = columns[0];
2025-04-30 01:13:44 +00:00
var groupName = columns[1];
var newUser = new ImportStudents
2024-12-05 08:26:58 +00:00
{
2025-04-30 01:13:44 +00:00
fio = fio,
groupName = groupName
2024-12-05 08:26:58 +00:00
};
2025-04-30 01:13:44 +00:00
createdUsers.Add(newUser);
}
2024-12-22 16:52:52 +00:00
2025-04-30 01:13:44 +00:00
foreach (var user in createdUsers)
{
var success = await _userApiClient.CreateUser(user.fio, user.groupName);
if (!success)
2024-12-22 16:52:52 +00:00
{
2025-04-30 01:13:44 +00:00
return;
2024-12-22 16:52:52 +00:00
}
2024-12-05 08:26:58 +00:00
}
2025-04-30 01:13:44 +00:00
await RefreshGroupsAsync();
2024-12-05 08:26:58 +00:00
}
}
2025-04-30 01:13:44 +00:00
private async Task DeleteUsersByGroupAsync()
2024-12-05 08:26:58 +00:00
{
2024-12-22 16:52:52 +00:00
if (SelectedGroupItem == null) return;
2025-04-30 01:13:44 +00:00
var groupId = SelectedGroupItem.Id;
var success = await _userApiClient.DeleteUsersByGroupIdAsync(groupId);
if (success)
2024-12-22 16:52:52 +00:00
{
2025-04-30 01:13:44 +00:00
await RefreshGroupsAsync();
2024-12-22 16:52:52 +00:00
}
}
2025-04-30 01:13:44 +00:00
private async Task DeleteUserAsync(UserPresenter user)
{
2024-12-22 16:52:52 +00:00
if (user == null) return;
2025-04-30 01:13:44 +00:00
var success = await _userApiClient.DeleteUserAsync(user.Guid);
if (success)
{
await RefreshGroupsAsync();
2024-12-22 16:52:52 +00:00
}
}
2025-04-30 01:13:44 +00:00
private async Task UpdateUserFIOAsync(UserPresenter user)
2024-12-22 16:52:52 +00:00
{
2025-04-30 01:13:44 +00:00
if (user == null || string.IsNullOrWhiteSpace(NewFIO))
2024-12-22 16:52:52 +00:00
{
2025-04-30 01:13:44 +00:00
return;
}
2024-12-22 16:52:52 +00:00
2025-04-30 01:13:44 +00:00
var success = await _userApiClient.UpdateUserFioAsync(user.Guid, NewFIO);
if (success)
2024-12-05 08:26:58 +00:00
{
2025-04-30 01:13:44 +00:00
user.Name = NewFIO;
2024-12-22 16:52:52 +00:00
NewFIO = string.Empty;
2025-04-30 01:13:44 +00:00
this.RaisePropertyChanged(nameof(Users));
await RefreshGroupsAsync();
2024-12-05 08:26:58 +00:00
}
}
public string? UrlPathSegment { get; }
public IScreen HostScreen { get; }
}
}