<?php

    # Multiple functions mainly to load and save data in settings, posts , user accounts

    # Load the settings file and return an error message if the file is missing
    class getXMLSettings {
    
        function __construct() {
            
            $file = 'filesinfo/settings.xml';
            
            if (is_file($file)) {
                
                $f = simplexml_load_file($file);
                
                if ($f !== false) :

                $this->ownerid = $f->general->ownerid;
                $this->title = $f->general->title;
                $this->description = $f->general->description;
                $this->indexresults = $f->general->indexposts->results;
                $this->indexlastmod = $f->general->indexposts->lastmod;
                $this->dateshow = $f->general->dateshow;
                $this->maximagesize = $f->general->maximagesize;
                $this->modified = $f->general->modified;
                $this->togsign = $f->general->togsign;
                $this->togcategories = $f->general->togcategories;
                $this->togtags = $f->general->togtags;
                $this->togreadold = $f->general->togreadold;
                    
                else :
                
                $_SESSION['ERROR:Settings'] = true;
                

                endif;
            }
            
            return true;
        }
    }

    


    # Load a post
    class getXMLPost {
        
        function __construct($file) {
            
            if (is_file($file)) {
                
                $cfile = file_get_contents($file);
                
                $postinfo = ['savedpost',
                             'postinfo',
                             'post',
                             'title',
                             'description',
                             'filename',
                             'createdby',
                             'editedby',
                             'modified',
                             'excerpt',
                             'type',
                             'category',
                             'tags',
                             'ptime',
                             'path',
                             'firstpost'];
                
                $c=0;
                foreach($postinfo as $tag) {
                    # valid xml does not allow '&' character
                    if (strpos($cfile,'&') !== false) {
                        $cfile = str_replace('&amp;','&',$cfile);
                        $cfile = str_replace('&','&amp;',$cfile);
                    }


                    
                    $f = simplexml_load_string($cfile);
                    if ($f !== false) :
                    
                    $this->title = $f->postinfo->post->title;
                    $this->description = $f->postinfo->post->description;
                    $this->filename = $f->postinfo->post->filename;
                    $this->createdby = $f->postinfo->post->createdby;
                    $this->editedby = $f->postinfo->post->editedby;
                    $this->modified = $f->postinfo->post->modified;
                    $this->excerpt = $f->postinfo->post->excerpt;
                    $this->type = $f->postinfo->post->type;
                    $this->category = $f->postinfo->post->category;
                    $this->tags = $f->postinfo->post->tags;
                    $this->ptime = $f->postinfo->post->ptime;
                    $this->path = $f->postinfo->post->path;
                    $this->firstpost = $f->postinfo->post->firstpost;
                    
                    endif;
                    
                }
            }
            $x=0;
            $all=[];
            foreach($f->postinfo->post->children() as $key=>$val) {
                $all[$key]=$val;
                $x++;
                
                
            }
    
            return true;
            
        }
    }



    # Simple getxmlpost function, will find any xml tag of a post xml file.
    function getxmlpost($file) {
    
        if (is_file($file)) {        
            
            $cfile = file_get_contents($file);
            $f = simplexml_load_string($cfile);
            $x=0;
            $all=[];
            foreach($f->postinfo->post->children() as $key=>$val) {
                $all[$key]=(string)$val;
                $x++;    
            }
                
            return($all);
            
        }
    }




    # Load a xml system file or a page or a post. You can use a simplexml class to gain control over a file
    # instead of getting or applying predefined object elements, like update_log() or get_log() functions do.
    # $a [l -> load a xml , e -> create new simplexml element]  $type[post,page,null]
    function simplexml_object($filename,$a='l',$type='null') {
        
        $folders = ['post'=>'autosaves/','page'=>'savedpages/',''=>'filesinfo/'];
        foreach($folders as $key=>$val) {
            
            if ($type == $key) {
                $fold = $val;
                break;
            }
        }
        
        
        $mf = 'monofiles';
        $filename = basename($filename);//support values of $filename containing paths
        
        
        if (is_dir($mf))
            $root = $mf.'/'.$fold;
    
        elseif (is_dir($fold))
            $root = $fold;
        
        else
            $root = '../../'.$mf.'/'.$fold;
            
        
        
        $file = $root.$filename;
        
        $error = ['missingfile'];
        
        if (is_file($file)) {
            
            $falsexml = ['falsexml'];
            libxml_use_internal_errors(true);
            simplexml_load_file($file);

            if (!empty(libxml_get_errors())) {
                $object = $falsexml;
                libxml_clear_errors();
             }
            
            else  {
            
            if ($a == 'l') 
                $object = simplexml_load_file($file);
            
            elseif ($a == 'e') 
                $object = new simpleXMLElement($file,null,true);
            
            }
            
        }

        else 
            $object = $error;
        
        
        return $object;

    }


    

    # Save an xml file from a xml object - type can be post, page or null
    function simplexml_object_save($file,$obj,$type=null) {
        
        libxml_use_internal_errors();
        
        $folders = ['post'=>'autosaves','page'=>'savedpages',''=>'filesinfo'];
        foreach($folders as $key=>$val) {
            
            if ($type == $key) {
                $fold = $val;
                break;
            }
        }
        
        
        if ($obj[0] != 'missingfile' && $obj[0] != 'falsexml') {

            $obj->asXML($fold.'/'.$file);
            return true;
            
        }

        else
            return false;

    }




    # Load settings on your website pages
    function cmsetup() {

        libxml_clear_errors();
        libxml_use_internal_errors(true);

        $set = simplexml_object('settings.xml','l',null);

        $a = ['website_title' => $set->general->title,
              'website_description' => $set->general->description,
              'results_per_page' => $set->general->indexposts->results,
              'results_per_page_lastmod' => $set->general->indexposts->lastmod,
              'show_date' => $set->general->dateshow,
              'sign_posts' => $set->general->togsign,
              'show_category' => $set->general->togcategories,
              'show_tags' => $set->general->togtags,
              'read_old_link' => $set->general->togreadold
              ];

        return $a;

    }




    # Load categories into an array [folder name => category name]
    function get_categories() {
        
        $cats = simplexml_object('categories.xml','l',null);
        
        if (!is_array($cats)) {
            $ctgs = [];
            foreach($cats->folders->children() as $key=>$val)
                $ctgs[$key] = (string)$val->name;
        
            return $ctgs;
        }
            
            else 
            return false;
    
    }



    # Load basic log info
    function get_log() {
        
        $loginfoxml = simplexml_object('log.xml','l',null);
        
        $i_log = ['posts' => (string)$loginfoxml->info->posts,
                  'pages' => (string)$loginfoxml->info->pages,
                  'failed' => (string)$loginfoxml->info->failed,
                  'modified' => (string)$loginfoxml->info->modified,
                  'plugins'=> (string)$loginfoxml->plugins
                  ];
        
        return $i_log;
        
    }




    # Load installed plugins. get_plugins returns an array with all the plugins, containing the plugin name,
    # title & description, plugin status (on/off) and plugin directory
    function get_plugins() {
        
        $loginfoxml = simplexml_object('log.xml','l',null);
        $stat = [];
        
        $system_dir = glob('../plugins/*.php');
        $user_dir = glob('../plugins/user/*.php');
        
        $plugins_dir = array_merge($system_dir,$user_dir);
    
        foreach($plugins_dir as $val) {
                
            
            $path = pathinfo($val);
            $d = $path['dirname'];
            $f = $path['filename'];
            
            if ($d =='../plugins') {
                $st = (string)$loginfoxml->plugins->$f;
            }
            else {
                $u=0;
                foreach ($loginfoxml->user as $user)
                    if ($user->name == $_SESSION['username'])
                        $st = (string)$user->$f;
            }
            
            if (is_file($d.'/'.$f.'.txt'))
                $stat[$f] = array($st,file($d.'/'.$f.'.txt')[0],file($d.'/'.$f.'.txt')[1],$d);
        
        }
        ksort($stat);
        return $stat;
    }




    # Load account info using a parameter of 'username' or 'userid'
    function get_account($value = 'null') {
        

        $log = simplexml_object('log.xml','l',null);
        $account_info = [];
        
        $c=0;
        foreach($log->user as $userinfo) {
            
            if ($userinfo->userID == $value || $userinfo->name == $value) {
                
                $account_info = array('name' => (string)$userinfo->name,
                                      'pshs' => (string)$userinfo->pshs,
                                      'rights' => (string)$userinfo->rights,
                                      'login' => (string)$userinfo->login,
                                      'ip' => (string)$userinfo->ip,
                                      'icon' => (string)$userinfo->icon,
                                      'userID' => (string)$userinfo->userID,
                                      'editorname' => (string)$userinfo->editorname,
                                      'created' => (string)$userinfo->created,
                                      'results_posts' => (string)$userinfo->results->posts,
                                      'results_pages' => (string)$userinfo->results->pages,
                                      'results_images' => (string)$userinfo->results->images,
                                      'status' => (string)$userinfo->status,
                                      'urlicon'=>(string)$userinfo->urlicon,
                                      'texteditor'=>(string)$userinfo->texteditor,
                                      'theme'=>(string)$userinfo->theme,
                                      'sortposts'=>(string)$userinfo->sortposts,
                                      'sortpages'=>(string)$userinfo->sortpages
                                     );

                break;
            }
            else
                $account_info = ['name'=> 'no username',
                                 'pshs' => 'x',
                                 'rights' => 'x',
                                 'login' => 'no info',
                                 'ip' => 'no info',
                                 'icon' => 'x',
                                 'userID' => 'user deleted',
                                 'editorname' => 'deleted user',
                                 'created' => 'x',
                                 'results_posts' => 'x',
                                 'results_pages' => 'x',
                                 'results_images' => 'x',
                                 'status' => 'x',
                                 'urlicon'=> 'x',
                                 'texteditor'=>'x',
                                 'theme'=>'x',
                                 'sortposts'=>'x',
                                 'sortpages'=>'x'
                                ];
            
            $c++;
        }
            
        return $account_info;

    }
    



    # Save log
    function update_log($tag,$value) {
        
        $log_element = simplexml_object('log.xml','e',null);
        
        $log_element->info->$tag = $value;
        $log_element->info->modified = time();
        
        simplexml_object_save('log.xml',$log_element,null);

        return true;

    }


    
    
    # Save account info using userID and an action.
    function update_account($id,$action = 'set'){
        
        $logsave = simplexml_object('log.xml','e',null);
        
        $c=0;
        $upd = false;
        foreach($logsave->user as $user) {
                
            if ($user->userID == $id && $user->pshs != '-') {

                if ($action == 'delete') {

                    $logsave->user[$c]->name = (string)$logsave->user[$c]->name.'[deleted]';
                    $logsave->user[$c]->pshs = '-';
                    $logsave->user[$c]->rights = '-';
                    $logsave->user[$c]->icon = '-';
                    $logsave->user[$c]->description = '-';
                    $logsave->user[$c]->editorname = '-';
                    $logsave->user[$c]->activity = '-';
                    $logsave->user[$c]->created = '-';
                    $logsave->user[$c]->results->posts = '-';
                    $logsave->user[$c]->results->pages = '-';
                    $logsave->user[$c]->results->images = '-';
                    $logsave->user[$c]->texteditor = '-';
                    $logsave->user[$c]->theme = '-';
                    $logsave->user[$c]->status = 'del';
                    $logsave->user[$c]->sortposts = '-';
                    $logsave->user[$c]->sortpages = '-';
                    


                    if ($_SESSION['userID'] == $id)
                        session_destroy();
                }

                if ($action == 'set') {

                    $values = array('name' => $_POST['username'],
                                    'pshs' => $_POST['password'], # <- new value of POST['password']
                                    'rights' => $_POST['accounttype'],
                                    'icon' => $_SESSION['usericon'],
                                    'editorname' => $_POST['usereditorname'],
                                    'created' => $_POST['created'],
                                    'posts' => $_GET['postsperpage'],
                                    'pages' => $_GET['pagesperpage'],
                                    'images' => $_GET['imgsperpage'],
                                    'urlicon' => $_POST['urlicon'],
                                    'texteditor' => $_POST['texteditor'],
                                    'theme' => $_POST['theme'],
                                    'sortposts' => $_SESSION['sortposts'],
                                    'sortpages' => $_SESSION['sortpages']
                                    );

                    foreach($values as $tag => $set) {

                        if (isset($set)) {

                            if ($tag == 'posts' || $tag == 'pages' || $tag == 'images')
                                $user->results->$tag = $set;

                            else    
                            $user->$tag = $set;
                        }
                    }
                }

                simplexml_object_save('log.xml',$logsave,null);
                $upd = true;
                break;
            }
            $c++;
        }
        
        return $upd;
    }



    # Quickly edit your account by giving a tag name and a value
    function edit_useraccount($tag,$value) {
    
            $log = simplexml_object('log.xml','e',null);
            $c=0;
            foreach($log->user as $userval) {
                
                if ($userval->userID == $_SESSION['userID']) {
                    $log->user[$c]->$tag = $value;
                    simplexml_object_save('log.xml',$log,null);
                }
                
                $c++;
            }
            
        return $log;
    }


    

    # Load your own posts
    function myPosts() {

        $myID = $_SESSION['userID'];
        $directory = new DirectoryIterator('autosaves/');

        $myp = array();
        $c=0;
        foreach($directory as $fileinfo) {

            if ($fileinfo->isFile()) {
                $fname = $fileinfo->getFilename();

                if (strpos($fname,'nu.xml') === false && strpos($fname,'.xml') !== false) {

                    $filexml = simplexml_object($fname,'l','post');
                    if ($filexml->postinfo->post->createdby == $myID) {
                        $myp[] = $fname;
                        $c++;

                    }
                }
            }
        }
        array_unshift($myp,$c);
        return $myp;
    }




    ## this is for older versions support only ##
    # Make a string or an array of a php date() valid format, from a string or an object($dates_custom)
    function phpdate_($mydate) {

        
        # date formats from dateform.xml and their date() "counterpart"
        $dates_custom = ['day-n','day-t','day-f','month-n','month-t','month-f','year','hour','minute','second'];
        $dates_lang = ['d','D','l','m','M','F','Y','H','i','s'];
        #
        
        
        $dates = array();
        
        if (is_object($mydate)) {

            foreach($mydate as $format) {

                $replace = str_replace($dates_custom,$dates_lang,(string)$format);
                $dates[] = $replace;

            }
        }
        
        elseif (in_array($mydate,$dates_custom))
            $dates = str_replace($dates_custom,$dates_lang,$mydate);
            
        
        return($dates);
    }
    
    

    
    # Put multiple dates from xml into an array
    function phpdate($mydate) {

        $dates = array();        
        if (is_object($mydate))
            foreach($mydate as $format)
                $dates[] = $format;
        
        return($dates);
    }

    

    
    # format date for use in control panel, depending on dateform.xml
    function date_form($datestr) {

        $dif = time() - (int)$datestr;
        $day = 86400; # 1 day
        
        
        $a = simplexml_object('dateform.xml','l',null);
        
        
        # recent value is = < of 24h
        # old value is > of 24h
        
        if ($a->dates->recent->dd == '') {
        
            $recent = (string)$a->dates->recent;
            $old = (string)$a->dates->old;
        
        }
        
        else {
        
            $recent = phpdate_($a->dates->recent->dd)[0];
            $old = phpdate_($a->dates->old->dd)[0];
        
        }
        
        
        if ($dif > $day)
            $date = date($old,$datestr);
        

        else {
            
            if (date('d') != date('d',$datestr))
                $date = date($old,$datestr);
            else                 
                $date = date($recent,$datestr);
        }
        
        
        return $date;
    
    }
    
    
    
    
    # Find errors in date format
    function dateval($date) {
        
        try {
        $datech = new DateTimeImmutable((string)$date);
         }
         
        catch (Exception $e) {
        
        if (DateTimeImmutable::getLastErrors() !== false)
            foreach(DateTimeImmutable::getLastErrors() as $key=>$val)
                if ($key == 'errors')
                    foreach($val as $v)
                        if ($v == 'Unexpected character')
                            echo 'old format found';
        }
    }




    # Show a notification to confirm a user action or report an error
    function action_confirm() {
            
        $lang_actions = ['newpost'=>'Posted',
                        'errorpost'=>'You cannot edit this post',
                        'MONchanged_to_draft'=>'Post changed to draft',
                        'MONdeleted'=>'Post deleted',
                        'settingsset'=>'Settings saved',
                        'settingssetuser'=>'Settings saved',
                        'panelset'=>'Saved',
                        'themeset'=>'Theme saved',
                        'MONimg_notuploaded'=>'An Error was found while uploading a file',
                        'MONimg_wrongtype'=>'A file type was incorrect. File extensions allowed:&nbsp;.gif&nbsp;.jpg&nbsp;.png',
                        'MONimg_upload_success'=>'Image uploaded',
                        'MONimg_upload_error'=>'Error uploading file',
                        'MONimg_upload_file_type'=>'File type is not supported. File extensions allowed: .gif .jpg .png',
                        'MONimg_removed'=>'Image deleted',
                        'MONpagedeleted'=>'Page deleted',
                        'MON_newcat'=>'Category created',
                        'MON_delcat'=>'Category deleted',
                        'MON_cat_notset'=>'Category or folder name is missing',
                        'MON_cat_exists'=>'Category and folder name already exist',
                        'MON_cat_falsexml'=>'An error was found',
                        'MON_plugins'=>'Plugins saved',
                        'MON_plugins_not_exist'=>'No plugins to load',
                        'ERROR:xmlpost'=>'Errors were found in post file',
                        'ERROR:Settings'=>'Settings file is corrupt',
                        'ERROR:maximagesize'=>'Max upload image size was not valid',
                        'ERROR:indexposts'=>'Results in home page was not valid',
                        'ERROR:userdescription'=>'Editor description was too big',
                        'ERROR:editorname'=>'Editor name was too big',
                        'account_username_not_valid'=>'Username must be between 3-40 characters',
                        'account_missing'=>'Account does not exist',
                        'account_modified'=>'Account modified',
                        'account_username_exists'=>'Username is already in use',
                        'account_created'=>'Account created',
                        'account_owner_del'=>'Cannot delete this account',
                        'account_deleted'=>'Account deleted',
                        'account_set_to_owner'=>'Account set to owner',
                        'account_cannot_set'=>'Could not set to owner',
                        'account_could_not_modify'=>'Could not modify account',
                        'owner_account_could_not_modify'=>'Cannot edit this account',
                        'User_logged_in'=>'Welcome',
                        'iconerror'=>'Error uploading icon',
                        'iconfiletype'=>'File type was incorrect',
                        'pass_try_again'=>'Please try again',
                        'pass_match'=>'Passwords did not match',
                        'MONitemset'=>'Navigation menu saved',
                        'MONitemnotset'=>'Please create a new item',
                        'MONpagepublished_on'=>'Page has been published',
                        'MONpagepublished_hidden'=>'Page marked as unpublished'
                        ];


        foreach($lang_actions as $key=>$val) {
            if (isset($_SESSION[$key])) {
                print '<div id="action-confirm"><span>'.$val.'</span></div>';
                unset($_SESSION[$key]);
                break;
            }
        }
    }




    # Results per page. $files should be one of 'posts', 'pages' or 'images'
    function pageResults($files,$link_param=null) {
        
        $get_num = simplexml_object('results_pages.xml','l',null);
        
        foreach($get_num->value as $val) { 
            if ($val == 0 || strlen($val) > 4)
                continue;
            $numbers[] = abs((int)$val);
        }
        
        $numbers = array_unique($numbers);
        
        $filetypes = ['posts'=>['results_posts','postsperpage'],
                      'pages'=>['results_pages','pagesperpage'],
                      'images'=>['results_images','imgsperpage']
                     ];
        
        $file_type = (string)$filetypes[$files][0];
        $file_type_param = $filetypes[$files][1];
        $account_results = get_account($_SESSION['username'])[$file_type];
        
        print '<select onchange="window.location=this.value">'.PHP_EOL.'<option value="#">'.$account_results.'</option>';
        
        $del = array_search($account_results,$numbers);
        if ($del !== false)
            unset($numbers[$del]);
        
        $link_param = $link_param != '' ? '?'.ltrim($link_param,'&').'&' : '?';
        foreach($numbers as $option)
            echo '<option value="res-set.php'.$link_param.$file_type_param.'='.$option.'">'.$option.'</option>';

        
        print PHP_EOL.'</select>';
        
        return true;

    }




    # Get number of pages, published unpublished status included
    function numberofpages() {
    
        if (file_exists('savedpages')) {
                
            $directory = new DirectoryIterator('savedpages/');
                    
            $s=$p=$u = 0;
            foreach ($directory as $fileinfo) {
                
                if ($fileinfo->isFile() && substr($fileinfo->getBasename(),-4) == '.xml' && $fileinfo->getSize() > 0) {
                                            
                    $name = $fileinfo->getBasename();
                    $sp = simplexml_object($name,'l','page');
                    $mtime = $sp->pageinfo->page->modified;
                    $pubstat = $sp->pageinfo->page->published;
                    if ($pubstat == 'hidden') 
                        $u=$u+1;
                    else 
                        $p=$p+1;
                    
                    $s++;
                }
            }
            return array($s,$p,$u);
        }
    
    }

?>