import java.io.*;
import java.nio.channels.FileChannel;
import java.util.LinkedList;
import java.util.Objects;
import java.util.Scanner;

public class CommandParser {

    private final Scanner scanner = new Scanner(System.in);
    private String workingDirectory=System.getProperty("user.dir");

    CommandParser(){
        //workingDirectory=System.getProperty("user.dir");
    }
    void startParsing(){

            String input = scanner.nextLine();
            String[] cmd = input.split(" ");
            if (cmd[0].equals("hello")) {
                cmdHello(cmd);
            } else if(cmd[0].equals("exit")){
                cmdExit(cmd);
            } else if(cmd[0].equals("pwd")){
                cmdPwd(cmd);
            } else if(cmd[0].equals("ls")){
                cmdLs(cmd);
            } else if(cmd[0].equals("cd")){
                cmdCd(cmd);
            } else if(cmd[0].equals("rm")){
                cmdRm(cmd);
            } else if(cmd[0].equals("mkdir")){
                cmdMkdir(cmd);
            } else if(cmd[0].equals("mv")){
                cmdMv(cmd);
            } else if(cmd[0].equals("cp")){
                cmdCp(cmd);
            } else if(cmd[0].equals("cat")){
                cmdCat(cmd);
            } else if(cmd[0].equals("head")){
                cmdHead(cmd);
            } else if(cmd[0].equals("tail")){
                cmdTail(cmd);
            } else if(cmd[0].equals("wc")){
                cmdWc(cmd);
            } else if(cmd[0].equals("length")){
                cmdLength(cmd);
            } else if(cmd[0].equals("grep")){
                cmdGrep(cmd);
            }
    }
    protected void cmdPwd(String[] cmd){


        System.out.println(workingDirectory);

        File dir = new File(workingDirectory);
        System.out.println("Fájlok és almappák száma: "+ Objects.requireNonNull(dir.listFiles()).length);

    }
    protected void cmdLs(String[] cmd){
        File dir = new File(workingDirectory);
        File[] files = dir.listFiles();

        if(files==null){
            return;
        }


        String mode = "";
        if(cmd.length>1){
            mode = cmd[1];
        }

        for(int i=0;i<files.length;i++){
            switch (mode){
                case "-l":
                    System.out.println(files[i].getName()+ " - Méret: "+(files[i].length())+"B.");
                    break;
                case "-f":
                    if(files[i].isDirectory()==false){
                        System.out.println(files[i].getName());
                    }
                    break;
                case "-d":
                    if(files[i].isDirectory()==true){
                        System.out.println(files[i].getName());
                    }
                    break;
                default:
                    System.out.println(files[i].getName());
                    break;
            }

        }
    }
    protected void cmdCd(String[] cmd){
        if(cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }
        if(cmd[1].equals("..")){
            try {
                workingDirectory = new File(workingDirectory).getParentFile().getCanonicalPath();
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
        } else {
            File f = new File(workingDirectory, cmd[1]);
            if (f.exists()) {
                try {
                    workingDirectory= f.getCanonicalPath();
                } catch (IOException e) {
                    throw new RuntimeException(e);
                }
            } else {
                System.out.println("A megadott elérési útvonal nem létezik.");
            }
        }

    }
    protected void cmdRm(String[] cmd){
        if(cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].equals("")){
            System.out.println("Üres megadott paraméter!");
            return;
        }

        File f = new File(workingDirectory, cmd[1]);
        if (f.delete()) {
            System.out.println("Fájl törölve: " + f.getName());
        } else {
            System.out.println("Fájl törlése sikertelen"+f.getName());
        }

    }
    protected void cmdMkdir(String[] cmd){
        if(cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].equals("")){
            System.out.println("Üres megadott paraméter!");
            return;
        }

        File f = new File(workingDirectory, cmd[1]);
        if (f.mkdir()) {
            System.out.println("Könyvtár létrehozva: " + f.getName());
        } else {
            System.out.println("Már létezik könyvtár ezzel a névvel: "+f.getName());
        }

    }
    protected void cmdMv(String[] cmd){
        if(cmd.length!=3){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].isEmpty() || cmd[2].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        File f = new File(workingDirectory, cmd[1]);
        File rename = new File(workingDirectory, cmd[2]);
        if (f.renameTo(rename)) {
            System.out.println("Átnevezve: " + f.getName());
        } else {
            System.out.println("Átnevezés sikertelen: "+f.getName());
        }

    }

    protected void cmdCp(String[] cmd){
        if(cmd.length!=3){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].isEmpty() || cmd[2].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        File file1 = new File(workingDirectory, cmd[1]);
        File file2 = new File(workingDirectory, cmd[2]);
        FileChannel src = null;
        try {
            src = new FileInputStream(file1).getChannel();
        } catch (FileNotFoundException e) {
            System.out.println("A fájl nem létezik!");
            throw new RuntimeException(e);
        }

        FileChannel dest = null;
        try {
            dest = new FileOutputStream(file2).getChannel();
        } catch (FileNotFoundException e) {
            System.out.println("A fájl nem létezik!");
            throw new RuntimeException(e);
        }

        try {
            dest.transferFrom(src, 0, src.size());
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

    }

    protected void cmdCat(String[] cmd){
        if(cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        File file1 = new File(workingDirectory, cmd[1]);

        try (Scanner myReader = new Scanner(file1)) {
            while (myReader.hasNextLine()) {
                String data = myReader.nextLine();
                System.out.println(data);
            }
        } catch (FileNotFoundException e) {
            System.out.println("Hiba történt a cat parancs során!");
        }

    }

    protected void cmdWc(String[] cmd){
        if(cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        File file1 = new File(workingDirectory, cmd[1]);

        String contents="";
        try (Scanner myReader = new Scanner(file1)) {
            while (myReader.hasNextLine()) {
                String data = myReader.nextLine();
                contents+=data;
            }
            System.out.println("Szavak száma: "+contents.split(" ").length);
        } catch (FileNotFoundException e) {
            System.out.println("Hiba történt a parancs során! (Fájl nem létezik)");
        }

    }

    protected void cmdLength(String[] cmd){
        if(cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        if(cmd[1].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        File file1 = new File(workingDirectory, cmd[1]);

        String contents="";
        try (Scanner myReader = new Scanner(file1)) {
            while (myReader.hasNextLine()) {
                String data = myReader.nextLine();
                contents+=data;
            }
            System.out.println("Length: "+contents.length());
        } catch (FileNotFoundException e) {
            System.out.println("Hiba történt a parancs során! (Fájl nem létezik)");
        }

    }

    protected void cmdHead(String[] cmd){
        if(cmd.length!=4 && cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        int n=10;
        File file1=null;

        if(cmd.length==4){
            n= Integer.parseInt(cmd[2]);
            file1 = new File(workingDirectory, cmd[3]);
        } else {
            file1 = new File(workingDirectory, cmd[1]);
        }

        if(cmd[1].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        try (Scanner myReader = new Scanner(file1)) {
            while (myReader.hasNextLine()&&n!=0) {
                String data = myReader.nextLine();
                System.out.println(data);
                n--;
            }
        } catch (FileNotFoundException e) {
            System.out.println("Hiba történt a head parancs során!");
        }

    }

    protected void cmdGrep(String[] cmd){
        if(cmd.length!=3){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        String pattern = ".*"+cmd[1]+".*";
        File file1 = new File(workingDirectory, cmd[2]);



        try (Scanner myReader = new Scanner(file1)) {
            while (myReader.hasNextLine()) {
                String data = myReader.nextLine();
                if(data.matches(pattern)){
                    System.out.println(data);
                }

            }
        } catch (FileNotFoundException e) {
            System.out.println("Hiba történt a grep parancs során!");
        }

    }

    protected void cmdTail(String[] cmd){
        if(cmd.length!=4 && cmd.length!=2){
            System.out.println("Hibás argumentum szám!");
            return;
        }

        int n=10;
        File file1=null;

        if(cmd.length==4){
            n= Integer.parseInt(cmd[2]);
            file1 = new File(workingDirectory, cmd[3]);
        } else {
            file1 = new File(workingDirectory, cmd[1]);
        }

        if(cmd[1].isEmpty()){
            System.out.println("Üres megadott paraméter(ek)!");
            return;
        }

        LinkedList<String> lines = new LinkedList<>();

        try (Scanner myReader = new Scanner(file1)) {
            while (myReader.hasNextLine()) {
                String data = myReader.nextLine();
                lines.add(data);
            }
        } catch (FileNotFoundException e) {
            System.out.println("Hiba történt a tail parancs során!");
        }

        String[] lines2 = new String[n];
        for(int i=0;i<n;i++){
            lines2[n-i-1]=(lines.removeLast());
        }
        for(int i=0;i<n;i++){
            System.out.println(lines2[i]);
        }

    }

    protected void cmdHello(String[] cmd){
        System.out.println("Hello world!");
    }
    protected void cmdExit(String[] cmd){
        System.exit(0);
    }
}
