#!/usr/local/cpanel/3rdparty/bin/perl

package Lsws::lswsAdminBin;

use utf8;
use strict;
use Data::Dumper;
use File::Path qw(make_path);
use File::Touch;
use Archive::Extract;
use Cwd qw(abs_path);
use IPC::Run;

#Note: not using "use IPC::Run qw(run);" to avoid conflict with
# "__PACKAGE__->run()" line.


#Make this module inherit from this "groundwork" admin module.
#This eliminates a large swath of the boilerplate code that admin #modules used to require!
use parent 'Cpanel::AdminBin::Script::Call';

#Run the module as a script if (and only if) it is called that way.
#This "modulino" approach helps to facilitate testing and code
#reusability; for example, you could put some of this class's methods
#into a base class, then have 2 or more admin modules inherit
#from that base class.
__PACKAGE__->run() if !caller;

#This special function is a "whitelist" of actions that
#a caller may call. Anything not listed here cannot be called.
#
#By convention, these functions are named
#in ALLCAPS_SNAKE_CASE.
sub _actions {
    return qw(
        IS_EA4
        GET_WP_PHP_BINARY
        EXEC_ISSUE_CMD
        RETRIEVE_LSCWP_TRANSLATION
        REMOVE_LSCWP_TRANSLATION_ZIP
        REMOVE_NEW_LSCWP_FLAG_FILE
    );
}

sub IS_EA4 {
    
    if ( -e '/etc/cpanel/ea4/is_ea4' ) {
        return 1;
    }
    else {
        return 0;
    }
}

sub GET_WP_PHP_BINARY {
    my ($self, $username, $cmd) = @_;

    my @suCmd = _getSuCmdArr($username);
    
    my @fullCmd = ();
    push @fullCmd, @suCmd;
    push @fullCmd, $cmd;
    
    my $output = '';

    IPC::Run::run \@fullCmd, \undef, \$output;

    chomp($output);

    return $output;
}

sub EXEC_ISSUE_CMD {
    my ($self, $username, $cmd) = @_;

    my @suCmd = _getSuCmdArr($username);

    my @fullCmd = ();
    push @fullCmd, @suCmd;
    push @fullCmd, $cmd;

    my $output = '';

    IPC::Run::run \@fullCmd, \undef, \$output;

    # Looking for UserCommand custom exit/return value here
    my $retVar = $? >> 8;

    chomp($output);

    return ( retVar => $retVar, output => $output);
}

sub RETRIEVE_LSCWP_TRANSLATION {
    my ($self, $locale, $pluginVer) = @_;

    # Strip invalid chars from input
    $locale =~ s/[^A-Za-z_]//g;
    $pluginVer =~ s/[^0-9.]//g;

    my $translationDir = '/usr/src/litespeed-wp-plugin/' . $pluginVer . '/translations';
    my $zipFile = $locale . '.zip';
    my $localZipFile = $translationDir . '/' . $zipFile;

    if ( ! -d $translationDir ) {
        make_path($translationDir, { chmod => 0755 });
    }

    touch($translationDir . '/' . '.ls_translation_check_' . $locale);

    # downloads.wordpress.org looks to always return a '200 OK' status,
    # even when serving a 404 page. As such invalid downloads can only be
    # checked through user failure to unzip through WP func unzip_file()
    # as we do not assume that root has the ability to unzip.
    my $url = 'https://downloads.wordpress.org/translation/plugin/litespeed-cache/' . $pluginVer
            . '/' . $locale . '.zip';

    my @wget_command = (
        "wget",
        "-q",
        "--tries=1",
        "--no-check-certificate",
        $url,
        "-P",
        $translationDir
    );

    system(@wget_command);

    if ( $? == -1 || $? & 127 || ($? >> 8) != 0 ) {
        return 0;
    }

    # WordPress user can unzip for us if this call fails.
    my $m = Archive::Extract->new( archive => $localZipFile );
    $m->extract( to => $translationDir );

    return 1;
}

sub REMOVE_LSCWP_TRANSLATION_ZIP {
    my ($self, $locale, $pluginVer) = @_;

    # Strip invalid chars from input
    $locale =~ s/[^A-Za-z_]//g;
    $pluginVer =~ s/[^0-9.]//g;

    my $dlDir = '/usr/src/litespeed-wp-plugin';

    my $zipFile =
            abs_path($dlDir . '/' . $pluginVer . '/translations/' . $locale . '.zip');

    if ( substr($zipFile, 0, length $dlDir) eq $dlDir ) {
        unlink $zipFile;
    }
}

sub REMOVE_NEW_LSCWP_FLAG_FILE {
    my ($self, $path) = @_;

    my $flagFile = $path . '/.lscm_new_lscwp';

    if ( -f $flagFile ) {
        unlink $flagFile or return 0;
    }

    return 1;
}

sub _getSuCmdArr {
   my ($username) = @_;

    my @suCmd = (
        "su",
        $username,
        "-s",
        "/bin/bash",
        "-c"
    );

    return @suCmd;
}

1;
