Упражнение №3 - LINQ, колекции и хелпър функции | Програмни Среди
Прескочи до съдържанието
Упражнение №3 - LINQ, колекции и хелпър функции
Published:

Упражнение №3 - LINQ, колекции и хелпър функции

Table of contents

Open Table of contents

Въведение

Цел на упражнението

Запознаване с работа с колекции, заявки с LINQ и Helper функции.

Задачите в упражнението изграждат:

  • Малка студентска информационна система

В това упражнение:

  • Създаване на колекция UserData
  • Имплементиране на методи за работа с колекцията
  • Използване на хелпър функции

Очакван резултат

Ще създадем възможност за потребител да влезе в системата с потребителско име и парола, след което ще визуализираме данните му.

Задачи за домашна работа

  1. Създаване на логър, който да записва във файл всеки успешен вход.
  2. Създаване на логър, който да записва всеки неуспешен опит за вход, със съответната грешка.

Важни концепции

  • LINQ
  • Collections
  • Lists
  • Helpers

Зареждане на проект в Visual Studio

  1. Отворете Visual Studio 2022.
  2. Заредете Solution-а от предишното упражнение.

Допълване на проект Welcome

Добавяне на полета в User

  1. Добавете следните частни променливи и публични свойства:
  • private int id;
  • public int Id { get; set; }
  • private DateTime expires;
  • public DateTime Expires { get; set; }

Разширяване на проекта WelcomeExtended

Създаване на папка Data

  1. Десен бутон върху WelcomeExtendedAddNew FolderData

Създаване на клас UserData

  1. Десен бутон върху DataAddNew Item…ClassUserData.cs
  2. Добавете следните полета:
private List<User> _users;
private int _nextId;
  1. Създайте конструктор:
public UserData()
{
    _nextId = 0;
    _users = new List<User>();
}
  1. Методи за работа с UserData:
public void AddUser(User user)
{
    user.Id = _nextId++;
    _users.Add(user);
}

public void DeleteUser(User user)
{
    _users.Remove(user);
}
  1. Методи с LINQ:
public User GetUser(string username, string password)
{
    return _users.FirstOrDefault(u => u.Username == username && u.Password == password);
}

public void SetActive(string username, DateTime expires)
{
    var user = _users.FirstOrDefault(u => u.Username == username);
    if (user != null)
        user.Expires = expires;
}

public void AssignUserRole(string username, UserRole role)
{
    var user = _users.FirstOrDefault(u => u.Username == username);
    if (user != null)
        user.Role = role;
}

Създаване на UserHelper

  1. В папка HelpersAddNew Item…ClassUserHelper.cs
  2. Направете класа static и добавете метод ToString като extension метод:
public static class UserHelper
{
    public static string ToString(this User user)
    {
        return $"ID: {user.Id}, Name: {user.Username}, Role: {user.Role}, Expires: {user.Expires}";
    }
}
  1. Добавете два нови хелпър метода за UserData:
public static class UserDataHelper
{
    public static void ValidateCredentials(this UserData data, string name, string password)
    {
        if (string.IsNullOrEmpty(name))
            throw new Exception("The name cannot be empty");
        if (string.IsNullOrEmpty(password))
            throw new Exception("The password cannot be empty");
    }

    public static User GetUser(this UserData data, string name, string password)
    {
        return data.GetUser(name, password);
    }
}

Навързване на кода

Добавяне на логика за вход в Program.cs

UserData users = new UserData();
users.AddUser(new User { Username = "Student1", Password = "123", Role = UserRole.Student });
users.AddUser(new User { Username = "Student2", Password = "123", Role = UserRole.Student });
users.AddUser(new User { Username = "Teacher", Password = "1234", Role = UserRole.Professor });
users.AddUser(new User { Username = "Admin", Password = "12345", Role = UserRole.Administrator });

Console.Write("Enter username: ");
string username = Console.ReadLine();
Console.Write("Enter password: ");
string password = Console.ReadLine();

try
{
    users.ValidateCredentials(username, password);
    User loggedInUser = users.GetUser(username, password);
    if (loggedInUser == null)
        throw new Exception("Потребителят не е намерен");

    Console.WriteLine("Успешен вход!");
    Console.WriteLine(loggedInUser.ToString());
}
catch (Exception ex)
{
    Console.WriteLine("Грешка: " + ex.Message);
}

Добавяне на събития и делегати

Създаване на клас за събития

  1. В папка HelpersAddNew Item…ClassLoginEventArgs.cs
  2. Създайте класа:
// Дефиниране на event аргументи за събитието "ColorChanged"
public class LoginEventArgs : EventArgs
{
    public string Username { get; set; }
    public UserRole Role { get; set; }
}

Създаване на клас Logger

  1. В папка HelpersAddNew Item…ClassEventLogger.cs
  2. Създайте класа:
public class EventLogger
{
    public event EventHandler<LoginEventArgs> LoginSuccessful;
    public void LogLogin(User user)
    {
        Console.WriteLine($"Успешен вход на потребител: {user.Username}");
        LoginSuccessful?.Invoke(this, new LoginEventArgs { Username = user.Username, Role = user.Role });
    }
}

Създаване на клас ActivityMonitor

  1. В папка HelpersAddNew Item…ClassActivityMonitor.cs
  2. Създайте класа:
public class ActivityMonitor
{
    public void OnLoginSuccessful(object sender, LoginEventArgs e)
    {
        Console.WriteLine($"Активност: {e.Username} влезе в системата. {GetRoleAction(e.Role)}");
    }

    private string GetRoleAction(UserRole role)
    {
        switch (role)
        {
            case UserRole.Administrator:
                return "Предоставен пълен достъп.";
            case UserRole.Professor:
                return "Предоставен достъп до оценяване.";
            case UserRole.Student:
                return "Предоставен достъп до курсове.";
            default:
                return "Предоставен ограничен достъп.";
        }
    }
}

Обновен Main метод в Program класа

class Program
{
    static void Main(string[] args)
    {
        UserData users = new UserData();
        EventLogger logger = new ();
        ActivityMonitor monitor = new ();
        
        // Прикачане на метода който ще се изпълнява при успешен вход
        logger.LoginSuccessful += monitor.OnLoginSuccessful;
        
        // Добавяне на потребители
        // ...

        // Въвеждане на потребителско име и парола
        // ...

        try
        {
            
            // Вашият код тук
            
            // Извикване на логването при успешен вход
            logger.LogLogin(loggedInUser);
        }
        catch (Exception ex)
        {
            // Вашият код тук
        }
    }
}

Обяснение на кода

  1. LoginEventArgs
  • Наследява EventArgs
  • Съдържа свойства Username и Role за информация за влезлия потребител
  1. Logger
  • Дефинира събитие LoginSuccessful
  • Метод LogLogin който задейства събитието при успешен вход
  1. ActivityMonitor
  • Метод OnLoginSuccessful който реагира на събитието за успешен вход
  • Помощен метод GetRoleAction за определяне на достъпа според ролята
  1. Program
  • Създава инстанции на UserData, Logger и ActivityMonitor
  • Свързва обработчика на събитието
  • Демонстрира работата чрез опит за вход в системата

Изпълнение

При успешен вход в системата ще видите:

Enter username: Admin
Enter password: 12345
Успешен вход!
ID: 3, Name: Admin, Role: Administrator, Expires: 01/01/0001 00:00:00
Успешен вход на потребител: Admin
Активност: Admin влезе в системата. Предоставен пълен достъп.

Заключение

След изпълнението на тези стъпки ще имаме конзолно приложение, което работи с LINQ, списъци, хелпър функции и система за вход с потребителско име и парола.

Бележка: В следващи упражнения ще се добави файлова логика и по-добро управление на потребителските данни.