home *** CD-ROM | disk | FTP | other *** search
/ Cricao de Sites - 650 Layouts Prontos / WebMasters.iso / Servidores / xampp-win32-1.6.7-installer.exe / phpMyAdmin / libraries / import / sql.php < prev   
Encoding:
PHP Script  |  2008-06-23  |  9.6 KB  |  290 lines

  1. <?php
  2. /* vim: set expandtab sw=4 ts=4 sts=4: */
  3. /**
  4.  * SQL import plugin for phpMyAdmin
  5.  *
  6.  * @version $Id: sql.php 11326 2008-06-17 21:32:48Z lem9 $
  7.  */
  8. if (! defined('PHPMYADMIN')) {
  9.     exit;
  10. }
  11.  
  12. /**
  13.  *
  14.  */
  15. if (isset($plugin_list)) {
  16.     $plugin_list['sql'] = array(
  17.         'text' => 'strSQL',
  18.         'extension' => 'sql',
  19.         'options_text' => 'strOptions',
  20.         );
  21.     $compats = PMA_DBI_getCompatibilities();
  22.     if (count($compats) > 0) {
  23.         $values = array();
  24.         foreach($compats as $val) {
  25.             $values[$val] = $val;
  26.         }
  27.         $plugin_list['sql']['options'] = array(
  28.             array('type' => 'select', 'name' => 'compatibility', 'text' => 'strSQLCompatibility', 'values' => $values, 'doc' => array('manual_MySQL_Database_Administration', 'Server_SQL_mode'))
  29.             );
  30.     }
  31.  
  32.     /* We do not define function when plugin is just queried for information above */
  33.     return;
  34. }
  35.  
  36. $buffer = '';
  37. // Defaults for parser
  38. $sql = '';
  39. $start_pos = 0;
  40. $i = 0;
  41. $len= 0;
  42. if (isset($_POST['sql_delimiter'])) {
  43.     $sql_delimiter = $_POST['sql_delimiter'];
  44. } else {
  45.     $sql_delimiter = ';';
  46. }
  47.  
  48. // Handle compatibility option
  49. if (isset($_REQUEST['sql_compatibility'])) {
  50.     PMA_DBI_try_query('SET SQL_MODE="' . $_REQUEST['sql_compatibility'] . '"');
  51. }
  52. while (!($finished && $i >= $len) && !$error && !$timeout_passed) {
  53.     $data = PMA_importGetNextChunk();
  54.     if ($data === FALSE) {
  55.         // subtract data we didn't handle yet and stop processing
  56.         $offset -= strlen($buffer);
  57.         break;
  58.     } elseif ($data === TRUE) {
  59.         // Handle rest of buffer
  60.     } else {
  61.         // Append new data to buffer
  62.         $buffer .= $data;
  63.         // free memory
  64.         unset($data);
  65.         // Do not parse string when we're not at the end and don't have ; inside
  66.         if ((strpos($buffer, $sql_delimiter, $i) === FALSE) && !$finished)  {
  67.             continue;
  68.         }
  69.     }
  70.     // Current length of our buffer
  71.     $len = strlen($buffer);
  72.     // prepare an uppercase copy of buffer for PHP < 5
  73.     // outside of the loop
  74.     if (PMA_PHP_INT_VERSION < 50000) {
  75.         $buffer_upper = strtoupper($buffer);
  76.     }
  77.     // Grab some SQL queries out of it
  78.      while ($i < $len) {
  79.         $found_delimiter = false;
  80.         // Find first interesting character, several strpos seem to be faster than simple loop in php:
  81.         //while (($i < $len) && (strpos('\'";#-/', $buffer[$i]) === FALSE)) $i++;
  82.         //if ($i == $len) break;
  83.         $oi = $i;
  84.         $big_value = 2147483647;
  85.         $first_quote = strpos($buffer, '\'', $i);
  86.         if ($first_quote === FALSE) {
  87.             $first_quote = $big_value;
  88.         }
  89.         $p2 = strpos($buffer, '"', $i);
  90.         if ($p2 === FALSE) {
  91.             $p2 = $big_value;
  92.         }
  93.         /**
  94.          * @todo it's a shortcoming to look for a delimiter that might be
  95.          *       inside quotes (or even double-quotes)
  96.          */
  97.         $first_sql_delimiter = strpos($buffer, $sql_delimiter, $i);
  98.         if ($first_sql_delimiter === FALSE) {
  99.             $first_sql_delimiter = $big_value;
  100.         } else {
  101.             $found_delimiter = true;
  102.         }
  103.         $p4 = strpos($buffer, '#', $i);
  104.         if ($p4 === FALSE) {
  105.             $p4 = $big_value;
  106.         }
  107.         $p5 = strpos($buffer, '--', $i);
  108.         if ($p5 === FALSE || $p5 >= ($len - 2) || $buffer[$p5 + 2] > ' ') {
  109.             $p5 = $big_value;
  110.         }
  111.         $p6 = strpos($buffer, '/*', $i);
  112.         if ($p6 === FALSE) {
  113.             $p6 = $big_value;
  114.         }
  115.         $p7 = strpos($buffer, '`', $i);
  116.         if ($p7 === FALSE) {
  117.             $p7 = $big_value;
  118.         }
  119.         // catch also "delimiter"
  120.         if (PMA_PHP_INT_VERSION >= 50000) {
  121.             $p8 = stripos($buffer, 'DELIMITER', $i);
  122.         } else {
  123.             $p8 = strpos($buffer_upper, 'DELIMITER', $i);
  124.         }
  125.         if ($p8 === FALSE || $p8 >= ($len - 11) || $buffer[$p8 + 9] > ' ') {
  126.             $p8 = $big_value;
  127.         }
  128.         $i = min ($first_quote, $p2, $first_sql_delimiter, $p4, $p5, $p6, $p7, $p8);
  129.         unset($first_quote, $p2, $p4, $p5, $p6, $p7, $p8);
  130.         if ($i == $big_value) {
  131.             $i = $oi;
  132.             if (!$finished) {
  133.                 break;
  134.             }
  135.             // at the end there might be some whitespace...
  136.             if (trim($buffer) == '') {
  137.                 $buffer = '';
  138.                 $len = 0;
  139.                 break;
  140.             }
  141.             // We hit end of query, go there!
  142.             $i = strlen($buffer) - 1;
  143.         }
  144.  
  145.         // Grab current character
  146.         $ch = $buffer[$i];
  147.  
  148.         // Quotes
  149.         if (strpos('\'"`', $ch) !== FALSE) {
  150.             $quote = $ch;
  151.             $endq = FALSE;
  152.             while (!$endq) {
  153.                 // Find next quote
  154.                 $pos = strpos($buffer, $quote, $i + 1);
  155.                 // No quote? Too short string
  156.                 if ($pos === FALSE) {
  157.                     // We hit end of string => unclosed quote, but we handle it as end of query
  158.                     if ($finished) {
  159.                         $endq = TRUE;
  160.                         $i = $len - 1;
  161.                     }
  162.                     $found_delimiter = false;
  163.                     break;
  164.                 }
  165.                 // Was not the quote escaped?
  166.                 $j = $pos - 1;
  167.                 while ($buffer[$j] == '\\') $j--;
  168.                 // Even count means it was not escaped
  169.                 $endq = (((($pos - 1) - $j) % 2) == 0);
  170.                 // Skip the string
  171.                 $i = $pos;
  172.  
  173.                 if ($first_sql_delimiter < $pos) {
  174.                     $found_delimiter = false;
  175.                 }
  176.             }
  177.             if (!$endq) {
  178.                 break;
  179.             }
  180.             $i++;
  181.             // Aren't we at the end?
  182.             if ($finished && $i == $len) {
  183.                 $i--;
  184.             } else {
  185.                 continue;
  186.             }
  187.         }
  188.  
  189.         // Not enough data to decide
  190.         if ((($i == ($len - 1) && ($ch == '-' || $ch == '/'))
  191.           || ($i == ($len - 2) && (($ch == '-' && $buffer[$i + 1] == '-')
  192.             || ($ch == '/' && $buffer[$i + 1] == '*')))) && !$finished) {
  193.             break;
  194.         }
  195.  
  196.         // Comments
  197.         if ($ch == '#'
  198.                 || ($i < ($len - 1) && $ch == '-' && $buffer[$i + 1] == '-' && (($i < ($len - 2) && $buffer[$i + 2] <= ' ') || ($i == ($len - 1) && $finished)))
  199.                 || ($i < ($len - 1) && $ch == '/' && $buffer[$i + 1] == '*')
  200.                 ) {
  201.             // Copy current string to SQL
  202.             if ($start_pos != $i) {
  203.                 $sql .= substr($buffer, $start_pos, $i - $start_pos);
  204.             }
  205.             // Skip the rest
  206.             $j = $i;
  207.             $i = strpos($buffer, $ch == '/' ? '*/' : "\n", $i);
  208.             // didn't we hit end of string?
  209.             if ($i === FALSE) {
  210.                 if ($finished) {
  211.                     $i = $len - 1;
  212.                 } else {
  213.                     break;
  214.                 }
  215.             }
  216.             // Skip *
  217.             if ($ch == '/') {
  218.                 // Check for MySQL conditional comments and include them as-is
  219.                 if ($buffer[$j + 2] == '!') {
  220.                     $comment = substr($buffer, $j + 3, $i - $j - 3);
  221.                     if (preg_match('/^[0-9]{5}/', $comment, $version)) {
  222.                         if ($version[0] <= PMA_MYSQL_INT_VERSION) {
  223.                             $sql .= substr($comment, 5);
  224.                         }
  225.                     } else {
  226.                         $sql .= $comment;
  227.                     }
  228.                 }
  229.                 $i++;
  230.             }
  231.             // Skip last char
  232.             $i++;
  233.             // Next query part will start here
  234.             $start_pos = $i;
  235.             // Aren't we at the end?
  236.             if ($i == $len) {
  237.                 $i--;
  238.             } else {
  239.                 continue;
  240.             }
  241.         }
  242.        // Change delimiter, if redefined, and skip it (don't send to server!)
  243.        if ((strtoupper(substr($buffer, $i, 9)) == "DELIMITER") && ($buffer[$i + 9] <= ' ') && ($i<$len-11) && (!(strpos($buffer,"\n",$i+11)===FALSE))) {
  244.            $new_line_pos = strpos($buffer, "\n", $i + 10);
  245.            $sql_delimiter = substr($buffer, $i+10, $new_line_pos - $i -10);
  246.            $i= $new_line_pos + 1;
  247.            // Next query part will start here
  248.            $start_pos = $i;
  249.            continue;
  250.         }
  251.  
  252.         // End of SQL
  253.         if ($found_delimiter || ($finished && ($i == $len - 1))) {
  254.             $tmp_sql = $sql;
  255.             if ($start_pos < $len) {
  256.                 $length_to_grab = $i - $start_pos;
  257.                 if (!$found_delimiter) {
  258.                     $length_to_grab++;
  259.                 }
  260.                 $tmp_sql .= substr($buffer, $start_pos, $length_to_grab);
  261.                 unset($length_to_grab);
  262.             }
  263.             // Do not try to execute empty SQL
  264.             if (!preg_match('/^([\s]*;)*$/', trim($tmp_sql))) {
  265.                 $sql = $tmp_sql;
  266.                 PMA_importRunQuery($sql, substr($buffer, 0, $i + strlen($sql_delimiter)));
  267.                 $buffer = substr($buffer, $i + strlen($sql_delimiter));
  268.                 // Reset parser:
  269.                 $len = strlen($buffer);
  270.                 $sql = '';
  271.                 $i = 0;
  272.                 $start_pos = 0;
  273.                 // Any chance we will get a complete query?
  274.                 //if ((strpos($buffer, ';') === FALSE) && !$finished) {
  275.                 if ((strpos($buffer, $sql_delimiter) === FALSE) && !$finished) {
  276.                     break;
  277.                 }
  278.             } else {
  279.                 $i++;
  280.                 $start_pos = $i;
  281.             }
  282.         }
  283.  
  284.     } // End of parser loop
  285. } // End of import loop
  286. // Commit any possible data in buffers
  287. PMA_importRunQuery('', substr($buffer, 0, $len));
  288. PMA_importRunQuery();
  289. ?>
  290.