<?php

/*
 * PuzzleApp
 * Webemyos
 * Jérôme Oliva
 * GNU Licence
 */

namespace Apps\EeApp\Helper;

use Core\Entity\Entity\Argument;
use Apps\EeApp\Entity\EeAppUser;
use Apps\EeApp\Entity\EeAppApp;
use Apps\EeApp\Entity\EeAppAdmin;
use Apps\EeApp\Entity\EeAppPlugin;
use Apps\EeApp\Entity\EeAppPluginApp;
use Core\Utility\File\File;
use Apps\EeApp\Helper\UploadHelper;
use Apps\EeApp\Widget\PluginForm\PluginForm;
use Apps\EeApp\Widget\PluginAppForm\PluginAppForm;
use Apps\EeApp\Widget\TemplateForm\TemplateForm;
use Apps\EeApp\Entity\EeAppTemplate;
use Apps\EeApp\Widget\MenuUserForm\MenuUserForm;
use Apps\EeApp\Entity\EeMenuUser;

class AppHelper {

    /**
     * Obtient les applications utilisateurs
     * @param type $core
     * @param type $userId
     */
    public static function GetByUser($core, $userId) {
        $appUser = new EeAppUser($core);
        $appUser->AddArgument(new Argument("Apps\EeApp\Entity\EeAppUser", "UserId", EQUAL, $userId));

        return $appUser->GetByArg();
    }

    /**
     * Obtient les app selon les critères
     * @param type $core
     */
    public static function GetByParameters($core) {
        $app = new EeAppApp($core);

        return $app->GetAll();
    }

    /**
     * Obtient toutes les app
     * @param type $core
     */
    public static function GetAll($core) {
        $app = new EeAppApp($core);
        return $app->GetAll();
    }

    /*     * *
     * Obtient les templates discponible
     */

    public static function GetTemplates($core) {
        $app = new EeAppTemplate($core);
        return $app->GetAll();
    }

    /*     * *
     * Get The App For The /Membre space
     */

    public static function GetForMember($core) {

        $apps = new EeAppApp($core);

        return $apps->Find("Member=1");
    }

    /**
     * Ajoute une app à l'utilisateur
     * @param type $core
     * @param type $appId
     */
    public static function Add($core, $appId, $appName) {
        $appUser = new EeAppUser($core);
        $appUser->UserId->Value = $core->User->IdEntite;

        if ($appId != false) {
            $appUser->AppId->Value = $appId;
        } else {
            $app = new EeAppApp($core);

            $app->GetByName($appName);
            $appId = $app->IdEntite;
            $appUser->AppId->Value = $app->IdEntite;
        }

        if (!AppHelper::UserHave($core, $appId)) {
            return $appUser->Save();
        } else {
            return $core->GetCode("EeApp.AppInDesktop");
        }
    }

    /**
     * Supprime une app a l'utilisateur
     * @param type $core
     * @param type $appId
     */
    public static function Remove($core, $appId) {
        $appUser = new EeAppUser($core);
        $appUser->GetById($appId);
        $appUser->Delete();
    }

    /**
     * Verifie si l'utilisateur à l'app
     * @param type $core
     * @param type $appId
     */
    public static function UserHave($core, $appId) {
        $appUser = new EeAppUser($core);
        $appUser->AddArgument(new Argument("Apps\EeApp\Entity\EeAppUser", "UserId", EQUAL, $core->User->IdEntite));
        $appUser->AddArgument(new Argument("Apps\EeApp\Entity\EeAppUser", "AppId", EQUAL, $appId));

        return (count($appUser->GetByArg()) > 0);
    }

    /**
     * Obtient les applications actives
     */
    public static function GetActif($core, $limit = "") {
        $app = new EeAppApp($core);
        $app->AddArgument(new Argument("Apps\EeApp\Entity\EeAppApp", "Actif", EQUAL, "1"));

        if ($limit != "") {
            $app->SetLimit(1, $limit);
        }

        return $app->GetByArg();
    }

    /**
     * Obtient les applications actives
     */
    public static function GetByCategory($core, $category) {
        //Recuperation de la categorie par son nom
        $appCategory = new EeAppCategory($core);
        $appCategory->GetByName($category);

        $app = new EeAppApp($core);
        $app->AddArgument(new Argument("Apps\EeApp\Entity\EeAppApp", "Actif", EQUAL, "1"));
        $app->AddArgument(new Argument("Apps\EeApp\Entity\EeAppApp", "CategoryId", EQUAL, $appCategory->IdEntite));

        return $app->GetByArg();
    }

    /**
     * Retourne une app depuis son Id
     * @param type $core
     * @param type $id
     */
    public static function GetById($core, $id) {
        $app = new EeAppApp($core);
        $app->GetById($id);

        return $app;
    }

    /**
     * Retourne une app depuis son nom
     * @param type $core
     * @param type $id
     */
    public static function GetByName($core, $name) {
        $app = new EeAppApp($core);
        $app->GetByName($name);

        return $app;
    }

    /**
     * Retourne es catégories des applications
     * @param type $core
     */
    public static function GetCategory($core) {
        $category = new EeAppCategory($core);
        return $category->GetAll();
    }

    /**
     * Définie si un utilisateur est admin de l'app
     * @param type $core
     * @param type $appName
     * @param type $userId
     */
    public static function IsAdmin($core, $appName, $userId) {
        $app = new EeAppApp($core);
        $app = $app->GetByName($appName);

        $appAdmin = new EeAppAdmin($core);
        $appAdmin->AddArgument(new Argument("Apps\EeApp\Entity\EeAppAdmin", "AppId", EQUAL, $app->IdEntite));
        $appAdmin->AddArgument(new Argument("Apps\EeApp\Entity\EeAppAdmin", "UserId", EQUAL, $userId));

        return (count($appAdmin->GetByArg()) > 0);
    }

    /*
     * Défine si EeApp est installé
     */

    public static function IsInstalled($core) {
        $EeApp = new EeAppApp($core);
        $app = $EeApp->GetByName("EeApp");

        return ($app != false);
    }

    /**
     * Install the App
     * Ad set the first user as a admin
     */
    public static function Install($core) {
        $request = File::GetFileContent(__DIR__ . "\..\Db\install.sql");
        $core->Db->ExecuteMulti($request);
    }

    /*
     * Sauvegarde une application
     */

    public static function Save($core, $name, $description, $categoryId, $appId) {
        $app = new EeAppApp($core);

        if ($appId != "") {
            $app->GetById($appId);
        }

        $app->Name->Value = $name;
        $app->Description->Value = $description;
        $app->CategoryId->Value = $categoryId;
        $app->Actif->Value = "0";
        $app->Save();
    }

    /*
     * Delete the app File And in the DataBase
     */

    public static function RemoveApp($core, $appId) {
        //Recuperation de l'app
        $app = new EeAppApp($core);
        $app->GetById($appId);
        $appName = $app->Name->Value;

        //Drop table
        echo __DIR__ . "/../../" . $appName . "/Db/unInstall.sql";

        echo "<br/> Suppression des tables de la base de donnée :";
        echo $request = File::GetFileContent(__DIR__ . "/../../" . $appName . "/Db/unInstall.sql");
        $core->Db->ExecuteMulti($request);

        //Supprimer les utilisateur et les administrateur
        echo "<br/> Suppression des utilisateurs et administrateurs";
        $admin = new EeAppAdmin($core);
        $admin->AddArgument(new Argument("Apps\EeApp\Entity\EeAppAdmin", "AppId", EQUAL, $app->IdEntite));
        $admin->DeleteByArg();

        $users = new EeAppUser($core);
        $users->AddArgument(new Argument("Apps\EeApp\Entity\EeAppUser", "AppId", EQUAL, $app->IdEntite));
        $users->DeleteByArg();

        //Suppression
        $app->Delete();

        //Suppression des fichiers
        echo "<br/> Suppression des fichiers : ../../" . $appName;
        File::RemoveAllDir(__DIR__ . "/../../" . $appName);
    }

    /*     * *
     * Installe une application depuis le store
     */

    public static function InstallApp($core, $app) {

        //Recuperation du package depuis le site
        $url = $core->Config->GetKey("puzzleAppUrl");
        $baseUrl = $url . "Downloader/Download/" . $app;
        $package = file_get_contents($baseUrl);

        File::CreateDirectory("Data/Tmp/" . $app);
        //Enregistrement temp
        file_put_contents("Data/Tmp/" . $app . "/$app.zip", $package);
        UploadHelper::DoUploadApp($app, "Data/Tmp/" . $app . "/$app.zip", $package);
    }

    /*     * *
     * Define parame of a app
     */

    public static function UpdateAppParams($core, $appName, $version, $description, $widget, $member) {

        $app = new EeAppApp($core);
        $apps = $app->Find("Name='" . $appName . "'");
        $app = $apps[0];

        $app->Version->Value = $version;
        $app->Description->Value = $description;
        $app->Widget->Value = $widget;
        $app->Member->Value = $member;
        $app->Save();
    }

    //Create Data directory
    public static function CreateDataDir($appName) {
        $dataDir = "Data/Apps/" . $appName;
        File::CreateDirectory($dataDir);

        chmod($dataDir, 0777);
    }

    /*     * *
     * Installe un plugin depuis le store
     */

    public static function InstallPlugin($core, $app) {

        //Recuperation du package depuis le site
        $url = $core->Config->GetKey("puzzleAppUrl");
        echo $baseUrl = $url . "Downloader/Download/" . $app;
        $package = file_get_contents($baseUrl);

        File::CreateDirectory("Data/Tmp/" . $app);
        //Enregistrement temp
        file_put_contents("Data/Tmp/" . $app . "/$app.zip", $package);
        UploadHelper::DoUploadPlugin($app, "Data/Tmp/" . $app . "/$app.zip", $package);
    }

    /*     * *
     * Installe un plugin depuis le store
     */

    public static function InstallTemplate($core, $app) {

        //Recuperation du package depuis le site
        $url = $core->Config->GetKey("puzzleAppUrl");
        echo $baseUrl = $url . "Downloader/Download/" . $app;
        $package = file_get_contents($baseUrl);

        File::CreateDirectory("Data/Tmp/" . $app);
        //Enregistrement temp
        file_put_contents("Data/Tmp/" . $app . "/$app.zip", $package);
        UploadHelper::DoUploadTemplate($app, "Data/Tmp/" . $app . "/$app.zip", $package);
    }

    /*     * *
     * Get the plugin
     */

    public static function GetPlugins($core) {

        $EeAppPlugin = new EeAppPlugin($core);
        return $EeAppPlugin->GetAll();
    }

    /*     * *
     * Save A plugin
     */

    public static function SavePlugin($core, $data) {
        $PluginForm = new PluginForm($core, $data);

        if ($PluginForm->Validate($data)) {

            $EeAppPlugin = new EeAppPlugin($core);
            $PluginForm->Populate($EeAppPlugin);
            $EeAppPlugin->Code->Value = $data["Name"];
            $EeAppPlugin->Save();

            return true;
        }
    }

    /**
     * Add Plugin To a App
     */
    public static function AddPluginToApp($core, $data) {
        $PluginAppForm = new PluginAppForm($core, $data);

        if ($PluginAppForm->Validate($data)) {

            $EeAppPlugin = new EeAppPluginApp($core);
            $PluginAppForm->Populate($EeAppPlugin);
            $EeAppPlugin->Save();
        }
    }

    /*     * *
     * Remove plugin to a app
     */

    public static function RemovePluginApp($core, $pluginAppId) {
        $EeAppPlugin = new EeAppPluginApp($core);
        $EeAppPlugin->GetById($pluginAppId);
        $EeAppPlugin->Delete();
    }

    /*     * *
     * Get Plugin of a App
     */

    public static function GetPluginApp($core, $appName) {

        $app = new EeAppApp($core);
        $app = $app->GetByName($appName);

        $pluginApp = new EeAppPluginApp($core);
        $pluginApp->Select("Plugin.Name", "PluginName");
        $pluginApp->Select("Plugin.Id", "PluginId");
        $pluginApp->Join("EeAppPlugin", "Plugin", "Left", "Plugin.Id = EeAppPluginApp.PluginId");

        return $pluginApp->Find("AppId= " . $app->IdEntite);
    }

    /*     * *
     * Return the first plugin 
     */

    public static function GetPluginType($core, $appName, $type) {

        $pluginsApp = self::GetPluginApp($core, $appName);

        foreach ($pluginsApp as $pluginApp) {

            $pluginName = $pluginApp->PluginName->Value;

            $pluginPath = "\\Plugins\\" . $pluginName . "\\" . $pluginName;
            $plugin = new $pluginPath($core);

            if ($plugin->GetType() == $type) {

                $appPlugin = new EeAppPlugin($core);
                $appPlugin->GetById($pluginApp->PluginId->Value);

                $plugin->Parameters = $appPlugin->Parameters->Value;

                return $plugin;
            }
        }

        return null;
    }

    /*     * *
     * Save A template
     */

    public static function SaveTemplate($core, $data) {

        $TemplateForm = new TemplateForm($core, $data);

        if ($TemplateForm->Validate($data)) {

            $EeAppTemplate = new EeAppTemplate($core);
            $TemplateForm->Populate($EeAppTemplate);
            $EeAppTemplate->Save();

            return true;
        }
    }

    /*     * *
     * Define actif template
     */

    public static function DefineTemplateActif($core, $templateId) {

        $request = "Update EeAppTemplate set actif = null where id > 0";
        $core->Db->Execute($request);

        $EeAppTemplate = new EeAppTemplate($core);
        $EeAppTemplate->GetById($templateId);
        $EeAppTemplate->Actif->Value = 1;
        $EeAppTemplate->Save();
    }

    /**
     * Get the Actif template
     * @param type $core
     */
    public static function GetTemplateActif($core) {

        if ($core->Db == null) {
            return;
        }

        $EeAppTemplate = new EeAppTemplate($core);
        $actifTemplate = $EeAppTemplate->Find("Actif = 1");

        if (count($actifTemplate) > 0) {
            return $actifTemplate[0];
        }

        return null;
    }

    /*     * *
     * App installed
     */

    public static function HaveApp($core, $appName) {

        $app = new EeAppApp($core);
        $app = $app->Find("Name = '" . $appName . "'");

        if (count($app) > 0) {
            return $app[0];
        }

        return false;
    }

    /*     * *
     * Plugin installed
     */

    public static function HavePlugin($core, $appName) {

        $app = new EeAppPlugin($core);
        $app = $app->Find("Name = '" . $appName . "'");

        if (count($app) > 0) {
            return $app[0];
        }

        return false;
    }

    /*
     * Save the config for the plugin
     * */

    public static function SaveConfigPlugin($core, $data) {

        $app = new EeAppPlugin($core);
        $app->GetById($data["Id"]);
        $app->Parameters->Value = json_encode($data);
        $app->Save();
    }

    /*     * *
     * Save menu
     */

    public static function SaveMenu($core, $data) {
        $menuForm = new MenuUserForm($core, $data);

        if ($menuForm->Validate($data)) {

            $menuUser = new EeMenuUser($core);

            if ($data["Id"]) {
                $menuUser->GetById($data["Id"]);
            }

            $menuForm->Populate($menuUser);

            $menuUser->Save();

            return true;
        } else {
            return false;
        }
    }

    /***
     * Delete a menu user
     */
    public static function DeleteMenu($core, $menuId) {

        $menuUser = new EeMenuUser($core);

        $menuUser->GetById($menuId);
        $menuUser->Delete();
        return true;
    }
    
}
    