#!/usr/bin/env perl6

use DSL::Translators;
use Clipboard;

my %*SUB-MAIN-OPTS = :named-anywhere;

#| Translates natural language commands into programming code.
multi sub MAIN(
        Str $command,                                      #= A string with one or many commands (separated by ';').
        Str :f(:$from-language) is copy = 'Whatever',      #= Language to translate from; one of 'Bulgarian', 'English', 'Russian', or 'Whatever'.
        Str :t(:$to-language) is copy = 'R',               #= Language to translate to: one of 'Bulgarian', 'English', 'Python', 'R', 'Raku', 'Russian', or 'WL';
        Str :$format = 'automatic',                        #= The format of the output, one of 'automatic', 'ast', 'code', 'hash', 'json', or 'raku'.
        Bool :$guess-grammar = True,                       #= Should the DSL grammar of $command of be guessed or not?
        UInt :$degree = 1,                                 #= Positive integer for the degree parallelism.
        Bool :$ast = False,                                #= Should Match object be returned for the key "CODE" or not?,
        Str :c(:$clipboard-command) is copy = 'Whatever'   #= Clipboard command to use.
               ) {

    my $formatSpec = ($ast and $format.lc (elem) <auto automatic whatever>) ?? 'code' !! $format;
    $formatSpec = 'code' when $formatSpec.lc (elem) <auto automatic whatever>;

    if $from-language.lc ∈ <Whatever Automatic Nil>>>.lc {
        my %counts = $command.subst(/\s/, '').comb.map({ $_ ∈ ('А' .. 'я') }).classify({ $_ }).map({ $_.key => $_.value.elems });
        my $total = [+] %counts.values;
        my %freqs = %counts.deepmap({ $_ / $total });
        if %freqs<True>:exists {
            $from-language = %freqs<True> ≥ 0.40 ?? 'Bulgarian' !! 'English';
            warn "Heuristic determination of the command (from-)language to be $from-language.";
        } else {
            $from-language = 'English';
        }
    }

    my $res = DSL::Translators::ToDSLCode($command,
                                          language => $from-language,
                                          format => $formatSpec,
                                          defaultTargetsSpec => $to-language,
                                          guessGrammar => $guess-grammar,
                                          :$degree, :$ast);

    say $res;

    if $clipboard-command.lc ne 'none' {
        copy-to-clipboard($res, :$clipboard-command);
    }
}

multi sub MAIN(Str $progLang,                         #= Programming language.
               Str $command,                          #= A string with one or many commands (separated by ';').
               Str :f(:$from-language) = 'Whatever',  #= The natural language to translate from.
               Str :$format = 'automatic',            #= The format of the output, one of 'automatic', 'ast', 'code', 'hash', 'json', or 'raku'.
               Bool :$guess-grammar = True,           #= Should the DSL grammar of $command of be guessed or not?
               UInt :$degree = 1,                     #= Positive integer for the degree parallelism.
               Bool :$ast = False,                    #= Should Match object be returned for the key "CODE" or not?
               Str :c(:$clipboard-command) is copy = 'Whatever'   #= Clipboard command to use.
               ) {
    MAIN($command,
            :$from-language,
            to-language => $progLang,
            :$format,
            :$guess-grammar,
            :$degree,
            :$ast,
            :$clipboard-command);
}

sub USAGE() {
    say "Translates natural language commands into programming code.";
    say $*USAGE;
    say "\n";
    my $usage = Q:c:to/EOH/;
    Details:
        If --language is 'Whatever' then:
            1. If at least 40% of the letters are Cyrillic then Bulgarian is used.
            2. Otherwise English is used.
    EOH

    say $usage ~ copy-to-clipboard(:usage-message);
}