﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;


enum NodeType { Folder, File }


class FileSystemNode
{
    public string Name { get; set; }
    public FileSystemNode Parent { get; set; }
    public List<FileSystemNode> Children { get; set; } = new List<FileSystemNode>();
    public NodeType Type { get; set; }


    public FileSystemNode(string name, NodeType type, FileSystemNode parent = null)
    {
        Name = name;
        Type = type;
        Parent = parent;
    }


    public void Show() // Tiek izsaukts kad ievada komandu dir
    {
        if (Type == NodeType.File)// pārbauda vai tas ir fails vai mape
        {
            Console.WriteLine($"/[datne] {Name}");
        }
        else
        {
            Console.WriteLine($"/[mape] {Name}");
            foreach (var child in Children)
            {
                Console.WriteLine($"  - {child.Name} ({child.Type})");
            }
        }
    }


    public FileSystemNode GetChild(string name) => Children.FirstOrDefault(c => c.Name == name);


    public bool HasChild(string name) => Children.Any(c => c.Name == name);


    public void AddChild(FileSystemNode child)// konstruktors
    {
        if (!HasChild(child.Name)) // pārbauda vai ir fails ar tādu nosaukumu
            Children.Add(child);
        else
            Console.WriteLine("Jau eksistē bērns ar tādu nosaukumu.");
    }


    public void DeleteChild(string name) // destruktors
    {
        var node = GetChild(name);
        if (node != null) // pārbauda vai tāds pastāv
        {
            if (node.Type == NodeType.Folder && node.Children.Count > 0) // pārbauda vai mape ir bērni un jautā lietotājaim vai to tiešām dzēst
            {
                Console.Write($"Mapei '{name}' ir bērni. Vai tiešām vēlaties to dzēst? (y/n): ");
                if (Console.ReadLine().ToLower() != "y") return;
            }
            Console.WriteLine($"Izdzēsts: {node.Name}");
            if (node.Type == NodeType.File && File.Exists(node.Name))
            File.Delete(node.Name);
            Children.Remove(node);
        }
        else
        {
            Console.WriteLine("Nav atrasts.");
        }
    }
}


class FileSystemSimulator
{
    FileSystemNode root = new FileSystemNode("C:", NodeType.Folder);
    FileSystemNode current;


    public FileSystemSimulator()
    {
        current = root;
    }


    public void Run()
    {
        while (true)
        {
            Console.Write($"{GetPath(current)}> ");
            var input = Console.ReadLine();
            if (string.IsNullOrEmpty(input)) continue;


            var args = input.Split(' ', 2);
            var command = args[0];
            var argument = args.Length > 1 ? args[1] : "";


            switch (command)
            {
                case "mkdir": CreateNode(argument, NodeType.Folder); break;
                case "create": CreateNode(argument, NodeType.File); break;
                case "rm": current.DeleteChild(argument); break;
                case "del": DeleteFile(argument); break;
                case "dir":
                    if (argument.StartsWith(">"))
                        WriteDirToFile(argument.Substring(1).Trim()); // ja komandā iekšā ir > tad šis tiek izpildīts
                    else
                        current.Show(); // ja ievada dir bez > tad šis
                    break;
                case "cd": ChangeDirectory(argument); break;
                case "edit": EditFile(argument); break;
                case "help":
                 Console.WriteLine();
                 Console.WriteLine("help         Parāda visas iespējamās komandas");
                 Console.WriteLine("mkdir        Piesaista jaunu mapi");
                 Console.WriteLine("create       Piesaista jaunu datni");
                 Console.WriteLine("rm           Dzēš mapi/mapes");
                 Console.WriteLine("dir          Parāda mapes bērnus");
                 Console.WriteLine("cd           Parvieto uz ievadīto mapi");
                 Console.WriteLine("edit         Parāda datnes nosaukumu");
                 Console.WriteLine("del          Izdzēš datni");
                 Console.WriteLine("exit         Aizver Programmu");
                break;
                case "exit": return;
                default:
                Console.WriteLine ("Šāda komanda nepastāv! Izmantojiet (help) lai pārādītu iespējamās komandas");
                Console.WriteLine ("Nospiežiet jebkuru taustiņu lai turninātu...");
                Console.ReadKey();
                break;
            }
        }
    }


    void CreateNode(string name, NodeType type)
    {
        if (current.HasChild(name))
        {
            Console.WriteLine("Nosaukums jau eksistē.");
            return;
        }


        var newNode = new FileSystemNode(name, type, current);
        current.AddChild(newNode);


        if (type == NodeType.File)
        {
            File.WriteAllText(name, ""); // izveido tukšu datni
        }
    }


    void DeleteFile(string name)
    {
        var node = current.GetChild(name);
        if (node != null && node.Type == NodeType.File)
        {
            if (File.Exists(name))
                File.Delete(name);
            current.Children.Remove(node);
            Console.WriteLine($"Datne {name} dzēsta.");
        }
        else
        {
            Console.WriteLine("Datne nav atrasta.");
        }
    }


    void ChangeDirectory(string name)
    {
        if (name == "..")
        {
            if (current.Parent != null)
                current = current.Parent;
            else
                Console.WriteLine("Jau atrodaties saknē.");
        }
        else if (name == "/")
        {
            current = root;
        }
        else
        {
            var node = current.GetChild(name);
            if (node != null && node.Type == NodeType.Folder)
                current = node;
            else
                Console.WriteLine("Māpe nav atrasta.");
        }
    }


    void WriteDirToFile(string filename)
    {
        var path = filename;
        var existing = current.GetChild(filename);
        if (existing != null && existing.Type == NodeType.File)
        {
            File.Delete(filename);
            current.Children.Remove(existing);
        }


        File.WriteAllLines(filename, current.Children.Select(c => $"{c.Name} ({c.Type})"));
        var newFile = new FileSystemNode(filename, NodeType.File, current);
        current.AddChild(newFile);
        Console.WriteLine($"Dati ierakstīti failā {filename}");
    }


    void EditFile(string filename)
    {
        var node = current.GetChild(filename);
        if (node == null || node.Type != NodeType.File)
        {
            Console.WriteLine("Datne nav atrasta.");
            return;
        }


        Console.WriteLine($"Datne: {node.Name}");
        if (File.Exists(node.Name))
        {
            Console.WriteLine(File.ReadAllText(node.Name));
        }
        else
        {
            Console.WriteLine("[Datne tukša vai neeksistē]");
        }
    }


    string GetPath(FileSystemNode node)
    {
        var parts = new List<string>();
        while (node != null)
        {
            parts.Insert(0, node.Name);
            node = node.Parent;
        }
        return string.Join("\\", parts);
    }
}


class Program
{
    static void Main(string[] args)
    {
        var fs = new FileSystemSimulator();
        fs.Run();
    }
}