Seditio Source
Root |
./othercms/dotclear-2.22/inc/libs/clearbricks/xmlsql/class.xmlsql.php
<?php
/**
 * @class xmlsql
 *
 * @package Clearbricks
 *
 * @copyright Olivier Meunier & Association Dotclear
 * @copyright GPL-2.0-only
 */
class xmlsql
{
    protected
$con;
    protected
$xml;

    protected
$tables;

    protected
$stack;

    public
$test_version = 0;

    public function
__construct(&$con, $xml)
    {
       
$this->con = &$con;
       
$this->xml = $xml;

       
$schema       = dbSchema::init($this->con);
       
$this->tables = $schema->getTables();
        unset(
$schema);
    }

    public function
replace($str, $rep)
    {
       
$this->xml = str_replace($str, $rep, $this->xml);
    }

    public function
execute($version = 0)
    {
       
$this->test_version = $version;

       
$x = @simplexml_load_string($this->xml);
        if (!
$x) {
            throw new
Exception('Unable to load XML file.');
        }

       
$this->parseNode($x);
    }

    protected function
parseNode($node)
    {
        foreach (
$node->children() as $n) {
            switch (
dom_import_simplexml($n)->nodeName) {
                case
'test':
                   
$this->performTest($n);

                    break;
                case
'action':
                   
$this->performAction($n);

                    break;
            }
        }
    }

    protected function
performTest($node)
    {
       
$test = [];

       
/* Test like:
        <test type="table" name="table name" [eq="neq"]>...</test>
         */
       
if (isset($node['type']) && (string) $node['type'] == 'table') {
           
$test['result'] = in_array($node['name'], $this->tables);
           
$test['label']  = 'Table %s does not exists';
           
$test['string'] = (string) $node['name'];

           
$xtest = $node;
        }
       
/* Test syntax:
        <test type="column" name"table.column" [eq="neq"]>...</test>
         */
       
elseif (isset($node['type']) && (string) $node['type'] == 'column') {
           
$c = explode('.', (string) $node['name']);

            if (
count($c) != 2) {
                return
false;
            }

            [
$table, $col] = $c;

           
$rs = $this->con->getColumns($table);

           
$test['result'] = isset($rs[$col]);
           
$test['label']  = 'Column %s does not exists';
           
$test['string'] = (string) $node['name'];

           
$xtest = $node;
        }
       
/* Test syntax:
        <test type="version" name="version number" [comp=">"]>...</test>
         */
       
elseif (isset($node['type']) && (string) $node['type'] == 'version') {
           
$comp           = $node['comp'] ?? '>';
           
$test['result'] = version_compare($node['name'], $this->test_version, $comp);
           
$test['label']  = 'Version %s is too low';
           
$test['string'] = (string) $node['name'];

           
$xtest = $node;
        }

       
# End tests
       
if (isset($xtest)) {
            if (
$xtest['eq'] == 'neq') {
               
$test['result'] = !$test['result'];
            }

            if (isset(
$xtest['alert'])) {
               
$test['alert'] = (bool) (int) $xtest['alert'];
            } else {
               
$test['alert'] = false;
            }

            if (isset(
$xtest['label'])) {
               
$test['label'] = (string) $xtest['label'];
            }
            if (isset(
$xtest['string'])) {
               
$test['string'] = (string) $xtest['string'];
            }
            unset(
$xtest);

           
# Test false
           
if (!$test['result']) {
                if (
$test['alert']) {
                    throw new
Exception(sprintf($test['label'], $test['string']));
                }
            }
           
# Test true
           
else {
               
$this->parseNode($node);
            }
        } else {
            return
false;
        }
    }

    protected function
performAction($node)
    {
       
$req = trim((string) $node);
        if (
$req) {
            try {
               
$this->con->execute($req);
            } catch (
Exception $e) {
                if (
$node['silent'] != 1) {
                    throw
$e;
                }
            }
        }
    }
}