extra_type = 'AND'; if (!empty($table)) { $this->table = $table; $this->left_table = $left_table; $this->left_field = $left_field; $this->field = $field; $this->extra = $extra; $this->type = strtoupper($type); } else if (!empty($this->definition)) { // if no arguments, construct from definition. // These four must exist or it will throw notices. $this->table = $this->definition['table']; $this->left_table = $this->definition['left_table']; $this->left_field = $this->definition['left_field']; $this->field = $this->definition['field']; if (!empty($this->definition['extra'])) { $this->extra = $this->definition['extra']; } if (!empty($this->definition['extra type'])) { $this->extra = strtoupper($this->definition['extra_type']); } $this->type = !empty($this->definition['type']) ? strtoupper($this->definition['type']) : 'LEFT'; } } /** * Build the SQL for the join this object represents. */ function join($table, &$query) { $left = $query->get_table_info($this->left_table); $output = " $this->type JOIN {" . $this->table . "} $table[alias] ON $left[alias].$this->left_field = $table[alias].$this->field"; // Tack on the extra. if (isset($this->extra)) { if (is_array($this->extra)) { $extras = array(); foreach ($this->extra as $info) { $extra = ''; // Figure out the table name. Remember, only use aliases provided // if at all possible. $join_table = ''; if (!array_key_exists('table', $info)) { $join_table = $table['alias'] . '.'; } elseif (isset($info['table'])) { $join_table = $info['table'] . '.'; } // And now deal with the value and the operator. Set $q to // a single-quote for non-numeric values and the // empty-string for numeric values, then wrap all values in $q. $raw_value = $this->db_safe($info['value']); $q = (empty($info['numeric']) ? "'" : ''); if (is_array($raw_value)) { $operator = !empty($info['operator']) ? $info['operator'] : 'IN'; // Transform from IN() notation to = notation if just one value. if (count($raw_value) == 1) { $value = $q . array_shift($raw_value) . $q; $operator = $operator == 'NOT IN' ? '!=' : '='; } else { $value = "($q" . implode("$q, $q", $raw_value) . "$q)"; } } else { $operator = !empty($info['operator']) ? $info['operator'] : '='; $value = "$q$raw_value$q"; } $extras[] = "$join_table$info[field] $operator $value"; } if ($extras) { if (count($extras) == 1) { $output .= ' AND ' . array_shift($extras); } else { $output .= ' AND (' . implode(' ' . $this->extra_type . ' ', $extras) . ')'; } } } else if ($this->extra && is_string($this->extra)) { $output .= " AND ($this->extra)"; } } return $output; } /** * Ensure that input is db safe. We only check strings and ints tho * so something that needs floats in their joins needs to do their * own type checking. */ function db_safe($input) { if (is_array($input)) { $output = array(); foreach ($input as $value) { if (empty($info['numeric'])) { $output[] = db_escape_string($value); } else { $output[] = intval($value); } } } else if (empty($info['numeric'])) { $output = db_escape_string($input); } else { $output = intval($input); } return $output; } } /** * @} */