namespace ScooterRental
{
    public class DuplicateScooterException : Exception
    {
        public DuplicateScooterException() : base("Scooter already exists")
        {

        }
    }

    internal class InvalidIdException : Exception
    {
        public InvalidIdException() : base("Id cannot be null or empty")
        {
        }
    }

    public class NegativePriceException : Exception
    {
        public NegativePriceException() : base("Price cannot be negative.")
        {
        }
    }

    public interface IRentalCompany
    {
        /// <summary>
        /// Name of the company.
        /// </summary>
        string Name { get; }
        /// <summary>
        /// Start the rent of the scooter.
        /// </summary>
        /// <param name="id">ID of the scooter</param>
        void StartRent(string id);
        /// <summary>
        /// End the rent of the scooter.
        /// </summary>
        /// <param name="id">ID of the scooter</param>
        /// <returns>The total price of rental. It has to calculated taking into account for how long time scooter was rented.
        /// If total amount per day reaches 20 EUR than timer must be stopped and restarted at beginning of next day at 0:00 am.</returns>
        decimal EndRent(string id);
        /// <summary>
        /// Income report.
        /// </summary>
        /// <param name="year">Year of the report. Sum all years if value is not set.</param>
        /// <param name="includeNotCompletedRentals">Include income from the scooters that are rented out (rental has not ended yet) and
        ///calculate rental
        /// price as if the rental would end at the time when this report was requested.</param>
        /// <returns>The total price of all rentals filtered by year if given.</returns>
        decimal CalculateIncome(int? year, bool includeNotCompletedRentals);
    }

    public interface IScooterService
    {
        /// <summary>
        /// Add scooter.
        /// </summary>
        /// <param name="id">Unique ID of the scooter</param>
        /// <param name="pricePerMinute">Rental price of the scooter per one minute</param>
        void AddScooter(string id, decimal pricePerMinute);
        /// <summary>
        /// Remove scooter. This action is not allowed for scooters if the rental is in progress.
        /// </summary>
        /// <param name="id">Unique ID of the scooter</param>
        void RemoveScooter(string id);
        /// <summary>
        /// List of scooters that belong to the company.
        /// </summary>
        /// <returns>Return a list of available scooters.</returns>
        IList<Scooter> GetScooters();
        /// <summary>
        /// Get particular scooter by ID.
        /// </summary>
        /// <param name="scooterId">Unique ID of the scooter.</param>
        /// <returns>Return a particular scooter.</returns>
        Scooter GetScooterById(string scooterId);
    }

    public class Scooter
    {
        /// <summary>
        /// Create new instance of the scooter.
        /// </summary>
        /// <param name="id">ID of the scooter.</param>
        /// <param name="pricePerMinute">Rental price of the scooter per one minute.</param>
        public Scooter(string id, decimal pricePerMinute)
        {
            Id = id;
            PricePerMinute = pricePerMinute;
        }
        /// <summary>
        /// Unique ID of the scooter.
        /// </summary>
        public string Id { get; }
        /// <summary>
        /// Rental price of the scooter per one
        ///minute.
        /// </summary>
        public decimal PricePerMinute { get; }
        /// <summary>
        /// Identify if someone is renting this
        ///scooter.
        /// </summary>
        public bool IsRented { get; set; }
    }

    public class RentalCompany : IRentalCompany
    {
        private readonly IScooterService _scooterService;
        public static List<RentedScooter> _rentedScooterList = new List<RentedScooter>(); // Make it public static
        private decimal _totalIncome = 0; // Add a field to keep track of the total income
        private DateTime _lastDay = DateTime.MinValue; // Add a field to keep track of the last day

        public RentalCompany(string name, IScooterService scooterService, List<RentedScooter> rentedScooterList)
        {
            Name = name;
            _scooterService = scooterService;
            _rentedScooterList = rentedScooterList;
        }

        public string Name { get; }
        public void StartRent(string id)
        {
            var scooter = _scooterService.GetScooterById(id);
            scooter.IsRented = true;
            _rentedScooterList.Add(new RentedScooter(scooter.Id, DateTime.Now));
        }

        public decimal EndRent(string id)
        {
            var scooter = _scooterService.GetScooterById(id);
            scooter.IsRented = false;
            var rentalRecord = _rentedScooterList.FirstOrDefault(s => s.Id == scooter.Id && !s.RentEnd.HasValue);
            rentalRecord.RentEnd = DateTime.Now;

            return (rentalRecord.RentEnd - rentalRecord.RentStart).Value.Minutes * scooter.PricePerMinute;
        }

        public decimal CalculateIncome(int? year, bool includeNotCompletedRentals)
        {
            if (!includeNotCompletedRentals)
            {
                _rentedScooterList.RemoveAll(s => !s.RentEnd.HasValue);
            }

            decimal totalIncome = 0;

            foreach (var rentedScooter in _rentedScooterList)
            {
                if (!year.HasValue || rentedScooter.RentStart.Year == year)
                {
                    var scooter = _scooterService.GetScooterById(rentedScooter.Id);

                    totalIncome += EndRent(scooter.Id);
                }
            }

            _totalIncome = totalIncome; // Update the total income

            return totalIncome;
        }
    }


    public class RentedScooter
    {
        public RentedScooter(string id, DateTime startTime)
        {
            Id = id;
            RentStart = startTime;
        }

        public string Id { get; set; }
        public DateTime RentStart { get; set; }
        public DateTime? RentEnd { get; set; }
    }



    public class ScooterService : IScooterService
    {

        private readonly List<Scooter> _scooters;
        public ScooterService(List<Scooter> scooterStorage)
        {
            _scooters = scooterStorage;
        }
        public void AddScooter(string id, decimal pricePerMinute)
        {
            if (_scooters.Any(s => s.Id == id))
            {
                throw new DuplicateScooterException();
            }
            _scooters.Add(new Scooter(id, pricePerMinute));

            if (pricePerMinute <= 0)
            {
                throw new NegativePriceException();
            }

            if (string.IsNullOrEmpty(id))
            {
                throw new InvalidIdException();
            }
        }

        public void RemoveScooter(string id)
        {
            var scooterToRemove = _scooters.FirstOrDefault(s => s.Id == id);

            if (scooterToRemove != null)
            {
                _scooters.Remove(scooterToRemove);
            }

            /*if (scooterToRemove.IsRented)
            {
                throw new Exception("Scooter is currently rented and cannot be removed.");
            }
            else
            {
                throw new Exception("Scooter not found.");

            }*/


        }

        public IList<Scooter> GetScooters()
        {
            return _scooters.ToList();
        }

        public Scooter GetScooterById(string scooterId)
        {
            return _scooters.FirstOrDefault(s => s.Id == scooterId);
        }
    }


    class Program
    {
        static void Main(string[] args)
        {
            // Create a list to store rented scooters
            List<RentedScooter> rentedScooters = new List<RentedScooter>();

            // Create a scooter service with an initial list of scooters
            List<Scooter> scooterStorage = new List<Scooter>
            {
                new Scooter("1", 1.0m),
                new Scooter("2", 0.15m),
                new Scooter("3", 0.2m)
            };
            IScooterService scooterService = new ScooterService(scooterStorage);

            // Create a rental company
            IRentalCompany rentalCompany = new RentalCompany("MyCompany", scooterService, rentedScooters);

            // Simulate scooter rentals
            rentalCompany.StartRent("1");
            Console.WriteLine("Started renting scooter 1.");

            RentalCompany._rentedScooterList.Add(new RentedScooter("1", DateTime.Now.AddMinutes(-5)));

            decimal price = rentalCompany.EndRent("1");
            Console.WriteLine($"Ended renting scooter 1. Price: {price} EUR");


            //rentalCompany.StartRent("2");
            //Console.WriteLine("Started renting scooter 2.");

            // Simulate some more time passing
            //_rentedScooterList.Add(new RentedScooter("2", DateTime.Now.AddMinutes(0)));

            //price = rentalCompany.EndRent("2");
            //Console.WriteLine($"Ended renting scooter 2. Price: {price} EUR");

            // Calculate total income for the current year (including not completed rentals)
            decimal totalIncome = rentalCompany.CalculateIncome(DateTime.Now.Year, true);
            Console.WriteLine($"Total income for the year: {totalIncome} EUR");

            // Calculate total income for the current year (excluding not completed rentals)
            totalIncome = rentalCompany.CalculateIncome(DateTime.Now.Year, false);
            Console.WriteLine($"Total income for the year (excluding not completed rentals): {totalIncome} EUR");

            // Calculate total income for all years (including not completed rentals)
            totalIncome = rentalCompany.CalculateIncome(null, true);
            Console.WriteLine($"Total income for all years: {totalIncome} EUR");

            // Calculate total income for all years (excluding not completed rentals)
            totalIncome = rentalCompany.CalculateIncome(null, false);
            Console.WriteLine($"Total income for all years (excluding not completed rentals): {totalIncome} EUR");

            // List all available scooters
            var availableScooters = scooterService.GetScooters();
            Console.WriteLine("Available Scooters:");
            foreach (var scooter in availableScooters)
            {
                Console.WriteLine($"Scooter ID: {scooter.Id}, Price per Minute: {scooter.PricePerMinute} EUR");
            }

            // Remove a scooter
            scooterService.RemoveScooter("3");
            Console.WriteLine("Removed scooter 3.");

            // List available scooters after removal
            availableScooters = scooterService.GetScooters();
            Console.WriteLine("Available Scooters after removal:");
            foreach (var scooter in availableScooters)
            {
                Console.WriteLine($"Scooter ID: {scooter.Id}, Price per Minute: {scooter.PricePerMinute} EUR");
            }

            Console.ReadLine();
        }
    }
}...   Please fix and modify EndRent and CalculateIncome methods to give desired result.  EndRent returns price per particulary scooter rental. Keep in mind: The total price of rental. It has to calculated taking into account for how long time scooter was rented. If total amount per day reaches 20 EUR than timer must be stopped and restarted at beginning of next day at 0:00 am