Перейти к содержанию

FuelProcessing - Архитектура проекта

Обзор архитектуры

FuelProcessing — это распределённая система управления топливными картами и транзакциями, построенная по архитектуре N-уровневого приложения (N-Layer Architecture) с использованием Clean Architecture принципов.

┌─────────────────────────────────────────────────────────────────┐
│                        Presentation Layer                        │
├─────────────────────────────────────────────────────────────────┤
│  FuelProcessing.Web  │  FuelProcessing.Api  │ FuelProcessing.   │
│      (MVC UI)        │     (REST API)       │ ClientApi         │
└──────────────────────────┬──────────────────────────────────────┘
┌──────────────────────────▼──────────────────────────────────────┐
│                     Application Layer                            │
├─────────────────────────────────────────────────────────────────┤
│  Controllers  │  Services  │  Validators  │  ViewModels         │
└──────────────────────────┬──────────────────────────────────────┘
┌──────────────────────────▼──────────────────────────────────────┐
│                       Domain Layer                              │
├─────────────────────────────────────────────────────────────────┤
│           FuelProcessing.Core (доменная модель)                 │
│  Entities  │  Enums  │  Interfaces  │  Business Logic           │
└──────────────────────────┬──────────────────────────────────────┘
┌──────────────────────────▼──────────────────────────────────────┐
│                    Infrastructure Layer                         │
├─────────────────────────────────────────────────────────────────┤
│      FuelProcessing.Data (EF Core, Repositories)                │
│  ApiClients (11 ВИНК)  │  DataContext  │  Migrations            │
└─────────────────────────────────────────────────────────────────┘

Структура решения (Solution)

Основные модули

Модуль Тип Описание
FuelProcessing.Core Class Library Доменная модель, бизнес-логика
FuelProcessing.Data Class Library EF Core, репозитории
FuelProcessing.Web Web App MVC интерфейс
FuelProcessing.Api Web API REST API
FuelProcessing.ClientApi Web API Клиентское API
FuelProcessing.TransactionHandler Worker Service Обработка транзакций
FuelProcessing.ReportGenerationHandler Worker Service Генерация отчётов
FuelProcessing.Tests Test Project Тесты

API проекты интеграций

Проект Провайдер
TrackApi Трасса
TatneftApi Татнефть
GazpromApi Газпромнефть
LukoilApi Лукойл
Rosneft.API Роснефть
VezdehodApi Вездеход
NatCarApi НатКар
InforkomApi Инфорком
SoftEngineeringApi АСМАП
TaifNKApi ТаифНК
Globaltruck.API Газпромнефть_gpn

Паттерны проектирования

1. Repository Pattern

Цель: Абстракция доступа к данным.

// Базовый репозиторий
public class BaseRepository<T> where T : Entity
{
    protected readonly DataContext Context;
    protected readonly IMapper Mapper;

    public virtual T Get(int id) => ...;
    public virtual IEnumerable<T> GetAll() => ...;
    public virtual void Add(T entity) => ...;
    public virtual void Update(T entity) => ...;
    public virtual void Delete(T entity) => ...;
}

// Специализированные репозитории
public class CardRepository : BaseRepository<Card> { ... }
public class CompanyRepository : BaseRepository<Company> { ... }
// ... 17 more repositories

Расположение: FuelProcessing.Data/Repository/


2. Service Layer Pattern

Цель: Инкапсуляция бизнес-логики и координация операций.

Services/
├── ApiClients/          # API клиенты для ВИНК
│   ├── Common/          # Общие интерфейсы (IApiService, ApiExecutor)
│   └── [VinkName]/      # Специфичные реализации
├── Billing/             # Сервис балансов
├── Card/                # Сервис карт
├── Company/             # Сервис компаний
├── Contract/            # Сервис контрактов
├── GasStation/          # Сервис АЗС
└── ...

3. Dependency Injection (DI)

Цель: Внедрение зависимостей для слабой связности.

Регистрация сервисов в Startup.cs каждого проекта:

// Scoped (один экземпляр на запрос)
services.AddScoped<ILoggingService, LoggingService>();
services.AddScoped<ICardService, CardService>();

// Singleton (один экземпляр на приложение)
services.AddSingleton<ISettingsService, SettingsService>();

// Transient (новый экземпляр каждый раз)
services.AddTransient<IMapper>(sp => new MapperConfiguration(...).CreateMapper());

4. Factory Pattern

Цель: Создание объектов без указания точных классов.

// ApiExecutor как Factory для API клиентов
public class ApiExecutor
{
    public IApiService ApiService(VinkType vinkType)
    {
        return vinkType switch
        {
            VinkType.Трасса => new TrackApiService(...),
            VinkType.Татнефть => new TatneftApiService(...),
            VinkType.Газпромнефть => new GazpromApiService(...),
            // ...
        };
    }
}

5. Strategy Pattern

Цель: Выбор алгоритма во время выполнения.

// Разные стратегии для разных ВИНК
public interface IApiService
{
    List<Card> GetCards(int contractId);
    void GetTransactions();
    void GetBalance();
    // ...
}

// Каждая реализация (Strategy) знает, как работать с конкретным ВИНКом
public class TrackApiService : IApiService { ... }
public class TatneftApiService : IApiServiceNight { ... }

6. Unit of Work Pattern

Цель: Группировка операций как единая транзакция.

// DataContext выступает как Unit of Work
public class DataContext : DbContext
{
    // SaveChanges() атомарно сохраняет все изменения
    public override int SaveChanges()
    {
        // Аудит, мягкое удаление, timestamp
        return base.SaveChanges();
    }
}

7. Specification Pattern (частично)

Цель: Инкапсуляция запросов.

// ViewModel как спецификации для чтения
public class FilterDesirializeModel
{
    public string Filter { get; set; }  // JSON фильтр от Telerik UI
    public int? CompanyId { get; set; }
    public DateTime? DateFrom { get; set; }
    public DateTime? DateTo { get; set; }
    // ...
}

8. Observer Pattern (через MassTransit/RabbitMQ)

Цель: Асинхронная обработка событий.

// Публикация события генерации отчёта
public class ReportPublisher
{
    public async Task PublishReportRequest(ReportData data)
    {
        await _endpoint.Publish(data);
    }
}

// Обработка готового отчёта
public class ReportAnswerConsumer : IConsumer<ReportAnswer>
{
    public async Task Consume(ConsumeContext<ReportAnswer> context)
    {
        // Обработка готового отчёта
    }
}

Внешние интеграции

Архитектура API клиентов

                    ┌─────────────────┐
                    │   ApiExecutor   │
                    │  (координатор)   │
                    └────────┬────────┘
                ┌────────────┼────────────┐
                │            │            │
        ┌───────▼──────┐ ┌──▼────────┐ ┌▼──────────┐
        │ TrackApi     │ │ TatneftApi│ │GazpromApi │
        │ Service      │ │ Service   │ │ Service   │
        └──────────────┘ └───────────┘ └───────────┘
                │            │            │
        ┌───────▼──────┐ ┌──▼────────┐ ┌▼──────────┐
        │  TrackApi/   │ │TatneftApi/│ │GazpromApi/│
        │  (проект)    │ │ (проект)  │ │ (проект)  │
        └──────────────┘ └───────────┘ └───────────┘

Общий интерфейс

public interface IApiService
{
    bool IsTest { get; set; }
    void InitRestClient(DirectContractWithVendor settings, bool isTest = false);
    List<Card> GetCards(int directContractWithVendorId);
    void GetTransactions();
    void GetGasStations();
    GasStationsForReport GetGasStationForReport();
    void GetBalance();
    List<SimpleRepeatItem> AddLimitsToCards(List<Limit> limit);
    void RestoreLimits(List<LimitVinkHistory> model);
    void BlockCard(CardBlockRepeat cardInfo);
    RepeatResultAnswer RepeatBlockCard(CardBlockRepeat cardInfo);
    IEnumerable<ApiLimitInfo> GetLimits(string cardNumber);
    IEnumerable<FinanceTransaction> GetFinanceTransactionsByMounth(DirectContractWithVendor settings);
}

public interface IApiServiceNight : IApiService
{
    void GetTransactionsByDay();  // Ночная синхронизация
}

Безопасность

Авторизация и права доступа

User → Role → SiteModule → RoleRights (Edit, View, Delete)

Роли: - Admin — полный доступ - SuperUser — управление компанией - Manager — ограниченный доступ - CarDriver — только просмотр

Механизм: 1. RoleRightService.HasRights() — проверка прав 2. AuthorizeRoleFilter — фильтр на контроллерах 3. SiteModule — enum модулей (60+ значений)


Конфигурация и Startup

Общий pipeline (все ASP.NET Core проекты)

1. CreateHostBuilder()
2. ConfigureServices()
   - База данных (PostgreSQL)
   - Identity
   - AutoMapper
   - FluentValidation
   - MassTransit/RabbitMQ (Web, Api, ReportHandler)
   - Kendo UI (Web)
3. Configure()
   - Middleware pipeline
   - Authentication/Authorization
   - Endpoints
4. Run()

База данных

Технологии

  • ORM: Entity Framework Core
  • СУБД: PostgreSQL
  • Миграции: Code First Migrations

DataContext

public class DataContext : DbContext
{
    // 80+ DbSets
    public DbSet<Card> Cards { get; set; }
    public DbSet<Company> Companies { get; set; }
    public DbSet<DirectContract> DirectContracts { get; set; }
    public DbSet<FinanceTransaction> FinanceTransactions { get; set; }
    public DbSet<GasStation> GasStations { get; set; }
    public DbSet<Limit> Limits { get; set; }
    public DbSet<User> Users { get; set; }
    // ... и еще 70+ DbSets
}

Асинхронная обработка

RabbitMQ + MassTransit

                    ┌──────────────┐
                    │ ReportPublisher│
                    └───────┬──────┘
                    ┌───────▼──────────┐
                    │    RabbitMQ      │
                    │   (очередь)      │
                    └───────┬──────────┘
                    ┌───────▼──────────────┐
                    │ReportGenerationHandler│
                    │ (консьюмер)          │
                    └──────────────────────┘

Используется в: - FuelProcessing.Web — публикация задач генерации - FuelProcessing.ReportGenerationHandler — обработка и создание отчётов


Мониторинг и логирование

Логирование

  • LoggingService — сервис логирования действий пользователя
  • LogUserAction — сущность для записи действий
  • ApiMonitoring — мониторинг синхронизации с ВИНК

Health Checks

  • FuelProcessing.TransactionHandler — фоновые health check jobs
  • Docker health checks для всех сервисов

Развёртывание

Docker

Каждый модуль имеет Dockerfile: - Dockerfile — production - DockerfileTest — тестовое окружение - Некоторые имеют DockerfileDevelop

CI/CD

.gitlab-ci.yml — автоматизация сборки и деплоя


Расширение системы

Добавление нового модуля

  1. Доменная модель — добавить в FuelProcessing.Core
  2. Репозиторий — создать в FuelProcessing.Data
  3. Сервис — создать в соответствующем модуле
  4. Контроллер — создать в FuelProcessing.Web или FuelProcessing.Api
  5. Права доступа — добавить в SiteModule, настроить в RoleConstructor

Добавление новой интеграции ВИНК

  1. Создать API проект (например NewVinkApi)
  2. Реализовать IApiService или IApiServiceNight
  3. Добавить VinkType в enum
  4. Зарегистрировать в ApiExecutor
  5. Настроить модель DirectContractWithVendor

Документация создана: 2026-01-05 Задача: fuel-780