Search moodle.org's
Developer Documentation

See Release Notes
Long Term Support Release

  • Bug fixes for general core bugs in 4.1.x will end 13 November 2023 (12 months).
  • Bug fixes for security issues in 4.1.x will end 10 November 2025 (36 months).
  • PHP version: minimum PHP 7.4.0 Note: minimum PHP version has increased since Moodle 4.0. PHP 8.0.x is supported too.
   1  <?php
   2  // This file is part of Moodle - http://moodle.org/
   3  //
   4  // Moodle is free software: you can redistribute it and/or modify
   5  // it under the terms of the GNU General Public License as published by
   6  // the Free Software Foundation, either version 3 of the License, or
   7  // (at your option) any later version.
   8  //
   9  // Moodle is distributed in the hope that it will be useful,
  10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12  // GNU General Public License for more details.
  13  //
  14  // You should have received a copy of the GNU General Public License
  15  // along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
  16  
  17  /**
  18   * @package    tool_xmldb
  19   * @copyright  2003 onwards Eloy Lafuente (stronk7) {@link http://stronk7.com}
  20   * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  21   */
  22  
  23  /**
  24   * This class will show the PHP needed (upgrade block) to perform
  25   * the desired DDL action with the specified field/key/index
  26   *
  27   * @package    tool_xmldb
  28   * @copyright  2003 onwards Eloy Lafuente (stronk7) {@link http://stronk7.com}
  29   * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  30   */
  31  class view_table_php extends XMLDBAction {
  32  
  33      /**
  34       * Init method, every subclass will have its own
  35       */
  36      function init() {
  37          parent::init();
  38  
  39          // Set own custom attributes
  40          $this->sesskey_protected = false; // This action doesn't need sesskey protection
  41  
  42          // Get needed strings
  43          $this->loadStrings(array(
  44              'selectaction' => 'tool_xmldb',
  45              'selectfieldkeyindex' => 'tool_xmldb',
  46              'view' => 'tool_xmldb',
  47              'table' => 'tool_xmldb',
  48              'selectonecommand' => 'tool_xmldb',
  49              'selectonefieldkeyindex' => 'tool_xmldb',
  50              'mustselectonefield' => 'tool_xmldb',
  51              'mustselectonekey' => 'tool_xmldb',
  52              'mustselectoneindex' => 'tool_xmldb',
  53              'back' => 'tool_xmldb'
  54          ));
  55      }
  56  
  57      /**
  58       * Invoke method, every class will have its own
  59       * returns true/false on completion, setting both
  60       * errormsg and output as necessary
  61       */
  62      function invoke() {
  63          parent::invoke();
  64  
  65          $result = true;
  66  
  67          // Set own core attributes
  68          $this->does_generate = ACTION_GENERATE_HTML;
  69  
  70          // These are always here
  71          global $CFG, $XMLDB, $OUTPUT;
  72  
  73          // Do the job, setting result as needed
  74          // Get the dir containing the file
  75          $dirpath = required_param('dir', PARAM_PATH);
  76          $dirpath = $CFG->dirroot . $dirpath;
  77  
  78          // Get the correct dirs
  79          if (!empty($XMLDB->dbdirs)) {
  80              $dbdir = $XMLDB->dbdirs[$dirpath];
  81          } else {
  82              return false;
  83          }
  84          if (!empty($XMLDB->editeddirs)) {
  85              $editeddir = $XMLDB->editeddirs[$dirpath];
  86              $structure = $editeddir->xml_file->getStructure();
  87          }
  88  
  89          $tableparam = required_param('table', PARAM_PATH);
  90  
  91          $table = $structure->getTable($tableparam);
  92          $fields = $table->getFields();
  93          $field = reset($fields);
  94          $defaultfieldkeyindex = null;
  95          if ($field) {
  96              $defaultfieldkeyindex = 'f#' . $field->getName();
  97          }
  98          $keys = $table->getKeys();
  99          $indexes = $table->getIndexes();
 100  
 101          // Get parameters
 102          $commandparam = optional_param('command', 'add_field', PARAM_PATH);
 103          $origfieldkeyindexparam = optional_param('fieldkeyindex', $defaultfieldkeyindex, PARAM_PATH);
 104          $fieldkeyindexparam = preg_replace('/[fki]#/i', '', $origfieldkeyindexparam); // Strip the initials
 105          $fieldkeyindexinitial = substr($origfieldkeyindexparam, 0, 1); //To know what we have selected
 106  
 107          // The back to edit xml button
 108          $b = ' <p class="centerpara buttons">';
 109          $b .= '<a href="index.php?action=edit_table&amp;dir=' . urlencode(str_replace($CFG->dirroot, '', $dirpath)) . '&amp;table=' . $tableparam . '">[' . $this->str['back'] . ']</a>';
 110          $b .= '</p>';
 111          $o = $b;
 112  
 113          // The table currently being edited
 114          $o .= '<h3 class="main">' . $this->str['table'] . ': ' . s($tableparam) . '</h3>';
 115  
 116          // To indent the menu selections
 117          $optionspacer = '&nbsp;&nbsp;&nbsp;';
 118  
 119          // Calculate the popup of commands
 120          $commands = array('Fields',
 121                           $optionspacer . 'add_field',
 122                           $optionspacer . 'drop_field',
 123                           $optionspacer . 'rename_field',
 124                           $optionspacer . 'change_field_type',
 125                           $optionspacer . 'change_field_precision',
 126                           $optionspacer . 'change_field_notnull',
 127                           $optionspacer . 'change_field_default',
 128                           'Keys',
 129                           $optionspacer . 'add_key',
 130                           $optionspacer . 'drop_key',
 131                           $optionspacer . 'rename_key',
 132                           'Indexes',
 133                           $optionspacer . 'add_index',
 134                           $optionspacer . 'drop_index',
 135                           $optionspacer . 'rename_index');
 136          foreach ($commands as $command) {
 137              $popcommands[str_replace($optionspacer, '', $command)] = str_replace('_', ' ', $command);
 138          }
 139          // Calculate the popup of fields/keys/indexes
 140          if ($fields) {
 141              $popfields['fieldshead'] = 'Fields';
 142              foreach ($fields as $field) {
 143                  $popfields['f#' . $field->getName()] = $optionspacer . $field->getName();
 144              }
 145          }
 146          if ($keys) {
 147              $popfields['keyshead'] = 'Keys';
 148              foreach ($keys as $key) {
 149                  $popfields['k#' . $key->getName()] = $optionspacer . $key->getName();
 150              }
 151          }
 152          if ($indexes) {
 153              $popfields['indexeshead'] = 'Indexes';
 154              foreach ($indexes as $index) {
 155                  $popfields['i#' . $index->getName()] = $optionspacer . $index->getName();
 156              }
 157          }
 158  
 159          // Now build the form
 160          $o.= '<form id="form" action="index.php" method="post">';
 161          $o.= '<div>';
 162          $o.= '    <input type="hidden" name ="dir" value="' . str_replace($CFG->dirroot, '', $dirpath) . '" />';
 163          $o.= '    <input type="hidden" name ="table" value="' . s($tableparam) . '" />';
 164          $o.= '    <input type="hidden" name ="action" value="view_table_php" />';
 165          $o .= '    <table id="formelements" cellpadding="5">';
 166          $o.= '      <tr><td><label for="menucommand" accesskey="c">' . $this->str['selectaction'] .' </label>' . html_writer::select($popcommands, 'command', $commandparam, false) . '&nbsp;<label for="menufieldkeyindex" accesskey="f">' . $this->str['selectfieldkeyindex'] . ' </label>' .html_writer::select($popfields, 'fieldkeyindex', $origfieldkeyindexparam, false) . '</td></tr>';
 167          $o.= '      <tr><td colspan="2" align="center"><input type="submit" value="' .$this->str['view'] . '" /></td></tr>';
 168          $o.= '    </table>';
 169          $o.= '</div></form>';
 170  
 171          $o.= '    <table id="phpcode" class="boxaligncenter" cellpadding="5">';
 172          $o .= '      <tr><td><textarea cols="80" rows="32" class="form-control">';
 173          // Check we have selected some field/key/index from the popup
 174          if ($fieldkeyindexparam == 'fieldshead' || $fieldkeyindexparam == 'keyshead' || $fieldkeyindexparam == 'indexeshead') {
 175              $o.= s($this->str['selectonefieldkeyindex']);
 176          // Check we have selected some command from the popup
 177          } else if ($commandparam == 'Fields' || $commandparam == 'Keys' || $commandparam == 'Indexes') {
 178              $o.= s($this->str['selectonecommand']);
 179          } else {
 180              // Based on current params, call the needed function
 181              switch ($commandparam) {
 182                  case 'add_field':
 183                      if ($fieldkeyindexinitial == 'f') { //Only if we have got one field
 184                          $o.= s($this->add_field_php($structure, $tableparam, $fieldkeyindexparam));
 185                      } else {
 186                          $o.= $this->str['mustselectonefield'];
 187                      }
 188                      break;
 189                  case 'drop_field':
 190                      if ($fieldkeyindexinitial == 'f') { //Only if we have got one field
 191                          $o.= s($this->drop_field_php($structure, $tableparam, $fieldkeyindexparam));
 192                      } else {
 193                          $o.= $this->str['mustselectonefield'];
 194                      }
 195                      break;
 196                  case 'rename_field':
 197                      if ($fieldkeyindexinitial == 'f') { //Only if we have got one field
 198                          $o.= s($this->rename_field_php($structure, $tableparam, $fieldkeyindexparam));
 199                      } else {
 200                          $o.= $this->str['mustselectonefield'];
 201                      }
 202                      break;
 203                  case 'change_field_type':
 204                      if ($fieldkeyindexinitial == 'f') { //Only if we have got one field
 205                          $o.= s($this->change_field_type_php($structure, $tableparam, $fieldkeyindexparam));
 206                      } else {
 207                          $o.= $this->str['mustselectonefield'];
 208                      }
 209                      break;
 210                  case 'change_field_precision':
 211                      if ($fieldkeyindexinitial == 'f') { //Only if we have got one field
 212                          $o.= s($this->change_field_precision_php($structure, $tableparam, $fieldkeyindexparam));
 213                      } else {
 214                          $o.= $this->str['mustselectonefield'];
 215                      }
 216                      break;
 217                  case 'change_field_notnull':
 218                      if ($fieldkeyindexinitial == 'f') { // Only if we have got one field
 219                          $o.= s($this->change_field_notnull_php($structure, $tableparam, $fieldkeyindexparam));
 220                      } else {
 221                          $o.= $this->str['mustselectonefield'];
 222                      }
 223                      break;
 224                  case 'change_field_default':
 225                      if ($fieldkeyindexinitial == 'f') { // Only if we have got one field
 226                          $o.= s($this->change_field_default_php($structure, $tableparam, $fieldkeyindexparam));
 227                      } else {
 228                          $o.= $this->str['mustselectonefield'];
 229                      }
 230                      break;
 231                  case 'add_key':
 232                      if ($fieldkeyindexinitial == 'k') { // Only if we have got one key
 233                          $o.= s($this->add_key_php($structure, $tableparam, $fieldkeyindexparam));
 234                      } else {
 235                          $o.= $this->str['mustselectonekey'];
 236                      }
 237                      break;
 238                  case 'drop_key':
 239                      if ($fieldkeyindexinitial == 'k') { // Only if we have got one key
 240                          $o.= s($this->drop_key_php($structure, $tableparam, $fieldkeyindexparam));
 241                      } else {
 242                          $o.= $this->str['mustselectonekey'];
 243                      }
 244                      break;
 245                  case 'rename_key':
 246                      if ($fieldkeyindexinitial == 'k') { // Only if we have got one key
 247                          $o.= s($this->rename_key_php($structure, $tableparam, $fieldkeyindexparam));
 248                      } else {
 249                          $o.= $this->str['mustselectonekey'];
 250                      }
 251                      break;
 252                  case 'add_index':
 253                      if ($fieldkeyindexinitial == 'i') { // Only if we have got one index
 254                          $o.= s($this->add_index_php($structure, $tableparam, $fieldkeyindexparam));
 255                      } else {
 256                          $o.= $this->str['mustselectoneindex'];
 257                      }
 258                      break;
 259                  case 'drop_index':
 260                      if ($fieldkeyindexinitial == 'i') { // Only if we have got one index
 261                          $o.= s($this->drop_index_php($structure, $tableparam, $fieldkeyindexparam));
 262                      } else {
 263                          $o.= $this->str['mustselectoneindex'];
 264                      }
 265                      break;
 266                  case 'rename_index':
 267                      if ($fieldkeyindexinitial == 'i') { // Only if we have got one index
 268                          $o.= s($this->rename_index_php($structure, $tableparam, $fieldkeyindexparam));
 269                      } else {
 270                          $o.= $this->str['mustselectoneindex'];
 271                      }
 272                      break;
 273              }
 274          }
 275          $o.= '</textarea></td></tr>';
 276          $o.= '    </table>';
 277  
 278          $this->output = $o;
 279  
 280          // Launch postaction if exists (leave this here!)
 281          if ($this->getPostAction() && $result) {
 282              return $this->launch($this->getPostAction());
 283          }
 284  
 285          // Return ok if arrived here
 286          return $result;
 287      }
 288  
 289      /**
 290       * This function will generate all the PHP code needed to
 291       * create one field using XMLDB objects and functions
 292       *
 293       * @param xmldb_structure structure object containing all the info
 294       * @param string table table name
 295       * @param string field field name to be created
 296       * @return string PHP code to be used to create the field
 297       */
 298      function add_field_php($structure, $table, $field) {
 299  
 300          $result = '';
 301          // Validate if we can do it
 302          if (!$table = $structure->getTable($table)) {
 303              return false;
 304          }
 305          if (!$field = $table->getField($field)) {
 306              return false;
 307          }
 308          if ($table->getAllErrors()) {
 309              return false;
 310          }
 311  
 312          // Add the standard PHP header
 313          $result .= XMLDB_PHP_HEADER;
 314  
 315          // Add contents
 316          $result .= XMLDB_LINEFEED;
 317          $result .= '        // Define field ' . $field->getName() . ' to be added to ' . $table->getName() . '.' . XMLDB_LINEFEED;
 318          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 319          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "', " . $field->getPHP(true) . ');' . XMLDB_LINEFEED;
 320  
 321          // Launch the proper DDL
 322          $result .= XMLDB_LINEFEED;
 323          $result .= '        // Conditionally launch add field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 324          $result .= '        if (!$dbman->field_exists($table, $field)) {'. XMLDB_LINEFEED;
 325          $result .= '            $dbman->add_field($table, $field);' . XMLDB_LINEFEED;
 326          $result .= '        }'. XMLDB_LINEFEED;
 327  
 328          // Add the proper upgrade_xxxx_savepoint call
 329          $result .= $this->upgrade_savepoint_php ($structure);
 330  
 331          // Add standard PHP footer
 332          $result .= XMLDB_PHP_FOOTER;
 333  
 334          return $result;
 335      }
 336  
 337      /**
 338       * This function will generate all the PHP code needed to
 339       * drop one field using XMLDB objects and functions
 340       *
 341       * @param xmldb_structure structure object containing all the info
 342       * @param string table table name
 343       * @param string field field name to be dropped
 344       * @return string PHP code to be used to drop the field
 345       */
 346      function drop_field_php($structure, $table, $field) {
 347  
 348          $result = '';
 349          // Validate if we can do it
 350          if (!$table = $structure->getTable($table)) {
 351              return false;
 352          }
 353          if (!$field = $table->getField($field)) {
 354              return false;
 355          }
 356          if ($table->getAllErrors()) {
 357              return false;
 358          }
 359  
 360          // Add the standard PHP header
 361          $result .= XMLDB_PHP_HEADER;
 362  
 363          // Add contents
 364          $result .= XMLDB_LINEFEED;
 365          $result .= '        // Define field ' . $field->getName() . ' to be dropped from ' . $table->getName() . '.' . XMLDB_LINEFEED;
 366          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 367          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "'" . ');' . XMLDB_LINEFEED;
 368  
 369          // Launch the proper DDL
 370          $result .= XMLDB_LINEFEED;
 371          $result .= '        // Conditionally launch drop field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 372          $result .= '        if ($dbman->field_exists($table, $field)) {' . XMLDB_LINEFEED;
 373          $result .= '            $dbman->drop_field($table, $field);' . XMLDB_LINEFEED;
 374          $result .= '        }' . XMLDB_LINEFEED;
 375  
 376          // Add the proper upgrade_xxxx_savepoint call
 377          $result .= $this->upgrade_savepoint_php ($structure);
 378  
 379          // Add standard PHP footer
 380          $result .= XMLDB_PHP_FOOTER;
 381  
 382          return $result;
 383      }
 384  
 385      /**
 386       * This function will generate all the PHP code needed to
 387       * rename one field using XMLDB objects and functions
 388       *
 389       * @param xmldb_structure structure object containing all the info
 390       * @param string table table name
 391       * @param string field field name to be renamed
 392       * @return string PHP code to be used to rename the field
 393       */
 394      function rename_field_php($structure, $table, $field) {
 395  
 396          $result = '';
 397          // Validate if we can do it
 398          if (!$table = $structure->getTable($table)) {
 399              return false;
 400          }
 401          if (!$field = $table->getField($field)) {
 402              return false;
 403          }
 404          if ($table->getAllErrors()) {
 405              return false;
 406          }
 407  
 408          // Add the standard PHP header
 409          $result .= XMLDB_PHP_HEADER;
 410  
 411          // Add contents
 412          $result .= XMLDB_LINEFEED;
 413          $result .= '        // Rename field ' . $field->getName() . ' on table ' . $table->getName() . ' to NEWNAMEGOESHERE.'. XMLDB_LINEFEED;
 414          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 415          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "', " . $field->getPHP(true) . ');' . XMLDB_LINEFEED;
 416  
 417          // Launch the proper DDL
 418          $result .= XMLDB_LINEFEED;
 419          $result .= '        // Launch rename field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 420          $result .= '        $dbman->rename_field($table, $field, ' . "'" . 'NEWNAMEGOESHERE' . "'" . ');' . XMLDB_LINEFEED;
 421  
 422          // Add the proper upgrade_xxxx_savepoint call
 423          $result .= $this->upgrade_savepoint_php ($structure);
 424  
 425          // Add standard PHP footer
 426          $result .= XMLDB_PHP_FOOTER;
 427  
 428          return $result;
 429      }
 430  
 431      /**
 432       * This function will generate all the PHP code needed to
 433       * change the type of one field using XMLDB objects and functions.
 434       * Currently these conversions are supported:
 435       *     integer to char
 436       *     char to integer
 437       *     number to char
 438       *     char to number
 439       *     float to char
 440       *     char to float
 441       *
 442       * @param xmldb_structure structure object containing all the info
 443       * @param string table table name
 444       * @param string field field name to change precision
 445       */
 446      function change_field_type_php($structure, $table, $field) {
 447  
 448          $result = '';
 449          // Validate if we can do it
 450          if (!$table = $structure->getTable($table)) {
 451              return false;
 452          }
 453          if (!$field = $table->getField($field)) {
 454              return false;
 455          }
 456          if ($table->getAllErrors()) {
 457              return false;
 458          }
 459  
 460          // Calculate the type tip text
 461          $type = $field->getXMLDBTypeName($field->getType());
 462  
 463          // Add the standard PHP header
 464          $result .= XMLDB_PHP_HEADER;
 465  
 466          // Add contents
 467          $result .= XMLDB_LINEFEED;
 468          $result .= '        // Changing type of field ' . $field->getName() . ' on table ' . $table->getName() . ' to ' . $type . '.' . XMLDB_LINEFEED;
 469          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 470          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "', " . $field->getPHP(true) . ');' . XMLDB_LINEFEED;
 471  
 472          // Launch the proper DDL
 473          $result .= XMLDB_LINEFEED;
 474          $result .= '        // Launch change of type for field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 475          $result .= '        $dbman->change_field_type($table, $field);' . XMLDB_LINEFEED;
 476  
 477          // Add the proper upgrade_xxxx_savepoint call
 478          $result .= $this->upgrade_savepoint_php ($structure);
 479  
 480          // Add standard PHP footer
 481          $result .= XMLDB_PHP_FOOTER;
 482  
 483          return $result;
 484      }
 485  
 486      /**
 487       * This function will generate all the PHP code needed to
 488       * change the precision of one field using XMLDB objects and functions
 489       *
 490       * @param xmldb_structure structure object containing all the info
 491       * @param string table table name
 492       * @param string field field name to change precision
 493       */
 494      function change_field_precision_php($structure, $table, $field) {
 495  
 496          $result = '';
 497          // Validate if we can do it
 498          if (!$table = $structure->getTable($table)) {
 499              return false;
 500          }
 501          if (!$field = $table->getField($field)) {
 502              return false;
 503          }
 504          if ($table->getAllErrors()) {
 505              return false;
 506          }
 507  
 508          // Calculate the precision tip text
 509          $precision = '(' . $field->getLength();
 510          if ($field->getDecimals()) {
 511              $precision .= ', ' . $field->getDecimals();
 512          }
 513          $precision .= ')';
 514  
 515          // Add the standard PHP header
 516          $result .= XMLDB_PHP_HEADER;
 517  
 518          // Add contents
 519          $result .= XMLDB_LINEFEED;
 520          $result .= '        // Changing precision of field ' . $field->getName() . ' on table ' . $table->getName() . ' to ' . $precision . '.' . XMLDB_LINEFEED;
 521          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 522          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "', " . $field->getPHP(true) . ');' . XMLDB_LINEFEED;
 523  
 524          // Launch the proper DDL
 525          $result .= XMLDB_LINEFEED;
 526          $result .= '        // Launch change of precision for field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 527          $result .= '        $dbman->change_field_precision($table, $field);' . XMLDB_LINEFEED;
 528  
 529          // Add the proper upgrade_xxxx_savepoint call
 530          $result .= $this->upgrade_savepoint_php ($structure);
 531  
 532          // Add standard PHP footer
 533          $result .= XMLDB_PHP_FOOTER;
 534  
 535          return $result;
 536      }
 537  
 538      /**
 539       * This function will generate all the PHP code needed to
 540       * change the nullability of one field using XMLDB objects and functions
 541       *
 542       * @param xmldb_structure structure object containing all the info
 543       * @param string table table name
 544       * @param string field field name to change null/not null
 545       */
 546      function change_field_notnull_php($structure, $table, $field) {
 547  
 548          $result = '';
 549          // Validate if we can do it
 550          if (!$table = $structure->getTable($table)) {
 551              return false;
 552          }
 553          if (!$field = $table->getField($field)) {
 554              return false;
 555          }
 556          if ($table->getAllErrors()) {
 557              return false;
 558          }
 559  
 560          // Calculate the notnull tip text
 561          $notnull = $field->getNotnull() ? 'not null' : 'null';
 562  
 563          // Add the standard PHP header
 564          $result .= XMLDB_PHP_HEADER;
 565  
 566          // Add contents
 567          $result .= XMLDB_LINEFEED;
 568          $result .= '        // Changing nullability of field ' . $field->getName() . ' on table ' . $table->getName() . ' to ' . $notnull . '.' . XMLDB_LINEFEED;
 569          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 570          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "', " . $field->getPHP(true) . ');' . XMLDB_LINEFEED;
 571  
 572          // Launch the proper DDL
 573          $result .= XMLDB_LINEFEED;
 574          $result .= '        // Launch change of nullability for field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 575          $result .= '        $dbman->change_field_notnull($table, $field);' . XMLDB_LINEFEED;
 576  
 577          // Add the proper upgrade_xxxx_savepoint call
 578          $result .= $this->upgrade_savepoint_php ($structure);
 579  
 580          // Add standard PHP footer
 581          $result .= XMLDB_PHP_FOOTER;
 582  
 583          return $result;
 584      }
 585  
 586      /**
 587       * This function will generate all the PHP code needed to
 588       * change the default of one field using XMLDB objects and functions
 589       *
 590       * @param xmldb_structure structure object containing all the info
 591       * @param string table table name
 592       * @param string field field name to change null/not null
 593       */
 594      function change_field_default_php($structure, $table, $field) {
 595  
 596          $result = '';
 597          // Validate if we can do it
 598          if (!$table = $structure->getTable($table)) {
 599              return false;
 600          }
 601          if (!$field = $table->getField($field)) {
 602              return false;
 603          }
 604          if ($table->getAllErrors()) {
 605              return false;
 606          }
 607  
 608          // Calculate the default tip text
 609          $default = $field->getDefault() === null ? 'drop it' : $field->getDefault();
 610  
 611          // Add the standard PHP header
 612          $result .= XMLDB_PHP_HEADER;
 613  
 614          // Add contents
 615          $result .= XMLDB_LINEFEED;
 616          $result .= '        // Changing the default of field ' . $field->getName() . ' on table ' . $table->getName() . ' to ' . $default . '.' . XMLDB_LINEFEED;
 617          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 618          $result .= '        $field = new xmldb_field(' . "'" . $field->getName() . "', " . $field->getPHP(true) . ');' . XMLDB_LINEFEED;
 619  
 620          // Launch the proper DDL
 621          $result .= XMLDB_LINEFEED;
 622          $result .= '        // Launch change of default for field ' . $field->getName() . '.' . XMLDB_LINEFEED;
 623          $result .= '        $dbman->change_field_default($table, $field);' . XMLDB_LINEFEED;
 624  
 625          // Add the proper upgrade_xxxx_savepoint call
 626          $result .= $this->upgrade_savepoint_php ($structure);
 627  
 628          // Add standard PHP footer
 629          $result .= XMLDB_PHP_FOOTER;
 630  
 631          return $result;
 632      }
 633  
 634      /**
 635       * This function will generate all the PHP code needed to
 636       * create one key using XMLDB objects and functions
 637       *
 638       * @param xmldb_structure structure object containing all the info
 639       * @param string table table name
 640       * @param string key key name to be created
 641       * @return string PHP code to be used to create the key
 642       */
 643      function add_key_php($structure, $table, $key) {
 644  
 645          $result = '';
 646          // Validate if we can do it
 647          if (!$table = $structure->getTable($table)) {
 648              return false;
 649          }
 650          if (!$key = $table->getKey($key)) {
 651              return false;
 652          }
 653          if ($table->getAllErrors()) {
 654              return false;
 655          }
 656  
 657          // Add the standard PHP header
 658          $result .= XMLDB_PHP_HEADER;
 659  
 660          // Add contents
 661          $result .= XMLDB_LINEFEED;
 662          $result .= '        // Define key ' . $key->getName() . ' ('. $key->getXMLDBKeyName($key->getType()) . ') to be added to ' . $table->getName() . '.' . XMLDB_LINEFEED;
 663          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 664          $result .= '        $key = new xmldb_key(' . "'" . $key->getName() . "', " . $key->getPHP(true) . ');' . XMLDB_LINEFEED;
 665  
 666          // Launch the proper DDL
 667          $result .= XMLDB_LINEFEED;
 668          $result .= '        // Launch add key ' . $key->getName() . '.' . XMLDB_LINEFEED;
 669          $result .= '        $dbman->add_key($table, $key);' . XMLDB_LINEFEED;
 670  
 671          // Add the proper upgrade_xxxx_savepoint call
 672          $result .= $this->upgrade_savepoint_php ($structure);
 673  
 674          // Add standard PHP footer
 675          $result .= XMLDB_PHP_FOOTER;
 676  
 677          return $result;
 678      }
 679  
 680      /**
 681       * This function will generate all the PHP code needed to
 682       * drop one key using XMLDB objects and functions
 683       *
 684       * @param xmldb_structure structure object containing all the info
 685       * @param string table table name
 686       * @param string key key name to be dropped
 687       * @return string PHP code to be used to drop the key
 688       */
 689      function drop_key_php($structure, $table, $key) {
 690  
 691          $result = '';
 692          // Validate if we can do it
 693          if (!$table = $structure->getTable($table)) {
 694              return false;
 695          }
 696          if (!$key = $table->getKey($key)) {
 697              return false;
 698          }
 699          if ($table->getAllErrors()) {
 700              return false;
 701          }
 702  
 703          // Add the standard PHP header
 704          $result .= XMLDB_PHP_HEADER;
 705  
 706          // Add contents
 707          $result .= XMLDB_LINEFEED;
 708          $result .= '        // Define key ' . $key->getName() . ' ('. $key->getXMLDBKeyName($key->getType()) . ') to be dropped form ' . $table->getName() . '.' . XMLDB_LINEFEED;
 709          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 710          $result .= '        $key = new xmldb_key(' . "'" . $key->getName() . "', " . $key->getPHP(true) . ');' . XMLDB_LINEFEED;
 711  
 712          // Launch the proper DDL
 713          $result .= XMLDB_LINEFEED;
 714          $result .= '        // Launch drop key ' . $key->getName() . '.' . XMLDB_LINEFEED;
 715          $result .= '        $dbman->drop_key($table, $key);' . XMLDB_LINEFEED;
 716  
 717          // Add the proper upgrade_xxxx_savepoint call
 718          $result .= $this->upgrade_savepoint_php ($structure);
 719  
 720          // Add standard PHP footer
 721          $result .= XMLDB_PHP_FOOTER;
 722  
 723          return $result;
 724      }
 725  
 726      /**
 727       * This function will generate all the PHP code needed to
 728       * rename one key using XMLDB objects and functions
 729       *
 730       * @param xmldb_structure structure object containing all the info
 731       * @param string table table name
 732       * @param string key key name to be renamed
 733       * @return string PHP code to be used to rename the key
 734       */
 735      function rename_key_php($structure, $table, $key) {
 736  
 737          $result = '';
 738          // Validate if we can do it
 739          if (!$table = $structure->getTable($table)) {
 740              return false;
 741          }
 742          if (!$key = $table->getKey($key)) {
 743              return false;
 744          }
 745          if ($table->getAllErrors()) {
 746              return false;
 747          }
 748  
 749          // Prepend warning. This function isn't usable!
 750          $result .= 'DON\'T USE THIS FUNCTION (IT\'S ONLY EXPERIMENTAL). SOME DBs DON\'T SUPPORT IT!' . XMLDB_LINEFEED . XMLDB_LINEFEED;
 751  
 752          // Add the standard PHP header
 753          $result .= XMLDB_PHP_HEADER;
 754  
 755          // Add contents
 756          $result .= XMLDB_LINEFEED;
 757          $result .= '        // Define key ' . $key->getName() . ' ('. $key->getXMLDBKeyName($key->getType()) . ') to be renamed to NEWNAMEGOESHERE.' . XMLDB_LINEFEED;
 758          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 759          $result .= '        $key = new xmldb_key(' . "'" . $key->getName() . "', " . $key->getPHP(true) . ');' . XMLDB_LINEFEED;
 760  
 761          // Launch the proper DDL
 762          $result .= XMLDB_LINEFEED;
 763          $result .= '        // Launch rename key ' . $key->getName() . '.' . XMLDB_LINEFEED;
 764          $result .= '        $dbman->rename_key($table, $key, ' . "'" . 'NEWNAMEGOESHERE' . "'" . ');' . XMLDB_LINEFEED;
 765  
 766          // Add the proper upgrade_xxxx_savepoint call
 767          $result .= $this->upgrade_savepoint_php ($structure);
 768  
 769          // Add standard PHP footer
 770          $result .= XMLDB_PHP_FOOTER;
 771  
 772          return $result;
 773      }
 774  
 775      /**
 776       * This function will generate all the PHP code needed to
 777       * create one index using XMLDB objects and functions
 778       *
 779       * @param xmldb_structure structure object containing all the info
 780       * @param string table table name
 781       * @param string index index name to be created
 782       * @return string PHP code to be used to create the index
 783       */
 784      function add_index_php($structure, $table, $index) {
 785  
 786          $result = '';
 787          // Validate if we can do it
 788          if (!$table = $structure->getTable($table)) {
 789              return false;
 790          }
 791          if (!$index = $table->getIndex($index)) {
 792              return false;
 793          }
 794          if ($table->getAllErrors()) {
 795              return false;
 796          }
 797  
 798          // Add the standard PHP header
 799          $result .= XMLDB_PHP_HEADER;
 800  
 801          // Add contents
 802          $result .= XMLDB_LINEFEED;
 803          $result .= '        // Define index ' . $index->getName() . ' ('. ($index->getUnique() ? 'unique' : 'not unique') . ') to be added to ' . $table->getName() . '.' . XMLDB_LINEFEED;
 804          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 805          $result .= '        $index = new xmldb_index(' . "'" . $index->getName() . "', " . $index->getPHP(true) . ');' . XMLDB_LINEFEED;
 806  
 807          // Launch the proper DDL
 808          $result .= XMLDB_LINEFEED;
 809          $result .= '        // Conditionally launch add index ' . $index->getName() . '.' . XMLDB_LINEFEED;
 810          $result .= '        if (!$dbman->index_exists($table, $index)) {' . XMLDB_LINEFEED;
 811          $result .= '            $dbman->add_index($table, $index);' . XMLDB_LINEFEED;
 812          $result .= '        }' . XMLDB_LINEFEED;
 813  
 814          // Add the proper upgrade_xxxx_savepoint call
 815          $result .= $this->upgrade_savepoint_php ($structure);
 816  
 817          // Add standard PHP footer
 818          $result .= XMLDB_PHP_FOOTER;
 819  
 820          return $result;
 821      }
 822  
 823      /**
 824       * This function will generate all the PHP code needed to
 825       * drop one index using XMLDB objects and functions
 826       *
 827       * @param xmldb_structure structure object containing all the info
 828       * @param string table table name
 829       * @param string index index name to be dropped
 830       * @return string PHP code to be used to drop the index
 831       */
 832      function drop_index_php($structure, $table, $index) {
 833  
 834          $result = '';
 835          // Validate if we can do it
 836          if (!$table = $structure->getTable($table)) {
 837              return false;
 838          }
 839          if (!$index = $table->getIndex($index)) {
 840              return false;
 841          }
 842          if ($table->getAllErrors()) {
 843              return false;
 844          }
 845  
 846          // Add the standard PHP header
 847          $result .= XMLDB_PHP_HEADER;
 848  
 849          // Add contents
 850          $result .= XMLDB_LINEFEED;
 851          $result .= '        // Define index ' . $index->getName() . ' ('. ($index->getUnique() ? 'unique' : 'not unique') . ') to be dropped form ' . $table->getName() . '.' . XMLDB_LINEFEED;
 852          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 853          $result .= '        $index = new xmldb_index(' . "'" . $index->getName() . "', " . $index->getPHP(true) . ');' . XMLDB_LINEFEED;
 854  
 855          // Launch the proper DDL
 856          $result .= XMLDB_LINEFEED;
 857          $result .= '        // Conditionally launch drop index ' . $index->getName() . '.' . XMLDB_LINEFEED;
 858          $result .= '        if ($dbman->index_exists($table, $index)) {' . XMLDB_LINEFEED;
 859          $result .= '            $dbman->drop_index($table, $index);' . XMLDB_LINEFEED;
 860          $result .= '        }' . XMLDB_LINEFEED;
 861  
 862          // Add the proper upgrade_xxxx_savepoint call
 863          $result .= $this->upgrade_savepoint_php ($structure);
 864  
 865          // Add standard PHP footer
 866          $result .= XMLDB_PHP_FOOTER;
 867  
 868          return $result;
 869      }
 870  
 871      /**
 872       * This function will generate all the PHP code needed to
 873       * rename one index using XMLDB objects and functions
 874       *
 875       * @param xmldb_structure structure object containing all the info
 876       * @param string table table name
 877       * @param string index index name to be renamed
 878       * @return string PHP code to be used to rename the index
 879       */
 880      function rename_index_php($structure, $table, $index) {
 881  
 882          $result = '';
 883          // Validate if we can do it
 884          if (!$table = $structure->getTable($table)) {
 885              return false;
 886          }
 887          if (!$index = $table->getIndex($index)) {
 888              return false;
 889          }
 890          if ($table->getAllErrors()) {
 891              return false;
 892          }
 893  
 894          // Prepend warning. This function isn't usable!
 895          $result .= 'DON\'T USE THIS FUNCTION (IT\'S ONLY EXPERIMENTAL). SOME DBs DON\'T SUPPORT IT!' . XMLDB_LINEFEED . XMLDB_LINEFEED;
 896  
 897          // Add the standard PHP header
 898          $result .= XMLDB_PHP_HEADER;
 899  
 900          // Add contents
 901          $result .= XMLDB_LINEFEED;
 902          $result .= '        // Define index ' . $index->getName() . ' ('. ($index->getUnique() ? 'unique' : 'not unique') . ') to be renamed to NEWNAMEGOESHERE.' . XMLDB_LINEFEED;
 903          $result .= '        $table = new xmldb_table(' . "'" . $table->getName() . "'" . ');' . XMLDB_LINEFEED;
 904          $result .= '        $index = new xmldb_index(' . "'" . $index->getName() . "', " . $index->getPHP(true) . ');' . XMLDB_LINEFEED;
 905  
 906          // Launch the proper DDL
 907          $result .= XMLDB_LINEFEED;
 908          $result .= '        // Launch rename index ' . $index->getName() . '.' . XMLDB_LINEFEED;
 909          $result .= '        $dbman->rename_index($table, $index, ' . "'" . 'NEWNAMEGOESHERE' . "'" . ');' . XMLDB_LINEFEED;
 910  
 911          // Add the proper upgrade_xxxx_savepoint call
 912          $result .= $this->upgrade_savepoint_php ($structure);
 913  
 914          // Add standard PHP footer
 915          $result .= XMLDB_PHP_FOOTER;
 916  
 917          return $result;
 918      }
 919  
 920  }
 921