/** * Putting the word "Controller" at the end of each controller name is optional. * * <pre class="highlighted"><code class="php">Dispatcher::getUrl('post',array('post_id'=>5)); //outputs "http://application_url/blog/5" * Dispatcher::getUrl('post',array('post_id'=>5),'?offset=1'); //outputs "http://application_url/blog/5?offset=1" * Dispatcher::getUrl('post',array('post_id'=>5),array('offset'=>1)); //outputs "http://application_url/blog/5?offset=1" * Dispatcher::getUrl('post',array('post_id'=>5),false); //outputs "/blog/5" * Dispatcher::getUrl(array('BlogController','post'),array('post_id'=>5)); //outputs "http://application_url/blog/5" * Dispatcher::getUrl(array('Blog','post'),array('post_id'=>5)); //outputs "http://application_url/blog/5"</code></pre> * @param mixed $class_and_method String method_name if reffering to a method in the Controller class that is currently responding, or array('ControllerName,'methodName') if referring to a method in another Controller. * @param mixed $arguments Optional arguments to resolve the url. * @param mixed $include_base_url If true, includes the base_url, if false then not, if a string, then the base_url is included, and the string is appended to the end, if array base_url is included, and http_build_query is called with that array an appended * @return mixed String url or boolean false if the url could not be resolved. */ public static function getUrl($class_and_method, $arguments = false, $include_base_url = true) { if (!$arguments) { $arguments = array(); } if (!is_array($arguments) && !is_object($arguments)) { throw new Exception('PicoraDispatcher::getUrl second argument must be an array or object.'); } $arguments = array_merge(self::getCurrentController()->params, get_object_vars(self::getCurrentController()), (array) $arguments); if (is_string($class_and_method)) { $class_and_method = array(self::$status['current_controller'] . 'Controller', $class_and_method); } if (substr($class_and_method[0], -10) != 'Controller') { $class_and_method[0] .= 'Controller'; } $route_string = PicoraSupport::formatPropertyString(self::getRouteByClassAndMethod($class_and_method[0], $class_and_method[1]), $arguments); if ($route_string && !preg_match('/\\:[^\\/]/', $route_string)) { return ($include_base_url ? substr(self::$status['base_url'], 0, -1) : '') . $route_string . (is_string($include_base_url) || is_array($include_base_url) ? is_string($include_base_url) ? $include_base_url : http_build_query($include_base_url, null, '&') : ''); } throw new Exception('Could not resolve URL'); }
public function __call($method, $arguments) { foreach (self::getRelationshipList($this->__class_name__) as $relationship) { $relationship_type = $relationship[0]; $related_class_name = $relationship[1]; $foreign_key = isset($relationship[2]) ? $relationship[2] : PicoraSupport::singularize($related_class_name) . '_id'; switch ($relationship_type) { case 'has_one': switch ($method) { case 'get' . $related_class_name: return self::find($related_class_name, $this->{$foreign_key}); case 'build' . $related_class_name: return self::build($related_class_name, isset($arguments[0]) ? $arguments[0] : array()); case 'create' . $related_class_name: $record = self::create($related_class_name, isset($arguments[0]) ? $arguments[0] : array()); if ($this->id) { $this->updateAttribute($foreign_key, $record->id); } return $record; } break; case 'has_many': switch ($method) { case 'delete' . $related_class_name: $record = self::find($related_class_name, $arguments[0] instanceof PicoraActiveRecord ? $arguments[0]->{self::primaryKeyNameFromClassName(get_class($arguments[0]))} : $arguments[0]); return !$record ? false : (bool) $record->delete(); case 'get' . $related_class_name . 'List': case 'get' . $related_class_name . 'Count': $params = isset($arguments[0]) ? $arguments[0] : array(); $params['where'] = (isset($params['where']) ? PicoraSupport::formatPropertyString($params['where'], $this) . ' AND ' : '') . $foreign_key . ' = ' . self::escape($this->{self::primaryKeyNameFromClassName($this->__class_name__)}); if ('get' . $related_class_name . 'Count' == $method) { return self::count($related_class_name, array('where' => $params['where'])); } if (isset($relationship['order']) && !isset($params['order'])) { $params['order'] = $relationship['order']; } $list = self::findAll($related_class_name, $params); if ('get' . $related_class_name . 'List' == $method) { return $list; } foreach ($list as $item) { if (!isset($arguments[0]) || isset($arguments[0]) && $arguments[0] == $item->{self::primaryKeyNameFromClassName(get_class($item))}) { $item->delete(); } } break; case 'create' . $related_class_name: return self::create($related_class_name, array_merge(isset($arguments[0]) ? $arguments[0] : array(), array($foreign_key => $this->{self::primaryKeyNameFromClassName($this->__class_name__)}))); case 'build' . $related_class_name: return self::build($related_class_name, array_merge(isset($arguments[0]) ? $arguments[0] : array(), array($foreign_key => $this->{self::primaryKeyNameFromClassName($this->__class_name__)}))); } break; case 'belongs_to': switch ($method) { case 'get' . $related_class_name: return self::find($related_class_name, $this->{$foreign_key}); case 'build' . $related_class_name == $method: case 'create' . $related_class_name == $method: $record = self::build($related_class_name, isset($arguments[0]) ? $arguments[0] : array()); if (isset($relationship['counter'])) { $record->{$relationship['counter']} = 1; } if ('build' . $related_class_name == $method) { return $record; } if ($record->save() && $this->{self::primaryKeyNameFromClassName($this->__class_name__)}) { $this->updateAttribute($foreign_key, $record->{self::primaryKeyNameFromClassName(get_class($record))}); } return $record; } break; case 'has_and_belongs_to_many': $source_class_name = $this->__class_name__; $source_table_name = self::tableNameFromClassName($this->__class_name__); $target_class_name = $related_class_name; $target_table_name = self::tableNameFromClassName($related_class_name); $link_class_name = $relationship[2]; $link_table_name = self::tableNameFromClassName($relationship[2]); $source_key = $relationship[3]; $target_key = $relationship[4]; $params = isset($arguments[0]) ? $arguments[0] : array(); switch ($method) { case 'set' . $related_class_name . 'List': $links = array(); self::executeQuery('DELETE FROM ' . $link_table_name . ' WHERE ' . $source_key . ' = ' . self::escape($this->id)); foreach (isset($arguments[0]) ? $arguments[0] : array() as $id) { $links[] = self::create($link_class_name, array($source_key => $this->{self::primaryKeyNameFromClassName($this->__class_name__)}, $target_key => $id instanceof PicoraActiveRecord ? $id->{self::primaryKeyNameFromClassName(get_class($id))} : $id)); } return $links; case 'add' . $related_class_name: return self::create($link_class_name, array($source_key => $this->{self::primaryKeyNameFromClassName($this->__class_name__)}, $target_key => $arguments[0] instanceof PicoraActiveRecord ? $arguments[0]->{self::primaryKeyNameFromClassName(get_class($arguments[0]))} : $arguments[0])); case 'remove' . $related_class_name: self::executeQuery('DELETE FROM ' . $link_table_name . ' WHERE ' . $source_key . ' = ' . self::escape($this->{self::primaryKeyNameFromClassName($this->__class_name__)}) . ' AND ' . $target_key . ' = ' . self::escape($arguments[0] instanceof PicoraActiveRecord ? $arguments[0]->{self::primaryKeyNameFromClassName(get_class($argument[0]))} : $arguments[0])); break; case 'has' . $related_class_name: return (bool) self::find($link_class_name, array('where' => array($source_key => $this->id, $target_key => $arguments[0] instanceof PicoraActiveRecord ? $arguments[0]->{self::primaryKeyNameFromClassName(get_class($arguments[0]))} : $arguments[0]))); case 'get' . $related_class_name . 'List': case 'get' . $related_class_name . 'Count': $params['tables'] = $link_table_name; $params['join'] = 'LEFT JOIN ' . $target_table_name . ' ON (' . $link_table_name . '.' . $target_key . ' = ' . $target_table_name . '.' . self::primaryKeyNameFromClassName($target_class_name) . ')'; $condition = $link_table_name . '.' . $source_key . ' = ' . $this->{self::primaryKeyNameFromClassName($this->__class_name__)}; $params['where'] = (isset($params['where']) ? $params['where'] . ' AND ' : '') . (isset($relationship['where']) ? $relationship['where'] . ' AND ' . $condition : $condition); if (isset($relationship['order']) && !isset($params['order'])) { $params['order'] = $relationship['order']; } if ('get' . $related_class_name . 'Count' == $method) { return self::count($target_class_name, array('where' => $params['where'], 'join' => $params['join'])); } $instance_list = self::findAll($target_class_name, $params); foreach ($instance_list as $instance) { unset($instance->{$target_key}, $instance->{$source_key}); } if ('get' . $related_class_name . 'List' == $method) { return $instance_list; } break; } break; } } foreach (PicoraEvent::getObserverList('PicoraActiveRecord.call') as $callback) { $response = call_user_func($callback, $this, $method, $arguments); if (!is_null($response)) { return $response; } } throw new Exception('Method "' . $method . '" of "' . $this->__class_name__ . '" does not exist.'); }