* Copyright (c) 2001-2002 Jim Kraai * Versions 5.0 and higher developed by Ondrej Jombik * Copyright (c) 2002 Platon SDG, http://www.platon.sk/ * All rights reserved. * * See README file for more information about this software. * See COPYING file for license information. * * Download the latest version from * http://www.platon.sk/projects/phpMyEdit/ */ /* $Platon: phpMyEdit/phpMyEdit.class.php,v 1.25 2002/11/02 19:19:34 nepto Exp $ */ /* phpMyEdit intro {{{ */ /* This is a generic table editing program. The table and fields to be edited are defined in the calling program. This program works in three passes. Pass 1 (the last part of the program) displays the selected MySQL table in a scrolling table on the screen. Radio buttons are used to select a record for editing or deletion. If the user chooses Add, Change, or Delete buttons, Pass 2 starts, displaying the selected record. If the user chooses the Save button from this screen, Pass 3 processes the update and the display returns to the original table view (Pass 1). version 3.5 - 06-May-01 important variables passed between calls to this program $fm first record to display $inc no of records to display (SELECT ... LIMIT $fm,$inc) $fl is the filter row displayed (boolean) $rec unique id of record selected for editing $qf0,.. value of filter for column 0 $qfn value of all filters used during the last pass $sfn sort field number (- = descending sort order) $operation operation to do: Add, Change, Delete $message informational message to print $filter filter query $sw filter display/hide button $prev, $next navigation buttons $labels narrative for buttons, etc Conversion to PHP Classes by Pau Aliagas (pau@newtral.com) ToDo: 'Copy' button Aggregates: nonworking code commented out in list_table() doesn't work yet Query Building: Multi-Part Date Handling: Finish converting date handling to internal date handling functions Abstract date field gathering to get rid of _many_ redundant lines of code There was some kludged fix for dateformat'ting where '%'s are removed Better support for more date format macros Better documentation for valid date format macros Multi-Language support: Finish implementing language labels Use browser-supplied language if available Allow programmer override in setup.php generated .inc file Add 'Search' and 'Go!' to labels array Data Validation: Expand JS field validation to match JS regexes Create PHP field validation to match PHP regexes Change Tracking/Notification: Add change notification (via mail()) support Don't die if mail() not available CSS: Document & solicit feedback to standardize class names Even/Odd Coloring: Move to CSS Put values in setup.php generated file Timer Class: Solicit user input whether to put timer class into this lib */ /* }}} */ if (@include_once dirname(__FILE__).'/timer.class') { $phpMyEdit_timer = new timerClass(); } if (! function_exists('array_search')) { /* {{{ */ function array_search($needle, $haystack) { foreach ($haystack as $key => $value) { if ($needle == $value) return $key; } return false; } } /* }}} */ class phpMyEdit { var $hn; // hostname var $un; // user name var $pw; // password var $db; // database var $tb; // table var $key; // Name of field which is the unique key var $key_type; // Type of key field (int/real/string/date etc) var $key_delim; var $inc; // no of records to display (SELECT ... LIMIT $fm, $inc) var $fm; // first record to display var $fl; // is the filter row displayed (boolean) var $options; // Options for users: A(dd) C(hange) D(elete) F(ilter) V(iew) co(P)y U(nsorted) var $fdd; // field definitions var $qfn; // value of all filters used during the last pass var $sfn; // sort field number (- = descending sort order) var $rec; // no. of record selected for editing var $prev; // navigation buttons var $next; var $sw; // filter display/hide button var $labels; // labels for buttons, etc (multilingual) var $operation; // operation to do: Add, Change, Delete var $message; // informational message to print var $saveadd; var $moreeadd; var $savechange; var $savedelete; var $fds; // sql field names var $num_fds; // number of fields var $logtable; // name of optional logtable var $navigation; // navigation style function debug_var($name, $val) /* {{{ */ { if (is_array($val) || is_object($val)) { echo "
$name\n";
			ob_start();
			//print_r($val);
			var_dump($val);
			$content = ob_get_contents();
			ob_end_clean();
			echo htmlspecialchars($content);
			echo "
\n"; } else { echo 'debug_var()::'.htmlspecialchars($name).'::' .htmlspecialchars($val).'::'."
\n"; } } /* }}} */ function myquery($qry, $line = 0, $debug = 0) /* {{{ */ { global $debug_query; if ($debug_query || $debug) { $line = intval($line); echo '

MySQL query at line '.$line.'

'.htmlspecialchars($qry).'
'."\n"; } $this->elog("qry: $qry",$line); $ret = @mysql_db_query($this->db, $qry); if (! $ret) { $this->elog(mysql_errno().": ".mysql_error().' in '.$qry,__LINE__); } return $ret; } /* }}} */ function encode($field,$str) /* {{{ */ { if (isset($field['dbencode'])) { return eval( 'return ' .$field['dbencode'] .'(\''.$str.'\');'); } else { return $str; } } /* }}} */ function elog($str,$line) /* {{{ */ { error_log(__FILE__.":$line::\n$str",0); return true; } /* }}} */ function make_language_labels($language) /* {{{ */ { // just try the first language and variant // this isn't content-negotiation rfc compliant $language = strtoupper(substr($language,0,5)); // try the full language w/ variant $file = $this->dir['lang'].'PME.lang.'.$language.'.inc'; if (! file_exists($file)) { // try the language w/o variant $file = $this->dir['lang'].'PME.lang.'.substr($language,0,2).'.inc'; } if (! file_exists($file)) { // default to classical English $file = $this->dir['lang'].'PME.lang.EN.inc'; } $ret = @include($file); !isset($ret['of']) && $ret['of'] = '/'; $small = array( 'Search' => 'v', 'Hide' => '^', 'Clear' => 'X', 'Query' => htmlspecialchars('>')); if ((!$this->nav_text_links() && !$this->nav_graphic_links()) || !isset($ret['Search']) || !isset($ret['Query']) || !isset($ret['Hide']) || !isset($ret['Clear'])) { foreach ($small as $key => $val) { $ret[$key] = $val; } } return $ret; } /* }}} */ function set_values_from_table($field_num, $prepend = '') /* {{{ */ { /* echo "$field_num, "; var_dump($prepend); echo '
';
		   var_dump($this->fdd);
		   echo '
'; */ if($this->fdd[$field_num]['values']['db']) { $db = $this->fdd[$field_num]['values']['db']; } else { $db = $this->db; } $table = $this->fdd[$field_num]['values']['table']; $key = $this->fdd[$field_num]['values']['column']; $desc = $this->fdd[$field_num]['values']['description']; $qparts['type'] = 'select'; if ($table) { $qparts['select'] = 'DISTINCT '.$key; if ($desc) { //- $qparts['select'] .= ','.$desc; //- $qparts['orderby'] = $desc; // Changes 08/08/02 Shaun Johnston if (is_array($desc)) { $qparts['select'] .= ',CONCAT('; // ) $num_cols = sizeof($desc['columns']); for ($i = 0; $i <= $num_cols; $i++) { $qparts['select'] .= $desc['columns'][$i]; if ($desc['divs'][$i]) { $qparts['select'] .= ',"'.$desc['divs'][$i].'"'; } if ($i < ($num_cols - 1)) { $qparts['select'] .= ','; } } $qparts['select'] .= ') AS select_alias_'.$field_num; $qparts['orderby'] = empty($desc['orderby']) ? 'select_alias_'.$field_num : $desc['orderby']; } else { $qparts['select'] .= ','.$desc; $qparts['orderby'] = $desc; } } else { if ($key) { $qparts['orderby'] = $key; } } //$qparts['from'] = "$db.$table.$sel; $qparts['from'] = "$db.$table"; $qparts['where'] = $this->fdd[$field_num]['values']['filters']; if ($this->fdd[$field_num]['values']['orderby']) { $qparts['orderby'] = $this->fdd[$field_num]['values']['orderby']; } } else { /* simple value extraction */ $qparts['select'] = 'DISTINCT '.$this->fds[$field_num]; $qparts['from'] = $this->db.'.'.$this->tb; } $values = array(); $res = $this->myquery($this->query_make($qparts), __LINE__); while ($row = @mysql_fetch_array($res, MYSQL_NUM)) { $values[$row[0]] = $desc ? $row[1] : $row[0]; } $values2 = $this->fdd[$field_num]['values2']; is_array($values2) && $values = $values2 + $values; is_array($prepend) && $values = $prepend + $values; /* old wrong prepending -- REMOVE ME at December 2002 if (is_array($prepend)) { $values[$prepend[0]] = $prepend[1]; } */ return $values; } /* }}} */ /* * get the table/field name */ function fqn($field, $use_qfx = false, $dont_desc = false, $dont_cols = false) /* {{{ */ { if (is_string($field)) { $field = array_search($field,$this->fds); } // on copy/change always use simple key retrieving if ($this->add_operation() || $this->copy_operation() || $this->change_operation()) { $ret = 'Table0.'.$this->fds[$field]; } else { if (isset($this->fdd[$field]['expression'])) { $ret = $this->fdd[$field]['expression']; } elseif ($this->fdd[$this->fds[$field]]['values']['description'] && ! $dont_desc) { // Changed 06/08/02 Shaun Johnston $desc = $this->fdd[$this->fds[$field]]['values']['description']; if (is_array($desc)) { $ret = 'CONCAT('; // ) $num_cols = sizeof($desc['columns']); for ($i = 0; $i < $num_cols; $i++) { $ret .= 'JoinTable'.$field.'.'.$desc['columns'][$i]; if ($desc['divs'][$i]) { $ret .= ',"'.$desc['divs'][$i].'"'; } if ($i < ($num_cols - 1)) { $ret .= ','; } } $ret .= ')'; } else { $ret = 'JoinTable'.$field.'.'.$this->fdd[$this->fds[$field]]['values']['description']; } } elseif ($this->fdd[$this->fds[$field]]['values']['column'] && ! $dont_cols) { $ret = 'JoinTable'.$field.'.'.$this->fdd[$this->fds[$field]]['values']['column']; } else { $ret = 'Table0.'.$this->fds[$field]; } // TODO: not neccessary, remove me! if (is_array($this->fdd[$this->fds[$field]]['values2'])) { } } // what to do with $format XXX if ($use_qfx) $ret = 'qf'.$field; // return the value return $ret; } /* }}} */ function create_column_list() /* {{{ */ { $fields = array(); for ($k = 0; $k < $this->num_fds; $k++) { if (! $this->displayed[$k] && $k != $this->key_num) continue; if ($this->col_is_date($k)) { //$fields[] = 'DATE_FORMAT('.$this->fqn($k).',"%Y%m%d%H%i%s") AS qf'.$k; $fields[] = $this->fqn($k).' AS qf'.$k; } else { $fields[] = $this->fqn($k).' AS qf'.$k; if ($this->col_has_values($k)) { $fields[] = $this->fqn($k, false, true, true).' AS qf'.$k.'_idx'; } //echo '[['.$this->fqn($k).' AS qf'.$k.']]
'; } } return join(',',$fields); } /* }}} */ function query_make($parts) /* {{{ */ { foreach ($parts as $k => $v) { $parts[$k] = trim($parts[$k]); } switch ($parts['type']) { case 'select': $ret = 'SELECT '; if ($parts['DISTINCT']) $ret .= 'DISTINCT '; $ret .= $parts['select']; $ret .= ' FROM '.$parts['from']; if ($parts['where'] != '') $ret .= ' WHERE '.$parts['where']; if ($parts['groupby'] != '') $ret .= ' GROUP BY '.$parts['groupby']; if ($parts['having'] != '') $ret .= ' HAVING '.$parts['having']; if ($parts['orderby'] != '') $ret .= ' ORDER BY '.$parts['orderby']; if ($parts['limit'] != '') $ret .= ' LIMIT '.$parts['limit']; if ($parts['procedure'] != '') $ret .= ' PROCEDURE '.$parts['procedure']; break; case 'update': $ret = 'UPDATE '.$parts['table']; $ret .= ' SET '.$parts['fields']; if ($parts['where'] != '') $ret .= ' WHERE '.$parts['where']; break; case 'insert': $ret = 'INSERT INTO '.$parts['table']; $ret .= ' VALUES '.$parts['values']; break; case 'delete': $ret = 'DELETE FROM '.$parts['table']; if ($parts['where'] != '') $ret .= ' WHERE '.$parts['where']; break; default: die('unknown query type'); break; } return $ret; } /* }}} */ function create_join_clause() /* {{{ */ { $tbs[] = $this->tb; $join = $this->tb.' AS Table0'; for ($k = 0,$numfds = sizeof($this->fds); $k<$numfds; $k++) { $field = $this->fds[$k]; if($this->fdd[$field]['values']['db']) { $db = $this->fdd[$field]['values']['db']; } else { $db = $this->db; } $table = $this->fdd[$field]['values']['table']; $id = $this->fdd[$field]['values']['column']; $desc = $this->fdd[$field]['values']['description']; if ($desc != '' || $id != '') { $alias = 'JoinTable'.$k; if (!in_array($alias,$tbs)) { $join .= " LEFT OUTER JOIN $db.". $table. ' AS '.$alias. ' ON '.$alias. '.'.$id. '='.'Table0.'.$field; $tbs[]=$alias; } } } return $join; } /* }}} */ function make_where_from_query_opts($qp='') /* {{{ */ { if ($qp == '') $qp = $this->query_opts; $where = array(); foreach ($qp as $field => $ov) { $where[] = sprintf('%s %s %s',$field,$ov['oper'],$ov['value']); } // Add any coder specified filters if ($this->filters) $where[] = '('.$this->filters.')'; if (count($where) > 0) return join(' AND ',$where); return false; } /* }}} */ function make_text_where_from_query_opts($qp='') /* {{{ */ { if ($qp == '') $qp = $this->query_opts; $where = array(); foreach ($qp as $field => $ov) { $where[] = sprintf('%s %s %s',$field,$ov['oper'],$ov['value']); } if (count($where) > 0) return str_replace('%','*',join(' AND ',$where)); return false; } /* }}} */ /* * functions for get/post/query args */ function gather_post_vars() /* {{{ */ { global $HTTP_POST_VARS; foreach ($HTTP_POST_VARS as $key => $val) { if ($val != '' && $val != '*') { $pv[$key] = $val; } } $this->pv = $pv; } /* }}} */ function gather_query_opts() /* {{{ */ { // gathers query options into an array, $this->query_opts $query_opts = array(); $qo = array(); for ($k = 0; $k < $this->num_fds; $k++) { $l = 'qf'.$k; $lc = 'qf'.$k.'_comp'; $$l = $this->get_cgi_var($l); $$lc = $this->get_cgi_var($lc); $m = $this->web2plain($$l); // get the field name and value $mc = $this->web2plain($$lc); // get the comparison operator for numeric/date types $type = $this->fdd[$k]['type']; if ($m == '') { continue; } if (is_array($m)) { // multiple selection has been used if (!in_array('*',$m)) { // one '*' in a multiple selection is all you need $qf_op = ''; foreach (array_keys($m) as $key) { if ($qf_op == '') { $qf_op = 'IN'; $qf_val = "'".addslashes($m[$key])."'"; $afilter =" IN ('".addslashes($m[$key])."'"; } else { $afilter = $afilter.",'".addslashes($m[$key])."'"; $qf_val .= ",'".addslashes($m[$key])."'"; } } $afilter = $afilter.')'; // XXX: $dont_desc and $dont_cols hack $dont_desc = isset($this->fdd[$k]['values']['description']); $dont_cols = isset($this->fdd[$k]['values']['column']); $qo[$this->fqn($k, false, $dont_desc, $dont_cols)] = array( 'oper' => $qf_op, 'value' => '('.$qf_val.')'); } } else { $afilter = $m; if ($afilter != '*') { /* XXX: This is ugly fqn() hack. We must pass third $dont_desc parameter to fqn() method, as far as we want to return not description column, but ID one. */ if ($this->fdd[$k]['values']['description']) { // DEBUG // echo htmlspecialchars(' k = '.$k.' | fqn($k) = '.$this->fqn($k, false, true)); $qo[$this->fqn($k, false, true, true)] = array('oper' => '=', 'value' => "'".$afilter."'"); } elseif ($this->fdd[$k]['values']['column']) { $qo[$this->fqn($k, false, true, true)] = array('oper' => '=', 'value' => "'".$afilter."'"); } elseif ($this->col_is_string($k)) { // massage the filter for a string comparison if (($afilter != '') AND ($afilter != '*')) { $afilter = addslashes(addslashes('%' .str_replace('*', '%', $afilter).'%')); $qo[$this->fqn($k)] = array('oper' => 'like', 'value' => "'".$afilter."'"); } } elseif ($this->col_is_number($k) && ($$lc != '')) { if ($$lc != '') { $qo[$this->fqn($k)] = array('oper' => $mc, 'value' => $afilter); } } elseif ($this->col_is_date($k)) { #if ($$lc != '') { # $val = $this->gather_date_fields_into_type($$l,$type); # $val = $this->mdate_set(date($this->mdate_masks[$type],$this->mdate_getFromPost($k)),$type); # $val = $this->mdate_getFromPost($k); # if ($val != '') { # $qo[$this->fqn($k)] = # array( 'oper' => $mc, 'value' => '"'.$val.'"'); # } #} # massage the filter for a string comparison if (($afilter != '') AND ($afilter != '*')) { $afilter = addslashes(addslashes('%' .str_replace ('*', '%', $afilter).'%')); $qo[$this->fqn($k)] = array('oper' => 'like', 'value' => "'".$afilter."'"); } } elseif($this->col_has_values($k)) { //debug_var('col_is_string',$this->fdd[$k]['name'].'::'.$this->fdd[$k]['type']); $qo[$this->fqn($k)] = array( 'oper' => '=', 'value' => "'".$afilter."'"); } else { // unknown (to mysql/php interface) field type massage the filter for a string comparison $afilter = addslashes(addslashes('%'.str_replace ('*', '%', $afilter).'%')); $qo[$this->fqn($k)] = array('oper' => 'like', 'value' => "'".$afilter."'"); } } } } // for $this->query_opts = $qo; } // gather_query_opts /* }}} */ function gather_get_vars() /* {{{ */ { global $HTTP_SERVER_VARS; $vals = array(); $parts = split('&',$HTTP_SERVER_VARS['QUERY_STRING']); if (count($parts) > 0) { foreach ($parts as $part) { list($key,$val) = split('=',$part,2); $vals[$key] = $val; } } $this->get_opts = $vals; } /* }}} */ function unify_opts() /* {{{ */ { $all_opts = array(); if (count($this->qo) > 0) { foreach ($this->qo as $key=>$val) $all_opts[$key] = $val; } if (count($this->pv) > 0) { foreach ($this->pv as $key=>$val) $all_opts[$key] = $val; } if (count($this->get_opts) > 0) { foreach ($this->get_opts as $key=>$val) $all_opts[$key] = $val; } $this->all_opts = $all_opts; } /* }}} */ /* * type functions */ function col_is_date($k) { return in_array($this->fdd[$k]['type'], $this->dateTypes ); } function col_is_number($k) { return in_array($this->fdd[$k]['type'], $this->numberTypes); } function col_is_string($k) { return in_array($this->fdd[$k]['type'], $this->stringTypes); } function col_is_set($k) { return $this->fdd[$k]['type'] == 'set'; } function col_has_values($k) { return isset($this->fdd[$k]['values']) || isset($this->fdd[$k]['values2']); } /* * functions for indicating whether navigation style is enabled */ function nav_buttons() { return stristr($this->navigation, 'B'); } function nav_text_links() { return stristr($this->navigation, 'T'); } function nav_graphic_links() { return stristr($this->navigation, 'G'); } function nav_up() { return stristr($this->navigation, 'U'); } function nav_down() { return stristr($this->navigation, 'D'); } /* * functions for indicating whether operations are enabled */ function initial_sort_suppressed() { return (stristr ($this->options, 'I')); } function add_enabled() { return stristr($this->options, 'A'); } function change_enabled() { return stristr($this->options, 'C'); } function delete_enabled() { return stristr($this->options, 'D'); } function filter_enabled() { return stristr($this->options, 'F'); } function view_enabled() { return stristr($this->options, 'V'); } function copy_enabled() { return stristr($this->options, 'P') && $this->add_enabled(); } function hidden($k) { return stristr($this->fdd[$k]['options'],'H'); } function password($k) { return stristr($this->fdd[$k]['options'],'W'); } function readonly($k) { return stristr($this->fdd[$k]['options'],'R') || $this->fdd[$k]['expression']; } function add_operation() { return $this->operation == $this->labels['Add'] && $this->add_enabled(); } function change_operation() { return $this->operation == $this->labels['Change'] && $this->change_enabled(); } function copy_operation() { return $this->operation == $this->labels['Copy'] && $this->copy_enabled(); } function delete_operation() { return $this->operation == $this->labels['Delete'] && $this->delete_enabled(); } function view_operation() { return $this->operation == $this->labels['View'] && $this->view_enabled(); } function filter_operation() { return $this->fl && $this->filter_enabled(); } function next_operation() { return $this->next == $this->labels['Next']; } function prev_operation() { return $this->prev == $this->labels['Prev']; } function is_values2($k, $val = 'X') /* {{{ */ { return $val === null || (isset($this->fdd[$k]['values2']) && !isset($this->fdd[$k]['values']['table'])); } /* }}} */ function processed($k) /* {{{ */ { $options = $this->fdd[$k]['options']; return empty($options) || ($this->saveadd == $this->labels['Save'] && stristr($options, 'A')) || ($this->moreadd == $this->labels['More'] && stristr($options, 'A')) || ($this->savechange == $this->labels['Save'] && stristr($options, 'C')) || ($this->savechange == $this->labels['Save'] && stristr($options, 'P')) || ($this->savedelete == $this->labels['Save'] && stristr($options, 'D')); } /* }}} */ function displayed($k) /* {{{ */ { if (is_numeric($k)) { $k = $this->fds[$k]; } $options = $this->fdd[$k]['options']; if (! isset($options)) return true; if ($this->hidden($k)) return false; return ($this->add_operation() && stristr($options, 'A')) || ($this->view_operation() && stristr($options, 'V')) || ($this->change_operation() && stristr($options, 'C')) || ($this->copy_operation() && stristr($options, 'P')) || ($this->delete_operation() && stristr($options, 'D')) || ((stristr($options,'L') || ($this->filter_operation() && stristr($options, 'F'))) && ! $this->add_operation() && ! $this->view_operation() && ! $this->change_operation() && ! $this->copy_operation() && ! $this->delete_operation()); } /* }}} */ /* * Create JavaScripts */ function create_javascripts() /* {{{ */ { /* Need a lot of work in here using something like: $fdd['fieldname']['validate']['js_regex']='/something/'; $fdd['fieldname']['validate']['php_regex']='something'; */ $page_name = htmlspecialchars($this->page_name); if ($this->add_operation() || $this->change_operation()) { $required_ar = array(); for ($k = 0; $k < $this->num_fds; $k++) { if ($this->displayed[$k] && $this->fdd[$k]['required'] && ! $this->col_has_values($k)) { $required_ar[] = $k; if (isset($this->fdd[$k]['regex']['js'])) { /* TODO: Use a javascript regex to validate it */ } } } if (count($required_ar) > 0) { echo '' . "\n"; echo '
'."\n"; return true; } } echo ''."\n"; return true; } /* }}} */ /* * Display functions */ function display_add_record() /* {{{ */ { if (0) { // XXX: WTF? echo ' '."\n"; echo ' Field'."\n"; echo ' Value'."\n"; if ($this->guidance) echo ' Guidance'."\n"; echo ' '."\n"; } for ($k = 0; $k < $this->num_fds; $k++) { echo ''."\n"; if ($this->displayed[$k]) { echo ''.$this->fdd[$k]['name'].''."\n"; if ($this->fdd[$k]['select'] == 'M') { $a = ' multiple size="'.$this->multiple.'"'; } else { $a=''; } if ($this->col_has_values($k)) { echo ' ' ."\n"; $vals = isset($this->fdd[$k]['values']['table']) ? $this->set_values_from_table($k) : (array) $this->fdd[$k]['values2'] + (array) $this->fdd[$k]['values']; echo $this->htmlSelect($this->fds[$k], $vals, '', $this->col_is_set($k)); echo ''."\n"; } elseif (isset ($this->fdd[$k]['textarea'])) { echo ''."\n"; } else { // Simple edit box required $type = $this->fdd[$k]['type']; echo ''; if ($this->readonly($k)) { echo $this->htmlDisplay($this->fdd[$k], '', false, false, false) .''; } else { if ($this->col_is_string($k) || $this->col_is_number($k)) { // string type $maxwidth = intval($this->fdd[$k]['maxlen']); $size = min(60,$maxwidth); echo ''; } elseif ($this->col_is_date($k)) { // date type, get date components //if ($this->fdd[$k]['default']) // $value = $this->mdate_set($this->fdd[$k]['default'],$this->fdd[$k]['type']); //$value = time(); //echo $this->mdate_disperse($k,$value,true); // string type $maxwidth = intval($this->fdd[$k]['maxlen']); $size = min(60, $maxwidth); echo ''; } else { // unknown type echo ''; } } echo ''; } // if elseif else if ($this->guidance) { if ($this->fdd[$k]['help']) echo ''.$this->fdd[$k]['help'].''."\n"; } else { echo " \n"; } echo ''."\n"; } } // for k < this->num_fds } // display_add_record /* }}} */ function display_copy_change_delete_record() /* {{{ */ { /* * for delete or change: SQL SELECT to retrieve the selected record */ $qparts['type'] = 'select'; $qparts['select'] = $this->create_column_list(); $qparts['from'] = $this->create_join_clause(); $qparts['where'] = '('.$this->fqn($this->key).'=' .$this->key_delim.$this->rec.$this->key_delim.')'; $res = $this->myquery($this->query_make($qparts),__LINE__); if ($row = @mysql_fetch_array($res, MYSQL_ASSOC)) { for ($k = 0; $k < $this->num_fds; $k++) { if ($this->copy_operation()) { if ($this->displayed[$k]) { echo ''; echo ''.$this->fdd[$k]['name'].''."\n"; if ($this->readonly($k)) { echo $this->display_delete_field($row, $k); } elseif ($this->password($k)) { echo ''; } else { echo $this->display_change_field($row, $k); } if ($this->guidance) { if ($this->fdd[$k]['help']) echo ''.$this->fdd[$k]['help'].''."\n"; else echo ' '."\n"; } echo ''."\n"; } // if field displayed elseif ($this->hidden($k)) { if ($k != $this->key_num) { echo ''."\n"; } } } elseif ($this->change_operation()) { if ($this->hidden($k)) { echo ''."\n"; } elseif ($this->displayed[$k]) { echo ''."\n"; echo ''.$this->fdd[$k]['name'].''."\n"; $this->display_change_field($row, $k); if ($this->guidance) { if ($this->fdd[$k]['help']) echo ''.$this->fdd[$k]['help'].''."\n"; else echo ' '."\n"; } echo ''."\n"; } } elseif ($this->delete_operation() || $this->view_operation()) { if ($this->displayed[$k]) { echo ''."\n"; echo ''.$this->fdd[$k]['name'].''."\n"; $this->display_delete_field($row, $k); if ($this->guidance) if ($this->fdd[$k]['help']) echo ''.$this->fdd[$k]['help'].''."\n"; else echo ' '."\n"; echo ''."\n"; } } } // for } // if row } // display_copy_change_delete_record /* }}} */ function display_change_field($row, $k) /* {{{ */ { echo ''."\n"; if ($this->col_has_values($k)) { $vals = isset($this->fdd[$k]['values']['table']) ? $this->set_values_from_table($k) : (array) $this->fdd[$k]['values2'] + (array) $this->fdd[$k]['values']; echo $this->htmlSelect($this->fds[$k], $vals, $row["qf$k"], $this->col_is_set($k)); } elseif (isset($this->fdd[$k]['textarea'])) { echo ''."\n"; } else { if ($this->col_is_string($k) || $this->col_is_number($k)) { // string type $displaylen = 50; if (isset($this->fdd[$k]['maxlen'])) { $displaylen = min($displaylen,$this->fdd[$k]['maxlen']); } echo 'readonly($k)?'disabled ':'') .'name="'.$this->fds[$k].'" value="' .$this->htmlDisplay($this->fdd[$k], $row["qf$k"], false, true, false) .'" size="'.$displaylen.'"/>'; } elseif ($this->col_is_date($k)) { # date type, get date components #$value = $this->mdate_from_mysql($row[$k]); #if ($this->readonly($k)) { # $mask = $this->fdd[$k]['datemask']; # if (! $mask) # $mask = $this->mdate_masks[$this->fdd[$k]['type']]; # echo $this->mdate_format($value,$mask); #} else { # echo $this->mdate_disperse($k,$value,true); #} // string type $displaylen = 50; if (isset($this->fdd[$k]['maxlen'])) { $displaylen = min($displaylen,$this->fdd[$k]['maxlen']); } echo 'readonly($k)?'disabled ':'') .'name="'.$this->fds[$k].'" value="' .$this->htmlDisplay($this->fdd[$k], $row["qf$k"], false, true, false) .'" size="'.$displaylen.'">'; } else { // unknown type echo 'readonly($k)?'disabled ':'') .'name="'.$this->fds[$k].'" value="' .$this->htmlDisplay($this->fdd[$k],$row["qf$k"], false, true, false).'">'; } echo "\n"; } // if elseif else echo ''."\n"; } // display_change_field($row, $k) /* }}} */ function display_delete_field($row, $k) /* {{{ */ { echo ''; if ($this->is_values2($k, $row["qf$k"])) { echo nl2br($this->htmlDisplay($k, $this->fdd[$k]['values2'][$row['qf'.$k.'_idx']], true, true, true, false)); } else { echo nl2br($this->htmlDisplay($this->fdd[$k], $row["qf$k"])); } echo ''."\n"; } /* }}} */ function htmlHidden($name,$value) /* {{{ */ { return ''."\n"; } /* }}} */ /** * Creates HTML select element (tag) * * @param name element name * @param kv_array key => value array * @param selected selected key (it can be single string, array of * keys or multiple values separated by comma * @param multiple bool for mulptiple selection * @param nat_sort bool for natural sorting */ function htmlSelect($name, $kv_array, $selected = null, $multiple = false, $nat_sort = false) /* {{{ */ { $ret = ''; return $ret; } /* }}} */ /** * Returns HTML text * * @param field field name/number * @param str str to print * @param usemask flag if field mask should be used * @param usecodec flag if field codec should be used * @param disallow_empty flag if empty string is forbidden on output * @param escape flag if output should be HTML escaped */ function htmlDisplay($field, $str, /* ...) {{{ */ $usemask = true, $usecodec = true, $disallow_empty = true, $escape = true) { // undo the add slashes $str = stripslashes($str); // if there's a field mask, use it as first arg to sprintf if (isset($field['mask']) && $usemask) { $str = sprintf($field['mask'], $str); } // if db codec is in effect, use it if ($usecodec && isset($field['dbdecode'])) { $str = eval('return '.$field['dbdecode'].'(\''.$str.'\');'); } if ($escape) { $str = htmlspecialchars($str); } if ($disallow_empty) { strlen($str) <= 0 && $str = ' '; } return $str; } /* }}} */ function get_qf_hidden_fields() /* {{{ */ { /* If the filter input boxes are not displayed, we need to preserve the filter by its emulaion. */ $this->qfn = ''; $hidden_qfs = ''; for ($k = 0; $k < $this->num_fds; $k++) { $l = 'qf'.$k; $lc = 'qf'.$k.'_comp'; $$l = $this->get_cgi_var($l); $$lc = $this->get_cgi_var($lc); $m = $this->web2plain($$l); // get the field name and value $mc = $this->web2plain($$lc); // get the comparison operator for numeric/date types if (!isset($m)) { continue; } if (is_array($m)) { // multiple selection has been used if (!in_array('*',$m)) {// one '*' in a multiple selection is all you need for ($n=0; $nplain2web($m[$n]) != '') { $this->qfn = $this->qfn.'&qf'.$k.'['.$n.']=' .$this->plain2web($m[$n]); } $hidden_qfs .= ''."\n"; } } } else { // query field comparison operator (if any) if ($this->plain2web($mc) != '') { $this->qfn = $this->qfn.'&qf'.$k.'_comp='.$this->plain2web($mc); $hidden_qfs .= ''."\n"; } // preserve query field & value if ($this->plain2web($m) != '') { $this->qfn = $this->qfn.'&qf'.$k.'='.$this->plain2web($m); $hidden_qfs .= ''."\n"; } } } return $hidden_qfs; } /* }}} */ function web2plain($x) /* {{{ */ { if (isset($x)) { if (is_array($x)) { foreach (array_keys($x) as $key) { $x[$key] = rawurldecode($x[$key]); } } else { $x = rawurldecode($x); } } return $x; } /* }}} */ function plain2web($x) /* {{{ */ { if (isset($x)) { if (is_array($x)) { for ($n=0; $nplain2web($x[$n]); } } else { $x = rawurlencode($x); } } return $x; } /* }}} */ function get_cgi_var($name, $default_value = null) /* {{{ */ { //echo 'get_cgi_var(): requested: '.htmlspecialchars($name).'
'; if (isset($this) && isset($this->cgi['overwrite'][$name])) { return $this->cgi['overwrite'][$name]; } global $HTTP_GET_VARS; $var = $HTTP_GET_VARS[$name]; if (! isset($var)) { global $HTTP_POST_VARS; $var = $HTTP_POST_VARS[$name]; } if (isset($var)) { if (is_array($var)) { foreach (array_keys($var) as $key) { $var[$key] = stripslashes($var[$key]); } } else { $var = stripslashes($var); } } else { $var = $default_value; } if (isset($this) && $var === null && isset($this->cgi['append'][$name])) { return $this->cgi['append'][$name]; } return $var; } /* }}} */ function get_http_get_var_by_name($name) /* {{{ */ { return phpMyEdit::get_cgi_var($name); /* global $HTTP_GET_VARS; if (is_array($HTTP_GET_VARS)) $v = $HTTP_GET_VARS[$name]; // $v could be an array if we allowed bidimensional form fields return $v; */ } /* }}} */ function get_http_post_var_by_name ($name) /* {{{ */ { return phpMyEdit::get_cgi_var($name); /* global $HTTP_POST_VARS; if (is_array($HTTP_POST_VARS)) $v = $HTTP_POST_VARS[$name]; // $v could be an array if we allowed bidimensional form fields return $v; */ } /* }}} */ /* * Debug functions */ function print_get_vars ($miss = 'No GET variables found') // debug only /* {{{ */ { global $HTTP_GET_VARS; // we parse form GET variables if (is_array($HTTP_GET_VARS)) { echo "

Variables per GET "; foreach ($HTTP_GET_VARS as $k => $v) { if (is_array($v)) { foreach ($v as $akey => $aval) { // $HTTP_GET_VARS[$k][$akey] = strip_tags($aval); // $$k[$akey] = strip_tags($aval); echo "$k\[$akey\]=$aval "; } } else { // $HTTP_GET_VARS[$k] = strip_tags($val); // $$k = strip_tags($val); echo "$k=$v "; } } echo '

'; } else { echo '

'; echo $miss; echo '

'; } } /* }}} */ function print_post_vars($miss = 'No POST variables found') // debug only /* {{{ */ { global $HTTP_POST_VARS; // we parse form POST variables if (is_array($HTTP_POST_VARS)) { echo "

Variables per POST "; foreach ($HTTP_POST_VARS as $k => $v) { if (is_array($v)) { foreach ($v as $akey => $aval) { // $HTTP_POST_VARS[$k][$akey] = strip_tags($aval); // $$k[$akey] = strip_tags($aval); echo "$k\[$akey\]=$aval "; } } else { // $HTTP_POST_VARS[$k] = strip_tags($val); // $$k = strip_tags($val); echo "$k=$v "; } } echo '

'; } else { echo '

'; echo $miss; echo '

'; } } /* }}} */ function print_vars ($miss = 'Current instance variables') // debug only /* {{{ */ { echo "$miss "; echo 'page_name='.$this->page_name.' '; echo 'hn='.$this->hn.' '; echo 'un='.$this->un.' '; echo 'pw='.$this->pw.' '; echo 'db='.$this->db.' '; echo 'tb='.$this->tb.' '; echo 'key='.$this->key.' '; echo 'key_type='.$this->key_type.' '; echo 'inc='.$this->inc.' '; echo 'options='.$this->options.' '; echo 'fdd='.$this->fdd.' '; echo 'fl='.$this->fl.' '; echo 'fm='.$this->fm.' '; echo 'sfn='.$this->sfn.' '; echo 'qfn='.$this->qfn.' '; echo 'sw='.$this->sw.' '; echo 'rec='.$this->rec.' '; echo 'prev='.$this->prev.' '; echo 'next='.$this->next.' '; echo 'saveadd='.$this->saveadd.' '; echo 'moreadd='.$this->moreadd.' '; echo 'savechange='.$this->savechange.' '; echo 'savedelete='.$this->savedelete.' '; echo 'operation='.$this->operation.' '; echo "\n"; } /* }}} */ /* * Display buttons at top and bottom of page - sparky */ function display_list_table_buttons($total_recs) /* {{{ */ { // Are we doing a listall? $listall = $this->inc <= 0; // note that '; echo '' . "\n"; $disabled = ($this->fm > 0 && ! $listall) ? '' : ' disabled'; echo ' '; if ($this->add_enabled ()) { echo ' '; } if ($this->nav_buttons()) { if ($this->view_enabled()) { echo ' '; } if ($this->change_enabled()) { echo ' '; } if ($this->copy_enabled()) { echo ' '; } if ($this->delete_enabled()) { echo ' '; } // if else } $disabled = ($this->fm + $this->inc < $total_recs && ! $listall) ? '' : ' disabled'; echo ''; // Message is now written here echo ''.$this->message.''; // display page and records statistics echo '' . "\n"; if ($listall) { echo $this->labels['Page'].': 1 '.$this->labels['of'].' 1'; } else { echo $this->labels['Page'].': '; echo (($this->fm / $this->inc)+1); echo ' '.$this->labels['of'].' '; echo max(1, ceil($total_recs / abs($this->inc))); } echo '  '.$this->labels['Records'].': '.$total_recs; echo ''."\n"; } /* }}} */ /* * Display buttons at top and bottom of page - sparky */ function display_record_buttons() /* {{{ */ { // TODO: classify this table and cells echo ''; echo '
' . "\n"; if ($this->change_operation()) { echo ''."\n"; echo ''."\n"; } elseif ($this->add_operation()) { echo ''."\n"; echo ''."\n"; echo ''."\n"; } elseif ($this->copy_operation()) { echo ''."\n"; echo ''."\n"; } elseif ($this->delete_operation()) { echo ''."\n"; echo ''."\n"; } elseif ($this->view_operation()) { if ($this->change_enabled()) { echo ''."\n"; } echo ''."\n"; } echo '
'."\n"; } /* }}} */ /* * Table Page Listing */ function list_table() /* {{{ */ { global $HTTP_SERVER_VARS; $PHP_SELF = $HTTP_SERVER_VARS['PHP_SELF']; // Process any navigation buttons //if (!isset ($this->fm)) if ($this->fm == '') { $this->fm = 0; } if ($this->prev_operation()) { $this->fm = $this->fm - $this->inc; if ($this->fm < 0) { $this->fm = 0; } } if ($this->next_operation()) { $this->fm += $this->inc; } /* * If user is allowed to Change/Delete records, we need an extra column * to allow users to select a record */ $select_recs = $this->key != '' && ($this->change_enabled() || $this->delete_enabled() || $this->view_enabled()); //echo "sfn::".$this->sfn."::
\n"; // Default is to sort on first displayed field if (! is_numeric($this->sfn) && ! $this->initial_sort_suppressed() && ! isset($this->default_sort_columns)) { for ($k = 0; ! $this->displayed[$k]; $k++); $this->sfn = $k; } // Are we doing a listall? $listall = $this->inc <= 0; /* * Display the MySQL table in an HTML table */ $comp_ops = array( ''=>'','%3C'=>'%3C','%3C%3D'=>'%3C%3D', '%3D'=>'%3D','%3E%3D'=>'%3E%3D','%3E'=>'%3E'); echo ''."\n"; echo ''."\n"; echo ''."\n"; $prev_qfn = $this->qfn; $hidden_qfs = $this->get_qf_hidden_fields(); // if sort sequence has changed, restart listing $this->qfn != $prev_qfn && $this->fm = 0; if (0) { // TODO: delete me! echo '$this->qfn vs. $prev_qfn comparsion:::::'; echo ''.htmlspecialchars($this->qfn).':::::'; echo ''.htmlspecialchars($prev_qfn).':::::
'; echo 'comparsion '.($this->qfn == $prev_qfn ? 'proved' : 'failed').''; echo '
'; } //display buttons at top of page - sparky // setup query to get num_rows $total_recs = 0; $count_parts = array( 'type' => 'select', 'select' => 'count(*) as num_rows', 'from' => $this->create_join_clause(), 'where' => $this->make_where_from_query_opts()); $res = $this->myquery($this->query_make($count_parts), __LINE__); $row = @mysql_fetch_array($res, MYSQL_ASSOC); $total_recs = $row['num_rows']; if ($this->nav_up()) { $this->display_list_table_buttons($total_recs); echo '
'."\n"; } if (!$this->fl) { echo($hidden_qfs); } echo ''."\n"; echo ''."\n"; echo ''."\n"; echo ''."\n"; /* * System (navigation, selection) columns counting */ $sys_cols = 0; $sys_cols += intval($this->filter_enabled() || $select_recs); if ($sys_cols > 0) { $sys_cols += intval($this->nav_buttons() && ($this->nav_text_links() || $this->nav_graphic_links())); } /* * We need an initial column(s) (sys columns) * if we have filters, Changes or Deletes enabled */ if ($sys_cols) { echo ''."\n"; } for ($k = 0; $k < $this->num_fds; $k++) { $fd = $this->fds[$k]; /* if ((stristr($this->fdd[$fd]['options'],'L') || ! isset ($this->fdd[$fd]['options'])) && ! $this->hidden($k) ) */ if ($this->displayed[$k]) { $fdn = $this->fdd[$fd]['name']; if (isset ($this->fdd[$fd]['width'])) { $w = ' width="'.$this->fdd[$fd]['width'].'"'; } else { $w = ''; } if ($this->fdd[$fd]['sort']) { // clicking on the current sort field reverses the sort order echo ''.$fdn.''."\n"; } else { echo ''.$fdn.''."\n"; } } // if // if we have any aggregates going on, then we have to list all results $var_to_total = 'qf'.$k.'_aggr'; $$var_to_total = $this->get_cgi_var($var_to_total); if ($$var_to_total != '') { $listall = true; } } // for echo ''."\n"; /* * Prepare the SQL Query from the data definition file */ $qparts['type'] = 'select'; $qparts['select'] = $this->create_column_list(); // Even if the key field isn't displayed, we still need its value if ($select_recs) { if (!in_array ($this->key, $this->fds)) { $qparts['select'] .= ','.$this->fqn($this->key); } } $qparts['from'] = $this->create_join_clause(); $qparts['where'] = $this->make_where_from_query_opts(); // build up the ORDER BY clause if (is_numeric($this->sfn) || isset($this->default_sort_columns)) { $raw_sort_fields = array(); $sort_fields = array(); $sort_fields_w = array(); //if ($this->sfn != '') if (is_numeric($this->sfn)) { if (isset($this->fdd[$this->sfn]['expression'])) { $raw_sort_field = 'qf'.$this->sfn; $sort_field = 'qf'.$this->sfn; $sort_field_w = $this->sfn.'(expression)'; } else { $raw_sort_field = $this->fqn($this->sfn); $sort_field = $this->fqn($this->sfn); $sort_field_w = $this->fdd[$this->sfn]['name']; } if (! $this->sort_asc) { $sort_field .= ' DESC'; $sort_field_w .= ' descending'; } $raw_sort_fields[] = $raw_sort_field; $sort_fields[] = $sort_field; $sort_fields_w[] = $sort_field_w; } if (isset($this->default_sort_columns)) { foreach ($this->default_sort_columns as $dsc) { if ($dsc[0] == '-') { $field = substr($dsc, 1); $desc = true; } else { $field = $dsc; $desc = false; } $raw_candidate = $this->fqn($field); $candidate = $this->fqn($field,true); $sort_field_w = $this->fdd[$field]['name']; if ($desc) { $candidate .= ' DESC'; $sort_field_w .= ' descending'; } if (! in_array($raw_candidate,$raw_sort_fields)) { $sort_fields[] = $candidate; $sort_fields_w[] = $sort_field_w; } } } if (count($sort_fields) > 0) { $qparts['orderby'] = join(',',$sort_fields); } } $to = $this->fm + $this->inc; if ($listall) { $qparts['limit'] = $this->fm.',-1'; } else { $qparts['limit'] = $this->fm.','.$this->inc; } if ($qparts['orderby'] && $this->display['sort']) { // XXX this doesn't preserve filters echo ''; if ($this->sfn != 0) { echo ''; echo ''."\n"; } /* * FILTER * * Draw the filter and fill it with any data typed in last pass and stored * in the array parameter keyword 'filter'. Prepare the SQL WHERE clause. */ if ($this->fl) { echo ''; echo ''."\n"; for ($k = 0; $k < $this->num_fds; $k++) { $this->field_name = $this->fds[$k]; $fd = $this->field_name; $this->field = $this->fdd[$fd]; $l = 'qf'.$k; $lc = 'qf'.$k.'_comp'; $$l = $this->get_cgi_var($l); $$lc = $this->get_cgi_var($lc); $m = $this->web2plain($$l); // get the field name and value $mc = $this->web2plain($$lc); // get the comparison operator for numeric/date types $widthStyle = ''; if (isset($this->fdd[$fd]['width'])) { $widthStyle = ' STYLE=\'width: "'.(6*$this->fdd[$fd]['width']).'px"\''; } $opened = false; if ($this->displayed[$k]) { echo ''."\n"; } else { echo ''."\n"; } // if elseif else } // for echo ''."\n"; } // if first and fl /* * Display the current query */ $text_query = $this->make_text_where_from_query_opts(); if ($text_query != '' && $this->display['query']) { echo ''; echo ''."\n"; } /* * Each row of the HTML table is one record from the SQL Query * Main list_table() query */ $res = $this->myquery($this->query_make($qparts), __LINE__); $first = true; $rowCount = 0; if ($this->nav_text_links() || $this->nav_graphic_links()) { // gather query & GET options to preserve for Update/Delete links $qstrparts = array(); if (count($this->qo) > 0) { foreach ($this->qo as $key=>$val) { if ($key != '' && $key != 'operation' && ! is_array($val)) $qstrparts[] = "$key=$val"; } } if (count($this->get_opts) > 0) { foreach ($this->get_opts as $key=>$val) { if ($key != '' && $key != 'operation' && ! is_array($val)) $qstrparts[] = "$key=$val"; } } // preserve sort field number, filter row, and first record to display isset($this->sfn) && $qstrparts[] = 'sfn='.($this->sort_asc?'':'-').$this->sfn; isset($this->fl) && $qstrparts[] = 'fl='.$this->fl; isset($this->fm) && $qstrparts[] = 'fm='.$this->fm; // do we need to preserve filter (filter query) and sw (filter display/hide button)? $qpview = $qstrparts; $qpview[] = 'operation='.$this->labels['View']; $qpviewStr = '?'.join('&',$qpview).$this->qfn; $qpcopy = $qstrparts; $qpcopy[] = 'operation='.$this->labels['Copy']; $qpcopyStr = '?'.join('&',$qpcopy).$this->qfn; $qpchange = $qstrparts; $qpchange[] = 'operation='.$this->labels['Change']; $qpchangeStr = '?'.join('&',$qpchange).$this->qfn; $qpdelete = $qstrparts; $qpdelete[] = 'operation='.$this->labels['Delete']; $qpdeleteStr = '?'.join('&',$qpdelete).$this->qfn; } while ($row = @mysql_fetch_array($res, MYSQL_ASSOC)) { echo '\n"; if ($sys_cols) { $key_rec = $row['qf'.$this->key_num]; $qviewStr = $qpviewStr .'&rec='.$key_rec; $qcopyStr = $qpcopyStr .'&rec='.$key_rec; $qchangeStr = $qpchangeStr.'&rec='.$key_rec; $qdeleteStr = $qpdeleteStr.'&rec='.$key_rec; if ($select_recs) { if (! $this->nav_buttons() || $sys_cols > 1) { echo ''."\n"; } if ($this->nav_buttons()) { echo ''."\n"; } } elseif ($this->filter_enabled()) { echo ''."\n"; } } // calculate the url query string for optional URL support $urlqueryproto = 'fm='.$this->fm.'&sfn='.($this->sort_asc?'':'-') .$this->sfn.'&'.'fl='.$this->fl.'&qfn='.$this->qfn; for ($k = 0; $k < $this->num_fds; $k++) { $fd = $this->fds[$k]; if ($this->hidden($k) || $this->password($k)) { continue; } elseif (! $this->displayed[$k]) { continue; } // XXX: echo 'displayed: '.$k.'-'.$fd; /* TODO: what's this?! if ((trim($row[$k]) == '') or ($row[$k] == 'NULL')) { echo ' '."\n"; } else { */ // display the contents $colattrs = $this->fdd[$fd]['colattrs']; if ($colattrs != '') $colattrs = ' '.$colattrs; if ($this->fdd[$fd]['nowrap']) $colattrs .= ' nowrap'; if (isset($this->fdd[$fd]['width'])) { $colattrs .= ' width="'.$this->fdd[$fd]['width'].'"'; } echo ' '; if (! $this->hidden($k) && ! $this->password($k)) { // displayable if (isset($this->fdd[$k]['URL']) || isset($this->fdd[$k]['URLprefix']) || isset($this->fdd[$k]['URLpostfix'])) { /* It's an URL Put some conveniences in the namespace for the user to be able to use in the URL string. */ $key = $key_rec; $name = $this->fds[$k]; $value = $row["qf$k"]; $page = $this->page_name; $urlstr = $urlqueryproto.'&rec='.$key; $urllink = isset($this->fdd[$k]['URL']) ? eval('return "'.$this->fdd[$k]['URL'].'";') : $value; $urldisp = isset($this->fdd[$k]['URLdisp']) ? eval('return "'.$this->fdd[$k]['URLdisp'].'";') : $value; $target = isset($this->fdd[$k]['URLtarget']) ? 'target="'.htmlspecialchars($this->fdd[$k]['URLtarget']).'" ' : ''; isset($this->fdd[$k]['URLprefix']) && $urllink = $this->fdd[$k]['URLprefix'].$urllink; isset($this->fdd[$k]['URLpostfix']) && $urllink .= $this->fdd[$k]['URLpostfix']; if (strlen($urllink) <= 0 || strlen($urldisp) <= 0) { echo ' '; } else { $urllink = htmlspecialchars($urllink); $urldisp = htmlspecialchars($urldisp); echo ''.$urldisp.''; } } elseif (isset($this->fdd[$k]['datemask'])) { // display date according to a mask if any //echo $this->mdate_set($row[$k],$this->fdd[$k]['type'],$this->fdd[$k]['datemask']); //echo // $this->mdate_displayPlain( // $this->mdate_from_mysql( // $row[$k]), // ( // $this->fdd[$k]['datemask']? // $this->fdd[$k]['datemask'] // : // $this->mdate_masks[$this->fdd[$k]['type']] // ) // ); //echo $row[$k]; // it's a normal field $shortdisp = $row["qf$k"]; if ($this->fdd[$k]['strip_tags']) { $shortdisp = strip_tags($shortdisp); } if (isset($this->fdd[$k]['trimlen']) && strlen($shortdisp) > $this->fdd[$k]['trimlen']) { $shortdisp = ereg_replace("[\r\n\t ]+", ' ', $shortdisp); $shortdisp = substr($shortdisp,0,$this->fdd[$k]['trimlen']-3).'...'; } echo nl2br($this->htmlDisplay($this->fdd[$k], $shortdisp)); } else { // it's a normal field if ($this->is_values2($k, $row["qf$k"])) { $escape_flag = false; $shortdisp = $this->fdd[$k]['values2'][$row['qf'.$k.'_idx']]; } else { $escape_flag = true; $shortdisp = $row["qf$k"]; if ($this->fdd[$k]['strip_tags']) { $shortdisp = strip_tags($shortdisp); } if (isset($this->fdd[$k]['trimlen']) && strlen($shortdisp) > $this->fdd[$k]['trimlen']) { $shortdisp = ereg_replace("[\r\n\t ]+",' ',$shortdisp); $shortdisp = substr($shortdisp,0,$this->fdd[$k]['trimlen']-3).'...'; } } echo nl2br($this->htmlDisplay($this->fdd[$k], $shortdisp, true, true, true, $escape_flag)); } } else { // it's hidden or a password echo 'hidden'; } echo ''."\n"; } // for echo ' '."\n"; } // while /* * Display and accumulate column aggregation info, do totalling query * XXX this feature does not work yet!!! */ // aggregates listing (if any) if ($$var_to_total) { // do the aggregate query if necessary //if ($vars_to_total) { $qp = array(); $qp['type'] = 'select'; $qp['select'] = $aggr_from_clause; $qp['from'] = $this->create_join_clause (); $qp['where'] = $this->make_where_from_query_opts(); $tot_query = $this->query_make($qp); //$this->elog('TOT_QRY: '.$tot_query,__LINE__); $totals_result = $this->myquery($tot_query,__LINE__); $tot_row = @mysql_fetch_array($totals_result, MYSQL_ASSOC); //} $qp_aggr = $qp; echo "\n".''."\n".''."\n"; /* echo ''; echo ''; */ // display the results for ($k=0;$k<$this->num_fds;$k++) { $fd = $this->fds[$k]; if (stristr($this->fdd[$fd]['options'],'L') or !isset($this->fdd[$fd]['options'])) { echo ''."\n"; } } echo ''."\n"; } echo '
'; if ($this->filter_enabled()) { if ($this->fl) { echo ''; echo '
'; //echo ''; } else { echo ''; } } else { echo ' '; } echo '
'. ''.$this->labels['Clear'].''. 'Sorted By: '; } else { echo 'Default Sort Order: '; } echo join(', ',$sort_fields_w); echo '
'; echo ''; $opened = true; } $type = $this->fdd[$fd]['type']; if ($this->col_has_values($k)) { $type = 'string'; } /* if ( stristr($this->fdd[$fd]['options'],'L') or !isset ($this->fdd[$fd]['options']) ) */ if (! $this->displayed[$k]) { continue; } if ($this->fdd[$fd]['select'] == 'D' or $this->fdd[$fd]['select'] == 'M') { /* * Multiple fields processing - default size is 2 and array required for values */ $multiple = $this->fdd[$fd]['select'] == 'M'; $selected = $m; $x = isset($this->fdd[$k]['values']['table']) || !$this->col_has_values($k) ? $this->set_values_from_table($k, array('*' => '*')) : array('*' => '*') + (array) $this->fdd[$k]['values2'] + (array) $this->fdd[$k]['values']; echo $this->htmlSelect($l, $x, $selected, $multiple); } elseif ($this->fdd[$fd]['select'] == 'T') { // this is where we put the comparison selects if (! $this->password($k) && ! $this->hidden($k)) { $maxlen = intval($this->fdd[$k]['maxlen']); !$maxlen && $maxlen = mysql_field_len($res, "qf$k"); $size = $maxlen < 30 ? min($maxlen, 8) : 12; if ($this->col_is_string($k)) { // it's treated as a string echo ''; } elseif ($this->col_is_date($k)) { // it's a date //echo $this->htmlSelect($l.'_comp',$comp_ops,$$lc); // first get any date elements that were passed in //$filter_val = $this->gather_search_date_fields_into_mysql_timestamp('qf'.$k); // display the search formlet //if ($mc) { // //echo $this->display_search_field_date($type,'qf'.$k,$filter_val,$this->fdd[$k]['datemask']); // //echo $this->mdate_displayForm($filter_val,$type,'qf'.$k,$this->fdd[$k]['datemask'],true); // echo $this->mdate_disperse($k,true,$filter_val); //} //else { // //echo $this->display_search_field_date( $type,'qf'.$k,'',$this->fdd[$k]['datemask']); // echo $this->mdate_displayForm('',$type,'qf'.$k,$this->fdd[$k]['datemask'],true); //} // it's treated as a string echo ''; } elseif ($this->col_is_number($k)) { // it's a number echo $this->htmlSelect($l.'_comp',$comp_ops,$$lc); // it's treated as a string echo ''; } else { // type is 'unknown' or not set, it's treated as a string echo ''; } } else { echo " "; } // if it's int or real and if not password or hidden, display aggr options /* XXX Disabled until we have time to work on this if ((! $this->password($k) && ! $this->hidden($k)) && (($this->col_is_number($k)) && (! isset($this->fdd[$k]['values'])))) { $var_to_total = 'qf'.$k.'_aggr'; global $$var_to_total; $aggr_function = $$var_to_total; if (isset($$var_to_total)) { $vars_to_total[] = $this->fqn($k); $aggr_from_clause .= ' '.$aggr_function.'('. $this->fqn($k). ') as '.$var_to_total; } echo '
Aggr: '; echo $this->htmlSelect($var_to_total,$this->sql_aggrs,$$var_to_total); if ($$var_to_total != '') { $listall = true; } } else { echo ' '; } */ echo '
 
' .''.$this->labels['Clear'].'Current Query: ' .htmlspecialchars(stripslashes(stripslashes(stripslashes($text_query)))) .'
'; } if ($this->nav_graphic_links()) { $printed_out = false; if ($this->view_enabled()) { $printed_out = true; echo ''
								.htmlspecialchars($this->labels['View']).''; } if ($this->change_enabled()) { $printed_out && print(' '); $printed_out = true; echo ''
								.htmlspecialchars($this->labels['Change']).''; } if ($this->copy_enabled()) { $printed_out && print(' '); $printed_out = true; echo ''
								.htmlspecialchars($this->labels['Copy']).''; } if ($this->delete_enabled()) { $printed_out && print(' '); $printed_out = true; echo ''
								.htmlspecialchars($this->labels['Delete']).''; } } if ($this->nav_text_links()) { if ($this->nav_graphic_links()) { echo '
'; } $printed_out = false; if ($this->view_enabled()) { $printed_out = true; echo 'V '; } if ($this->change_enabled()) { $printed_out && print(' '); $printed_out = true; echo 'C '; } if ($this->copy_enabled()) { $printed_out && print(' '); $printed_out = true; echo 'P '; } if ($this->delete_enabled()) { $printed_out && print(' '); $printed_out = true; echo 'D'; } } if (! $this->nav_buttons() || $sys_cols > 1) { echo '
'; echo '  
 '; echo printarray($qp_aggr); echo printarray($vars_to_total); echo ''.$var_to_total.' '.$$var_to_total.''; $aggr_var = 'qf'.$k.'_aggr'; $$aggr_var = $this->get_cgi_var($aggr_var); if ($$aggr_var) { echo $this->sql_aggrs[$$aggr_var].': '.$tot_row[$aggr_var]; } else { echo ' '; } echo '
'."\n"; // end of table rows listing if ($this->nav_down()) { //display buttons at bottom of page - sparky echo '
'."\n"; $this->display_list_table_buttons($total_recs); } echo ''."\n"; //phpinfo(); /* foreach ( array( // '1999-12-31'=>'%Y-%m-%d', // '99-Mar-31'=>'%y-%M-%d', // '99-1-31'=>'%y-%n-%d' // 'March 8, 1999'=>'%F %j, %Y' // 'March 8, 1999 09:17:32'=>'%F %j, %Y %H:%i:%s' 'March 8, 1999 9:17:32'=>'%F %j, %Y %G:%i:%s' ) as $val=>$mask ) { echo "
\n"; debug_var('val,mask',"$val::$mask"); debug_var('mdate_parse',date('Y m d H:i:s',$this->mdate_parse($val,$mask))); } */ } /* }}} */ function display_record() /* {{{ */ { $this->create_javascripts(); if ($this->nav_up()) { //display buttons at top of page - sparky $this->display_record_buttons (); echo "
\n"; } echo ''."\n"; echo ''."\n"; echo ''."\n"; echo ''."\n"; echo ''."\n"; echo $this->get_qf_hidden_fields(); echo ''."\n"; /* $this->qfn = ''; for ($k = 0; $k < $this->num_fds; $k++) { $l = 'qf'.$k; $lc = 'qf'.$k.'_comp'; $$l = $this->get_cgi_var($l); $$lc = $this->get_cgi_var($lc); $m = $this->web2plain($$l); // get the field name and value $mc = $this->web2plain($$lc); // get the comparison operator for numeric/date types if (! isset($m)) { continue; } if (is_array($m)) { // multiple selection has been used if (!in_array('*',$m)) { // one '*' in a multiple selection is all you need for ($n=0; $nplain2web($m[$n]) != '') { $this->qfn = $this->qfn.'&qf'.$k.'['.$n.']=' .$this->plain2web($m[$n]); } echo ''."\n"; } } } } else { if ($this->plain2web($m) != '') { $this->qfn = $this->qfn.'&qf'.$k.'='.$m; echo ''."\n"; } } } */ if ($this->add_operation()) { $this->display_add_record(); } else { $this->display_copy_change_delete_record(); } echo '
'."\n"; if ($this->nav_down()) { //display buttons at bottom of page - sparky echo "
\n"; $this->display_record_buttons(); } echo ''."\n"; } /* }}} */ /* * Action functions */ function do_add_record() /* {{{ */ { global $HTTP_SERVER_VARS; $REMOTE_USER = $HTTP_SERVER_VARS['REMOTE_USER']; $REMOTE_ADDR = $HTTP_SERVER_VARS['REMOTE_ADDR']; $tib = true; // check for a before-add trigger if (isset($this->triggers['insert']['before'])) { $tib = include($this->triggers['insert']['before']); } if ($tib) { // before trigger returned good status let's do the main operation $key_col_val = ''; $qry = ''; for ($k = 0; $k < $this->num_fds; $k++) { if ($this->processed($k)) { $fd = $this->fds[$k]; if ($fd == $this->key) { $key_col_val = addslashes($this->encode($this->fdd[$k],$fn)); } if ($qry == '') { $qry = 'INSERT INTO '.$this->tb.' (`'.$fd.'`'; } else { $qry = $qry.',`'.$fd.'`'; } } } $tim = false; // do the main operation $val = ') VALUES ('; $vals = array(); for ($k = 0; $k < $this->num_fds; $k++) { $type = $this->fdd[$k]['type']; if ($this->processed($k)) { $fd = $this->fds[$k]; $fn = $this->get_http_post_var_by_name($fd); /* if ($this->col_is_date($k)) { //$vals[$k] = '"'.$this->mdate_set($this->mdate_getFromPost($k),$type,$this->fds[$k]['type']).'"'; if ($type == 'time') $vals[$k] = 'date_format(from_unixtime('.$this->mdate_getFromPost($k).'),"%H%i%s")'; elseif ($type == 'year') $vals[$k] = 'date_format(from_unixtime('.$this->mdate_getFromPost($k).'),"%Y")'; else $vals[$k] = 'from_unixtime('.$this->mdate_getFromPost($k).')'; } else // continued on next line */ /* Old Jim code: $this->col_is_set($k) && $fn != ''*/ if (is_array($fn)) { $vals[$k] = "'".addslashes($this->encode($this->fdd[$k],join(',',$fn)))."'"; } else { $vals[$k] = "'".addslashes($this->encode($this->fdd[$k],$fn))."'"; } } } $qry = $qry.$val.join(',',$vals).')'; $res = $this->myquery($qry,__LINE__); if ($res) { $tim = true; } $this->message = @mysql_affected_rows().' '.$this->labels['record added']; } if ( $tib && isset($this->triggers['insert']['after']) && $tim ) { // before executed ok // main op executed ok // let's do the after trigger $tia = include($this->triggers['insert']['after']); } // notify list $kv = array(); if (($this->notify['insert'])) { $user = $REMOTE_USER; if (! $user) $user = $REMOTE_ADDR; $body = 'A new item was added to '.$this->page_name." by ".$user." with the following fields:\n"; for ($k=0;$k<$this->num_fds;$k++) { if ($this->processed($k)) { $body .= $this->fdd[$k]['name'].': '.$vals[$k]."\n"; $kv[$this->fds[$k]] = $vals[$k]; } } // mail it mail($this->notify['insert'],'Record Added to '.$this->tb,$body); } // note change in log table if ($this->logtable) { $this->myquery( "INSERT INTO ".$this->logtable." VALUES (". "NOW(),". "'".$REMOTE_USER."',". "'".$REMOTE_ADDR."',". "'insert','". $this->tb."',". "'".$key_col_val."','','','". addslashes(serialize($kv))."')" ,__LINE__); } } /* }}} */ function do_change_record() /* {{{ */ { global $HTTP_SERVER_VARS; $REMOTE_USER = $HTTP_SERVER_VARS['REMOTE_USER']; $REMOTE_ADDR = $HTTP_SERVER_VARS['REMOTE_ADDR']; $tub = true; // check for a before-add trigger if (isset($this->triggers['update']['before'])) { $tub = include($this->triggers['update']['before']); } $tum = false; if ($tub) { // before trigger returned good status // let's do the main operation $qry = ''; $qry_old_rec = ''; for ($k = 0; $k < $this->num_fds; $k++) { $type = $this->fdd[$k]['type']; if ($this->processed($k) && ! $this->readonly($k)) { $fd = $this->fds[$k]; if ($fd == $this->key) { $key_col_val = addslashes($this->get_http_post_var_by_name($fd)); } $fn = $this->get_http_post_var_by_name($fd); /* if ($this->col_is_date($k)) { $fn = date(str_replace('%','',$this->mdate_masks[$type]),$this->mdate_getFromPost($k)); } */ /* Old Jim code: $this->col_is_set($k) && $fn != ''*/ if (is_array($fn)) { $newValue = addslashes($this->encode($this->fdd[$k],join(',',$fn))); } else { $newValue = addslashes($this->encode($this->fdd[$k],$fn)); } if ($qry == '') { $qry = 'UPDATE '.$this->tb.' SET `'.$fd.'`=\''.$newValue.'\''; $qry_old_rec = 'SELECT `'.$fd.'`'; } else { $qry = $qry.',`'.$fd.'`=\''.$newValue.'\''; $qry_old_rec .= ',`'.$fd.'`'; } $newvalues[$this->fds[$k]] = addslashes($fn); } elseif ($this->hidden($k)) { // XXX do something } } $qry = $qry.' WHERE ('.$this->key.' = '.$this->key_delim.$this->rec.$this->key_delim.')'; $qry_old_rec .= ' FROM '.$this->tb.' WHERE ('.$this->key.' = '.$this->key_delim.$this->rec.$this->key_delim.')'; // get the old data $res_old = $this->myquery($qry_old_rec, __LINE__); $oldvalues = mysql_fetch_array($res_old); // update the data //echo "\n

$qry

\n"; $res = $this->myquery($qry,__LINE__); // find and accumulate the changes $changes=array(); for ($k = 0; $k < $this->num_fds; $k++) { if ($this->processed($k)) { if ($oldvalues[$this->fds[$k]] != stripslashes($newvalues[$this->fds[$k]])) { $changes[$this->fds[$k]] = array(); $changes[$this->fds[$k]]['was'] = $oldvalues[$this->fds[$k]]; $changes[$this->fds[$k]]['is' ] = $newvalues[$this->fds[$k]]; } } } if ($res) { $tum = true; } /* echo '

Was:

'."\n"; echo '
';
print_r($oldvalues);
echo '
'."\n"; echo '

Is:

'."\n"; echo '
';
print_r($newvalues);
echo '
'."\n"; echo '

Changes to be sent in e-mail:

'."\n"; echo '
';
print_r($changes);
echo '
'."\n"; echo '
'.mysql_affected_rows ().' '.$this->labels['Change'].'
'."\n"; */ $this->message = @mysql_affected_rows().' '.$this->labels['record changed']; } if ( $tub && isset($this->triggers['update']['after']) && $tum ) { // before executed ok // main op executed ok // let's do the after trigger $tua = include($this->triggers['update']['after']); } // notify list if (($this->notify['update'])) { if (count($changes) > 0) { $user = $REMOTE_USER; if (! $user) $user = $REMOTE_ADDR; $body = 'An item with ' .$this->fdd[$this->key]['name'] .'=' .$this->key_delim.$this->rec.$this->key_delim .' was updated by '.$user.' in '.$this->page_name." with the following fields:\n"; foreach ($changes as $key=>$vals) { if ($this->processed($k)) { $fieldName = $this->fdd[$key]['name']; $body .= $fieldName.":\n". "was:\t\"".$vals['was']."\"\n". "is:\t\"".$vals['is']."\"\n"; } } // mail it mail($this->notify['update'],'Record Updated in '.$this->tb,$body); } } // note change in log table if ($this->logtable) { foreach ($changes as $key=>$vals) { $qry = "INSERT INTO ".$this->logtable." VALUES (". "NOW(),'".$REMOTE_USER."','".$REMOTE_ADDR."','update','". $this->tb."','".$key_col_val."','".$key."','". addslashes($vals['was'])."','". addslashes($vals['is'])."')"; $this->myquery($qry,__LINE__); } } } /* }}} */ function do_delete_record() /* {{{ */ { global $HTTP_SERVER_VARS; $REMOTE_USER = $HTTP_SERVER_VARS['REMOTE_USER']; $REMOTE_ADDR = $HTTP_SERVER_VARS['REMOTE_ADDR']; $tdb = true; // check for a before-add trigger if (isset($this->triggers['delete']['before'])) { $tdb = include($this->triggers['delete']['before']); } $tdm = false; // before trigger returned good status // let's do the main operation if ($tdb) { // before trigger returned good status // let's do the main operation for ($k = 0; $k < $this->num_fds; $k++) { if ($this->processed($k)) { $fd = $this->fds[$k]; if ($fd == $this->key) { $key_col_val = addslashes($this->encode($this->fdd[$k],$fn)); } } } if ($this->logtable) { $res = $this->myquery( 'select * from '.$this->tb.' where (`'.$this->key.'` = '.$this->key_delim.$this->rec.$this->key_delim.')' ,__LINE__); $oldrow = mysql_fetch_array($res); } $qry = 'DELETE FROM '.$this->tb.' WHERE (`'.$this->key.'` = '.$this->key_delim.$this->rec.$this->key_delim.')'; $res = $this->myquery($qry,__LINE__); if ($res) { $tdm = true; } $this->message = @mysql_affected_rows().' '.$this->labels['record deleted']; } if ( $tdb && isset($this->triggers['delete']['after']) && $tdm ) { // before executed ok // main op executed ok // let's do the after trigger $tda = include($this->triggers['delete']['after']); } // notify list if (($this->notify['delete'])) { $user = $REMOTE_USER; if (! $user) $user = $REMOTE_ADDR; $body = 'An item was deleted by '.$user.' from '.$this->page_name."\n"; foreach ($oldrow as $key=>$val) { if (is_string($key)) { $body .= $this->fdd[$key]['name'].":\t".$val."\n"; } } // mail it mail($this->notify['delete'],'Record Deleted in '.$this->tb,$body); } // note change in log table if ($this->logtable) { $this->myquery( "INSERT INTO ".$this->logtable." VALUES (". "SYSDATE(),". "'".$REMOTE_USER."',". "'".$REMOTE_ADDR."',". "'delete','". $this->tb."',". "'".$key_col_val."',". "'".$key."','". addslashes(serialize($oldrow))."','')" ,__LINE__); } } /* }}} */ /* * Recreate functions */ function recreate_fdd() /* {{{ */ { // TODO: one level deeper browsing $action_letter = 'L'; // list by default $this->filter_operation() && $action_letter = 'F'; $this->view_operation() && $action_letter = 'V'; $this->delete_operation() && $action_letter = 'D'; $this->add_operation() && $action_letter = 'A'; $this->change_operation() && $action_letter = 'C'; $this->copy_operation() && $action_letter = 'P'; // Restore backups (if exists) foreach (array_keys($this->fdd) as $column) { foreach (array_keys($this->fdd[$column]) as $col_option) { if ($col_option[strlen($col_option) - 1] != '~') continue; $this->fdd[$column][substr($col_option, 0, strlen($col_option) - 1)] = $this->fdd[$column][$col_option]; unset($this->fdd[$column][$col_option]); } } foreach (array_keys($this->fdd) as $column) { foreach (array_keys($this->fdd[$column]) as $col_option) { if (! strchr($col_option, '|')) continue; $col_ar = explode('|', $col_option, 2); if (! stristr($col_ar[1], $action_letter)) continue; // Make field backups $this->fdd[$column][$col_ar[0] .'~'] = $this->fdd[$column][$col_ar[0]]; $this->fdd[$column][$col_option.'~'] = $this->fdd[$column][$col_option]; // Set particular field $this->fdd[$column][$col_ar[0]] = $this->fdd[$column][$col_option]; unset($this->fdd[$column][$col_option]); } } } /* }}} */ function recreate_displayed($sort_field = '') /* {{{ */ { $field_num = 0; $num_fields_displayed = 0; $this->fds = array(); $this->displayed = array(); $this->guidance = false; foreach ($this->fdd as $akey => $aval) { if (preg_match('/^\d*$/', $akey)) /* skipping numeric keys */ continue; $this->fds[$field_num] = $akey; if ($sfn == '' && $akey == $sort_field) { $this->sfn = $field_num; } /* We must use here displayed() function, because displayed[] array is not created yet. We will simultaneously create that array as well. */ if ($this->displayed[$field_num] = $this->displayed($field_num)) { $num_fields_displayed++; } /* I *really* want to know what does this foreach() do! -- Nepto [17/10/2002] */ if (is_array($aval['values']) && (! $aval['values']['table'])) { $values = array(); foreach ($aval['values'] as $val) { $values[$val] = $val; } $aval['values'] = $values; } $this->fdd[$field_num] = $aval; $aval['help'] && $this->guidance = true; $field_num++; } if (0) { echo 'Displayed array:
';
			var_dump($this->displayed);
			echo '

'; } $this->num_fds = $field_num; $this->num_fields_displayed = $num_fields_displayed; $this->key_num = array_search($this->key, $this->fds); } /* }}} */ /* * Error handling function */ function error($message) /* {{{ */ { echo '

phpMyEdit error: '.htmlspecialchars($message).'

'."\n"; return false; } /* }}} */ /* * Database connection function */ function connect() /* {{{ */ { if (!isset($this->db)) { $this->error('no database defined'); return false; } if (!isset ($this->tb)) { $this->error('no table defined'); return false; } if ($dbl = @mysql_pconnect($this->hn, $this->un, $this->pw)) ; else { $this->error('could not connect to MySQL'); return false; } return true; } /* }}} */ /* * The workhorse */ function execute() /* {{{ */ { // DEBUG - uncomment to enable /* //phpinfo(); $this->print_get_vars(); $this->print_post_vars(); $this->print_vars(); echo "
query opts:\n";
		echo print_r($this->query_opts);
		echo "
\n"; echo "
get vars:\n";
		echo print_r($this->get_opts);
		echo "
\n"; */ /* Database connection */ if ($this->connect() == false) return false; /* * ====================================================================== * Pass 3: process any updates generated if the user has selected * a save button during Pass 2 * ====================================================================== */ if ($this->saveadd == $this->labels['Save']) { $this->do_add_record(); } if ($this->moreadd == $this->labels['More']) { $this->do_add_record(); $this->operation = $this->labels['Add']; // to force add operation } if ($this->savechange == $this->labels['Save']) { $this->do_change_record(); } if ($this->savedelete == $this->labels['Delete']) { $this->do_delete_record(); } /* * ====================================================================== * Pass 2: display an input/edit/confirmation screen if the user has * selected an editing button on Pass 1 through this page * ====================================================================== */ if ($this->add_operation() || $this->change_operation() || $this->delete_operation() || $this->view_operation() || $this->copy_operation()) { $this->display_record(); } /* * ====================================================================== * Pass 1 and Pass 3: display the MySQL table in a scrolling window on * the screen (skip this step in 'Add More' mode) * ====================================================================== */ else { $this->list_table(); } global $phpMyEdit_timer; if ($this->display['time'] && $phpMyEdit_timer) { echo $phpMyEdit_timer->end(); } } /* }}} */ /* * Class constructor */ function phpMyEdit($opts) /* {{{ */ { global $HTTP_SERVER_VARS; /* * Creating directory variables */ $this->dir['root'] = dirname(__FILE__) . (strlen(dirname(__FILE__)) > 0 ? '/' : ''); $this->dir['lang'] = $this->dir['root'].'lang/'; /* * Creting URL variables */ $this->url['images'] = 'images/'; isset($opts['url']['images']) && $this->url['images'] = $opts['url']['images']; /* * Instance class variables */ $this->hn = $opts['hn']; $this->hn = $opts['hn']; $this->un = $opts['un']; $this->pw = $opts['pw']; $this->db = $opts['db']; $this->tb = $opts['tb']; $this->key = $opts['key']; $this->key_type = $opts['key_type']; $this->inc = $opts['inc']; $this->options = $opts['options']; $this->fdd = $opts['fdd']; $this->multiple = intval($opts['multiple']); $this->multiple <= 0 && $this->multiple = 2; $this->display = $opts['display']; $this->filters = $opts['filters']; $this->triggers = $opts['triggers']; $this->logtable = $opts['logtable']; $this->page_name = $this->tb; $opts['page_name'] && $this->page_name = $opts['page_name']; $this->default_sort_columns = $opts['default_sort_columns']; // alternate row background colors /* What's this?! if (isset($opts['bgcolorOdd'])) { $this->bgcolorOdd = 'White'; } else { $this->bgcolorOdd = $opts['bgcolorOdd']; } if (isset($opts['bgColorEven'])) { $this->bgcolorEven = 'Silver'; } else { $this->bgcolorEven = $opts['bgcolorEven']; } */ // e-mail notification if (isset($opts['notify'])) { $this->notify = $opts['notify']; } // navigation $this->navigation = $opts['navigation']; if (! $this->nav_buttons() && ! $this->nav_text_links() && ! $this->nav_graphic_links()) { $this->navigation .= 'B'; // buttons are default } if (! $this->nav_up() && ! $this->nav_down()) { $this->navigation .= 'D'; // down position is default } // language labels (must go after navigation) $this->labels = $this->make_language_labels($opts['language'] ? $opts['language'] : $HTTP_SERVER_VARS['HTTP_ACCEPT_LANGUAGE']); // CGI variables $this->cgi['append'] = $opts['cgi']['append']; $this->cgi['overwrite'] = $opts['cgi']['overwrite']; /* * Find the URL to post forms */ $this->page_name = basename($HTTP_SERVER_VARS['PHP_SELF']); /* * Form variables all around */ $this->operation = $this->get_cgi_var('operation'); $this->apply = $this->get_cgi_var('apply'); $this->fl = intval($this->get_cgi_var('fl')); $this->fm = intval($this->get_cgi_var('fm')); $this->sfn = $this->get_cgi_var('sfn'); $this->sort_asc = $this->sfn[0] != '-'; $this->sfn = abs(intval($this->sfn)); $this->qfn = $this->get_cgi_var('qfn'); $this->sw = $this->get_cgi_var('sw'); $this->rec = $this->get_cgi_var('rec', ''); // Fixed #523390 [7/8/2002] [2/2] $this->prev = $this->get_cgi_var('prev'); $this->next = $this->get_cgi_var('next'); $this->saveadd = $this->get_cgi_var('saveadd'); $this->moreadd = $this->get_cgi_var('moreadd'); $this->savechange = $this->get_cgi_var('savechange'); $this->savedelete = $this->get_cgi_var('savedelete'); /* * Filter setting */ if (isset($this->sw)) { $this->sw == $this->labels['Search'] && $this->fl = 1; $this->sw == $this->labels['Hide'] && $this->fl = 0; $this->sw == $this->labels['Clear'] && $this->fl = 0; } /* * Specific $fdd modifications depending on performed action */ $this->recreate_fdd(); /* * Extract SQL Field Names and number of fields */ $this->recreate_displayed(); /* * Clear action */ if ($this->sw == $this->labels['Clear']) { for ($k = 0; $k < $this->num_fds; $k++) { $this->cgi['overwrite']["qf$k"] = ''; $this->cgi['overwrite']["qf$k".'_comp'] = ''; } } /* * Constants */ // code to use this is commented out $this->sql_aggrs = array( '' => '', 'sum' => 'Total', 'avg' => 'Average', 'min' => 'Minimum', 'max' => 'Maximum', 'count' => 'Count'); // to support quick type checking $this->stringTypes = array('string','blob','set','enum'); $this->numberTypes = array('int','real'); $this->dateTypes = array('date','datetime','timestamp','time','year'); // mdate constants $this->mdate_masks = array( 'date'=>'%Y-%m-%d', 'datetime'=>'%Y-%m-%d %H:%i:%s', 'timestamp'=>'%Y%m%d%H%i%s', 'time'=>'%H:%i:%s', 'year'=>'%Y'); $this->mdate_daterange = range(date('Y')-10,date('Y')+10); $this->months_short = array( '~~PME~~'=>0, 'Jan'=>1, 'Feb'=>2, 'Mar'=>3, 'Apr'=>4, 'May'=>5, 'Jun'=>6, 'Jul'=>7, 'Aug'=>8, 'Sep'=>9, 'Oct'=>10, 'Nov'=>11, 'Dec'=>12); $this->months_long = array( '~~PME~~'=>0, 'January'=>1,'February'=>2,'March'=>3, 'April'=>4,'May'=>5,'June'=>6, 'July'=>7,'August'=>8,'September'=>9, 'October'=>10,'November'=>11,'December'=>12); $this->months_long_keys = array_keys($this->months_long); /* If you are phpMyEdit developer, set this to 1. You can also hide some new unfinished and/or untested features under if ($this->development) { new_feature(); } statement. Also note, that this is currently unused. */ $this->development = 0; /* * Preparing some others values * (this was moved from execute() method) */ set_magic_quotes_runtime(0); // let's do explicit quoting ... it's safer // XXX fix this to use col_is_[type] if (in_array($this->key_type, array('string','blob','date','time','datetime','timestamp','year'))) { $this->key_delim = '"'; } else { $this->key_delim = ''; $this->rec = intval($this->rec); // Fixed #523390 [7/8/2002] [1/2] } $this->gather_query_opts(); $this->gather_get_vars(); $this->gather_post_vars(); $this->unify_opts(); // Call to Action // Moved this from the setup.php generated file to here !isset($opts['execute']) && $opts['execute'] = 1; $opts['execute'] && $this->execute(); } /* }}} */ } // end of phpMyEdit class /* Modeline for ViM {{{ * vim:set ts=4: * vim600:fdm=marker fdl=0 fdc=0: * }}} */ ?>