]> git.joonet.de Git - adminer.git/commitdiff
Move partitioning functions
authorJakub Vrana <jakub@vrana.cz>
Mon, 14 Apr 2025 11:51:43 +0000 (13:51 +0200)
committerJakub Vrana <jakub@vrana.cz>
Mon, 14 Apr 2025 11:54:20 +0000 (13:54 +0200)
adminer/create.inc.php
adminer/drivers/mysql.inc.php
adminer/include/driver.inc.php
adminer/include/editing.inc.php

index cf28adf247c3fc9af4e139f4ea967135569557e5..4eddfba421fa4db6326b7da83976d1a7a434ec48 100644 (file)
@@ -2,10 +2,8 @@
 namespace Adminer;
 
 $TABLE = $_GET["create"];
-$partition_by = array();
-foreach (array('HASH', 'LINEAR HASH', 'KEY', 'LINEAR KEY', 'RANGE', 'LIST') as $key) {
-       $partition_by[$key] = $key;
-}
+$partition_by = driver()->partitionBy;
+$partitions_info = driver()->partitionsInfo($TABLE);
 
 $referencable_primary = referencable_primary($TABLE);
 $foreign_keys = array();
@@ -81,39 +79,37 @@ if ($_POST && !process_fields($row["fields"]) && !$error) {
                }
 
                $partitioning = "";
-               if (support("partitioning")) {
-                       if (isset($partition_by[$row["partition_by"]])) {
-                               $params = array();
-                               foreach ($row as $key => $val) {
-                                       if (preg_match('~^partition~', $key)) {
-                                               $params[$key] = $val;
-                                       }
+               if (in_array($row["partition_by"], $partition_by)) {
+                       $params = array();
+                       foreach ($row as $key => $val) {
+                               if (preg_match('~^partition~', $key)) {
+                                       $params[$key] = $val;
                                }
-                               foreach ($params["partition_names"] as $key => $name) {
-                                       if ($name == "") {
-                                               unset($params["partition_names"][$key]);
-                                               unset($params["partition_values"][$key]);
-                                       }
+                       }
+                       foreach ($params["partition_names"] as $key => $name) {
+                               if ($name == "") {
+                                       unset($params["partition_names"][$key]);
+                                       unset($params["partition_values"][$key]);
                                }
-                               if ($params != get_partitions_info($TABLE)) {
-                                       $partitions = array();
-                                       if ($params["partition_by"] == 'RANGE' || $params["partition_by"] == 'LIST') {
-                                               foreach ($params["partition_names"] as $key => $name) {
-                                                       $value = $params["partition_values"][$key];
-                                                       $partitions[] = "\n  PARTITION " . idf_escape($name) . " VALUES " . ($params["partition_by"] == 'RANGE' ? "LESS THAN" : "IN") . ($value != "" ? " ($value)" : " MAXVALUE"); //! SQL injection
-                                               }
-                                       }
-                                       // $params["partition"] can be expression, not only column
-                                       $partitioning .= "\nPARTITION BY $params[partition_by]($params[partition])";
-                                       if ($partitions) {
-                                               $partitioning .= " (" . implode(",", $partitions) . "\n)";
-                                       } elseif ($params["partitions"]) {
-                                               $partitioning .= " PARTITIONS " . (+$params["partitions"]);
+                       }
+                       if ($params != $partitions_info) {
+                               $partitions = array();
+                               if ($params["partition_by"] == 'RANGE' || $params["partition_by"] == 'LIST') {
+                                       foreach ($params["partition_names"] as $key => $name) {
+                                               $value = $params["partition_values"][$key];
+                                               $partitions[] = "\n  PARTITION " . idf_escape($name) . " VALUES " . ($params["partition_by"] == 'RANGE' ? "LESS THAN" : "IN") . ($value != "" ? " ($value)" : " MAXVALUE"); //! SQL injection
                                        }
                                }
-                       } elseif (preg_match("~partitioned~", $table_status["Create_options"])) {
-                               $partitioning .= "\nREMOVE PARTITIONING";
+                               // $params["partition"] can be expression, not only column
+                               $partitioning .= "\nPARTITION BY $params[partition_by]($params[partition])";
+                               if ($partitions) {
+                                       $partitioning .= " (" . implode(",", $partitions) . "\n)";
+                               } elseif ($params["partitions"]) {
+                                       $partitioning .= " PARTITIONS " . (+$params["partitions"]);
+                               }
                        }
+               } elseif (preg_match("~partitioned~", $table_status["Create_options"])) {
+                       $partitioning .= "\nREMOVE PARTITIONING";
                }
 
                $message = lang('Table has been altered.');
@@ -159,8 +155,8 @@ if (!$_POST) {
                        $row["fields"][] = $field;
                }
 
-               if (support("partitioning")) {
-                       $row += get_partitions_info($TABLE);
+               if ($partition_by) {
+                       $row += $partitions_info;
                        $row["partition_names"][] = "";
                        $row["partition_values"][] = "";
                }
@@ -221,10 +217,10 @@ if (support("columns")) {
 <input type="submit" name="drop" value="<?php echo lang('Drop'); ?>"><?php echo confirm(lang('Drop %s?', $TABLE)); ?>
 <?php } ?>
 <?php
-if (support("partitioning")) {
+if ($partition_by && (JUSH == 'sql' || $TABLE == "")) {
        $partition_table = preg_match('~RANGE|LIST~', $row["partition_by"]);
        print_fieldset("partition", lang('Partition by'), $row["partition_by"]);
-       echo "<p>" . html_select("partition_by", array("" => "") + $partition_by, $row["partition_by"]) . on_help("event.target.value.replace(/./, 'PARTITION BY \$&')", 1) . script("qsl('select').onchange = partitionByChange;");
+       echo "<p>" . html_select("partition_by", array_merge(array(""), $partition_by), $row["partition_by"]) . on_help("event.target.value.replace(/./, 'PARTITION BY \$&')", 1) . script("qsl('select').onchange = partitionByChange;");
        echo "(<input name='partition' value='" . h($row["partition"]) . "'>)\n";
        echo lang('Partitions') . ": <input type='number' name='partitions' class='size" . ($partition_table || !$row["partition_by"] ? " hidden" : "") . "' value='" . h($row["partitions"]) . "'>\n";
        echo "<table id='partition-table'" . ($partition_table ? "" : " class='hidden'") . ">\n";
index 33f5ef4b7f6ac7182594a04f9e785d53adba1459..4309de3d12b08edaabedad2610c22bb62e68f8f1 100644 (file)
@@ -258,6 +258,9 @@ if (!defined('Adminer\DRIVER')) {
                                $this->types[lang('Numbers')]["vector"] = 16383;
                                $this->insertFunctions['vector'] = 'string_to_vector';
                        }
+                       if (min_version(5.1, '', $connection)) {
+                               $this->partitionBy = array("HASH", "LINEAR HASH", "KEY", "LINEAR KEY", "RANGE", "LIST");
+                       }
                        if (min_version(5.7, 10.2, $connection)) {
                                $this->generated = array("STORED", "VIRTUAL");
                        }
@@ -335,6 +338,17 @@ if (!defined('Adminer\DRIVER')) {
                        }
                }
 
+               function partitionsInfo(string $table): array {
+                       $from = "FROM information_schema.PARTITIONS WHERE TABLE_SCHEMA = " . q(DB) . " AND TABLE_NAME = " . q($table);
+                       $result = connection()->query("SELECT PARTITION_METHOD, PARTITION_EXPRESSION, PARTITION_ORDINAL_POSITION $from ORDER BY PARTITION_ORDINAL_POSITION DESC LIMIT 1");
+                       $return = array();
+                       list($return["partition_by"], $return["partition"], $return["partitions"]) = $result->fetch_row();
+                       $partitions = get_key_vals("SELECT PARTITION_NAME, PARTITION_DESCRIPTION $from AND PARTITION_NAME != '' ORDER BY PARTITION_ORDINAL_POSITION");
+                       $return["partition_names"] = array_keys($partitions);
+                       $return["partition_values"] = array_values($partitions);
+                       return $return;
+               }
+
                function hasCStyleEscapes(): bool {
                        static $c_style;
                        if ($c_style === null) {
@@ -1012,10 +1026,10 @@ if (!defined('Adminer\DRIVER')) {
        }
 
        /** Check whether a feature is supported
-       * @param literal-string $feature "check|comment|copy|database|descidx|drop_col|dump|event|indexes|kill|materializedview|partitioning|privileges|procedure|processlist|routine|scheme|sequence|status|table|trigger|type|variables|view|view_trigger"
+       * @param literal-string $feature "check|comment|copy|database|descidx|drop_col|dump|event|indexes|kill|materializedview|privileges|procedure|processlist|routine|scheme|sequence|status|table|trigger|type|variables|view|view_trigger"
        */
        function support(string $feature): bool {
-               return !preg_match("~scheme|sequence|type|view_trigger|materializedview" . (min_version(8) ? "" : "|descidx" . (min_version(5.1) ? "" : "|event|partitioning")) . (min_version('8.0.16', '10.2.1') ? "" : "|check") . "~", $feature);
+               return !preg_match("~scheme|sequence|type|view_trigger|materializedview" . (min_version(8) ? "" : "|descidx" . (min_version(5.1) ? "" : "|event")) . (min_version('8.0.16', '10.2.1') ? "" : "|check") . "~", $feature);
        }
 
        /** Kill a process
index 8cd1b2084bbf7dd1b45c1c650204616ccdc63a5e..f3a59819e2cec6045593c154972fe99f32742998 100644 (file)
@@ -26,6 +26,7 @@ abstract class SqlDriver {
        /** @var list<string> */ public $functions = array(); // functions used in select
        /** @var list<string> */ public $grouping = array(); // grouping functions used in select
        /** @var string */ public $onActions = "RESTRICT|NO ACTION|CASCADE|SET NULL|SET DEFAULT"; // used in foreign_keys()
+       /** @var list<string> */ public $partitionBy = array(); // supported partitioning types
        /** @var string */ public $inout = "IN|OUT|INOUT"; // used in routines
        /** @var string */ public $enumLength = "'(?:''|[^'\\\\]|\\\\.)*'"; // regular expression for parsing enum lengths
        /** @var list<string> */ public $generated = array(); // allowed types of generated columns
@@ -231,6 +232,13 @@ abstract class SqlDriver {
                return array();
        }
 
+       /** Get partitions info
+       * @return array{partition_by?:string, partition?:string, partitions?:string, partition_names?:list<string>, partition_values?:list<string>}
+       */
+       function partitionsInfo(string $table): array {
+               return array();
+       }
+
        /** Check if C-style escapes are supported */
        function hasCStyleEscapes(): bool {
                return false;
index 4af1f2722e22459bfe02fddc8fc60ffc9203ae6f..a7d3382a92264b1d831305fb65c929dc63ab291e 100644 (file)
@@ -201,20 +201,6 @@ function edit_type(string $key, array $field, array $collations, array $foreign_
        );
 }
 
-/** Get partition info
-* @return array{partition_by:string, partition:string, partitions:string, partition_names:list<string>, partition_values:list<string>}
-*/
-function get_partitions_info(string $table): array {
-       $from = "FROM information_schema.PARTITIONS WHERE TABLE_SCHEMA = " . q(DB) . " AND TABLE_NAME = " . q($table);
-       $result = connection()->query("SELECT PARTITION_METHOD, PARTITION_EXPRESSION, PARTITION_ORDINAL_POSITION $from ORDER BY PARTITION_ORDINAL_POSITION DESC LIMIT 1");
-       $return = array();
-       list($return["partition_by"], $return["partition"], $return["partitions"]) = $result->fetch_row();
-       $partitions = get_key_vals("SELECT PARTITION_NAME, PARTITION_DESCRIPTION $from AND PARTITION_NAME != '' ORDER BY PARTITION_ORDINAL_POSITION");
-       $return["partition_names"] = array_keys($partitions);
-       $return["partition_values"] = array_values($partitions);
-       return $return;
-}
-
 /** Filter length value including enums */
 function process_length(?string $length): string {
        $enum_length = driver()->enumLength;