function _db_create_tables($OLD, $NEW, $database, &$count)
{
    $count = 0;
    $query = "";
    foreach ($NEW as $newtable => $newdef) {
        if (@$newdef["VIEW"]) {
            $query .= _db_create_view($NEW, $newtable, $newdef["VIEW"]);
            continue;
        }
        if ($newdef["DB"] != $database) {
            $query .= "/* skipping table '{$newtable}', not in database '{$database}' */\n\n";
            continue;
        }
        if (!db_access_table($newtable, "w")) {
            $query .= "/* skipping table '{$newtable}', no write access */\n";
            continue;
        }
        if (!@$newdef["SCHEMA_CONTROL"]) {
            $query .= "/* skipping table '{$newtable}', no schema control over it */\n";
            continue;
        }
        $singular = _db_singular($newtable, $NEW);
        $primary = _db_primary($newtable, $NEW);
        $secondary = $singular . "_name";
        // !!! not generic!
        $restrict = @$newdef["USER_RESTRICT"];
        $tablename = $newtable;
        if ($restrict) {
            $tablename .= "_unrestr";
        }
        $tablename .= "_tp";
        // completely new table or delta?
        if (!isset($OLD[$newtable])) {
            $count++;
            $index = "";
            $query .= "create table if not exists {$tablename} (\n";
            foreach ($newdef["FIELDS"] as $field => $value) {
                if (@$value["VIRTUAL"]) {
                    $query .= "/* omitting VIRTUAL {$field} */\n";
                    continue;
                }
                $query .= __db_create_field($field, $value);
                $query .= ",\n";
            }
            $query .= "  primary key({$primary}";
            if ($newdef["TEMPORAL"]) {
                $query .= ", " . $NEW[$newtable]["FIELDNAME_VERSION"];
            }
            $query .= "),\n";
            $indices = _db_gen_indices($NEW, $newdef, $newtable, $secondary);
            foreach ($indices as $dummy => $index) {
                $query .= __db_create_index($index, false) . ",\n";
            }
            $engine = isset($DEF[$newtable]["ENGINE"]) ? $DEF[$newtable]["ENGINE"] : "";
            if (!$engine) {
                $engine = "myisam";
            }
            $query = preg_replace("/,\\s*\\Z/m", "\n", $query);
            $query .= ") engine={$engine};\n";
            $query .= __db_create_tpview($NEW, $newtable, $restrict);
        } else {
            // isset($OLD[$newtable]) => use "alter table"
            $olddef = $OLD[$newtable];
            $flag = 0;
            $flag_col = 0;
            $after = "";
            foreach ($newdef["FIELDS"] as $field => $value) {
                if (@$value["VIRTUAL"]) {
                    //$query .= "/* omitting VIRTUAL $field */\n";
                    continue;
                }
                if (isset($value["CHANGE_FROM"])) {
                    $count++;
                    $oldfield = $value["CHANGE_FROM"];
                    $query .= "alter table {$tablename}\n";
                    $query .= "  change column " . $oldfield . " " . __db_create_field($field, $value) . " {$after};\n";
                    unset($olddef["FIELDS"][$oldfield]);
                    $flag++;
                    $flag_col++;
                } elseif (isset($olddef["FIELDS"][$field])) {
                    $oldvalue = $olddef["FIELDS"][$field];
                    $diff = false;
                    foreach (array("SQL_TYPE", "DEFAULT", "BETWEEN", "LENGTH", "REGEX") as $test) {
                        if (isset($value[$test]) && (!isset($oldvalue[$test]) || $value[$test] != $oldvalue[$test])) {
                            $diff = true;
                        }
                    }
                    if ($diff) {
                        $count++;
                        $query .= "alter table {$tablename}\n";
                        $query .= "  modify column " . __db_create_field($field, $value) . " {$after};\n";
                        $flag++;
                        $flag_col++;
                    }
                    if (!isset($value["DEFAULT"]) && isset($oldvalue["DEFAULT"])) {
                        $query .= "alter table {$tablename}\n";
                        $query .= "  alter column " . $field . " drop default;\n";
                        $flag++;
                        $flag_col++;
                    }
                } else {
                    // create new column
                    $count++;
                    $query .= "alter table {$tablename}\n";
                    $query .= "  add column" . __db_create_field($field, $value) . " {$after};\n";
                    $flag++;
                    $flag_col++;
                }
                $after = "after {$field}";
            }
            $oldindices = _db_gen_indices($OLD, $olddef, $newtable, $secondary);
            $newindices = _db_gen_indices($NEW, $newdef, $newtable, $secondary);
            foreach ($newindices as $index) {
                if (!in_array($index, $oldindices)) {
                    $count++;
                    $query .= "alter table {$tablename}\n";
                    $query .= "  add" . __db_create_index($index, false) . ";\n";
                    $flag++;
                }
            }
            foreach ($oldindices as $index) {
                if (!in_array($index, $newindices)) {
                    $count++;
                    $query .= "alter table {$tablename}\n";
                    $query .= "  drop" . __db_create_index($index, true) . ";\n";
                    $flag++;
                }
            }
            foreach ($olddef["FIELDS"] as $field => $value) {
                if (@$value["VIRTUAL"]) {
                    //$query .= "/* omitting OLD VIRTUAL $field */\n";
                    continue;
                }
                if (!isset($newdef["FIELDS"][$field])) {
                    $count++;
                    $query .= "alter table {$tablename}\n";
                    $query .= "  drop column {$field};\n";
                    $flag++;
                    $flag_col++;
                }
            }
            if ($flag_col) {
                // whenever the *_tp table changes, mysql seems to require
                // recreation of the view (otherwise the old definition would remain)
                $count++;
                $query .= __db_create_tpview($NEW, $newtable, $restrict);
            } elseif ($flag) {
                $query .= "\n";
            }
        }
    }
    foreach ($OLD as $oldtable => $olddef) {
        if (!isset($NEW[$newtable])) {
            $count++;
            $query .= "drop table " . $oldtable . "_tp\n";
            $count++;
            $query .= "drop view " . $oldtable . "\n\n";
        }
    }
    return $query;
}
function engine_run_once()
{
    global $ENGINE;
    poll_childs();
    foreach ($ENGINE as $statefield => $deflist) {
        if ($statefield == "GLOBAL.GLOBAL") {
            continue;
        }
        $tmp = explode(".", $statefield);
        $tablename = $tmp[0];
        $fieldname = $tmp[1];
        $primary = _db_primary($tablename);
        $cond = make_selectcond($tablename, $fieldname, $deflist);
        if (!$cond) {
            continue;
        }
        $data = db_read($tablename, null, $cond, null, 0, 0);
        foreach ($data as $rec) {
            $cache = array();
            foreach ($deflist as $def) {
                $joinwith = $def["bp_joinwith"];
                if (!@$cache[$joinwith]) {
                    if ($joinwith) {
                        $subcond = $cond;
                        foreach (split(",", $primary) as $pri) {
                            $subcond[$pri] = $rec[$pri];
                        }
                        $subdata = db_read("{$tablename},{$joinwith}", null, $subcond, null, 0, 0);
                    } else {
                        $subdata = array($rec);
                    }
                    $cache[$joinwith] = $subdata;
                }
            }
            foreach ($cache as $subdata) {
                foreach ($subdata as $subrec) {
                    treat_rec($subrec, $deflist);
                }
            }
        }
    }
}
示例#3
0
function _db_make_idcond($table, $row)
{
    global $ERROR;
    global $debug;
    $primary = _db_primary($table);
    if ($debug) {
        echo "_db_make_idcond table='{$table}' row=";
        print_r($row);
        echo "<br>\n";
    }
    $ok = true;
    foreach (split(",", $primary) as $pr) {
        if (!array_key_exists($pr, @$row)) {
            $ok = false;
            break;
        }
    }
    $cond = array();
    if ($row && $ok) {
        foreach (split(",", $primary) as $pr) {
            $cond[$pr] = @$row[$pr];
        }
    } else {
        $keys = split(",", _db_unique($table));
        if (!$keys) {
            $ERROR = "primary key '{$primary}' is missing in your data, and other keys are not available";
            return null;
        }
        foreach ($keys as $key) {
            if (!$row || !array_key_exists($key, $row)) {
                $ERROR = "id-key '{$key}' is missing in your data, and primary key '{$primary}' is also missing";
                return null;
            }
            $cond[$key] = $row[$key];
        }
    }
    return $cond;
}
示例#4
0
function app_display_table($tp_table)
{
    global $SCHEMA;
    global $TOOL;
    global $ERROR;
    global $debug;
    _db_temporal($tp_table, $table);
    if (!db_access_table($table, "r")) {
        tpl_error_permission_denied(null);
        return;
    }
    app_tools($table);
    $cond = array();
    if (isset($SCHEMA[$table]["TOOLS"]["tool_search"]) && ($str = trim($TOOL["tool_search"])) && ($field = $TOOL["tool_search_field"])) {
        if ($debug) {
            echo "adding search condition '{$field}'<br>\n";
        }
        $cond["{$field}%"] = "%{$str}%";
    }
    $page_size = @$TOOL["tool_page_size"];
    if (!$page_size || $page_size < 0) {
        $page_size = 1;
    }
    $page_start = @$TOOL["tool_page_start"];
    if (!$page_start || $page_start < 0) {
        $page_start = 1;
    }
    if (!isset($SCHEMA[$table]["TOOLS"]["tool_page"])) {
        $page_size = 0;
    }
    // xxx not generic!!!
    if (@$SCHEMA[$table]["TOOLS"]["tool_level"]) {
        $prio = @$TOOL["tool_level"];
        //$cond["#class_name in (select class_name from classes where class_prio >= $prio)"] = true;
    }
    $tmp = db_read($tp_table, null, $cond, @$TOOL["order"], ($page_start - 1) * $page_size, $page_size);
    if ($ERROR) {
        tpl_error(array("ERROR" => $ERROR));
        return;
    }
    $data = _app_prepare_data($table, $tmp, "invalid");
    if (db_access_table($table, "w")) {
        $data["EXTRAHEAD"] = "extra_3buttons_head";
        $primary = _db_primary($table);
        $data["EXTRA"]["button_edit"] = $primary;
        $data["EXTRA"]["button_clone"] = $primary;
        $data["EXTRA"]["button_delete"] = $primary;
    }
    tpl_display_table($data);
}
示例#5
0
function _db_pass_typeinfo($MYSCHEMA)
{
    // augment with additional info
    $res = $MYSCHEMA;
    foreach ($MYSCHEMA as $table => $tinfo) {
        // default links from the primary and secondary keys to SELF
        $make_ref = array();
        $primary = _db_primary($table, $MYSCHEMA);
        if ($primary) {
            foreach (split(",", $primary) as $pr) {
                if (!@$res[$table]["FIELDS"][$pr]["DISPLAY_TYPE"]) {
                    $res[$table]["FIELDS"][$pr]["DISPLAY_TYPE"] = "hidden";
                }
            }
            $make_ref = array_merge(array($primary), @$tinfo["UNIQUE"]);
        }
        foreach ($make_ref as $fields) {
            foreach (split(",", $fields) as $field) {
                if (!@$tinfo["FIELDS"][$field]) {
                    continue;
                }
                if (!@$res[$table]["FIELDS"][$field]["TPL_DISPLAY"]) {
                    $res[$table]["FIELDS"][$field]["TPL_DISPLAY"] = "display_ref";
                }
                /* set to default */
            }
        }
        if (!@$tinfo["TOOLS"]) {
            $res[$table]["TOOLS"] = array("tool_search" => true, "tool_history" => true, "tool_page" => true);
            /* set to default */
        }
        // check all FIELDS
        foreach ($tinfo["FIELDS"] as $field => $finfo) {
            // add default REF_LINKS for the first possible REFERENCES
            if (@$finfo["REFERENCES"] && !array_key_exists("REF_LINKS", $finfo)) {
                foreach ($finfo["REFERENCES"] as $link => $dummy) {
                    $split = preg_split("/\\./", $link);
                    $ref_table = $split[0];
                    $ref_field = $split[1];
                    // only create a default runtime link when the reference identifies target tuples _uniquely_
                    if ($ref_field == @$MYSCHEMA[$ref_table]["PRIMARY"] || array_search($ref_field, @$MYSCHEMA[$ref_table]["UNIQUE"]) !== false) {
                        $finfo["REF_LINKS"] = $link;
                        $res[$table]["FIELDS"][$field]["REF_LINKS"] = $link;
                        if (!@$finfo["POOL_DATA"]) {
                            $pool = array("TABLE" => $ref_table, "ORDER" => $ref_field);
                            $finfo["POOL_DATA"] = $pool;
                            $res[$table]["FIELDS"][$field]["POOL_DATA"] = $pool;
                        }
                        if (!$finfo["SIZE"]) {
                            $finfo["SIZE"] = 4;
                            $res[$table]["FIELDS"][$field]["SIZE"] = 4;
                        }
                        //"SHOW_FIELD" => "profile_name",
                        break;
                    }
                }
            }
            // set some default values
            $res[$table]["FIELDS"][$field]["MINLEN"] = 0;
            /* set to dummy */
            $res[$table]["FIELDS"][$field]["MAXLEN"] = 999;
            /* set to dummy */
            $res[$table]["FIELDS"][$field]["SIZE"] = 40;
            /* set to default */
            $type = @$finfo["TYPE"];
            $res[$table]["FIELDS"][$field]["SQL_TYPE"] = $type;
            //echo "matching type '$type'\n";
            if (array_search($field, split(",", $primary)) !== false) {
                $restype = "hidden";
            } elseif (preg_match("/^(?:date)?time(stamp)?\$/", $type)) {
                $restype = "string";
            } elseif (preg_match("/^((?:tiny|small|medium)?int([\\(][0-9]+[\\)])?|bigint|decimal\\([0-9]+,[0-9]+\\))\$/", $type)) {
                $restype = "int";
                $res[$table]["FIELDS"][$field]["SIZE"] = 10;
                /* set to default */
            } elseif (preg_match("/^bool(ean)?\$/", $type)) {
                $restype = "bool";
                $res[$table]["FIELDS"][$field]["MAXLEN"] = null;
                $res[$table]["FIELDS"][$field]["SIZE"] = null;
                if (!@$res[$table]["FIELDS"][$field]["TPL_DISPLAY"]) {
                    $res[$table]["FIELDS"][$field]["TPL_DISPLAY"] = "display_bool";
                }
            } elseif (preg_match("/^(var)?char[\\(]([0-9]+)[\\)]\$/", $type, $matches)) {
                $restype = "string";
                if (!$matches[1]) {
                    $res[$table]["FIELDS"][$field]["MINLEN"] = $matches[2];
                }
                $res[$table]["FIELDS"][$field]["MAXLEN"] = $matches[2];
            } elseif (preg_match("/^(tiny|small|medium|long)?text\$/", $type, $matches)) {
                $restype = "text";
                $res[$table]["FIELDS"][$field]["SIZE"] = 80;
                /* set to default */
                $res[$table]["FIELDS"][$field]["LINES"] = 4;
                /* set to default */
                $res[$table]["FIELDS"][$field]["MAXLEN"] = null;
                if (!@$res[$table]["FIELDS"][$field]["TPL_DISPLAY"]) {
                    $res[$table]["FIELDS"][$field]["TPL_DISPLAY"] = "display_text";
                }
            } elseif (preg_match("/^(tiny|small|medium|long)?blob\$/", $type, $matches)) {
                $restype = "blob";
                if (!@$res[$table]["FIELDS"][$field]["TPL_DISPLAY"]) {
                    $res[$table]["FIELDS"][$field]["TPL_DISPLAY"] = "display_blob";
                }
            } elseif ($finfo) {
                $restype = "virtual";
            } else {
                die("ERROR in schema: cannot translate SQL type '{$type}'\n");
            }
            if ($ref = @$finfo["REF_LINKS"]) {
                //echo "Aha: table=$table field=$field<br>\n";
                $restype = "selector";
                $split = preg_split("/\\./", $ref);
                //print_r($split); echo "<br>\n";
                $res[$table]["FIELDS"][$field]["REF_TABLE"] = $split[0];
                $res[$table]["FIELDS"][$field]["REF_FIELD"] = $split[1];
                $res[$table]["FIELDS"][$field]["REF_FIELDS"] = split(",", $split[1]);
            }
            // Finally, store the result
            $res[$table]["FIELDS"][$field]["DISPLAY_TYPE"] = $restype;
            if (isset($finfo["LENGTH"])) {
                $res[$table]["FIELDS"][$field]["MINLEN"] = $finfo["LENGTH"][0];
                $res[$table]["FIELDS"][$field]["MAXLEN"] = $finfo["LENGTH"][1];
            }
            if ($fields = @$finfo["EXTRA_FIELD"]) {
                $res[$table]["FIELDS"][$field]["EXTRA_FIELD"] = split(",", $fields);
            } else {
                $res[$table]["FIELDS"][$field]["EXTRA_FIELD"] = array();
            }
            foreach (array("SUB_DATA", "POOL_DATA") as $qtype) {
                if ($sub_query = @$finfo[$qtype]) {
                    if (!@$sub_query["FIELD"]) {
                        // initialize with reasonable defaults: everything mentioned in JOINFIELDS and ORDER
                        $all = array();
                        if ($add = @$sub_query["JOINFIELDS"]) {
                            $all = explode(",", $add);
                        }
                        if ($add = @$sub_query["ORDER"]) {
                            $all = array_unique(array_merge(explode(",", $add), $all));
                        }
                        $res[$table]["FIELDS"][$field][$qtype]["FIELD"] = implode(",", $all);
                    }
                    if ($qtype == "SUB_DATA") {
                        if (!isset($finfo["VIRTUAL"])) {
                            $res[$table]["FIELDS"][$field]["VIRTUAL"] = true;
                        }
                        if (!isset($finfo["TPL_DISPLAY"])) {
                            $res[$table]["FIELDS"][$field]["TPL_DISPLAY"] = "display_reflist";
                        }
                        if (!isset($finfo["TPL_INPUT"])) {
                            $res[$table]["FIELDS"][$field]["TPL_INPUT"] = "input_sublist";
                        }
                    }
                }
            }
            // user settings always take precedence
            foreach (array("SIZE", "SORT", "LINES", "TPL_INPUT", "TPL_DISPLAY") as $further) {
                if (@$finfo[$further]) {
                    $res[$table]["FIELDS"][$field][$further] = $finfo[$further];
                }
            }
        }
    }
    return $res;
}
示例#6
0
function _mysql_make_idcond_base($qstruct, $row)
{
    global $ERROR;
    $table = $qstruct["TABLE"];
    if (!($cond = @$qstruct["COND"])) {
        if (!$row && isset($qstruct["DATA"])) {
            $primary = _db_primary($table);
            $subcond = array();
            foreach ($qstruct["DATA"] as $row) {
                $subsubcond = array();
                foreach (split(",", $primary) as $primfield) {
                    $subsubcond[$primfield] = $row[$primfield];
                }
                $subcond[] = $subsubcond;
            }
            $cond = array($subcond);
        } else {
            $cond = _db_make_idcond($table, $row);
        }
    }
    $idcond = array("TABLE" => array($table), "FIELD" => array(), "COND" => $cond, "ORDER" => array(), "START" => 0, "COUNT" => 0);
    if ($ERROR) {
        $ERROR = "in table '{$table}': {$ERROR}";
    }
    return $idcond;
}