Compare commits

...

9 Commits

Author SHA1 Message Date
Никита Шипилов
2cde8b4735 Правки 2024-12-08 21:00:44 +04:00
Никита Шипилов
dcaac2153e Лабораторная работа №4 Шаг 2/2 2024-12-08 20:39:47 +04:00
Никита Шипилов
1e3874d74c Лабораторная работа №4 Шаг 1/2 2024-12-08 20:07:10 +04:00
Никита Шипилов
bb3bb40a8d Правки 2024-11-25 02:16:25 +04:00
Никита Шипилов
a5f42d9b6b Удаление лишнего свойства 2024-11-24 23:32:29 +04:00
Никита Шипилов
c00314291d Лабораторная работа №3 2024-11-24 23:27:20 +04:00
Никита Шипилов
4ebe950696 Правка логики удаления при М:М 2024-11-09 21:09:38 +04:00
Никита Шипилов
1bf1efbe5a Лабораторная работа №2 2024-11-08 18:03:17 +04:00
Никита Шипилов
dc7df9998a Лабораторная работа №1 2024-10-28 01:34:50 +04:00
91 changed files with 21523 additions and 75 deletions

View File

@ -0,0 +1,20 @@
using ProjectGasStation.Entities.Enums;
using System.ComponentModel;
namespace ProjectGasStation.Entities;
public class Contractor
{
public int Id { get; private set; }
[DisplayName("Название")]
public string Name { get; private set; } = string.Empty;
[DisplayName("Поставляемое топливо")]
public ContractorFuelType Types { get; private set; }
public static Contractor CreateContractor(int id, string name, ContractorFuelType types)
{
return new Contractor { Id = id, Name = name, Types = types };
}
}

View File

@ -0,0 +1,39 @@
using ProjectGasStation.Entities.Enums;
using System.ComponentModel;
namespace ProjectGasStation.Entities;
public class ContractorFuel
{
public int Id { get; private set; }
[Browsable(false)]
public int ContractorId { get; private set; }
[DisplayName("Поставщик")]
public string ContractorName { get; private set; } = string.Empty;
[DisplayName("Дата поставки")]
public DateTime Date { get; private set; }
[DisplayName("Топливо")]
public string Fuel => ContractorFuelFuel != null ?
string.Join(", ", ContractorFuelFuel.Select(x => $"{(FuelType)x.FuelName} {x.Quantity}")) :
string.Empty;
[Browsable(false)]
public IEnumerable<ContractorFuelFuel> ContractorFuelFuel { get; private set; } = [];
public static ContractorFuel CreateContractorFuel(int id, int contractorId, DateTime date, IEnumerable<ContractorFuelFuel> contractorFuelFuel)
{
return new ContractorFuel { Id = id, ContractorId = contractorId, Date = date, ContractorFuelFuel = contractorFuelFuel};
}
public void SetContractorFuelFuel(IEnumerable<ContractorFuelFuel> contractorFuelFuel)
{
if (contractorFuelFuel != null && contractorFuelFuel.Any())
{
ContractorFuelFuel = contractorFuelFuel;
}
}
}

View File

@ -0,0 +1,17 @@
namespace ProjectGasStation.Entities;
public class ContractorFuelFuel
{
public int Id { get; private set; }
public int FuelId { get; private set; }
public int FuelName { get; private set; }
public int Quantity { get; private set; }
public static ContractorFuelFuel CreateContractorFuelFuel(int id, int fuelId, int quantity)
{
return new ContractorFuelFuel { Id = id, FuelId = fuelId, Quantity = quantity };
}
}

View File

@ -0,0 +1,11 @@
namespace ProjectGasStation.Entities.Enums;
[Flags]
public enum ContractorFuelType
{
None = 0,
GasolineAI92 = 1,
GasolineAI95 = 2,
Diesel = 4,
MotorOIL = 8,
}

View File

@ -0,0 +1,10 @@
namespace ProjectGasStation.Entities.Enums;
public enum FuelType
{
None,
GasolineAI92,
GasolineAI95,
Diesel,
MotorOIL,
}

View File

@ -0,0 +1,8 @@
namespace ProjectGasStation.Entities.Enums;
public enum ShiftType
{
None,
Day,
Night
}

View File

@ -0,0 +1,20 @@
using ProjectGasStation.Entities.Enums;
using System.ComponentModel;
namespace ProjectGasStation.Entities;
public class Fuel
{
public int Id { get; private set; }
[DisplayName("Тип топлива")]
public FuelType Type { get; private set; }
[DisplayName("Цена")]
public double Price { get; private set; }
public static Fuel CreateFuel(int id, FuelType type, double price)
{
return new Fuel { Id = id, Type = type, Price = price };
}
}

View File

@ -0,0 +1,17 @@
namespace ProjectGasStation.Entities;
public class FuelFuelSale
{
public int Id { get; private set; }
public int FuelId { get; private set; }
public int FuelName { get; private set; }
public int Quantity { get; private set; }
public static FuelFuelSale CreateFuelFuelSale(int id, int fuelId, int quantity)
{
return new FuelFuelSale { Id = id, FuelId = fuelId, Quantity = quantity};
}
}

View File

@ -0,0 +1,55 @@
using ProjectGasStation.Entities.Enums;
using System.ComponentModel;
namespace ProjectGasStation.Entities;
public class FuelSale
{
public int Id { get; private set; }
[Browsable(false)]
public int SalespersonId { get; private set; }
[Browsable(false)]
public int ShiftId { get; private set; }
[DisplayName("Продавец")]
public string SalespersonName { get; private set; } = string.Empty;
[Browsable(false)]
public int TypeShift { get; private set; }
[DisplayName("Смена")]
public string ShiftName => $"{SaleDate.Date.ToString("dd.MM.yyyy")} {(ShiftType)TypeShift}";
[Browsable(false)]
public DateTime SaleDate { get; private set; }
[DisplayName("Топливо")]
public string Fuel => FuelFuelSale != null ?
string.Join(", ", FuelFuelSale.Select(x => $"{(FuelType)x.FuelName} {x.Quantity}")) :
string.Empty;
[Browsable(false)]
public IEnumerable<FuelFuelSale> FuelFuelSale { get; private set; } = [];
public static FuelSale CreateFuelSale(int id, int salesPersonId, int shiftId, DateTime saleDate, IEnumerable<FuelFuelSale> fuelFuelSale)
{
return new FuelSale
{
Id = id,
SalespersonId = salesPersonId,
ShiftId = shiftId,
SaleDate = saleDate,
FuelFuelSale = fuelFuelSale
};
}
public void SetFuelFuelSale(IEnumerable<FuelFuelSale> fuelFuelSale)
{
if(fuelFuelSale != null && fuelFuelSale.Any())
{
FuelFuelSale = fuelFuelSale;
}
}
}

View File

@ -0,0 +1,19 @@
using System.ComponentModel;
namespace ProjectGasStation.Entities;
public class Salesperson
{
public int Id { get; private set; }
[DisplayName("Имя")]
public string FirstName { get; private set; } = string.Empty;
[DisplayName("Фамилия")]
public string LastName { get; private set; } = string.Empty;
public static Salesperson CreateSalesperson(int id, string firstName, string lastName)
{
return new Salesperson { Id = id, FirstName = firstName, LastName = lastName };
}
}

View File

@ -0,0 +1,28 @@
using ProjectGasStation.Entities.Enums;
using System.ComponentModel;
namespace ProjectGasStation.Entities;
public class Shift
{
public int Id { get; private set; }
[DisplayName("Время начала")]
public TimeSpan StartTime { get; private set; }
[DisplayName("Время конца")]
public TimeSpan EndTime { get; private set; }
[DisplayName("Дата")]
public DateTime Date { get; private set; }
[DisplayName("Тип смены")]
public ShiftType Type { get; private set; }
public string DisplayName => $"{Date:yyyy-MM-dd} ({Type})";
public static Shift CreateShift(int id, TimeSpan startTime, TimeSpan endTime, DateTime date, ShiftType type)
{
return new Shift { Id = id, EndTime = endTime, StartTime = startTime, Date = date, Type = type };
}
}

View File

@ -1,39 +0,0 @@
namespace ProjectGasStation
{
partial class Form1
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
this.components = new System.ComponentModel.Container();
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(800, 450);
this.Text = "Form1";
}
#endregion
}
}

View File

@ -1,10 +0,0 @@
namespace ProjectGasStation
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
}
}

View File

@ -0,0 +1,178 @@
namespace ProjectGasStation
{
partial class FormGasStation
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(FormGasStation));
menuStrip1 = new MenuStrip();
справочникиToolStripMenuItem = new ToolStripMenuItem();
toolStripMenuItemSalepersons = new ToolStripMenuItem();
toolStripMenuItemShifts = new ToolStripMenuItem();
toolStripMenuItemContractors = new ToolStripMenuItem();
toolStripMenuItemFuels = new ToolStripMenuItem();
toolStripMenuItem2 = new ToolStripMenuItem();
toolStripMenuItemFuelSale = new ToolStripMenuItem();
toolStripMenuItemContractorFuel = new ToolStripMenuItem();
отчетыToolStripMenuItem = new ToolStripMenuItem();
toolStripMenuItemDirectoryReport = new ToolStripMenuItem();
toolStripMenuItemFuelReport = new ToolStripMenuItem();
toolStripMenuItemFuelDistribution = new ToolStripMenuItem();
menuStrip1.SuspendLayout();
SuspendLayout();
//
// menuStrip1
//
menuStrip1.Items.AddRange(new ToolStripItem[] { справочникиToolStripMenuItem, toolStripMenuItem2, отчетыToolStripMenuItem });
menuStrip1.Location = new Point(0, 0);
menuStrip1.Name = "menuStrip1";
menuStrip1.Size = new Size(784, 24);
menuStrip1.TabIndex = 0;
menuStrip1.Text = "menuStrip1";
//
// справочникиToolStripMenuItem
//
справочникиToolStripMenuItem.DropDownItems.AddRange(new ToolStripItem[] { toolStripMenuItemSalepersons, toolStripMenuItemShifts, toolStripMenuItemContractors, toolStripMenuItemFuels });
справочникиToolStripMenuItem.Name = "справочникиToolStripMenuItem";
справочникиToolStripMenuItem.Size = new Size(94, 20);
справочникиToolStripMenuItem.Text = "Справочники";
//
// toolStripMenuItemSalepersons
//
toolStripMenuItemSalepersons.Name = "toolStripMenuItemSalepersons";
toolStripMenuItemSalepersons.Size = new Size(144, 22);
toolStripMenuItemSalepersons.Text = "Сотрудники";
toolStripMenuItemSalepersons.Click += toolStripMenuItemSalepersons_Click;
//
// toolStripMenuItemShifts
//
toolStripMenuItemShifts.Name = "toolStripMenuItemShifts";
toolStripMenuItemShifts.Size = new Size(144, 22);
toolStripMenuItemShifts.Text = "Смены";
toolStripMenuItemShifts.Click += toolStripMenuItemShifts_Click;
//
// toolStripMenuItemContractors
//
toolStripMenuItemContractors.Name = "toolStripMenuItemContractors";
toolStripMenuItemContractors.Size = new Size(144, 22);
toolStripMenuItemContractors.Text = "Поставщики";
toolStripMenuItemContractors.Click += toolStripMenuItemContractors_Click;
//
// toolStripMenuItemFuels
//
toolStripMenuItemFuels.Name = "toolStripMenuItemFuels";
toolStripMenuItemFuels.Size = new Size(144, 22);
toolStripMenuItemFuels.Text = "Топливо";
toolStripMenuItemFuels.Click += toolStripMenuItemFuels_Click;
//
// toolStripMenuItem2
//
toolStripMenuItem2.DropDownItems.AddRange(new ToolStripItem[] { toolStripMenuItemFuelSale, toolStripMenuItemContractorFuel });
toolStripMenuItem2.Name = "toolStripMenuItem2";
toolStripMenuItem2.Size = new Size(75, 20);
toolStripMenuItem2.Text = "Операции";
//
// toolStripMenuItemFuelSale
//
toolStripMenuItemFuelSale.Name = "toolStripMenuItemFuelSale";
toolStripMenuItemFuelSale.Size = new Size(160, 22);
toolStripMenuItemFuelSale.Text = "Новая продажа";
toolStripMenuItemFuelSale.Click += toolStripMenuItemFuelSale_Click;
//
// toolStripMenuItemContractorFuel
//
toolStripMenuItemContractorFuel.Name = "toolStripMenuItemContractorFuel";
toolStripMenuItemContractorFuel.Size = new Size(160, 22);
toolStripMenuItemContractorFuel.Text = "Новая поставка";
toolStripMenuItemContractorFuel.Click += toolStripMenuItemContractorFuel_Click;
//
// отчетыToolStripMenuItem
//
отчетыToolStripMenuItem.DropDownItems.AddRange(new ToolStripItem[] { toolStripMenuItemDirectoryReport, toolStripMenuItemFuelReport, toolStripMenuItemFuelDistribution });
отчетыToolStripMenuItem.Name = "отчетыToolStripMenuItem";
отчетыToolStripMenuItem.Size = new Size(60, 20);
отчетыToolStripMenuItem.Text = "Отчеты";
//
// toolStripMenuItemDirectoryReport
//
toolStripMenuItemDirectoryReport.Name = "toolStripMenuItemDirectoryReport";
toolStripMenuItemDirectoryReport.ShortcutKeys = Keys.Control | Keys.W;
toolStripMenuItemDirectoryReport.Size = new Size(300, 22);
toolStripMenuItemDirectoryReport.Text = "Документ со справочниками";
toolStripMenuItemDirectoryReport.Click += toolStripMenuItemDirectoryReport_Click;
//
// toolStripMenuItemFuelReport
//
toolStripMenuItemFuelReport.Name = "toolStripMenuItemFuelReport";
toolStripMenuItemFuelReport.ShortcutKeys = Keys.Control | Keys.E;
toolStripMenuItemFuelReport.Size = new Size(300, 22);
toolStripMenuItemFuelReport.Text = "Движение топлива";
toolStripMenuItemFuelReport.Click += toolStripMenuItemFuelReport_Click;
//
// toolStripMenuItemFuelDistribution
//
toolStripMenuItemFuelDistribution.Name = "toolStripMenuItemFuelDistribution";
toolStripMenuItemFuelDistribution.ShortcutKeys = Keys.Control | Keys.P;
toolStripMenuItemFuelDistribution.Size = new Size(300, 22);
toolStripMenuItemFuelDistribution.Text = "Распределение поставок топлива";
toolStripMenuItemFuelDistribution.Click += toolStripMenuItemFuelDistribution_Click;
//
// FormGasStation
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
BackgroundImage = (Image)resources.GetObject("$this.BackgroundImage");
BackgroundImageLayout = ImageLayout.Stretch;
ClientSize = new Size(784, 411);
Controls.Add(menuStrip1);
MainMenuStrip = menuStrip1;
Name = "FormGasStation";
StartPosition = FormStartPosition.CenterScreen;
Text = "Заправка";
menuStrip1.ResumeLayout(false);
menuStrip1.PerformLayout();
ResumeLayout(false);
PerformLayout();
}
#endregion
private MenuStrip menuStrip1;
private ToolStripMenuItem справочникиToolStripMenuItem;
private ToolStripMenuItem toolStripMenuItemSalepersons;
private ToolStripMenuItem toolStripMenuItemShifts;
private ToolStripMenuItem toolStripMenuItemContractors;
private ToolStripMenuItem toolStripMenuItem2;
private ToolStripMenuItem отчетыToolStripMenuItem;
private ToolStripMenuItem toolStripMenuItemFuelSale;
private ToolStripMenuItem toolStripMenuItemContractorFuel;
private ToolStripMenuItem toolStripMenuItemFuels;
private ToolStripMenuItem toolStripMenuItemDirectoryReport;
private ToolStripMenuItem toolStripMenuItemFuelReport;
private ToolStripMenuItem toolStripMenuItemFuelDistribution;
}
}

View File

@ -0,0 +1,131 @@
using ProjectGasStation.Forms;
using Unity;
namespace ProjectGasStation;
public partial class FormGasStation : Form
{
private readonly IUnityContainer _container;
public FormGasStation(IUnityContainer container)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
}
private void toolStripMenuItemSalepersons_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormSalespersons>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemShifts_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormShifts>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemContractors_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormContractors>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemFuels_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormFuels>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemContractorFuel_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormContractorFuels>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemFuelSale_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormFuelSales>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemDirectoryReport_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormDirectoryReport>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemFuelReport_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormFuelReport>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void toolStripMenuItemFuelDistribution_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormContractorFuelDistributionReport>().ShowDialog();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Îøèáêà ïðè çàãðóçêå",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,119 @@
namespace ProjectGasStation.Forms
{
partial class FormContractor
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
checkedListBoxFuelTypes = new CheckedListBox();
label1 = new Label();
textBoxName = new TextBox();
label2 = new Label();
buttonSave = new Button();
buttonCancel = new Button();
SuspendLayout();
//
// checkedListBoxFuelTypes
//
checkedListBoxFuelTypes.FormattingEnabled = true;
checkedListBoxFuelTypes.Location = new Point(105, 48);
checkedListBoxFuelTypes.Name = "checkedListBoxFuelTypes";
checkedListBoxFuelTypes.Size = new Size(199, 94);
checkedListBoxFuelTypes.TabIndex = 0;
//
// label1
//
label1.AutoSize = true;
label1.Location = new Point(34, 12);
label1.Name = "label1";
label1.Size = new Size(65, 15);
label1.TabIndex = 1;
label1.Text = "Название: ";
//
// textBoxName
//
textBoxName.Location = new Point(105, 9);
textBoxName.Name = "textBoxName";
textBoxName.Size = new Size(199, 23);
textBoxName.TabIndex = 2;
//
// label2
//
label2.AutoSize = true;
label2.Location = new Point(12, 48);
label2.Name = "label2";
label2.Size = new Size(87, 15);
label2.TabIndex = 3;
label2.Text = "Типы топлива:";
//
// buttonSave
//
buttonSave.Location = new Point(105, 148);
buttonSave.Name = "buttonSave";
buttonSave.Size = new Size(75, 23);
buttonSave.TabIndex = 4;
buttonSave.Text = "Сохранить";
buttonSave.UseVisualStyleBackColor = true;
buttonSave.Click += buttonSave_Click;
//
// buttonCancel
//
buttonCancel.Location = new Point(229, 148);
buttonCancel.Name = "buttonCancel";
buttonCancel.Size = new Size(75, 23);
buttonCancel.TabIndex = 5;
buttonCancel.Text = "Отмена";
buttonCancel.UseVisualStyleBackColor = true;
buttonCancel.Click += buttonCancel_Click;
//
// FormContractor
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(344, 191);
Controls.Add(buttonCancel);
Controls.Add(buttonSave);
Controls.Add(label2);
Controls.Add(textBoxName);
Controls.Add(label1);
Controls.Add(checkedListBoxFuelTypes);
Name = "FormContractor";
StartPosition = FormStartPosition.CenterParent;
Text = "Поставщик";
ResumeLayout(false);
PerformLayout();
}
#endregion
private CheckedListBox checkedListBoxFuelTypes;
private Label label1;
private TextBox textBoxName;
private Label label2;
private Button buttonSave;
private Button buttonCancel;
}
}

View File

@ -0,0 +1,88 @@
using ProjectGasStation.Entities;
using ProjectGasStation.Entities.Enums;
using ProjectGasStation.Repositories;
namespace ProjectGasStation.Forms;
public partial class FormContractor : Form
{
private readonly IContractorRepository _contractorRepository;
private int? _contractorId;
public int Id
{
set
{
try
{
var contractor = _contractorRepository.ReadContractorById(value);
if (contractor == null)
{
throw new InvalidDataException(nameof(contractor));
}
foreach (ContractorFuelType elem in Enum.GetValues(typeof(ContractorFuelType)))
{
if ((elem & contractor.Types) != 0)
{
checkedListBoxFuelTypes.SetItemChecked(checkedListBoxFuelTypes.Items.IndexOf(elem), true);
}
}
textBoxName.Text = contractor.Name;
_contractorId = value;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при получении данных", MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
}
}
public FormContractor(IContractorRepository contractorRepository)
{
InitializeComponent();
_contractorRepository = contractorRepository ?? throw new ArgumentNullException(nameof(contractorRepository));
foreach (ContractorFuelType fuelType in Enum.GetValues(typeof(ContractorFuelType)))
{
if (fuelType == ContractorFuelType.None) continue;
checkedListBoxFuelTypes.Items.Add(fuelType);
}
}
private void buttonSave_Click(object sender, EventArgs e)
{
try
{
if (string.IsNullOrWhiteSpace(textBoxName.Text) || checkedListBoxFuelTypes.CheckedItems.Count == 0)
{
throw new Exception("Имеются незаполненные поля");
}
if (_contractorId.HasValue)
{
_contractorRepository.UpdateContractor(CreateContractor(_contractorId.Value));
}
else
{
_contractorRepository.CreateContractor(CreateContractor(0));
}
Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при сохранении",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonCancel_Click(object sender, EventArgs e) => Close();
private Contractor CreateContractor(int id)
{
ContractorFuelType fuelType = ContractorFuelType.None;
foreach (var elem in checkedListBoxFuelTypes.CheckedItems)
{
fuelType |= (ContractorFuelType)elem;
}
return Contractor.CreateContractor(id, textBoxName.Text, fuelType);
}
}

View File

@ -1,17 +1,17 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
@ -26,36 +26,36 @@
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->

View File

@ -0,0 +1,173 @@
namespace ProjectGasStation.Forms
{
partial class FormContractorFuel
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
label1 = new Label();
comboBoxContractor = new ComboBox();
buttonSave = new Button();
buttonCancel = new Button();
groupBox = new GroupBox();
dataGridView = new DataGridView();
ColumnFuel = new DataGridViewComboBoxColumn();
ColumnQuantity = new DataGridViewTextBoxColumn();
label2 = new Label();
dateTimePickerDate = new DateTimePicker();
groupBox.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridView).BeginInit();
SuspendLayout();
//
// label1
//
label1.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
label1.AutoSize = true;
label1.Location = new Point(14, 19);
label1.Name = "label1";
label1.Size = new Size(73, 15);
label1.TabIndex = 0;
label1.Text = "Поставщик:";
//
// comboBoxContractor
//
comboBoxContractor.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
comboBoxContractor.FormattingEnabled = true;
comboBoxContractor.Location = new Point(93, 16);
comboBoxContractor.Name = "comboBoxContractor";
comboBoxContractor.Size = new Size(206, 23);
comboBoxContractor.TabIndex = 4;
//
// buttonSave
//
buttonSave.Anchor = AnchorStyles.Bottom | AnchorStyles.Left;
buttonSave.Location = new Point(12, 381);
buttonSave.Name = "buttonSave";
buttonSave.Size = new Size(75, 23);
buttonSave.TabIndex = 6;
buttonSave.Text = "Сохранить";
buttonSave.UseVisualStyleBackColor = true;
buttonSave.Click += buttonSave_Click;
//
// buttonCancel
//
buttonCancel.Anchor = AnchorStyles.Bottom | AnchorStyles.Right;
buttonCancel.Location = new Point(224, 381);
buttonCancel.Name = "buttonCancel";
buttonCancel.Size = new Size(75, 23);
buttonCancel.TabIndex = 7;
buttonCancel.Text = "Отменить";
buttonCancel.UseVisualStyleBackColor = true;
buttonCancel.Click += buttonCancel_Click;
//
// groupBox
//
groupBox.Anchor = AnchorStyles.Top | AnchorStyles.Bottom | AnchorStyles.Left | AnchorStyles.Right;
groupBox.Controls.Add(dataGridView);
groupBox.Location = new Point(12, 87);
groupBox.Name = "groupBox";
groupBox.Size = new Size(287, 288);
groupBox.TabIndex = 8;
groupBox.TabStop = false;
groupBox.Text = "Топливо";
//
// dataGridView
//
dataGridView.AllowUserToResizeColumns = false;
dataGridView.AllowUserToResizeRows = false;
dataGridView.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridView.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridView.Columns.AddRange(new DataGridViewColumn[] { ColumnFuel, ColumnQuantity });
dataGridView.Dock = DockStyle.Fill;
dataGridView.Location = new Point(3, 19);
dataGridView.MultiSelect = false;
dataGridView.Name = "dataGridView";
dataGridView.RowHeadersVisible = false;
dataGridView.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridView.Size = new Size(281, 266);
dataGridView.TabIndex = 0;
//
// ColumnFuel
//
ColumnFuel.HeaderText = "Топливо";
ColumnFuel.Name = "ColumnFuel";
//
// ColumnQuantity
//
ColumnQuantity.HeaderText = "Количество";
ColumnQuantity.Name = "ColumnQuantity";
//
// label2
//
label2.AutoSize = true;
label2.Location = new Point(52, 62);
label2.Name = "label2";
label2.Size = new Size(35, 15);
label2.TabIndex = 9;
label2.Text = "Дата:";
//
// dateTimePickerDate
//
dateTimePickerDate.Location = new Point(93, 56);
dateTimePickerDate.Name = "dateTimePickerDate";
dateTimePickerDate.Size = new Size(206, 23);
dateTimePickerDate.TabIndex = 10;
//
// FormContractorFuel
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(311, 416);
Controls.Add(dateTimePickerDate);
Controls.Add(label2);
Controls.Add(groupBox);
Controls.Add(buttonCancel);
Controls.Add(buttonSave);
Controls.Add(comboBoxContractor);
Controls.Add(label1);
Name = "FormContractorFuel";
StartPosition = FormStartPosition.CenterParent;
Text = "Новая поставка";
groupBox.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridView).EndInit();
ResumeLayout(false);
PerformLayout();
}
#endregion
private Label label1;
private ComboBox comboBoxContractor;
private Button buttonSave;
private Button buttonCancel;
private GroupBox groupBox;
private DataGridView dataGridView;
private DataGridViewComboBoxColumn ColumnFuel;
private DataGridViewTextBoxColumn ColumnQuantity;
private Label label2;
private DateTimePicker dateTimePickerDate;
}
}

View File

@ -0,0 +1,63 @@
using ProjectGasStation.Entities;
using ProjectGasStation.Repositories;
namespace ProjectGasStation.Forms;
public partial class FormContractorFuel : Form
{
private readonly IContractorFuelRepository _contractorFuelRepository;
public FormContractorFuel(
IContractorFuelRepository contractorFuelRepository,
IContractorRepository contractorRepository,
IFuelRepository fuelRepository)
{
InitializeComponent();
_contractorFuelRepository = contractorFuelRepository ?? throw new ArgumentNullException(nameof(contractorRepository));
comboBoxContractor.DataSource = contractorRepository.ReadContractors();
comboBoxContractor.DisplayMember = "Name";
comboBoxContractor.ValueMember = "Id";
ColumnFuel.DataSource = fuelRepository.ReadFuels();
ColumnFuel.DisplayMember = "Type";
ColumnFuel.ValueMember = "Id";
}
private void buttonSave_Click(object sender, EventArgs e)
{
try
{
if (comboBoxContractor.SelectedIndex < 0 || dataGridView.RowCount < 1)
{
throw new Exception("Имеются незаполненные поля");
}
_contractorFuelRepository.CreateContractorFuel(ContractorFuel.CreateContractorFuel(0,
(int)comboBoxContractor.SelectedValue!, dateTimePickerDate.Value, CreateListContractorFuelFuelFromDataGrid()));
Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при сохранении",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonCancel_Click(object sender, EventArgs e) => Close();
private List<ContractorFuelFuel> CreateListContractorFuelFuelFromDataGrid()
{
var list = new List<ContractorFuelFuel>();
foreach (DataGridViewRow row in dataGridView.Rows)
{
if (row.Cells["ColumnFuel"].Value == null ||
row.Cells["ColumnQuantity"].Value == null)
{
continue;
}
list.Add(ContractorFuelFuel.CreateContractorFuelFuel(0,
Convert.ToInt32(row.Cells["ColumnFuel"].Value),
Convert.ToInt32(row.Cells["ColumnQuantity"].Value)));
}
return list.GroupBy(x => x.FuelId, x => x.Quantity, (id, counts) => ContractorFuelFuel.CreateContractorFuelFuel(0, id, counts.Sum())).ToList();
}
}

View File

@ -0,0 +1,132 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<metadata name="ColumnFuel.UserAddedColumn" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>True</value>
</metadata>
<metadata name="ColumnQuantity.UserAddedColumn" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>True</value>
</metadata>
<metadata name="ColumnFuel.UserAddedColumn" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>True</value>
</metadata>
<metadata name="ColumnQuantity.UserAddedColumn" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>True</value>
</metadata>
</root>

View File

@ -0,0 +1,107 @@
namespace ProjectGasStation.Forms
{
partial class FormContractorFuelDistributionReport
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
dateTimePicker = new DateTimePicker();
label1 = new Label();
labelFileName = new Label();
buttonFile = new Button();
buttonBuild = new Button();
SuspendLayout();
//
// dateTimePicker
//
dateTimePicker.Location = new Point(70, 44);
dateTimePicker.Name = "dateTimePicker";
dateTimePicker.Size = new Size(200, 23);
dateTimePicker.TabIndex = 0;
//
// label1
//
label1.AutoSize = true;
label1.Location = new Point(29, 50);
label1.Name = "label1";
label1.Size = new Size(35, 15);
label1.TabIndex = 1;
label1.Text = "Дата:";
//
// labelFileName
//
labelFileName.AutoSize = true;
labelFileName.Location = new Point(111, 16);
labelFileName.Name = "labelFileName";
labelFileName.Size = new Size(36, 15);
labelFileName.TabIndex = 2;
labelFileName.Text = "Файл";
//
// buttonFile
//
buttonFile.Location = new Point(29, 12);
buttonFile.Name = "buttonFile";
buttonFile.Size = new Size(75, 23);
buttonFile.TabIndex = 3;
buttonFile.Text = "Выбрать";
buttonFile.UseVisualStyleBackColor = true;
buttonFile.Click += buttonFile_Click;
//
// buttonBuild
//
buttonBuild.Location = new Point(29, 85);
buttonBuild.Name = "buttonBuild";
buttonBuild.Size = new Size(241, 23);
buttonBuild.TabIndex = 4;
buttonBuild.Text = "Сформировать";
buttonBuild.UseVisualStyleBackColor = true;
buttonBuild.Click += buttonBuild_Click;
//
// FormContractorFuelDistributionReport
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(291, 137);
Controls.Add(buttonBuild);
Controls.Add(buttonFile);
Controls.Add(labelFileName);
Controls.Add(label1);
Controls.Add(dateTimePicker);
Name = "FormContractorFuelDistributionReport";
Text = "FormContractorFuelDistributionReport";
ResumeLayout(false);
PerformLayout();
}
#endregion
private DateTimePicker dateTimePicker;
private Label label1;
private Label labelFileName;
private Button buttonFile;
private Button buttonBuild;
}
}

View File

@ -0,0 +1,69 @@
using ProjectGasStation.Reports;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using Unity;
namespace ProjectGasStation.Forms
{
public partial class FormContractorFuelDistributionReport : Form
{
private string _fileName = string.Empty;
private readonly IUnityContainer _container;
public FormContractorFuelDistributionReport(IUnityContainer container)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
}
private void buttonBuild_Click(object sender, EventArgs e)
{
try
{
if (string.IsNullOrWhiteSpace(_fileName))
{
throw new Exception("Отсутствует имя файла для отчета");
}
if
(_container.Resolve<ChartReport>().CreateChart(_fileName, dateTimePicker.Value))
{
MessageBox.Show("Документ сформирован",
"Формирование документа",
MessageBoxButtons.OK,
MessageBoxIcon.Information);
}
else
{
MessageBox.Show("Возникли ошибки при формировании документа.Подробности в логах",
"Формирование документа",
MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при создании очета",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonFile_Click(object sender, EventArgs e)
{
var sfd = new SaveFileDialog()
{
Filter = "Pdf Files | *.pdf"
};
if (sfd.ShowDialog() == DialogResult.OK)
{
_fileName = sfd.FileName;
labelFileName.Text = Path.GetFileName(_fileName);
}
}
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,112 @@
namespace ProjectGasStation.Forms
{
partial class FormContractorFuels
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
panel1 = new Panel();
buttonDelete = new Button();
buttonAdd = new Button();
dataGridViewData = new DataGridView();
panel1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridViewData).BeginInit();
SuspendLayout();
//
// panel1
//
panel1.Controls.Add(buttonDelete);
panel1.Controls.Add(buttonAdd);
panel1.Dock = DockStyle.Right;
panel1.Location = new Point(789, 0);
panel1.Name = "panel1";
panel1.Size = new Size(95, 361);
panel1.TabIndex = 0;
//
// buttonDelete
//
buttonDelete.BackgroundImage = Properties.Resources._1828843;
buttonDelete.BackgroundImageLayout = ImageLayout.Stretch;
buttonDelete.Location = new Point(14, 83);
buttonDelete.Name = "buttonDelete";
buttonDelete.Size = new Size(68, 65);
buttonDelete.TabIndex = 2;
buttonDelete.UseVisualStyleBackColor = true;
buttonDelete.Click += buttonDelete_Click;
//
// buttonAdd
//
buttonAdd.BackgroundImage = Properties.Resources._5610959;
buttonAdd.BackgroundImageLayout = ImageLayout.Stretch;
buttonAdd.Location = new Point(14, 12);
buttonAdd.Name = "buttonAdd";
buttonAdd.Size = new Size(68, 65);
buttonAdd.TabIndex = 0;
buttonAdd.UseVisualStyleBackColor = true;
buttonAdd.Click += buttonAdd_Click;
//
// dataGridViewData
//
dataGridViewData.AllowUserToAddRows = false;
dataGridViewData.AllowUserToDeleteRows = false;
dataGridViewData.AllowUserToResizeColumns = false;
dataGridViewData.AllowUserToResizeRows = false;
dataGridViewData.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridViewData.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridViewData.Dock = DockStyle.Fill;
dataGridViewData.Location = new Point(0, 0);
dataGridViewData.MultiSelect = false;
dataGridViewData.Name = "dataGridViewData";
dataGridViewData.ReadOnly = true;
dataGridViewData.RowHeadersVisible = false;
dataGridViewData.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridViewData.Size = new Size(789, 361);
dataGridViewData.TabIndex = 1;
//
// FormContractorFuels
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(884, 361);
Controls.Add(dataGridViewData);
Controls.Add(panel1);
Name = "FormContractorFuels";
StartPosition = FormStartPosition.CenterParent;
Text = "Поставки";
Load += FormContractors_Load;
panel1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridViewData).EndInit();
ResumeLayout(false);
}
#endregion
private Panel panel1;
private Button buttonDelete;
private Button buttonAdd;
private DataGridView dataGridViewData;
}
}

View File

@ -0,0 +1,85 @@
using ProjectGasStation.Repositories;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormContractorFuels : Form
{
private readonly IUnityContainer _container;
private readonly IContractorFuelRepository _contractorFuelRepository;
public FormContractorFuels(IUnityContainer container, IContractorFuelRepository contractorFuelRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
_contractorFuelRepository = contractorFuelRepository ?? throw new ArgumentNullException(nameof(contractorFuelRepository));
}
private void FormContractors_Load(object sender, EventArgs e)
{
try
{
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при загрузке", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonAdd_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormContractorFuel>().ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при добавлении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonDelete_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
if (MessageBox.Show("Удалить запись?", "Удаление", MessageBoxButtons.YesNo) != DialogResult.Yes)
{
return;
}
try
{
_contractorFuelRepository.DeleteContractorFuel(findId);
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при удалении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadList()
{
dataGridViewData.DataSource = _contractorFuelRepository.ReadContractorFuels();
dataGridViewData.Columns["Id"].Visible = false;
}
private bool TryGetIdentifierFromSelectedRow(out int id)
{
id = 0;
if(dataGridViewData.SelectedRows.Count < 1)
{
MessageBox.Show("Нет выбранной записи", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
id = Convert.ToInt32(dataGridViewData.SelectedRows[0].Cells["Id"].Value);
return true;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,126 @@
namespace ProjectGasStation.Forms
{
partial class FormContractors
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
panel1 = new Panel();
buttonDelete = new Button();
buttonUpdate = new Button();
buttonAdd = new Button();
dataGridViewData = new DataGridView();
panel1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridViewData).BeginInit();
SuspendLayout();
//
// panel1
//
panel1.Controls.Add(buttonDelete);
panel1.Controls.Add(buttonUpdate);
panel1.Controls.Add(buttonAdd);
panel1.Dock = DockStyle.Right;
panel1.Location = new Point(789, 0);
panel1.Name = "panel1";
panel1.Size = new Size(95, 361);
panel1.TabIndex = 0;
//
// buttonDelete
//
buttonDelete.BackgroundImage = Properties.Resources._1828843;
buttonDelete.BackgroundImageLayout = ImageLayout.Stretch;
buttonDelete.Location = new Point(15, 154);
buttonDelete.Name = "buttonDelete";
buttonDelete.Size = new Size(68, 65);
buttonDelete.TabIndex = 2;
buttonDelete.UseVisualStyleBackColor = true;
buttonDelete.Click += buttonDelete_Click;
//
// buttonUpdate
//
buttonUpdate.BackgroundImage = Properties.Resources.edit_icon;
buttonUpdate.BackgroundImageLayout = ImageLayout.Stretch;
buttonUpdate.Location = new Point(15, 83);
buttonUpdate.Name = "buttonUpdate";
buttonUpdate.Size = new Size(68, 65);
buttonUpdate.TabIndex = 1;
buttonUpdate.UseVisualStyleBackColor = true;
buttonUpdate.Click += buttonUpdate_Click;
//
// buttonAdd
//
buttonAdd.BackgroundImage = Properties.Resources._5610959;
buttonAdd.BackgroundImageLayout = ImageLayout.Stretch;
buttonAdd.Location = new Point(14, 12);
buttonAdd.Name = "buttonAdd";
buttonAdd.Size = new Size(68, 65);
buttonAdd.TabIndex = 0;
buttonAdd.UseVisualStyleBackColor = true;
buttonAdd.Click += buttonAdd_Click;
//
// dataGridViewData
//
dataGridViewData.AllowUserToAddRows = false;
dataGridViewData.AllowUserToDeleteRows = false;
dataGridViewData.AllowUserToResizeColumns = false;
dataGridViewData.AllowUserToResizeRows = false;
dataGridViewData.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridViewData.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridViewData.Dock = DockStyle.Fill;
dataGridViewData.Location = new Point(0, 0);
dataGridViewData.MultiSelect = false;
dataGridViewData.Name = "dataGridViewData";
dataGridViewData.ReadOnly = true;
dataGridViewData.RowHeadersVisible = false;
dataGridViewData.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridViewData.Size = new Size(789, 361);
dataGridViewData.TabIndex = 1;
//
// FormContractors
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(884, 361);
Controls.Add(dataGridViewData);
Controls.Add(panel1);
Name = "FormContractors";
StartPosition = FormStartPosition.CenterParent;
Text = "Поставщики";
Load += FormContractors_Load;
panel1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridViewData).EndInit();
ResumeLayout(false);
}
#endregion
private Panel panel1;
private Button buttonDelete;
private Button buttonUpdate;
private Button buttonAdd;
private DataGridView dataGridViewData;
}
}

View File

@ -0,0 +1,104 @@
using ProjectGasStation.Repositories;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormContractors : Form
{
private readonly IUnityContainer _container;
private readonly IContractorRepository _contractorRepository;
public FormContractors(IUnityContainer container, IContractorRepository contractorRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
_contractorRepository = contractorRepository ?? throw new ArgumentNullException(nameof(contractorRepository));
}
private void FormContractors_Load(object sender, EventArgs e)
{
try
{
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при загрузке", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonAdd_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormContractor>().ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при добавлении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonUpdate_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
try
{
var form = _container.Resolve<FormContractor>();
form.Id = findId;
form.ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при изменении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonDelete_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
if (MessageBox.Show("Удалить запись?", "Удаление", MessageBoxButtons.YesNo) != DialogResult.Yes)
{
return;
}
try
{
_contractorRepository.DeleteContractor(findId);
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при удалении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadList()
{
dataGridViewData.DataSource = _contractorRepository.ReadContractors();
dataGridViewData.Columns["Id"].Visible = false;
}
private bool TryGetIdentifierFromSelectedRow(out int id)
{
id = 0;
if(dataGridViewData.SelectedRows.Count < 1)
{
MessageBox.Show("Нет выбранной записи", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
id = Convert.ToInt32(dataGridViewData.SelectedRows[0].Cells["Id"].Value);
return true;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,112 @@
namespace ProjectGasStation.Forms
{
partial class FormDirectoryReport
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
checkBoxShifts = new CheckBox();
checkBoxSalespersons = new CheckBox();
checkBoxFuels = new CheckBox();
checkBoxContractors = new CheckBox();
buttonBuild = new Button();
SuspendLayout();
//
// checkBoxShifts
//
checkBoxShifts.AutoSize = true;
checkBoxShifts.Location = new Point(12, 12);
checkBoxShifts.Name = "checkBoxShifts";
checkBoxShifts.Size = new Size(65, 19);
checkBoxShifts.TabIndex = 0;
checkBoxShifts.Text = "Смены";
checkBoxShifts.UseVisualStyleBackColor = true;
//
// checkBoxSalespersons
//
checkBoxSalespersons.AutoSize = true;
checkBoxSalespersons.Location = new Point(12, 46);
checkBoxSalespersons.Name = "checkBoxSalespersons";
checkBoxSalespersons.Size = new Size(83, 19);
checkBoxSalespersons.TabIndex = 1;
checkBoxSalespersons.Text = "Продавцы";
checkBoxSalespersons.UseVisualStyleBackColor = true;
//
// checkBoxFuels
//
checkBoxFuels.AutoSize = true;
checkBoxFuels.Location = new Point(12, 82);
checkBoxFuels.Name = "checkBoxFuels";
checkBoxFuels.Size = new Size(73, 19);
checkBoxFuels.TabIndex = 2;
checkBoxFuels.Text = "Топливо";
checkBoxFuels.UseVisualStyleBackColor = true;
//
// checkBoxContractors
//
checkBoxContractors.AutoSize = true;
checkBoxContractors.Location = new Point(12, 118);
checkBoxContractors.Name = "checkBoxContractors";
checkBoxContractors.Size = new Size(96, 19);
checkBoxContractors.TabIndex = 3;
checkBoxContractors.Text = "Поставщики";
checkBoxContractors.UseVisualStyleBackColor = true;
//
// buttonBuild
//
buttonBuild.Location = new Point(12, 159);
buttonBuild.Name = "buttonBuild";
buttonBuild.Size = new Size(139, 23);
buttonBuild.TabIndex = 4;
buttonBuild.Text = "Сформировать";
buttonBuild.UseVisualStyleBackColor = true;
buttonBuild.Click += buttonBuild_Click;
//
// FormDirectoryReport
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(167, 197);
Controls.Add(buttonBuild);
Controls.Add(checkBoxContractors);
Controls.Add(checkBoxFuels);
Controls.Add(checkBoxSalespersons);
Controls.Add(checkBoxShifts);
Name = "FormDirectoryReport";
Text = "FormDirectoryReport";
ResumeLayout(false);
PerformLayout();
}
#endregion
private CheckBox checkBoxShifts;
private CheckBox checkBoxSalespersons;
private CheckBox checkBoxFuels;
private CheckBox checkBoxContractors;
private Button buttonBuild;
}
}

View File

@ -0,0 +1,53 @@
using ProjectGasStation.Reports;
using System.ComponentModel;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormDirectoryReport : Form
{
private readonly IUnityContainer _container;
public FormDirectoryReport(IUnityContainer container)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
}
private void buttonBuild_Click(object sender, EventArgs e)
{
try
{
if (!checkBoxShifts.Checked && !checkBoxSalespersons.Checked && !checkBoxFuels.Checked && !checkBoxContractors.Checked)
{
throw new Exception("Не выбран ни один справочник для выгрузки");
}
var sfd = new SaveFileDialog()
{
Filter = "Docx Files | *.docx"
};
if (sfd.ShowDialog() != DialogResult.OK)
{
throw new Exception("Не выбран файла для отчета");
}
if
(_container.Resolve<DocReport>().CreateDoc(sfd.FileName, checkBoxShifts.Checked, checkBoxSalespersons.Checked, checkBoxFuels.Checked, checkBoxContractors.Checked))
{
MessageBox.Show("Документ сформирован",
"Формирование документа",
MessageBoxButtons.OK,
MessageBoxIcon.Information);
}
else
{
MessageBox.Show("Возникли ошибки при формировании документа.Подробности в логах",
"Формирование документа",
MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при создании отчета", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,124 @@
namespace ProjectGasStation.Forms
{
partial class FormFuel
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
comboBoxType = new ComboBox();
numericUpDownCost = new NumericUpDown();
buttonSave = new Button();
buttonCancel = new Button();
label1 = new Label();
label2 = new Label();
((System.ComponentModel.ISupportInitialize)numericUpDownCost).BeginInit();
SuspendLayout();
//
// comboBoxType
//
comboBoxType.FormattingEnabled = true;
comboBoxType.Location = new Point(98, 57);
comboBoxType.Name = "comboBoxType";
comboBoxType.Size = new Size(139, 23);
comboBoxType.TabIndex = 0;
//
// numericUpDownCost
//
numericUpDownCost.DecimalPlaces = 2;
numericUpDownCost.ImeMode = ImeMode.On;
numericUpDownCost.Location = new Point(98, 18);
numericUpDownCost.Maximum = new decimal(new int[] { 10000, 0, 0, 0 });
numericUpDownCost.Name = "numericUpDownCost";
numericUpDownCost.Size = new Size(139, 23);
numericUpDownCost.TabIndex = 1;
//
// buttonSave
//
buttonSave.Location = new Point(14, 90);
buttonSave.Name = "buttonSave";
buttonSave.Size = new Size(75, 23);
buttonSave.TabIndex = 2;
buttonSave.Text = "Сохранить";
buttonSave.UseVisualStyleBackColor = true;
buttonSave.Click += buttonSave_Click;
//
// buttonCancel
//
buttonCancel.Location = new Point(162, 90);
buttonCancel.Name = "buttonCancel";
buttonCancel.Size = new Size(75, 23);
buttonCancel.TabIndex = 3;
buttonCancel.Text = "Отмена";
buttonCancel.UseVisualStyleBackColor = true;
buttonCancel.Click += buttonCancel_Click;
//
// label1
//
label1.AutoSize = true;
label1.Location = new Point(14, 60);
label1.Name = "label1";
label1.Size = new Size(78, 15);
label1.TabIndex = 4;
label1.Text = "Вид топлива:";
//
// label2
//
label2.AutoSize = true;
label2.Location = new Point(54, 20);
label2.Name = "label2";
label2.Size = new Size(38, 15);
label2.TabIndex = 5;
label2.Text = "Цена:";
//
// FormFuel
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(264, 136);
Controls.Add(label2);
Controls.Add(label1);
Controls.Add(buttonCancel);
Controls.Add(buttonSave);
Controls.Add(numericUpDownCost);
Controls.Add(comboBoxType);
Name = "FormFuel";
StartPosition = FormStartPosition.CenterParent;
Text = "Топливо";
((System.ComponentModel.ISupportInitialize)numericUpDownCost).EndInit();
ResumeLayout(false);
PerformLayout();
}
#endregion
private ComboBox comboBoxType;
private NumericUpDown numericUpDownCost;
private Button buttonSave;
private Button buttonCancel;
private Label label1;
private Label label2;
}
}

View File

@ -0,0 +1,71 @@
using ProjectGasStation.Entities;
using ProjectGasStation.Entities.Enums;
using ProjectGasStation.Repositories;
using ProjectGasStation.Repositories.Implementations;
namespace ProjectGasStation.Forms;
public partial class FormFuel : Form
{
private readonly IFuelRepository _fuelRepository;
private int? _fuelId;
public int Id
{
set
{
try
{
var fuel = _fuelRepository.ReadFuelById(value);
if (fuel == null)
{
throw new InvalidDataException(nameof(fuel));
}
numericUpDownCost.Value = (decimal)fuel.Price;
comboBoxType.SelectedItem = fuel.Type;
_fuelId = fuel.Id;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при получении данных", MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
}
}
public FormFuel(IFuelRepository fuelRepository)
{
InitializeComponent();
_fuelRepository = fuelRepository ?? throw new ArgumentNullException(nameof(fuelRepository));
comboBoxType.DataSource = Enum.GetValues(typeof(FuelType));
}
private void buttonSave_Click(object sender, EventArgs e)
{
try
{
if (numericUpDownCost.Value == 0 || comboBoxType.SelectedIndex < 1)
{
throw new Exception("Имеются незаполненные поля");
}
if (_fuelId.HasValue)
{
_fuelRepository.UpdateFuel(CreateFuel(_fuelId.Value));
}
else
{
_fuelRepository.CreateFuel(CreateFuel(0));
}
Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при сохранении",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonCancel_Click(object sender, EventArgs e) => Close();
private Fuel CreateFuel(int id) => Fuel.CreateFuel(id, (FuelType)comboBoxType.SelectedItem!, (double)numericUpDownCost.Value);
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,162 @@
namespace ProjectGasStation.Forms
{
partial class FormFuelReport
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
dateTimePickerEnd = new DateTimePicker();
dateTimePickerStart = new DateTimePicker();
comboBoxFuel = new ComboBox();
textBoxFilePath = new TextBox();
buttonFile = new Button();
buttonBuild = new Button();
label1 = new Label();
label2 = new Label();
label3 = new Label();
label4 = new Label();
SuspendLayout();
//
// dateTimePickerEnd
//
dateTimePickerEnd.Location = new Point(118, 137);
dateTimePickerEnd.Name = "dateTimePickerEnd";
dateTimePickerEnd.Size = new Size(200, 23);
dateTimePickerEnd.TabIndex = 0;
//
// dateTimePickerStart
//
dateTimePickerStart.Location = new Point(118, 99);
dateTimePickerStart.Name = "dateTimePickerStart";
dateTimePickerStart.Size = new Size(200, 23);
dateTimePickerStart.TabIndex = 1;
//
// comboBoxFuel
//
comboBoxFuel.FormattingEnabled = true;
comboBoxFuel.Location = new Point(118, 59);
comboBoxFuel.Name = "comboBoxFuel";
comboBoxFuel.Size = new Size(198, 23);
comboBoxFuel.TabIndex = 2;
//
// textBoxFilePath
//
textBoxFilePath.Location = new Point(118, 20);
textBoxFilePath.Name = "textBoxFilePath";
textBoxFilePath.Size = new Size(166, 23);
textBoxFilePath.TabIndex = 3;
//
// buttonFile
//
buttonFile.Location = new Point(290, 20);
buttonFile.Name = "buttonFile";
buttonFile.Size = new Size(26, 23);
buttonFile.TabIndex = 4;
buttonFile.Text = "...";
buttonFile.UseVisualStyleBackColor = true;
buttonFile.Click += buttonFile_Click;
//
// buttonBuild
//
buttonBuild.Location = new Point(22, 181);
buttonBuild.Name = "buttonBuild";
buttonBuild.Size = new Size(296, 23);
buttonBuild.TabIndex = 5;
buttonBuild.Text = "Сформировать";
buttonBuild.UseVisualStyleBackColor = true;
buttonBuild.Click += buttonBuild_Click;
//
// label1
//
label1.AutoSize = true;
label1.Location = new Point(22, 23);
label1.Name = "label1";
label1.Size = new Size(90, 15);
label1.TabIndex = 6;
label1.Text = "Путь до файла:";
//
// label2
//
label2.AutoSize = true;
label2.Location = new Point(22, 62);
label2.Name = "label2";
label2.Size = new Size(57, 15);
label2.TabIndex = 7;
label2.Text = "Топливо:";
//
// label3
//
label3.AutoSize = true;
label3.Location = new Point(22, 105);
label3.Name = "label3";
label3.Size = new Size(77, 15);
label3.TabIndex = 8;
label3.Text = "Дата начала:";
//
// label4
//
label4.AutoSize = true;
label4.Location = new Point(22, 143);
label4.Name = "label4";
label4.Size = new Size(71, 15);
label4.TabIndex = 9;
label4.Text = "Дата конца:";
//
// FormFuelReport
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(345, 227);
Controls.Add(label4);
Controls.Add(label3);
Controls.Add(label2);
Controls.Add(label1);
Controls.Add(buttonBuild);
Controls.Add(buttonFile);
Controls.Add(textBoxFilePath);
Controls.Add(comboBoxFuel);
Controls.Add(dateTimePickerStart);
Controls.Add(dateTimePickerEnd);
Name = "FormFuelReport";
Text = "Отчет по топливу";
ResumeLayout(false);
PerformLayout();
}
#endregion
private DateTimePicker dateTimePickerEnd;
private DateTimePicker dateTimePickerStart;
private ComboBox comboBoxFuel;
private TextBox textBoxFilePath;
private Button buttonFile;
private Button buttonBuild;
private Label label1;
private Label label2;
private Label label3;
private Label label4;
}
}

View File

@ -0,0 +1,83 @@
using ProjectGasStation.Reports;
using ProjectGasStation.Repositories;
using ProjectGasStation.Repositories.Implementations;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using Unity;
namespace ProjectGasStation.Forms
{
public partial class FormFuelReport : Form
{
private readonly IUnityContainer _container;
public FormFuelReport(IUnityContainer container, IFuelRepository fuelRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
comboBoxFuel.DataSource = fuelRepository.ReadFuels();
comboBoxFuel.DisplayMember = "Type";
comboBoxFuel.ValueMember = "Id";
}
private void buttonFile_Click(object sender, EventArgs e)
{
var sfd = new SaveFileDialog()
{
Filter = "Excel Files | *.xlsx"
};
if (sfd.ShowDialog() != DialogResult.OK)
{
return;
}
textBoxFilePath.Text = sfd.FileName;
}
private void buttonBuild_Click(object sender, EventArgs e)
{
try
{
if (string.IsNullOrWhiteSpace(textBoxFilePath.Text))
{
throw new Exception("Отсутствует имя файла для отчета");
}
if (comboBoxFuel.SelectedIndex < 0)
{
throw new Exception("Не выбран корм");
}
if (dateTimePickerEnd.Value <= dateTimePickerStart.Value)
{
throw new Exception("Дата начала должна быть раньше даты окончания");
}
if (_container.Resolve<TableReport>().CreateTable(textBoxFilePath.Text,(int)comboBoxFuel.SelectedValue!, dateTimePickerStart.Value, dateTimePickerEnd.Value))
{
MessageBox.Show("Документ сформирован",
"Формирование документа",
MessageBoxButtons.OK,
MessageBoxIcon.Information);
}
else
{
MessageBox.Show("Возникли ошибки при формировании документа.Подробности в логах",
"Формирование документа",
MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при создании очета",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,200 @@
namespace ProjectGasStation.Forms
{
partial class FormFuelSale
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
comboBoxSalesperson = new ComboBox();
comboBoxShift = new ComboBox();
dateTimePickerDate = new DateTimePicker();
buttonSave = new Button();
buttonCancel = new Button();
label1 = new Label();
label2 = new Label();
label3 = new Label();
groupBox1 = new GroupBox();
dataGridView = new DataGridView();
ColumnFuel = new DataGridViewComboBoxColumn();
ColumnQuantity = new DataGridViewTextBoxColumn();
groupBox1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridView).BeginInit();
SuspendLayout();
//
// comboBoxSalesperson
//
comboBoxSalesperson.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
comboBoxSalesperson.FormattingEnabled = true;
comboBoxSalesperson.Location = new Point(127, 12);
comboBoxSalesperson.Name = "comboBoxSalesperson";
comboBoxSalesperson.Size = new Size(222, 23);
comboBoxSalesperson.TabIndex = 0;
//
// comboBoxShift
//
comboBoxShift.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
comboBoxShift.FormattingEnabled = true;
comboBoxShift.Location = new Point(127, 41);
comboBoxShift.Name = "comboBoxShift";
comboBoxShift.Size = new Size(222, 23);
comboBoxShift.TabIndex = 1;
//
// dateTimePickerDate
//
dateTimePickerDate.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
dateTimePickerDate.Location = new Point(127, 70);
dateTimePickerDate.Name = "dateTimePickerDate";
dateTimePickerDate.Size = new Size(222, 23);
dateTimePickerDate.TabIndex = 4;
//
// buttonSave
//
buttonSave.Anchor = AnchorStyles.Bottom | AnchorStyles.Left;
buttonSave.Location = new Point(12, 302);
buttonSave.Name = "buttonSave";
buttonSave.Size = new Size(75, 23);
buttonSave.TabIndex = 5;
buttonSave.Text = "Сохранить";
buttonSave.UseVisualStyleBackColor = true;
buttonSave.Click += buttonSave_Click;
//
// buttonCancel
//
buttonCancel.Anchor = AnchorStyles.Bottom | AnchorStyles.Right;
buttonCancel.Location = new Point(274, 302);
buttonCancel.Name = "buttonCancel";
buttonCancel.Size = new Size(75, 23);
buttonCancel.TabIndex = 6;
buttonCancel.Text = "Отмена";
buttonCancel.UseVisualStyleBackColor = true;
buttonCancel.Click += buttonCancel_Click;
//
// label1
//
label1.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
label1.AutoSize = true;
label1.Location = new Point(57, 15);
label1.Name = "label1";
label1.Size = new Size(64, 15);
label1.TabIndex = 7;
label1.Text = "Продавец:";
//
// label2
//
label2.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
label2.AutoSize = true;
label2.Location = new Point(75, 44);
label2.Name = "label2";
label2.Size = new Size(46, 15);
label2.TabIndex = 8;
label2.Text = "Смена:";
//
// label3
//
label3.Anchor = AnchorStyles.Top | AnchorStyles.Left | AnchorStyles.Right;
label3.AutoSize = true;
label3.Location = new Point(34, 74);
label3.Name = "label3";
label3.Size = new Size(87, 15);
label3.TabIndex = 9;
label3.Text = "Дата продажи:";
//
// groupBox1
//
groupBox1.Anchor = AnchorStyles.Top | AnchorStyles.Bottom | AnchorStyles.Left | AnchorStyles.Right;
groupBox1.Controls.Add(dataGridView);
groupBox1.Location = new Point(12, 99);
groupBox1.Name = "groupBox1";
groupBox1.Size = new Size(337, 197);
groupBox1.TabIndex = 10;
groupBox1.TabStop = false;
groupBox1.Text = "Топливо";
//
// dataGridView
//
dataGridView.AllowUserToResizeColumns = false;
dataGridView.AllowUserToResizeRows = false;
dataGridView.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridView.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridView.Columns.AddRange(new DataGridViewColumn[] { ColumnFuel, ColumnQuantity });
dataGridView.Dock = DockStyle.Fill;
dataGridView.Location = new Point(3, 19);
dataGridView.MultiSelect = false;
dataGridView.Name = "dataGridView";
dataGridView.RowHeadersVisible = false;
dataGridView.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridView.Size = new Size(331, 175);
dataGridView.TabIndex = 0;
//
// ColumnFuel
//
ColumnFuel.HeaderText = "Топливо";
ColumnFuel.Name = "ColumnFuel";
//
// ColumnQuantity
//
ColumnQuantity.HeaderText = "Количество";
ColumnQuantity.Name = "ColumnQuantity";
//
// FormFuelSale
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(371, 341);
Controls.Add(groupBox1);
Controls.Add(label3);
Controls.Add(label2);
Controls.Add(label1);
Controls.Add(buttonCancel);
Controls.Add(buttonSave);
Controls.Add(dateTimePickerDate);
Controls.Add(comboBoxShift);
Controls.Add(comboBoxSalesperson);
Name = "FormFuelSale";
StartPosition = FormStartPosition.CenterParent;
Text = "Новая продажа";
groupBox1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridView).EndInit();
ResumeLayout(false);
PerformLayout();
}
#endregion
private ComboBox comboBoxSalesperson;
private ComboBox comboBoxShift;
private DateTimePicker dateTimePickerDate;
private Button buttonSave;
private Button buttonCancel;
private Label label1;
private Label label2;
private Label label3;
private GroupBox groupBox1;
private DataGridView dataGridView;
private DataGridViewComboBoxColumn ColumnFuel;
private DataGridViewTextBoxColumn ColumnQuantity;
}
}

View File

@ -0,0 +1,66 @@
using ProjectGasStation.Entities;
using ProjectGasStation.Repositories;
namespace ProjectGasStation.Forms;
public partial class FormFuelSale : Form
{
private readonly IFuelSaleRepository _fuelSaleRepository;
public FormFuelSale(IFuelSaleRepository fuelSaleRepository,
ISalespersonRepository salespersonRepository,
IShiftRepository shiftRepository,
IFuelRepository fuelRepository)
{
InitializeComponent();
_fuelSaleRepository = fuelSaleRepository ?? throw new ArgumentNullException(nameof(fuelSaleRepository));
comboBoxSalesperson.DataSource = salespersonRepository.ReadSalespersons();
comboBoxSalesperson.DisplayMember = "FirstName";
comboBoxSalesperson.ValueMember = "Id";
comboBoxShift.DataSource = shiftRepository.ReadShifts();
comboBoxShift.DisplayMember = "DisplayName";
comboBoxShift.ValueMember = "Id";
ColumnFuel.DataSource = fuelRepository.ReadFuels();
ColumnFuel.DisplayMember = "Type";
ColumnFuel.ValueMember = "Id";
}
private void buttonSave_Click(object sender, EventArgs e)
{
try
{
if (comboBoxSalesperson.SelectedIndex < 0 || comboBoxShift.SelectedIndex < 0 || dataGridView.RowCount < 1)
{
throw new Exception("Имеются незаполненные поля");
}
_fuelSaleRepository.CreateFuelSale(FuelSale.CreateFuelSale(0,
(int)comboBoxSalesperson.SelectedValue!, (int)comboBoxShift.SelectedValue!, dateTimePickerDate.Value, CreateListFuelFuelSaleFromDataGrid()));
Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при сохранении",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonCancel_Click(object sender, EventArgs e) => Close();
private List<FuelFuelSale> CreateListFuelFuelSaleFromDataGrid()
{
var list = new List<FuelFuelSale>();
foreach (DataGridViewRow row in dataGridView.Rows)
{
if (row.Cells["ColumnFuel"].Value == null ||
row.Cells["ColumnQuantity"].Value == null)
{
continue;
}
list.Add(FuelFuelSale.CreateFuelFuelSale(0,
Convert.ToInt32(row.Cells["ColumnFuel"].Value),
Convert.ToInt32(row.Cells["ColumnQuantity"].Value)));
}
return list.GroupBy(x => x.FuelId, x => x.Quantity, (id, counts) => FuelFuelSale.CreateFuelFuelSale(0, id, counts.Sum())).ToList();
}
}

View File

@ -0,0 +1,126 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<metadata name="ColumnFuel.UserAddedColumn" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>True</value>
</metadata>
<metadata name="ColumnQuantity.UserAddedColumn" type="System.Boolean, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>True</value>
</metadata>
</root>

View File

@ -0,0 +1,112 @@
namespace ProjectGasStation.Forms
{
partial class FormFuelSales
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
panel1 = new Panel();
buttonDelete = new Button();
buttonAdd = new Button();
dataGridViewData = new DataGridView();
panel1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridViewData).BeginInit();
SuspendLayout();
//
// panel1
//
panel1.Controls.Add(buttonDelete);
panel1.Controls.Add(buttonAdd);
panel1.Dock = DockStyle.Right;
panel1.Location = new Point(789, 0);
panel1.Name = "panel1";
panel1.Size = new Size(95, 361);
panel1.TabIndex = 0;
//
// buttonDelete
//
buttonDelete.BackgroundImage = Properties.Resources._1828843;
buttonDelete.BackgroundImageLayout = ImageLayout.Stretch;
buttonDelete.Location = new Point(15, 83);
buttonDelete.Name = "buttonDelete";
buttonDelete.Size = new Size(68, 65);
buttonDelete.TabIndex = 2;
buttonDelete.UseVisualStyleBackColor = true;
buttonDelete.Click += buttonDelete_Click;
//
// buttonAdd
//
buttonAdd.BackgroundImage = Properties.Resources._5610959;
buttonAdd.BackgroundImageLayout = ImageLayout.Stretch;
buttonAdd.Location = new Point(14, 12);
buttonAdd.Name = "buttonAdd";
buttonAdd.Size = new Size(68, 65);
buttonAdd.TabIndex = 0;
buttonAdd.UseVisualStyleBackColor = true;
buttonAdd.Click += buttonAdd_Click;
//
// dataGridViewData
//
dataGridViewData.AllowUserToAddRows = false;
dataGridViewData.AllowUserToDeleteRows = false;
dataGridViewData.AllowUserToResizeColumns = false;
dataGridViewData.AllowUserToResizeRows = false;
dataGridViewData.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridViewData.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridViewData.Dock = DockStyle.Fill;
dataGridViewData.Location = new Point(0, 0);
dataGridViewData.MultiSelect = false;
dataGridViewData.Name = "dataGridViewData";
dataGridViewData.ReadOnly = true;
dataGridViewData.RowHeadersVisible = false;
dataGridViewData.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridViewData.Size = new Size(789, 361);
dataGridViewData.TabIndex = 1;
//
// FormFuelSales
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(884, 361);
Controls.Add(dataGridViewData);
Controls.Add(panel1);
Name = "FormFuelSales";
StartPosition = FormStartPosition.CenterParent;
Text = "Продажи";
Load += FormFuels_Load;
panel1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridViewData).EndInit();
ResumeLayout(false);
}
#endregion
private Panel panel1;
private Button buttonDelete;
private Button buttonAdd;
private DataGridView dataGridViewData;
}
}

View File

@ -0,0 +1,84 @@
using ProjectGasStation.Repositories;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormFuelSales : Form
{
private readonly IUnityContainer _container;
private readonly IFuelSaleRepository _fuelSaleRepository;
public FormFuelSales(IUnityContainer container, IFuelSaleRepository fuelSaleRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
_fuelSaleRepository = fuelSaleRepository ?? throw new ArgumentNullException(nameof(fuelSaleRepository));
}
private void FormFuels_Load(object sender, EventArgs e)
{
try
{
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при загрузке", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonAdd_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormFuelSale>().ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при добавлении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonDelete_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
if (MessageBox.Show("Удалить запись?", "Удаление", MessageBoxButtons.YesNo) != DialogResult.Yes)
{
return;
}
try
{
_fuelSaleRepository.DeleteFuelSale(findId);
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при удалении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadList()
{
dataGridViewData.DataSource = _fuelSaleRepository.ReadFuelSales();
dataGridViewData.Columns["Id"].Visible = false;
}
private bool TryGetIdentifierFromSelectedRow(out int id)
{
id = 0;
if(dataGridViewData.SelectedRows.Count < 1)
{
MessageBox.Show("Нет выбранной записи", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
id = Convert.ToInt32(dataGridViewData.SelectedRows[0].Cells["Id"].Value);
return true;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,126 @@
namespace ProjectGasStation.Forms
{
partial class FormFuels
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
panel1 = new Panel();
buttonDelete = new Button();
buttonUpdate = new Button();
buttonAdd = new Button();
dataGridViewData = new DataGridView();
panel1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridViewData).BeginInit();
SuspendLayout();
//
// panel1
//
panel1.Controls.Add(buttonDelete);
panel1.Controls.Add(buttonUpdate);
panel1.Controls.Add(buttonAdd);
panel1.Dock = DockStyle.Right;
panel1.Location = new Point(789, 0);
panel1.Name = "panel1";
panel1.Size = new Size(95, 361);
panel1.TabIndex = 0;
//
// buttonDelete
//
buttonDelete.BackgroundImage = Properties.Resources._1828843;
buttonDelete.BackgroundImageLayout = ImageLayout.Stretch;
buttonDelete.Location = new Point(15, 154);
buttonDelete.Name = "buttonDelete";
buttonDelete.Size = new Size(68, 65);
buttonDelete.TabIndex = 2;
buttonDelete.UseVisualStyleBackColor = true;
buttonDelete.Click += buttonDelete_Click;
//
// buttonUpdate
//
buttonUpdate.BackgroundImage = Properties.Resources.edit_icon;
buttonUpdate.BackgroundImageLayout = ImageLayout.Stretch;
buttonUpdate.Location = new Point(15, 83);
buttonUpdate.Name = "buttonUpdate";
buttonUpdate.Size = new Size(68, 65);
buttonUpdate.TabIndex = 1;
buttonUpdate.UseVisualStyleBackColor = true;
buttonUpdate.Click += buttonUpdate_Click;
//
// buttonAdd
//
buttonAdd.BackgroundImage = Properties.Resources._5610959;
buttonAdd.BackgroundImageLayout = ImageLayout.Stretch;
buttonAdd.Location = new Point(14, 12);
buttonAdd.Name = "buttonAdd";
buttonAdd.Size = new Size(68, 65);
buttonAdd.TabIndex = 0;
buttonAdd.UseVisualStyleBackColor = true;
buttonAdd.Click += buttonAdd_Click;
//
// dataGridViewData
//
dataGridViewData.AllowUserToAddRows = false;
dataGridViewData.AllowUserToDeleteRows = false;
dataGridViewData.AllowUserToResizeColumns = false;
dataGridViewData.AllowUserToResizeRows = false;
dataGridViewData.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridViewData.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridViewData.Dock = DockStyle.Fill;
dataGridViewData.Location = new Point(0, 0);
dataGridViewData.MultiSelect = false;
dataGridViewData.Name = "dataGridViewData";
dataGridViewData.ReadOnly = true;
dataGridViewData.RowHeadersVisible = false;
dataGridViewData.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridViewData.Size = new Size(789, 361);
dataGridViewData.TabIndex = 1;
//
// FormFuels
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(884, 361);
Controls.Add(dataGridViewData);
Controls.Add(panel1);
Name = "FormFuels";
StartPosition = FormStartPosition.CenterParent;
Text = "Топливо";
Load += FormFuels_Load;
panel1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridViewData).EndInit();
ResumeLayout(false);
}
#endregion
private Panel panel1;
private Button buttonDelete;
private Button buttonUpdate;
private Button buttonAdd;
private DataGridView dataGridViewData;
}
}

View File

@ -0,0 +1,104 @@
using ProjectGasStation.Repositories;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormFuels : Form
{
private readonly IUnityContainer _container;
private readonly IFuelRepository _fuelRepository;
public FormFuels(IUnityContainer container, IFuelRepository fuelRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
_fuelRepository = fuelRepository ?? throw new ArgumentNullException(nameof(fuelRepository));
}
private void FormFuels_Load(object sender, EventArgs e)
{
try
{
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при загрузке", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonAdd_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormFuel>().ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при добавлении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonUpdate_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
try
{
var form = _container.Resolve<FormFuel>();
form.Id = findId;
form.ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при изменении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonDelete_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
if (MessageBox.Show("Удалить запись?", "Удаление", MessageBoxButtons.YesNo) != DialogResult.Yes)
{
return;
}
try
{
_fuelRepository.DeleteFuel(findId);
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при удалении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadList()
{
dataGridViewData.DataSource = _fuelRepository.ReadFuels();
dataGridViewData.Columns["Id"].Visible = false;
}
private bool TryGetIdentifierFromSelectedRow(out int id)
{
id = 0;
if(dataGridViewData.SelectedRows.Count < 1)
{
MessageBox.Show("Нет выбранной записи", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
id = Convert.ToInt32(dataGridViewData.SelectedRows[0].Cells["Id"].Value);
return true;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,118 @@
namespace ProjectGasStation.Forms
{
partial class FormSalesperson
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
label1 = new Label();
label2 = new Label();
textBoxLastName = new TextBox();
textBoxFirstName = new TextBox();
buttonSave = new Button();
buttonCancel = new Button();
SuspendLayout();
//
// label1
//
label1.AutoSize = true;
label1.Location = new Point(70, 20);
label1.Name = "label1";
label1.Size = new Size(34, 15);
label1.TabIndex = 0;
label1.Text = "Имя:";
//
// label2
//
label2.AutoSize = true;
label2.Location = new Point(40, 62);
label2.Name = "label2";
label2.Size = new Size(64, 15);
label2.TabIndex = 1;
label2.Text = "Фамилия: ";
//
// textBoxLastName
//
textBoxLastName.Location = new Point(110, 59);
textBoxLastName.Name = "textBoxLastName";
textBoxLastName.Size = new Size(176, 23);
textBoxLastName.TabIndex = 2;
//
// textBoxFirstName
//
textBoxFirstName.Location = new Point(110, 17);
textBoxFirstName.Name = "textBoxFirstName";
textBoxFirstName.Size = new Size(176, 23);
textBoxFirstName.TabIndex = 3;
//
// buttonSave
//
buttonSave.Location = new Point(42, 116);
buttonSave.Name = "buttonSave";
buttonSave.Size = new Size(75, 23);
buttonSave.TabIndex = 4;
buttonSave.Text = "Сохранить";
buttonSave.UseVisualStyleBackColor = true;
buttonSave.Click += buttonSave_Click;
//
// buttonCancel
//
buttonCancel.Location = new Point(211, 116);
buttonCancel.Name = "buttonCancel";
buttonCancel.Size = new Size(75, 23);
buttonCancel.TabIndex = 5;
buttonCancel.Text = "Отмена";
buttonCancel.UseVisualStyleBackColor = true;
buttonCancel.Click += buttonCancel_Click;
//
// FormSalesperson
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(369, 151);
Controls.Add(buttonCancel);
Controls.Add(buttonSave);
Controls.Add(textBoxFirstName);
Controls.Add(textBoxLastName);
Controls.Add(label2);
Controls.Add(label1);
Name = "FormSalesperson";
StartPosition = FormStartPosition.CenterParent;
Text = "Продавец";
ResumeLayout(false);
PerformLayout();
}
#endregion
private Label label1;
private Label label2;
private TextBox textBoxLastName;
private TextBox textBoxFirstName;
private Button buttonSave;
private Button buttonCancel;
}
}

View File

@ -0,0 +1,69 @@
using ProjectGasStation.Entities;
using ProjectGasStation.Repositories;
namespace ProjectGasStation.Forms;
public partial class FormSalesperson : Form
{
public readonly ISalespersonRepository _salespersonRepository;
private int? _salespersonId;
public int Id
{
set
{
try
{
var salesperson = _salespersonRepository.ReadSalespersonById(value);
if (salesperson == null)
{
throw new InvalidDataException(nameof(salesperson));
}
textBoxFirstName.Text = salesperson.FirstName;
textBoxLastName.Text = salesperson.LastName;
_salespersonId = salesperson.Id;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при получении данных", MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
}
}
public FormSalesperson(ISalespersonRepository salespersonRepository)
{
InitializeComponent();
_salespersonRepository = salespersonRepository ?? throw new ArgumentNullException(nameof(salespersonRepository));
}
private void buttonSave_Click(object sender, EventArgs e)
{
try
{
if (string.IsNullOrWhiteSpace(textBoxFirstName.Text) || string.IsNullOrWhiteSpace(textBoxLastName.Text))
{
throw new Exception("Имеются незаполненные поля");
}
if (_salespersonId.HasValue)
{
_salespersonRepository.UpdateSalesperson(CreateSalesperson(_salespersonId.Value));
}
else
{
_salespersonRepository.CreateSalesperson(CreateSalesperson(0));
}
Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при сохранении",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonCancel_Click(object sender, EventArgs e) => Close();
private Salesperson CreateSalesperson(int id) => Salesperson.CreateSalesperson(id, textBoxFirstName.Text, textBoxLastName.Text);
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,126 @@
namespace ProjectGasStation.Forms
{
partial class FormSalespersons
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
panel1 = new Panel();
buttonDelete = new Button();
buttonUpdate = new Button();
buttonAdd = new Button();
dataGridViewData = new DataGridView();
panel1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridViewData).BeginInit();
SuspendLayout();
//
// panel1
//
panel1.Controls.Add(buttonDelete);
panel1.Controls.Add(buttonUpdate);
panel1.Controls.Add(buttonAdd);
panel1.Dock = DockStyle.Right;
panel1.Location = new Point(789, 0);
panel1.Name = "panel1";
panel1.Size = new Size(95, 361);
panel1.TabIndex = 0;
//
// buttonDelete
//
buttonDelete.BackgroundImage = Properties.Resources._1828843;
buttonDelete.BackgroundImageLayout = ImageLayout.Stretch;
buttonDelete.Location = new Point(15, 154);
buttonDelete.Name = "buttonDelete";
buttonDelete.Size = new Size(68, 65);
buttonDelete.TabIndex = 2;
buttonDelete.UseVisualStyleBackColor = true;
buttonDelete.Click += buttonDelete_Click;
//
// buttonUpdate
//
buttonUpdate.BackgroundImage = Properties.Resources.edit_icon;
buttonUpdate.BackgroundImageLayout = ImageLayout.Stretch;
buttonUpdate.Location = new Point(15, 83);
buttonUpdate.Name = "buttonUpdate";
buttonUpdate.Size = new Size(68, 65);
buttonUpdate.TabIndex = 1;
buttonUpdate.UseVisualStyleBackColor = true;
buttonUpdate.Click += buttonUpdate_Click;
//
// buttonAdd
//
buttonAdd.BackgroundImage = Properties.Resources._5610959;
buttonAdd.BackgroundImageLayout = ImageLayout.Stretch;
buttonAdd.Location = new Point(14, 12);
buttonAdd.Name = "buttonAdd";
buttonAdd.Size = new Size(68, 65);
buttonAdd.TabIndex = 0;
buttonAdd.UseVisualStyleBackColor = true;
buttonAdd.Click += buttonAdd_Click;
//
// dataGridViewData
//
dataGridViewData.AllowUserToAddRows = false;
dataGridViewData.AllowUserToDeleteRows = false;
dataGridViewData.AllowUserToResizeColumns = false;
dataGridViewData.AllowUserToResizeRows = false;
dataGridViewData.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridViewData.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridViewData.Dock = DockStyle.Fill;
dataGridViewData.Location = new Point(0, 0);
dataGridViewData.MultiSelect = false;
dataGridViewData.Name = "dataGridViewData";
dataGridViewData.ReadOnly = true;
dataGridViewData.RowHeadersVisible = false;
dataGridViewData.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridViewData.Size = new Size(789, 361);
dataGridViewData.TabIndex = 1;
//
// FormSalespersons
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(884, 361);
Controls.Add(dataGridViewData);
Controls.Add(panel1);
Name = "FormSalespersons";
StartPosition = FormStartPosition.CenterParent;
Text = "Продавцы";
Load += FormSalespersons_Load;
panel1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridViewData).EndInit();
ResumeLayout(false);
}
#endregion
private Panel panel1;
private Button buttonDelete;
private Button buttonUpdate;
private Button buttonAdd;
private DataGridView dataGridViewData;
}
}

View File

@ -0,0 +1,104 @@
using ProjectGasStation.Repositories;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormSalespersons : Form
{
private readonly IUnityContainer _container;
private readonly ISalespersonRepository _salespersonRepository;
public FormSalespersons(IUnityContainer container, ISalespersonRepository salespersonRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
_salespersonRepository = salespersonRepository ?? throw new ArgumentNullException(nameof(salespersonRepository));
}
private void FormSalespersons_Load(object sender, EventArgs e)
{
try
{
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при загрузке", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonAdd_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormSalesperson>().ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при добавлении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonUpdate_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
try
{
var form = _container.Resolve<FormSalesperson>();
form.Id = findId;
form.ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при изменении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonDelete_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
if (MessageBox.Show("Удалить запись?", "Удаление", MessageBoxButtons.YesNo) != DialogResult.Yes)
{
return;
}
try
{
_salespersonRepository.DeleteSalesperson(findId);
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при удалении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadList()
{
dataGridViewData.DataSource = _salespersonRepository.ReadSalespersons();
dataGridViewData.Columns["Id"].Visible = false;
}
private bool TryGetIdentifierFromSelectedRow(out int id)
{
id = 0;
if(dataGridViewData.SelectedRows.Count < 1)
{
MessageBox.Show("Нет выбранной записи", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
id = Convert.ToInt32(dataGridViewData.SelectedRows[0].Cells["Id"].Value);
return true;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,168 @@
namespace ProjectGasStation.Forms
{
partial class FormShift
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
dateTimePickerStart = new DateTimePicker();
dateTimePickerEnd = new DateTimePicker();
comboBoxType = new ComboBox();
dateTimePickerDate = new DateTimePicker();
label1 = new Label();
label2 = new Label();
label3 = new Label();
label4 = new Label();
buttonCancel = new Button();
buttonSave = new Button();
SuspendLayout();
//
// dateTimePickerStart
//
dateTimePickerStart.Format = DateTimePickerFormat.Time;
dateTimePickerStart.Location = new Point(105, 18);
dateTimePickerStart.Name = "dateTimePickerStart";
dateTimePickerStart.ShowUpDown = true;
dateTimePickerStart.Size = new Size(200, 23);
dateTimePickerStart.TabIndex = 0;
//
// dateTimePickerEnd
//
dateTimePickerEnd.Format = DateTimePickerFormat.Time;
dateTimePickerEnd.Location = new Point(105, 47);
dateTimePickerEnd.Name = "dateTimePickerEnd";
dateTimePickerEnd.ShowUpDown = true;
dateTimePickerEnd.Size = new Size(200, 23);
dateTimePickerEnd.TabIndex = 1;
//
// comboBoxType
//
comboBoxType.FormattingEnabled = true;
comboBoxType.Location = new Point(105, 105);
comboBoxType.Name = "comboBoxType";
comboBoxType.Size = new Size(200, 23);
comboBoxType.TabIndex = 2;
//
// dateTimePickerDate
//
dateTimePickerDate.Format = DateTimePickerFormat.Short;
dateTimePickerDate.Location = new Point(105, 76);
dateTimePickerDate.Name = "dateTimePickerDate";
dateTimePickerDate.Size = new Size(200, 23);
dateTimePickerDate.TabIndex = 3;
//
// label1
//
label1.AutoSize = true;
label1.Location = new Point(12, 24);
label1.Name = "label1";
label1.Size = new Size(87, 15);
label1.TabIndex = 4;
label1.Text = "Время начала:";
//
// label2
//
label2.AutoSize = true;
label2.Location = new Point(18, 53);
label2.Name = "label2";
label2.Size = new Size(81, 15);
label2.TabIndex = 5;
label2.Text = "Время конца:";
//
// label3
//
label3.AutoSize = true;
label3.Location = new Point(64, 82);
label3.Name = "label3";
label3.Size = new Size(35, 15);
label3.TabIndex = 6;
label3.Text = "Дата:";
//
// label4
//
label4.AutoSize = true;
label4.Location = new Point(29, 108);
label4.Name = "label4";
label4.Size = new Size(70, 15);
label4.TabIndex = 7;
label4.Text = "Тип смены:";
//
// buttonCancel
//
buttonCancel.Location = new Point(230, 144);
buttonCancel.Name = "buttonCancel";
buttonCancel.Size = new Size(75, 23);
buttonCancel.TabIndex = 8;
buttonCancel.Text = "Отмена";
buttonCancel.UseVisualStyleBackColor = true;
buttonCancel.Click += buttonCancel_Click;
//
// buttonSave
//
buttonSave.Location = new Point(105, 144);
buttonSave.Name = "buttonSave";
buttonSave.Size = new Size(75, 23);
buttonSave.TabIndex = 9;
buttonSave.Text = "Сохранить";
buttonSave.UseVisualStyleBackColor = true;
buttonSave.Click += buttonSave_Click;
//
// FormShift
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(324, 191);
Controls.Add(buttonSave);
Controls.Add(buttonCancel);
Controls.Add(label4);
Controls.Add(label3);
Controls.Add(label2);
Controls.Add(label1);
Controls.Add(dateTimePickerDate);
Controls.Add(comboBoxType);
Controls.Add(dateTimePickerEnd);
Controls.Add(dateTimePickerStart);
Name = "FormShift";
StartPosition = FormStartPosition.CenterParent;
Text = "Смена";
ResumeLayout(false);
PerformLayout();
}
#endregion
private DateTimePicker dateTimePickerStart;
private DateTimePicker dateTimePickerEnd;
private ComboBox comboBoxType;
private DateTimePicker dateTimePickerDate;
private Label label1;
private Label label2;
private Label label3;
private Label label4;
private Button buttonCancel;
private Button buttonSave;
}
}

View File

@ -0,0 +1,81 @@
using ProjectGasStation.Entities;
using ProjectGasStation.Entities.Enums;
using ProjectGasStation.Repositories;
using ProjectGasStation.Repositories.Implementations;
namespace ProjectGasStation.Forms;
public partial class FormShift : Form
{
public readonly IShiftRepository _shiftRepository;
private int? _shiftId;
public int Id
{
set
{
try
{
var shift = _shiftRepository.ReadShiftById(value);
if (shift == null)
{
throw new InvalidDataException(nameof(shift));
}
dateTimePickerStart.Value = shift.Date.Date + shift.StartTime;
dateTimePickerEnd.Value = shift.Date.Date + shift.EndTime;
dateTimePickerDate.Value = shift.Date.Date;
comboBoxType.SelectedItem = shift.Type;
_shiftId = shift.Id;
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при получении данных", MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
}
}
public FormShift(IShiftRepository shiftRepository)
{
InitializeComponent();
_shiftRepository = shiftRepository ?? throw new ArgumentNullException(nameof(shiftRepository));
comboBoxType.DataSource = Enum.GetValues(typeof(ShiftType));
}
private void buttonSave_Click(object sender, EventArgs e)
{
try
{
if (comboBoxType.SelectedIndex < 1)
{
throw new Exception("Имеются незаполненные поля");
}
if (_shiftId.HasValue)
{
_shiftRepository.UpdateShift(CreateShift(_shiftId.Value));
}
else
{
_shiftRepository.CreateShift(CreateShift(0));
}
Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при сохранении",
MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonCancel_Click(object sender, EventArgs e) => Close();
private Shift CreateShift(int id)
{
var startTime = dateTimePickerStart.Value.TimeOfDay;
var endTime = dateTimePickerEnd.Value.TimeOfDay;
var startTimeRounded = new TimeSpan(startTime.Hours, startTime.Minutes, startTime.Seconds);
var endTimeRounded = new TimeSpan(endTime.Hours, endTime.Minutes, endTime.Seconds);
return Shift.CreateShift(id, startTimeRounded, endTimeRounded, dateTimePickerDate.Value.Date, (ShiftType)comboBoxType.SelectedItem!);
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,126 @@
namespace ProjectGasStation.Forms
{
partial class FormShifts
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
panel1 = new Panel();
buttonDelete = new Button();
buttonUpdate = new Button();
buttonAdd = new Button();
dataGridViewData = new DataGridView();
panel1.SuspendLayout();
((System.ComponentModel.ISupportInitialize)dataGridViewData).BeginInit();
SuspendLayout();
//
// panel1
//
panel1.Controls.Add(buttonDelete);
panel1.Controls.Add(buttonUpdate);
panel1.Controls.Add(buttonAdd);
panel1.Dock = DockStyle.Right;
panel1.Location = new Point(789, 0);
panel1.Name = "panel1";
panel1.Size = new Size(95, 361);
panel1.TabIndex = 0;
//
// buttonDelete
//
buttonDelete.BackgroundImage = Properties.Resources._1828843;
buttonDelete.BackgroundImageLayout = ImageLayout.Stretch;
buttonDelete.Location = new Point(15, 154);
buttonDelete.Name = "buttonDelete";
buttonDelete.Size = new Size(68, 65);
buttonDelete.TabIndex = 2;
buttonDelete.UseVisualStyleBackColor = true;
buttonDelete.Click += buttonDelete_Click;
//
// buttonUpdate
//
buttonUpdate.BackgroundImage = Properties.Resources.edit_icon;
buttonUpdate.BackgroundImageLayout = ImageLayout.Stretch;
buttonUpdate.Location = new Point(15, 83);
buttonUpdate.Name = "buttonUpdate";
buttonUpdate.Size = new Size(68, 65);
buttonUpdate.TabIndex = 1;
buttonUpdate.UseVisualStyleBackColor = true;
buttonUpdate.Click += buttonUpdate_Click;
//
// buttonAdd
//
buttonAdd.BackgroundImage = Properties.Resources._5610959;
buttonAdd.BackgroundImageLayout = ImageLayout.Stretch;
buttonAdd.Location = new Point(14, 12);
buttonAdd.Name = "buttonAdd";
buttonAdd.Size = new Size(68, 65);
buttonAdd.TabIndex = 0;
buttonAdd.UseVisualStyleBackColor = true;
buttonAdd.Click += buttonAdd_Click;
//
// dataGridViewData
//
dataGridViewData.AllowUserToAddRows = false;
dataGridViewData.AllowUserToDeleteRows = false;
dataGridViewData.AllowUserToResizeColumns = false;
dataGridViewData.AllowUserToResizeRows = false;
dataGridViewData.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
dataGridViewData.ColumnHeadersHeightSizeMode = DataGridViewColumnHeadersHeightSizeMode.AutoSize;
dataGridViewData.Dock = DockStyle.Fill;
dataGridViewData.Location = new Point(0, 0);
dataGridViewData.MultiSelect = false;
dataGridViewData.Name = "dataGridViewData";
dataGridViewData.ReadOnly = true;
dataGridViewData.RowHeadersVisible = false;
dataGridViewData.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
dataGridViewData.Size = new Size(789, 361);
dataGridViewData.TabIndex = 1;
//
// FormShifts
//
AutoScaleDimensions = new SizeF(7F, 15F);
AutoScaleMode = AutoScaleMode.Font;
ClientSize = new Size(884, 361);
Controls.Add(dataGridViewData);
Controls.Add(panel1);
Name = "FormShifts";
StartPosition = FormStartPosition.CenterParent;
Text = "Смены";
Load += FormShifts_Load;
panel1.ResumeLayout(false);
((System.ComponentModel.ISupportInitialize)dataGridViewData).EndInit();
ResumeLayout(false);
}
#endregion
private Panel panel1;
private Button buttonDelete;
private Button buttonUpdate;
private Button buttonAdd;
private DataGridView dataGridViewData;
}
}

View File

@ -0,0 +1,105 @@
using ProjectGasStation.Repositories;
using Unity;
namespace ProjectGasStation.Forms;
public partial class FormShifts : Form
{
private readonly IUnityContainer _container;
private readonly IShiftRepository _shiftRepository;
public FormShifts(IUnityContainer container, IShiftRepository shiftRepository)
{
InitializeComponent();
_container = container ?? throw new ArgumentNullException(nameof(container));
_shiftRepository = shiftRepository ?? throw new ArgumentNullException(nameof(shiftRepository));
}
private void FormShifts_Load(object sender, EventArgs e)
{
try
{
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при загрузке", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonAdd_Click(object sender, EventArgs e)
{
try
{
_container.Resolve<FormShift>().ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при добавлении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonUpdate_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
try
{
var form = _container.Resolve<FormShift>();
form.Id = findId;
form.ShowDialog();
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при изменении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void buttonDelete_Click(object sender, EventArgs e)
{
if (!TryGetIdentifierFromSelectedRow(out var findId))
{
return;
}
if (MessageBox.Show("Удалить запись?", "Удаление", MessageBoxButtons.YesNo) != DialogResult.Yes)
{
return;
}
try
{
_shiftRepository.DeleteShift(findId);
LoadList();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message, "Ошибка при удалении", MessageBoxButtons.OK, MessageBoxIcon.Error);
}
}
private void LoadList()
{
dataGridViewData.DataSource = _shiftRepository.ReadShifts();
dataGridViewData.Columns["Id"].Visible = false;
dataGridViewData.Columns["DisplayName"].Visible = false;
}
private bool TryGetIdentifierFromSelectedRow(out int id)
{
id = 0;
if(dataGridViewData.SelectedRows.Count < 1)
{
MessageBox.Show("Нет выбранной записи", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
id = Convert.ToInt32(dataGridViewData.SelectedRows[0].Cells["Id"].Value);
return true;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -1,3 +1,11 @@
using Unity;
using ProjectGasStation.Repositories;
using ProjectGasStation.Repositories.Implementations;
using Unity.Microsoft.Logging;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using Serilog;
namespace ProjectGasStation
{
internal static class Program
@ -11,7 +19,36 @@ namespace ProjectGasStation
// To customize application configuration such as set high DPI settings or default font,
// see https://aka.ms/applicationconfiguration.
ApplicationConfiguration.Initialize();
Application.Run(new Form1());
Application.Run(CreateContainer().Resolve<FormGasStation>());
}
private static IUnityContainer CreateContainer()
{
var container = new UnityContainer();
container.AddExtension(new LoggingExtension(CreateLoggerFactory()));
container.RegisterType<IContractorFuelRepository, ContractorFuelRepository>();
container.RegisterType<IContractorRepository, ContractorRepository>();
container.RegisterType<IFuelRepository, FuelRepository>();
container.RegisterType<IFuelSaleRepository, FuelSaleRepository>();
container.RegisterType<ISalespersonRepository, SalespersonRepository>();
container.RegisterType<IShiftRepository, ShiftRepository>();
container.RegisterType<IConnectionString, ConnectionString>();
return container;
}
private static LoggerFactory CreateLoggerFactory()
{
var loggerFactory = new LoggerFactory();
loggerFactory.AddSerilog(new LoggerConfiguration()
.ReadFrom.Configuration(new ConfigurationBuilder()
.SetBasePath(Directory.GetCurrentDirectory())
.AddJsonFile("appsettings.json")
.Build())
.CreateLogger());
return loggerFactory;
}
}
}

View File

@ -8,4 +8,58 @@
<ImplicitUsings>enable</ImplicitUsings>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Dapper" Version="2.1.35" />
<PackageReference Include="DocumentFormat.OpenXml" Version="3.2.0" />
<PackageReference Include="Microsoft.Extensions.Configuration" Version="8.0.0" />
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="8.0.1" />
<PackageReference Include="Microsoft.Extensions.Logging" Version="8.0.1" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
<PackageReference Include="Npgsql" Version="8.0.5" />
<PackageReference Include="PdfSharp.MigraDoc.Standard" Version="1.51.15" />
<PackageReference Include="Serilog" Version="4.1.0" />
<PackageReference Include="Serilog.Extensions.Logging" Version="8.0.0" />
<PackageReference Include="Serilog.Settings.Configuration" Version="8.0.4" />
<PackageReference Include="Serilog.Sinks.File" Version="6.0.0" />
<PackageReference Include="System.Data.SqlClient" Version="4.8.6" />
<PackageReference Include="Unity" Version="5.11.10" />
<PackageReference Include="Unity.Microsoft.Logging" Version="5.11.1" />
</ItemGroup>
<ItemGroup>
<Compile Update="Forms\FormContractorFuels.cs">
<SubType>Form</SubType>
</Compile>
<Compile Update="Forms\FormContractors.cs">
<SubType>Form</SubType>
</Compile>
<Compile Update="Forms\FormFuelSales.cs">
<SubType>Form</SubType>
</Compile>
<Compile Update="Forms\FormFuels.cs">
<SubType>Form</SubType>
</Compile>
<Compile Update="Forms\FormShifts.cs">
<SubType>Form</SubType>
</Compile>
<Compile Update="Properties\Resources.Designer.cs">
<DesignTime>True</DesignTime>
<AutoGen>True</AutoGen>
<DependentUpon>Resources.resx</DependentUpon>
</Compile>
</ItemGroup>
<ItemGroup>
<EmbeddedResource Update="Properties\Resources.resx">
<Generator>ResXFileCodeGenerator</Generator>
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
</EmbeddedResource>
</ItemGroup>
<ItemGroup>
<None Update="appsettings.json">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
</ItemGroup>
</Project>

View File

@ -0,0 +1,103 @@
//------------------------------------------------------------------------------
// <auto-generated>
// Этот код создан программой.
// Исполняемая версия:4.0.30319.42000
//
// Изменения в этом файле могут привести к неправильной работе и будут потеряны в случае
// повторной генерации кода.
// </auto-generated>
//------------------------------------------------------------------------------
namespace ProjectGasStation.Properties {
using System;
/// <summary>
/// Класс ресурса со строгой типизацией для поиска локализованных строк и т.д.
/// </summary>
// Этот класс создан автоматически классом StronglyTypedResourceBuilder
// с помощью такого средства, как ResGen или Visual Studio.
// Чтобы добавить или удалить член, измените файл .ResX и снова запустите ResGen
// с параметром /str или перестройте свой проект VS.
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "17.0.0.0")]
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
[global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
internal class Resources {
private static global::System.Resources.ResourceManager resourceMan;
private static global::System.Globalization.CultureInfo resourceCulture;
[global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
internal Resources() {
}
/// <summary>
/// Возвращает кэшированный экземпляр ResourceManager, использованный этим классом.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Resources.ResourceManager ResourceManager {
get {
if (object.ReferenceEquals(resourceMan, null)) {
global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("ProjectGasStation.Properties.Resources", typeof(Resources).Assembly);
resourceMan = temp;
}
return resourceMan;
}
}
/// <summary>
/// Перезаписывает свойство CurrentUICulture текущего потока для всех
/// обращений к ресурсу с помощью этого класса ресурса со строгой типизацией.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Globalization.CultureInfo Culture {
get {
return resourceCulture;
}
set {
resourceCulture = value;
}
}
/// <summary>
/// Поиск локализованного ресурса типа System.Drawing.Bitmap.
/// </summary>
internal static System.Drawing.Bitmap _1828843 {
get {
object obj = ResourceManager.GetObject("1828843", resourceCulture);
return ((System.Drawing.Bitmap)(obj));
}
}
/// <summary>
/// Поиск локализованного ресурса типа System.Drawing.Bitmap.
/// </summary>
internal static System.Drawing.Bitmap _5610959 {
get {
object obj = ResourceManager.GetObject("5610959", resourceCulture);
return ((System.Drawing.Bitmap)(obj));
}
}
/// <summary>
/// Поиск локализованного ресурса типа System.Drawing.Bitmap.
/// </summary>
internal static System.Drawing.Bitmap edit_icon {
get {
object obj = ResourceManager.GetObject("edit-icon", resourceCulture);
return ((System.Drawing.Bitmap)(obj));
}
}
/// <summary>
/// Поиск локализованного ресурса типа System.Drawing.Bitmap.
/// </summary>
internal static System.Drawing.Bitmap magical_mystical_landscape_wallpaper_purple_tones {
get {
object obj = ResourceManager.GetObject("magical-mystical-landscape-wallpaper-purple-tones", resourceCulture);
return ((System.Drawing.Bitmap)(obj));
}
}
}
}

View File

@ -0,0 +1,133 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<assembly alias="System.Windows.Forms" name="System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
<data name="magical-mystical-landscape-wallpaper-purple-tones" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\magical-mystical-landscape-wallpaper-purple-tones.jpg;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="5610959" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\5610959.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="1828843" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\1828843.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="edit-icon" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\edit-icon.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
</root>

View File

@ -0,0 +1,48 @@
using Microsoft.Extensions.Logging;
using ProjectGasStation.Repositories;
using ProjectGasStation.Repositories.Implementations;
namespace ProjectGasStation.Reports;
internal class ChartReport
{
private readonly IContractorFuelRepository _contractorFuelRepository;
private readonly IFuelRepository _fuelRepository;
private readonly ILogger<ChartReport> _logger;
public ChartReport(IContractorFuelRepository contractorFuelRepository, IFuelRepository fuelRepository, ILogger<ChartReport> logger)
{
_contractorFuelRepository = contractorFuelRepository ?? throw new ArgumentNullException(nameof(contractorFuelRepository));
_fuelRepository = fuelRepository ?? throw new ArgumentNullException(nameof(fuelRepository));
_logger = logger ?? throw new ArgumentNullException(nameof(logger));
}
public bool CreateChart(string filePath, DateTime dateTime)
{
try
{
new PdfBuilder(filePath)
.AddHeader("Поставки топлива")
.AddPieChart($"Поставленные виды топлива на {dateTime:dd.MM.yyyy}", GetData(dateTime))
.Build();
return true;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при формировании документа");
return false;
}
}
private List<(string Caption, double Value)> GetData(DateTime dateTime)
{
var fuelNames = _fuelRepository.ReadFuels()
.ToDictionary(f => f.Id, f => f.Type);
return _contractorFuelRepository
.ReadContractorFuels(dateFrom: dateTime.Date, dateTo: dateTime.Date.AddDays(1))
.SelectMany(x => x.ContractorFuelFuel)
.GroupBy(x => x.FuelId)
.Select(g => (Caption: fuelNames[g.Key].ToString(), Value: (double)g.Sum(x => x.Quantity)))
.ToList();
}
}

View File

@ -0,0 +1,93 @@
using Microsoft.Extensions.Logging;
using ProjectGasStation.Repositories;
namespace ProjectGasStation.Reports;
public class DocReport
{
private readonly IShiftRepository _shiftRepository;
private readonly ISalespersonRepository _salespersonRepository;
private readonly IFuelRepository _fuelRepository;
private readonly IContractorRepository _contractorRepository;
private readonly ILogger<DocReport> _logger;
public DocReport(IShiftRepository shiftRepository, ISalespersonRepository salespersonRepository, IFuelRepository fuelRepository, IContractorRepository contractorRepository, ILogger<DocReport> logger)
{
_shiftRepository = shiftRepository ?? throw new ArgumentNullException(nameof(shiftRepository));
_salespersonRepository = salespersonRepository ?? throw new ArgumentNullException(nameof(salespersonRepository));
_fuelRepository = fuelRepository ?? throw new ArgumentNullException(nameof(fuelRepository));
_contractorRepository = contractorRepository ?? throw new ArgumentNullException(nameof(contractorRepository));
_logger = logger ?? throw new ArgumentNullException(nameof(logger));
}
public bool CreateDoc(string filePath, bool includeShifts, bool includeSalespersons, bool includeFuels, bool includeContractors)
{
try
{
var builder = new WordBuilder(filePath).AddHeader("Документ со справочниками");
if (includeShifts)
{
builder.AddParagraph("Смена").AddTable([2400, 2400, 2400, 2400], GetShifts());
}
if (includeSalespersons)
{
builder.AddParagraph("Продавцы").AddTable([2400, 2400], GetSalespersons());
}
if (includeFuels)
{
builder.AddParagraph("Топливо").AddTable([2400, 2400], GetFuels());
}
if (includeContractors)
{
builder.AddParagraph("Поставщики").AddTable([2400, 2400], GetContractors());
}
builder.Build();
return true;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при формировании документа");
return false;
}
}
private List<string[]> GetShifts()
{
return [
["Время начала", "Время конца", "Дата", "Тип"],
.. _shiftRepository
.ReadShifts()
.Select(x => new string[] { x.StartTime.ToString(), x.EndTime.ToString(), x.Date.ToString(), x.Type.ToString() }),
];
}
private List<string[]> GetSalespersons()
{
return [
["Имя", "Фамилия"],
.. _salespersonRepository
.ReadSalespersons()
.Select(x => new string[] { x.FirstName, x.LastName }),
];
}
private List<string[]> GetFuels()
{
return [
["Цена", "Тип"],
.. _fuelRepository
.ReadFuels()
.Select(x => new string[] { x.Price.ToString(), x.Type.ToString() }),
];
}
private List<string[]> GetContractors()
{
return [
["Название", "Типы поставляемого топлива"],
.. _contractorRepository
.ReadContractors()
.Select(x => new string[] { x.Name, x.Types.ToString() }),
];
}
}

View File

@ -0,0 +1,311 @@
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Spreadsheet;
using DocumentFormat.OpenXml;
namespace ProjectGasStation.Reports;
internal class ExcelBuilder
{
private readonly string _filePath;
private readonly SheetData _sheetData;
private readonly MergeCells _mergeCells;
private readonly Columns _columns;
private uint _rowIndex = 0;
public ExcelBuilder(string filePath)
{
if (string.IsNullOrWhiteSpace(filePath))
{
throw new ArgumentNullException(nameof(filePath));
}
if (File.Exists(filePath))
{
File.Delete(filePath);
}
_filePath = filePath;
_sheetData = new SheetData();
_mergeCells = new MergeCells();
_columns = new Columns();
_rowIndex = 1;
}
public ExcelBuilder AddHeader(string header, int startIndex, int count)
{
CreateCell(startIndex, _rowIndex, header, StyleIndex.BoldTextWithoutBorder);
for (int i = startIndex + 1; i < startIndex + count; ++i)
{
CreateCell(i, _rowIndex, "", StyleIndex.SimpleTextWithoutBorder);
}
_mergeCells.Append(new MergeCell()
{
Reference = new StringValue($"{GetExcelColumnName(startIndex)}{_rowIndex}:{GetExcelColumnName(startIndex + count - 1)}{_rowIndex}")
});
_rowIndex++;
return this;
}
public ExcelBuilder AddParagraph(string text, int columnIndex)
{
CreateCell(columnIndex, _rowIndex++, text, StyleIndex.SimpleTextWithoutBorder);
return this;
}
public ExcelBuilder AddTable(int[] columnsWidths, List<string[]> data)
{
if (columnsWidths == null || columnsWidths.Length == 0)
{
throw new ArgumentNullException(nameof(columnsWidths));
}
if (data == null || data.Count == 0)
{
throw new ArgumentNullException(nameof(data));
}
if (data.Any(x => x.Length != columnsWidths.Length))
{
throw new InvalidOperationException("widths.Length != data.Length");
}
uint counter = 1;
int coef = 2;
_columns.Append(columnsWidths.Select(x => new Column
{
Min = counter,
Max = counter++,
Width = x * coef,
CustomWidth = true
}));
for (var j = 0; j < data.First().Length; ++j)
{
CreateCell(j, _rowIndex, data.First()[j], StyleIndex.BoldTextWithBorder);
}
_rowIndex++;
for (var i = 1; i < data.Count - 1; ++i)
{
for (var j = 0; j < data[i].Length; ++j)
{
CreateCell(j, _rowIndex, data[i][j], StyleIndex.SimpleTextWithBorder);
}
_rowIndex++;
}
for (var j = 0; j < data.Last().Length; ++j)
{
CreateCell(j, _rowIndex, data.Last()[j], StyleIndex.BoldTextWithBorder);
}
_rowIndex++;
return this;
}
public void Build()
{
using var spreadsheetDocument = SpreadsheetDocument.Create(_filePath, SpreadsheetDocumentType.Workbook);
var workbookpart = spreadsheetDocument.AddWorkbookPart();
GenerateStyle(workbookpart);
workbookpart.Workbook = new Workbook();
var worksheetPart = workbookpart.AddNewPart<WorksheetPart>();
worksheetPart.Worksheet = new Worksheet();
if (_columns.HasChildren)
{
worksheetPart.Worksheet.Append(_columns);
}
worksheetPart.Worksheet.Append(_sheetData);
var sheets = spreadsheetDocument.WorkbookPart!.Workbook.AppendChild(new Sheets());
var sheet = new Sheet()
{
Id = spreadsheetDocument.WorkbookPart.GetIdOfPart(worksheetPart),
SheetId = 1,
Name = "Лист 1"
};
sheets.Append(sheet);
if (_mergeCells.HasChildren)
{
worksheetPart.Worksheet.InsertAfter(_mergeCells,
worksheetPart.Worksheet.Elements<SheetData>().First());
}
}
private static void GenerateStyle(WorkbookPart workbookPart)
{
var workbookStylesPart = workbookPart.AddNewPart<WorkbookStylesPart>();
workbookStylesPart.Stylesheet = new Stylesheet();
var fonts = new Fonts()
{
Count = 2,
KnownFonts = BooleanValue.FromBoolean(true)
};
fonts.Append(new DocumentFormat.OpenXml.Spreadsheet.Font
{
FontSize = new FontSize() { Val = 11 },
FontName = new FontName() { Val = "Calibri" },
FontFamilyNumbering = new FontFamilyNumbering() { Val = 2 },
FontScheme = new FontScheme()
{
Val = new EnumValue<FontSchemeValues>(FontSchemeValues.Minor)
}
});
fonts.Append(new DocumentFormat.OpenXml.Spreadsheet.Font
{
FontSize = new FontSize() { Val = 11 },
FontName = new FontName() { Val = "Calibri" },
FontFamilyNumbering = new FontFamilyNumbering() { Val = 2 },
FontScheme = new FontScheme()
{
Val = new EnumValue<FontSchemeValues>(FontSchemeValues.Minor)
},
Bold = new Bold() { Val = true }
});
workbookStylesPart.Stylesheet.Append(fonts);
// Default Fill
var fills = new Fills() { Count = 1 };
fills.Append(new Fill
{
PatternFill = new PatternFill()
{
PatternType = new EnumValue<PatternValues>(PatternValues.None)
}
});
workbookStylesPart.Stylesheet.Append(fills);
// Default Border
var borders = new Borders() { Count = 2 };
borders.Append(new Border
{
LeftBorder = new LeftBorder(),
RightBorder = new RightBorder(),
TopBorder = new TopBorder(),
BottomBorder = new BottomBorder(),
DiagonalBorder = new DiagonalBorder()
});
borders.Append(new Border
{
LeftBorder = new LeftBorder() { Style = BorderStyleValues.Thin },
RightBorder = new RightBorder() { Style = BorderStyleValues.Thin },
TopBorder = new TopBorder() { Style = BorderStyleValues.Thin },
BottomBorder = new BottomBorder() { Style = BorderStyleValues.Thin },
DiagonalBorder = new DiagonalBorder()
});
workbookStylesPart.Stylesheet.Append(borders);
// Default cell format and a date cell format
var cellFormats = new CellFormats() { Count = 4 };
cellFormats.Append(new CellFormat
{
NumberFormatId = 0,
FormatId = 0,
FontId = 0,
BorderId = 0,
FillId = 0,
Alignment = new Alignment()
{
Horizontal = HorizontalAlignmentValues.Left,
Vertical = VerticalAlignmentValues.Center,
WrapText = true
}
});
cellFormats.Append(new CellFormat
{
NumberFormatId = 0,
FormatId = 0,
FontId = 0,
BorderId = 1,
FillId = 0,
Alignment = new Alignment()
{
Horizontal = HorizontalAlignmentValues.Right,
Vertical = VerticalAlignmentValues.Center,
WrapText = true
}
});
cellFormats.Append(new CellFormat
{
NumberFormatId = 0,
FormatId = 0,
FontId = 1,
BorderId = 0,
FillId = 0,
Alignment = new Alignment()
{
Horizontal = HorizontalAlignmentValues.Center,
Vertical = VerticalAlignmentValues.Center,
WrapText = true
}
});
cellFormats.Append(new CellFormat
{
NumberFormatId = 0,
FormatId = 0,
FontId = 1,
BorderId = 1,
FillId = 0,
Alignment = new Alignment()
{
Horizontal = HorizontalAlignmentValues.Center,
Vertical = VerticalAlignmentValues.Center,
WrapText = true
}
});
workbookStylesPart.Stylesheet.Append(cellFormats);
}
private enum StyleIndex
{
SimpleTextWithoutBorder = 0,
SimpleTextWithBorder = 1,
BoldTextWithoutBorder = 2,
BoldTextWithBorder = 3,
}
private void CreateCell(int columnIndex, uint rowIndex, string text, StyleIndex styleIndex)
{
var columnName = GetExcelColumnName(columnIndex);
var cellReference = columnName + rowIndex;
var row = _sheetData.Elements<Row>().FirstOrDefault(r => r.RowIndex! == rowIndex);
if (row == null)
{
row = new Row() { RowIndex = rowIndex };
_sheetData.Append(row);
}
var newCell = row.Elements<Cell>().FirstOrDefault(c => c.CellReference != null &&
c.CellReference.Value == columnName + rowIndex);
if (newCell == null)
{
Cell? refCell = null;
foreach (Cell cell in row.Elements<Cell>())
{
if (cell.CellReference?.Value != null &&
cell.CellReference.Value.Length == cellReference.Length)
{
if (string.Compare(cell.CellReference.Value, cellReference, true) > 0)
{
refCell = cell;
break;
}
}
}
newCell = new Cell() { CellReference = cellReference };
row.InsertBefore(newCell, refCell);
}
newCell.CellValue = new CellValue(text);
newCell.DataType = CellValues.String;
newCell.StyleIndex = (uint)styleIndex;
}
private static string GetExcelColumnName(int columnNumber)
{
columnNumber += 1;
int dividend = columnNumber;
string columnName = string.Empty;
int modulo;
while (dividend > 0)
{
modulo = (dividend - 1) % 26;
columnName = Convert.ToChar(65 + modulo).ToString() + columnName;
dividend = (dividend - modulo) / 26;
}
return columnName;
}
}

View File

@ -0,0 +1,76 @@
using MigraDoc.DocumentObjectModel;
using MigraDoc.DocumentObjectModel.Shapes.Charts;
using MigraDoc.Rendering;
using System.Text;
namespace ProjectGasStation.Reports;
internal class PdfBuilder
{
private readonly string _filePath;
private readonly Document _document;
public PdfBuilder(string filePath)
{
if (string.IsNullOrWhiteSpace(filePath))
{
throw new ArgumentNullException(nameof(filePath));
}
if (File.Exists(filePath))
{
File.Delete(filePath);
}
_filePath = filePath;
_document = new Document();
DefineStyles();
}
public PdfBuilder AddHeader(string header)
{
_document.AddSection().AddParagraph(header, "NormalBold");
return this;
}
public PdfBuilder AddPieChart(string title, List<(string Caption, double Value)> data)
{
if (data == null || data.Count == 0)
{
return this;
}
var chart = new Chart(ChartType.Pie2D);
var series = chart.SeriesCollection.AddSeries();
series.Add(data.Select(x => x.Value).ToArray());
var xseries = chart.XValues.AddXSeries();
xseries.Add(data.Select(x => x.Caption).ToArray());
chart.DataLabel.Type = DataLabelType.Percent;
chart.DataLabel.Position = DataLabelPosition.OutsideEnd;
chart.Width = Unit.FromCentimeter(16);
chart.Height = Unit.FromCentimeter(12);
chart.TopArea.AddParagraph(title);
chart.XAxis.MajorTickMark = TickMarkType.Outside;
chart.YAxis.MajorTickMark = TickMarkType.Outside;
chart.YAxis.HasMajorGridlines = true;
chart.PlotArea.LineFormat.Width = 1;
chart.PlotArea.LineFormat.Visible = true;
chart.TopArea.AddLegend();
_document.LastSection.Add(chart);
return this;
}
public void Build()
{
Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);
var renderer = new PdfDocumentRenderer(true)
{
Document = _document
};
renderer.RenderDocument();
renderer.PdfDocument.Save(_filePath);
}
private void DefineStyles()
{
var headerStyle = _document.Styles.AddStyle("NormalBold", "Normal");
headerStyle.Font.Bold = true;
headerStyle.Font.Size = 14;
}
}

View File

@ -0,0 +1,69 @@
using Microsoft.Extensions.Logging;
using ProjectGasStation.Repositories;
namespace ProjectGasStation.Reports;
internal class TableReport
{
private readonly IContractorFuelRepository _contractorFuelRepository;
private readonly IFuelSaleRepository _fuelSaleRepository;
private readonly ILogger<TableReport> _logger;
internal static readonly string[] item = ["Дата", "Количество пришло", "Количество ушло"];
public TableReport(IContractorFuelRepository contractorFuelRepository, IFuelSaleRepository fuelSaleRepository, ILogger<TableReport> logger)
{
_contractorFuelRepository = contractorFuelRepository ?? throw new ArgumentNullException(nameof(contractorFuelRepository));
_fuelSaleRepository = fuelSaleRepository ?? throw new ArgumentNullException(nameof(fuelSaleRepository));
_logger = logger ?? throw new ArgumentNullException(nameof(logger));
}
public bool CreateTable(string filePath, int fuelId, DateTime startDate, DateTime endDate)
{
try
{
new ExcelBuilder(filePath)
.AddHeader("Сводка по движению топлива", 0, 3)
.AddParagraph($"за период {startDate:dd.MM.yyyy} по {endDate:dd.MM.yyyy}", 0)
.AddTable([10, 15, 15], GetData(fuelId, startDate, endDate))
.Build();
return true;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при формировании документа");
return false;
}
}
private List<string[]> GetData(int fuelId, DateTime startDate, DateTime endDate)
{
var data = _contractorFuelRepository
.ReadContractorFuels(startDate, endDate, fuelId)
.Select(x => new { x.Date, CountIn = x.ContractorFuelFuel.FirstOrDefault(y => y.FuelId == fuelId)?.Quantity, CountOut = (int?)null})
.Union(
_fuelSaleRepository
.ReadFuelSales(startDate, endDate, fuelId)
.Select(x => new { Date = x.SaleDate, CountIn = (int?)null, CountOut = x.FuelFuelSale.FirstOrDefault(y => y.FuelId == fuelId)?.Quantity })
)
.OrderBy(x => x.Date);
var groupedData = data
.GroupBy(x => x.Date)
.Select(g => new
{
Date = g.Key,
TotalIn = g.Sum(x => x.CountIn),
TotalOut = g.Sum(x => x.CountOut)
})
.OrderBy(x => x.Date);
return
new List<string[]>() { item }
.Union( groupedData
.Select(x => new string[] { x.Date.ToString("dd.MM.yyyy"), x.TotalIn?.ToString("N0") ?? string.Empty, x.TotalOut?.ToString("N0") ?? string.Empty }))
.Union(
new[] { new string[] { "Всего", groupedData.Sum(x => x.TotalIn)?.ToString("N0") ?? string.Empty, groupedData.Sum(x => x.TotalOut)?.ToString("N0") ?? string.Empty } }
)
.ToList();
}
}

View File

@ -0,0 +1,130 @@
using DocumentFormat.OpenXml.Drawing.Charts;
using DocumentFormat.OpenXml;
using DocumentFormat.OpenXml.Wordprocessing;
using DocumentFormat.OpenXml.Packaging;
namespace ProjectGasStation.Reports;
public class WordBuilder
{
private readonly string _filePath;
private readonly Document _document;
private readonly Body _body;
public WordBuilder(string filePath)
{
if (string.IsNullOrWhiteSpace(filePath))
{
throw new ArgumentNullException(nameof(filePath));
}
if (File.Exists(filePath))
{
File.Delete(filePath);
}
_filePath = filePath;
_document = new Document();
_body = _document.AppendChild(new Body());
}
public WordBuilder AddHeader(string header)
{
var paragraph = _body.AppendChild(new Paragraph());
var run = paragraph.AppendChild(new Run());
var runProperties = run.AppendChild(new RunProperties());
runProperties.AppendChild(new Bold());
run.AppendChild(new Text(header));
return this;
}
public WordBuilder AddParagraph(string text)
{
var paragraph = _body.AppendChild(new Paragraph());
var run = paragraph.AppendChild(new Run());
run.AppendChild(new Text(text));
return this;
}
public WordBuilder AddTable(int[] widths, List<string[]> data)
{
if (widths == null || widths.Length == 0)
{
throw new ArgumentNullException(nameof(widths));
}
if (data == null || data.Count == 0)
{
throw new ArgumentNullException(nameof(data));
}
if (data.Any(x => x.Length != widths.Length))
{
throw new InvalidOperationException("widths.Length != data.Length");
}
var table = new Table();
table.AppendChild(new TableProperties(
new TableBorders(
new TopBorder()
{
Val = new
EnumValue<BorderValues>(BorderValues.Single),
Size = 12
},
new BottomBorder()
{
Val = new
EnumValue<BorderValues>(BorderValues.Single),
Size = 12
},
new LeftBorder()
{
Val = new
EnumValue<BorderValues>(BorderValues.Single),
Size = 12
},
new RightBorder()
{
Val = new
EnumValue<BorderValues>(BorderValues.Single),
Size = 12
},
new InsideHorizontalBorder()
{
Val = new
EnumValue<BorderValues>(BorderValues.Single),
Size = 12
},
new InsideVerticalBorder()
{
Val = new
EnumValue<BorderValues>(BorderValues.Single),
Size = 12
}
)
));
var tr = new TableRow();
for (var j = 0; j < widths.Length; ++j)
{
tr.Append(new TableCell(
new TableCellProperties(new TableCellWidth()
{
Width =
widths[j].ToString()
}),
new Paragraph(new Run(new RunProperties(new Bold()), new
Text(data.First()[j])))));
}
table.Append(tr);
table.Append(data.Skip(1).Select(x =>
new TableRow(x.Select(y => new TableCell(new Paragraph(new Run(new Text(y))))))));
_body.Append(table);
return this;
}
public void Build()
{
using var wordDocument = WordprocessingDocument.Create(_filePath,
WordprocessingDocumentType.Document);
var mainPart = wordDocument.AddMainDocumentPart();
mainPart.Document = _document;
}
}

View File

@ -0,0 +1,12 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ProjectGasStation.Repositories;
public interface IConnectionString
{
public string ConnectionString { get; }
}

View File

@ -0,0 +1,11 @@
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories;
public interface IContractorFuelRepository
{
IEnumerable<ContractorFuel> ReadContractorFuels(DateTime? dateFrom = null, DateTime? dateTo = null,
int? fuelId = null);
void CreateContractorFuel(ContractorFuel contractorFuel);
void DeleteContractorFuel(int id);
}

View File

@ -0,0 +1,12 @@
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories;
public interface IContractorRepository
{
IEnumerable<Contractor> ReadContractors();
Contractor ReadContractorById(int id);
void CreateContractor(Contractor contractor);
void UpdateContractor(Contractor contractor);
void DeleteContractor(int id);
}

View File

@ -0,0 +1,12 @@
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories;
public interface IFuelRepository
{
IEnumerable<Fuel> ReadFuels();
Fuel ReadFuelById(int id);
void CreateFuel(Fuel fuel);
void UpdateFuel(Fuel fuel);
void DeleteFuel(int id);
}

View File

@ -0,0 +1,11 @@
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories;
public interface IFuelSaleRepository
{
IEnumerable<FuelSale> ReadFuelSales(DateTime? dateFrom = null, DateTime? dateTo = null,
int? fuelId = null);
void CreateFuelSale(FuelSale fuel);
void DeleteFuelSale(int id);
}

View File

@ -0,0 +1,12 @@
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories;
public interface ISalespersonRepository
{
IEnumerable<Salesperson> ReadSalespersons();
Salesperson ReadSalespersonById(int id);
void CreateSalesperson(Salesperson salesperson);
void UpdateSalesperson(Salesperson salesperson);
void DeleteSalesperson(int id);
}

View File

@ -0,0 +1,12 @@
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories;
public interface IShiftRepository
{
IEnumerable<Shift> ReadShifts();
Shift ReadShiftById(int id);
void CreateShift(Shift shift);
void UpdateShift(Shift shift);
void DeleteShift(int id);
}

View File

@ -0,0 +1,6 @@
namespace ProjectGasStation.Repositories.Implementations;
public class ConnectionString : IConnectionString
{
string IConnectionString.ConnectionString => "Host=localhost;Port=5432;Username=postgres;Password=030405;Database=OTP";
}

View File

@ -0,0 +1,150 @@
using Dapper;
using DocumentFormat.OpenXml.Spreadsheet;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Npgsql;
using PdfSharp.Pdf;
using ProjectGasStation.Entities;
using System.Transactions;
namespace ProjectGasStation.Repositories.Implementations;
public class ContractorFuelRepository : IContractorFuelRepository
{
private readonly IConnectionString _connectionString;
private readonly ILogger<ContractorFuelRepository> _logger;
public ContractorFuelRepository(IConnectionString connectionString, ILogger<ContractorFuelRepository> logger)
{
_connectionString = connectionString;
_logger = logger;
}
public void CreateContractorFuel(ContractorFuel contractorFuel)
{
_logger.LogInformation("Добавление объекта");
_logger.LogDebug("Объект: {json}",
JsonConvert.SerializeObject(contractorFuel));
try
{
using var connection = new
NpgsqlConnection(_connectionString.ConnectionString);
connection.Open();
using var transaction = connection.BeginTransaction();
var queryInsert = @"
INSERT INTO ContractorFuel (ContractorId, Date)
VALUES (@ContractorId, @Date);
SELECT MAX(Id) FROM ContractorFuel";
var contractorFuelId =
connection.QueryFirst<int>(queryInsert, contractorFuel, transaction);
var querySubInsert = @"
INSERT INTO ContractorFuelFuel (ContractorFuelId, FuelId, Quantity)
VALUES (@ContractorFuelId, @FuelId, @Quantity)";
foreach (var elem in contractorFuel.ContractorFuelFuel)
{
connection.Execute(querySubInsert, new
{
contractorFuelId,
elem.FuelId,
elem.Quantity
}, transaction);
}
transaction.Commit();
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при добавлении объекта");
throw;
}
}
public void DeleteContractorFuel(int id)
{
_logger.LogInformation("Удаление объекта");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
connection.Open();
using var transaction = connection.BeginTransaction();
var queryDeleteSub = @"
DELETE FROM ContractorFuelFuel
WHERE ContractorFuelId = @id";
connection.Execute(queryDeleteSub, new { id }, transaction);
var queryDelete = @"
DELETE FROM ContractorFuel
WHERE Id = @id";
connection.Execute(queryDelete, new { id }, transaction);
transaction.Commit();
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при удалении объекта");
throw;
}
}
public IEnumerable<ContractorFuel> ReadContractorFuels(DateTime? dateFrom = null, DateTime? dateTo = null,
int? fuelId = null)
{
_logger.LogInformation("Получение всех объектов");
try
{
var builder = new QueryBuilder();
if (dateFrom.HasValue)
{
builder.AddCondition("cf.Date >= @dateFrom");
}
if (dateTo.HasValue)
{
builder.AddCondition("cf.Date <= @dateTo");
}
if (fuelId.HasValue)
{
builder.AddCondition("cff.FuelId = @fuelId");
}
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = $@"SELECT
cf.*,
c.Name as ContractorName,
cff.FuelId,
cff.Quantity,
f.Type as FuelName
FROM ContractorFuel cf
LEFT JOIN Contractor c on c.Id = cf.ContractorId
INNER JOIN ContractorFuelFuel cff on cff.ContractorFuelId = cf.Id
LEFT JOIN Fuel f on f.Id = cff.FuelId
{builder.Build()}";
var contractorsDict = new Dictionary<int, List<ContractorFuelFuel>>();
var contractorFuels = connection.Query<ContractorFuel, ContractorFuelFuel, ContractorFuel>(querySelect,
(contractor, contractorFuel) =>
{
if (!contractorsDict.TryGetValue(contractor.Id, out var ccf))
{
ccf = [];
contractorsDict.Add(contractor.Id, ccf);
}
ccf.Add(contractorFuel);
return contractor;
}, splitOn: "FuelId", param: new { dateFrom, dateTo, fuelId });
_logger.LogDebug("Полученные объекты: {json}",
JsonConvert.SerializeObject(contractorFuels));
return contractorsDict.Select(x =>
{
var cf = contractorFuels.First(y => y.Id == x.Key);
cf.SetContractorFuelFuel(x.Value);
return cf;
}).ToArray();
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при чтении объектов");
throw;
}
}
}

View File

@ -0,0 +1,122 @@
using Dapper;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Npgsql;
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories.Implementations;
public class ContractorRepository : IContractorRepository
{
private readonly IConnectionString _connectionString;
private readonly ILogger<ContractorRepository> _logger;
public ContractorRepository(IConnectionString connectionString, ILogger<ContractorRepository> logger)
{
_connectionString = connectionString;
_logger = logger;
}
public void CreateContractor(Contractor contractor)
{
_logger.LogInformation("Добавление объекта");
_logger.LogDebug("Объект: {json}", JsonConvert.SerializeObject(contractor));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryInsert = @"
INSERT INTO Contractor (Name, Types)
VALUES (@Name, @Types)";
connection.Execute(queryInsert, contractor);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при добавлении объекта");
throw;
}
}
public void DeleteContractor(int id)
{
_logger.LogInformation("Удаление объекта");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryDelete = @"
DELETE FROM Contractor
WHERE Id=@id";
connection.Execute(queryDelete, new { id });
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при удалении объекта");
throw;
}
}
public Contractor ReadContractorById(int id)
{
_logger.LogInformation("Получение объекта по идентификатору");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = @"
SELECT * FROM Contractor
WHERE Id=@id";
var contractor = connection.QueryFirst<Contractor>(querySelect, new { id });
_logger.LogDebug("Найденный объект: {json}",
JsonConvert.SerializeObject(contractor));
return contractor;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при поиске объекта");
throw;
}
}
public IEnumerable<Contractor> ReadContractors()
{
_logger.LogInformation("Получение всех объектов");
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = "SELECT * FROM Contractor";
var contractors = connection.Query<Contractor>(querySelect);
_logger.LogDebug("Полученные объекты: {json}",
JsonConvert.SerializeObject(contractors));
return contractors;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при чтении объектов");
throw;
}
}
public void UpdateContractor(Contractor contractor)
{
_logger.LogInformation("Редактирование объекта");
_logger.LogDebug("Объект: {json}",
JsonConvert.SerializeObject(contractor));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryUpdate = @"
UPDATE Contractor
SET
Name=@Name,
Types=@Types
WHERE Id=@Id";
connection.Execute(queryUpdate, contractor);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при редактировании объекта");
throw;
}
}
}

View File

@ -0,0 +1,122 @@
using Dapper;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Npgsql;
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories.Implementations;
public class FuelRepository : IFuelRepository
{
private readonly IConnectionString _connectionString;
private readonly ILogger<FuelRepository> _logger;
public FuelRepository(IConnectionString connectionString, ILogger<FuelRepository> logger)
{
_connectionString = connectionString;
_logger = logger;
}
public void CreateFuel(Fuel fuel)
{
_logger.LogInformation("Добавление объекта");
_logger.LogDebug("Объект: {json}", JsonConvert.SerializeObject(fuel));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryInsert = @"
INSERT INTO Fuel (Type, Price)
VALUES (@Type, @Price)";
connection.Execute(queryInsert, fuel);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при добавлении объекта");
throw;
}
}
public void DeleteFuel(int id)
{
_logger.LogInformation("Удаление объекта");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryDelete = @"
DELETE FROM Fuel
WHERE Id=@id";
connection.Execute(queryDelete, new { id });
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при удалении объекта");
throw;
}
}
public Fuel ReadFuelById(int id)
{
_logger.LogInformation("Получение объекта по идентификатору");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = @"
SELECT * FROM Fuel
WHERE Id=@id";
var fuel = connection.QueryFirst<Fuel>(querySelect, new { id });
_logger.LogDebug("Найденный объект: {json}",
JsonConvert.SerializeObject(fuel));
return fuel;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при поиске объекта");
throw;
}
}
public IEnumerable<Fuel> ReadFuels()
{
_logger.LogInformation("Получение всех объектов");
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = "SELECT * FROM Fuel";
var fuels = connection.Query<Fuel>(querySelect);
_logger.LogDebug("Полученные объекты: {json}",
JsonConvert.SerializeObject(fuels));
return fuels;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при чтении объектов");
throw;
}
}
public void UpdateFuel(Fuel fuel)
{
_logger.LogInformation("Редактирование объекта");
_logger.LogDebug("Объект: {json}",
JsonConvert.SerializeObject(fuel));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryUpdate = @"
UPDATE Fuel
SET
Type=@Type,
Price=@Price
WHERE Id=@Id";
connection.Execute(queryUpdate, fuel);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при редактировании объекта");
throw;
}
}
}

View File

@ -0,0 +1,149 @@
using Dapper;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Npgsql;
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories.Implementations;
public class FuelSaleRepository : IFuelSaleRepository
{
private readonly IConnectionString _connectionString;
private readonly ILogger<FuelSaleRepository> _logger;
public FuelSaleRepository(IConnectionString connectionString, ILogger<FuelSaleRepository> logger)
{
_connectionString = connectionString;
_logger = logger;
}
public void CreateFuelSale(FuelSale fuel)
{
_logger.LogInformation("Добавление объекта");
_logger.LogDebug("Объект: {json}",
JsonConvert.SerializeObject(fuel));
try
{
using var connection = new
NpgsqlConnection(_connectionString.ConnectionString);
connection.Open();
using var transaction = connection.BeginTransaction();
var queryInsert = @"
INSERT INTO FuelSale (SalespersonId, ShiftId, SaleDate)
VALUES (@SalespersonId, @ShiftId, @SaleDate);
SELECT MAX(Id) FROM FuelSale";
var fuelSaleId =
connection.QueryFirst<int>(queryInsert, fuel, transaction);
var querySubInsert = @"
INSERT INTO FuelFuelSale (FuelSaleId, FuelId, Quantity)
VALUES (@FuelSaleId, @FuelId, @Quantity)";
foreach (var elem in fuel.FuelFuelSale)
{
connection.Execute(querySubInsert, new
{
fuelSaleId,
elem.FuelId,
elem.Quantity
}, transaction);
}
transaction.Commit();
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при добавлении объекта");
throw;
}
}
public IEnumerable<FuelSale> ReadFuelSales(DateTime? dateFrom = null, DateTime? dateTo = null, int? fuelId = null)
{
_logger.LogInformation("Получение всех объектов");
try
{
var builder = new QueryBuilder();
if (dateFrom.HasValue)
{
builder.AddCondition("fs.SaleDate >= @dateFrom");
}
if (dateTo.HasValue)
{
builder.AddCondition("fs.SaleDate <= @dateTo");
}
if (fuelId.HasValue)
{
builder.AddCondition("ffs.FuelId = @fuelId");
}
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = $@"SELECT
fs.*,
CONCAT(s.LastName, ' ', s.FirstName) as SalespersonName,
sh.Type as TypeShift,
ffs.FuelId,
ffs.Quantity,
f.Type as FuelName
FROM FuelSale fs
LEFT JOIN Salesperson s on s.Id = fs.SalespersonId
LEFT JOIN Shift sh on sh.id = fs.ShiftId
INNER JOIN FuelFuelSale ffs on ffs.FuelSaleId = fs.Id
LEFT JOIN Fuel f on f.id = ffs.FuelId
{builder.Build()}";
var salesDict = new Dictionary<int, List<FuelFuelSale>>();
var fuelSales = connection.Query<FuelSale, FuelFuelSale, FuelSale>(querySelect,
(sale, fuelSale) =>
{
if (!salesDict.TryGetValue(sale.Id, out var fss))
{
fss = [];
salesDict.Add(sale.Id, fss);
}
fss.Add(fuelSale);
return sale;
}, splitOn: "FuelId", param: new { dateFrom, dateTo, fuelId });
_logger.LogDebug("Полученные объекты: {json}",
JsonConvert.SerializeObject(fuelSales));
return salesDict.Select(x =>
{
var fs = fuelSales.First(y => y.Id == x.Key);
fs.SetFuelFuelSale(x.Value);
return fs;
}).ToArray();
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при чтении объектов");
throw;
}
}
public void DeleteFuelSale(int id)
{
_logger.LogInformation("Удаление объекта");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
connection.Open();
using var transaction = connection.BeginTransaction();
var queryDeleteSub = @"
DELETE FROM FuelFuelSale
WHERE FuelSaleId = @id";
connection.Execute(queryDeleteSub, new { id }, transaction);
var queryDelete = @"
DELETE FROM FuelSale
WHERE Id = @id";
connection.Execute(queryDelete, new { id }, transaction);
transaction.Commit();
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при удалении объекта");
throw;
}
}
}

View File

@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ProjectGasStation.Repositories.Implementations;
internal class QueryBuilder
{
private readonly StringBuilder _builder;
public QueryBuilder()
{
_builder = new();
}
public QueryBuilder AddCondition(string condition)
{
if (_builder.Length > 0)
{
_builder.Append(" AND ");
}
_builder.Append(condition);
return this;
}
public string Build()
{
if (_builder.Length == 0)
{
return string.Empty;
}
return $"WHERE {_builder}";
}
}

View File

@ -0,0 +1,122 @@
using Dapper;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Npgsql;
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories.Implementations;
public class SalespersonRepository : ISalespersonRepository
{
private readonly IConnectionString _connectionString;
private readonly ILogger<SalespersonRepository> _logger;
public SalespersonRepository(IConnectionString connectionString, ILogger<SalespersonRepository> logger)
{
_connectionString = connectionString;
_logger = logger;
}
public void CreateSalesperson(Salesperson salesperson)
{
_logger.LogInformation("Добавление объекта");
_logger.LogDebug("Объект: {json}", JsonConvert.SerializeObject(salesperson));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryInsert = @"
INSERT INTO Salesperson (FirstName, LastName)
VALUES (@FirstName, @LastName)";
connection.Execute(queryInsert, salesperson);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при добавлении объекта");
throw;
}
}
public void DeleteSalesperson(int id)
{
_logger.LogInformation("Удаление объекта");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryDelete = @"
DELETE FROM Salesperson
WHERE Id=@id";
connection.Execute(queryDelete, new { id });
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при удалении объекта");
throw;
}
}
public Salesperson ReadSalespersonById(int id)
{
_logger.LogInformation("Получение объекта по идентификатору");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = @"
SELECT * FROM Salesperson
WHERE Id=@id";
var salesperson = connection.QueryFirst<Salesperson>(querySelect, new { id });
_logger.LogDebug("Найденный объект: {json}",
JsonConvert.SerializeObject(salesperson));
return salesperson;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при поиске объекта");
throw;
}
}
public IEnumerable<Salesperson> ReadSalespersons()
{
_logger.LogInformation("Получение всех объектов");
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = "SELECT * FROM Salesperson";
var salespersons = connection.Query<Salesperson>(querySelect);
_logger.LogDebug("Полученные объекты: {json}",
JsonConvert.SerializeObject(salespersons));
return salespersons;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при чтении объектов");
throw;
}
}
public void UpdateSalesperson(Salesperson salesperson)
{
_logger.LogInformation("Редактирование объекта");
_logger.LogDebug("Объект: {json}",
JsonConvert.SerializeObject(salesperson));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryUpdate = @"
UPDATE Salesperson
SET
FirstName=@FirstName,
LastName=@LastName
WHERE Id=@Id";
connection.Execute(queryUpdate, salesperson);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при редактировании объекта");
throw;
}
}
}

View File

@ -0,0 +1,124 @@
using Dapper;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Npgsql;
using ProjectGasStation.Entities;
namespace ProjectGasStation.Repositories.Implementations;
public class ShiftRepository : IShiftRepository
{
private readonly IConnectionString _connectionString;
private readonly ILogger<ShiftRepository> _logger;
public ShiftRepository(IConnectionString connectionString, ILogger<ShiftRepository> logger)
{
_connectionString = connectionString;
_logger = logger;
}
public void CreateShift(Shift shift)
{
_logger.LogInformation("Добавление объекта");
_logger.LogDebug("Объект: {json}", JsonConvert.SerializeObject(shift));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryInsert = @"
INSERT INTO Shift (StartTime, EndTime, Date, Type)
VALUES (@StartTime, @EndTime, @Date, @Type)";
connection.Execute(queryInsert, shift);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при добавлении объекта");
throw;
}
}
public void DeleteShift(int id)
{
_logger.LogInformation("Удаление объекта");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryDelete = @"
DELETE FROM Shift
WHERE Id=@id";
connection.Execute(queryDelete, new { id });
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при удалении объекта");
throw;
}
}
public Shift ReadShiftById(int id)
{
_logger.LogInformation("Получение объекта по идентификатору");
_logger.LogDebug("Объект: {id}", id);
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = @"
SELECT * FROM Shift
WHERE Id=@id";
var shift = connection.QueryFirst<Shift>(querySelect, new { id });
_logger.LogDebug("Найденный объект: {json}",
JsonConvert.SerializeObject(shift));
return shift;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при поиске объекта");
throw;
}
}
public IEnumerable<Shift> ReadShifts()
{
_logger.LogInformation("Получение всех объектов");
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var querySelect = "SELECT * FROM Shift";
var shifts = connection.Query<Shift>(querySelect);
_logger.LogDebug("Полученные объекты: {json}",
JsonConvert.SerializeObject(shifts));
return shifts;
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при чтении объектов");
throw;
}
}
public void UpdateShift(Shift shift)
{
_logger.LogInformation("Редактирование объекта");
_logger.LogDebug("Объект: {json}",
JsonConvert.SerializeObject(shift));
try
{
using var connection = new NpgsqlConnection(_connectionString.ConnectionString);
var queryUpdate = @"
UPDATE Shift
SET
StartTime=@StartTime,
EndTime=@EndTime,
Date=@Date,
Type=@Type
WHERE Id=@Id";
connection.Execute(queryUpdate, shift);
}
catch (Exception ex)
{
_logger.LogError(ex, "Ошибка при редактировании объекта");
throw;
}
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.8 MiB

View File

@ -0,0 +1,15 @@
{
"Serilog": {
"Using": [ "Serilog.Sinks.File" ],
"MinimumLevel": "Debug",
"WriteTo": [
{
"Name": "File",
"Args": {
"path": "Logs/gas_log.txt",
"rollingInterval": "Day"
}
}
]
}
}