using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;

namespace Server
{
    class Program
    {
       public static gr672_pgvEntities db = new gr672_pgvEntities();
        static void Main(string[] args)
        {

           Listen();
           Console.Read();
        }

        public static async void Listen()
        {
            HttpListener listener = new HttpListener();
            listener.Prefixes.Add($"http://127.0.0.1:8080/");
            listener.Start();
            Console.WriteLine("Ожидание подключений...");
            while (true)
            {
                HttpListenerContext context = await listener.GetContextAsync();
                HttpListenerRequest request = context.Request;
                //Все заправочные станции на которых есть выбранный вид топлива
                if (request.RawUrl.Contains("/stations?fuel") && request.HttpMethod == "GET")
                {
                    string NameFuel = request.RawUrl.Split('=')[1];
                    HttpListenerResponse response = context.Response;
                    List<RootFuelInStation> rootFuelInStations  = new List<RootFuelInStation>();
                    var GasStation = db.FuelTypeOnGasStation.Where(x => x.FuelType.NameFuelType == NameFuel).ToList();
                    foreach (var item in GasStation)
                    {
                        rootFuelInStations.Add(new RootFuelInStation() { GasStationID = item.IDGasStation, Address = item.GasStation.Address, Price = item.Price });
                    }
                    var Json = JsonConvert.SerializeObject(rootFuelInStations);
                    byte[] buffer = System.Text.Encoding.UTF8.GetBytes(Json);
                    response.ContentLength64 = buffer.Length;
                    Stream output = response.OutputStream;
                    output.Write(buffer, 0, buffer.Length);
                    output.Close();
                    Console.WriteLine($"{Json}");
                }
                //Информация о заправочной станции
                if (request.RawUrl.Contains("/getStationInfo?id") && request.HttpMethod == "GET")
                {
                    int IDGasStation = Convert.ToInt32( request.RawUrl.Split('=')[1]);
                    var GasStation = db.GasStation.Find(IDGasStation);
                    if (GasStation == null)
                    {
                        HttpListenerResponse response = context.Response;
                        byte[] buffer = Encoding.UTF8.GetBytes("АЗС не найдено");
                        response.ContentLength64 = buffer.Length;
                        Stream output = response.OutputStream;
                        output.Write(buffer, 0, buffer.Length);
                        output.Close();
                        Console.WriteLine("АЗС не найдено");
                    }
                    else
                    {
                        RootDataOfGasStation dataOfGasStation = new RootDataOfGasStation();
                        dataOfGasStation.GasStationID = GasStation.GasStationID;
                        dataOfGasStation.Address = GasStation.Address;
                        List<FuelInCurrentGasStation> rootFuelTypes = new List<FuelInCurrentGasStation>();

                        foreach (var item in GasStation.FuelTypeOnGasStation)
                        {
                            rootFuelTypes.Add(new FuelInCurrentGasStation()
                            { IDFuelType = item.IDFuelType, AmountOfFuel = item.AmountOfFuel, Price = item.Price, NameFuelType = item.FuelType.NameFuelType });
                        }
                        dataOfGasStation.FuelInCurrentGasStation = rootFuelTypes;
                        var Json = JsonConvert.SerializeObject(dataOfGasStation);
                        byte[] buffer = Encoding.UTF8.GetBytes(Json);
                        HttpListenerResponse response = context.Response;
                        response.ContentLength64 = buffer.Length;
                        Stream output = response.OutputStream;
                        output.Write(buffer, 0, buffer.Length);
                        output.Close();
                        Console.WriteLine($"{Json}");
                    }

                }
                //Добавление или редактирование данных о заправочной станции
                if (request.RawUrl.Contains("/setStation") && request.HttpMethod == "POST")
                {
                    StreamReader reader = new StreamReader(request.InputStream, Encoding.UTF8);
                    string Json = await reader.ReadToEndAsync();
                    RootDataOfGasStation DataOfGasStation = JsonConvert.DeserializeObject<RootDataOfGasStation>(Json);
                    //Поиск заправочной станции
                    var FindGasStation = db.GasStation.Find(DataOfGasStation.GasStationID);
                    if (FindGasStation == null)
                    {
                        //Добавление новой заправочной станции
                        GasStation NewGasStation = new GasStation()
                        { 
                            GasStationID = DataOfGasStation.GasStationID,
                            Address = DataOfGasStation.Address
                        };
                        db.GasStation.Add(NewGasStation);
                        foreach (var item in DataOfGasStation.FuelInCurrentGasStation)
                        {
                            FuelTypeOnGasStation fuelTypeOnGasStation = new FuelTypeOnGasStation()
                            {
                                IDGasStation = NewGasStation.GasStationID,
                                IDFuelType = item.IDFuelType,
                                AmountOfFuel = item.AmountOfFuel,
                                Price = item.Price
                            };
                            db.FuelTypeOnGasStation.Add(fuelTypeOnGasStation);
                        }
                        db.SaveChanges();
                    }
                    else
                    {
                        //Редактирование заправочной станции
                        FindGasStation.GasStationID = DataOfGasStation.GasStationID;
                        FindGasStation.Address = DataOfGasStation.Address;
                        foreach (var item in DataOfGasStation.FuelInCurrentGasStation)
                        {
                            //Поиск цены на топливо
                            FuelTypeOnGasStation FindfuelTypeOnGasStation = db.FuelTypeOnGasStation.
                                FirstOrDefault(x => x.IDGasStation == FindGasStation.GasStationID && x.IDFuelType == item.IDFuelType);
                            if (FindfuelTypeOnGasStation == null)
                            {
                                //Добавление цен на топливо
                                FuelTypeOnGasStation fuelTypeOnGasStation = new FuelTypeOnGasStation()
                                {
                                    IDGasStation = FindGasStation.GasStationID,
                                    IDFuelType = item.IDFuelType,
                                    AmountOfFuel = item.AmountOfFuel,
                                    Price = item.Price
                                };
                                db.FuelTypeOnGasStation.Add(fuelTypeOnGasStation);
                            }
                            else
                            {
                                //Редактирование цен на топливо
                                FindfuelTypeOnGasStation.Price = item.Price;
                                FindfuelTypeOnGasStation.AmountOfFuel = item.AmountOfFuel;
                            }
                            db.SaveChanges();
                        }
                    }
                    HttpListenerResponse response = context.Response;
                    byte[] buffer = Encoding.UTF8.GetBytes("Выполненно");
                    response.ContentLength64 = buffer.Length;
                    Stream output = response.OutputStream;
                    output.Write(buffer, 0, buffer.Length);
                    output.Close();
                    Console.WriteLine("Выполненно");
                }

                if (request.RawUrl.Contains("/FindOrAddCar") && request.HttpMethod == "POST")
                {
                    StreamReader reader = new StreamReader(request.InputStream, Encoding.UTF8);
                    string Json = await reader.ReadToEndAsync();
                    DataOfCamera dataOfCamera = JsonConvert.DeserializeObject<DataOfCamera>(Json);
                    db.DataOfCamera.Add(dataOfCamera);
                    Car FindCar = db.Car.FirstOrDefault(x => x.CarNumber == dataOfCamera.CarNumber);
                    RootDataOfCar rootDataOfCar = new RootDataOfCar();
                    if (FindCar == null)
                    {
                        Car ResponseCar = new Car { CarNumber = dataOfCamera.CarNumber, VolumeTank = null, IDClient = null};
                        db.Car.Add(ResponseCar);
                        db.SaveChanges();

                        rootDataOfCar = new RootDataOfCar
                        {
                            CarID = ResponseCar.CarID,
                            CarNumber = ResponseCar.CarNumber,
                            VolumeTank = FindCar.VolumeTank,
                            CardOfCars = null
                        };
                    }
                    else
                    {
                        List<RootDataOfCard> CardOfCars = FindCar.IDClient is null ? null : new List<RootDataOfCard>();
                        foreach (var item in FindCar.Client.Card.ToList())
                        {
                            CardOfCars.Add(new RootDataOfCard {
                                CardID = item.CardID,
                                CardExpDate = item.CardExpDate,
                                Balance = item.Balance,
                                CardHolder = item.Client.LastName + " " + item.Client.Name,
                                IDCardIssuer = item.IDCardIssuer,
                                IDCardType = item.IDCardType,
                                NumberCard = item.NumberCard
                            });
                        }

                        rootDataOfCar = new RootDataOfCar
                        {
                            CarID = FindCar.CarID,
                            CarNumber = FindCar.CarNumber,
                            VolumeTank = FindCar.VolumeTank,
                            CardOfCars = CardOfCars
                        };

                    }
                    Json = JsonConvert.SerializeObject(rootDataOfCar);
                    HttpListenerResponse response = context.Response;
                    byte[] buffer = Encoding.UTF8.GetBytes(Json);
                    response.ContentLength64 = buffer.Length;
                    Stream output = response.OutputStream;
                    output.Write(buffer, 0, buffer.Length);
                    output.Close();
                    Console.WriteLine(Json);

                }

            }

        }

    }
}
