/** * Edits a label in the system. Fills the "label" (and possibly "icon") slot. * @param {array} $_REQUEST * @param {string} $_REQUEST.label The label * @param {string} [$_REQUEST.title] The title of the label * @param {string} [$_REQUEST.icon] Optional path to an icon * @param {string} [$_REQUEST.userId=Users::loggedInUser(true)->id] You can override the user id, if another plugin adds a hook that allows you to do this */ function Users_label_put($params = array()) { $req = array_merge($_REQUEST, $params); Q_Request::requireFields(array('label'), $req, true); $loggedInUserId = Users::loggedInUser(true)->id; $userId = Q::ifset($req, 'userId', $loggedInUserId); $l = $req['label']; $icon = Q::ifset($req, 'icon', null); $title = Q::ifset($req, 'title', null); Users::canManageLabels($loggedInUserId, $userId, $l, true); $label = new Users_Label(); $label->userId = $userId; $label->label = $l; if (!$label->retrieve()) { throw new Q_Exception_MissingRow(array('table' => 'Label', 'criteria' => json_encode($label->fields))); } if (isset($title)) { $label->title = $title; } if (is_array($icon)) { // Process any icon data $icon['path'] = 'uploads/Users'; $icon['subpath'] = "{$userId}/label/{$label}/icon"; $data = Q::event("Q/image/post", $icon); Q_Response::setSlot('icon', $data); $label->icon = Q_Request::baseUrl() . '/' . $data['']; } $label->save(); Q_Response::setSlot('label', $label->exportArray()); }
/** * Used to create a new stream * * @param {array} $_REQUEST * @param {String} [$_REQUEST.title] Required. The title of the interest. * @param {String} [$_REQUEST.publisherId] Optional. Defaults to the app name. * @return {void} */ function Streams_interest_delete() { $user = Users::loggedInUser(true); $title = Q::ifset($_REQUEST, 'title', null); if (!isset($title)) { throw new Q_Exception_RequiredField(array('field' => 'title')); } $app = Q_Config::expect('Q', 'app'); $publisherId = Q::ifset($_REQUEST, 'publisherId', $app); $name = 'Streams/interest/' . Q_Utils::normalize($title); $stream = Streams::fetchOne(null, $publisherId, $name); if (!$stream) { throw new Q_Exception_MissingRow(array('table' => 'stream', 'criteria' => Q::json_encode(compact('publisherId', 'name')))); } $miPublisherId = $user->id; $miName = 'Streams/user/interests'; $myInterests = Streams::fetchOne($user->id, $miPublisherId, $miName); if (!$myInterests) { throw new Q_Exception_MissingRow(array('table' => 'stream', 'criteria' => Q::json_encode(array('publisherId' => $miPublisherId, 'name' => $miName)))); } $stream->leave(); Streams::unrelate($user->id, $user->id, 'Streams/user/interests', 'Streams/interest', $publisherId, $name, array('adjustWeights' => true)); Q_Response::setSlot('publisherId', $publisherId); Q_Response::setSlot('streamName', $name); /** * Occurs when the logged-in user has successfully removed an interest via HTTP * @event Streams/interest/delete {after} * @param {string} publisherId The publisher of the interest stream * @param {string} title The title of the interest * @param {Users_User} user The logged-in user * @param {Streams_Stream} stream The interest stream * @param {Streams_Stream} myInterests The user's "Streams/user/interests" stream */ Q::event("Streams/interest/remove", compact('publisherId', 'title', 'subscribe', 'user', 'stream', 'myInterests'), 'after'); }
function Overlay_before_Q_responseExtras() { $app = Q_Config::expect('Q', 'app'); Q_Response::addStylesheet('plugins/Q/css/Q.css'); Q_Response::addStylesheet('css/Overlay.css', '@end'); Q_Response::addStylesheet('http://fonts.googleapis.com/css?family=Open+Sans:400italic,400,300,700'); if (Q_Config::get('Q', 'firebug', false)) { Q_Response::addScript("https://getfirebug.com/firebug-lite-debug.js"); } Q_Response::addScript('js/Overlay.js'); Q_Response::setMeta("title", "Customize My Pic!"); Q_Response::setMeta("description", "Make a statement on Facebook by customizing your profile picture, even from your smartphone."); Q_Response::setMeta("image", Q_Html::themedUrl('img/icon/icon.png')); if (Q_Request::isIE()) { header("X-UA-Compatible", "IE=edge"); } header('Vary: User-Agent'); // running an event for loading action-specific extras (if there are any) $uri = Q_Dispatcher::uri(); $module = $uri->module; $action = $uri->action; $event = "{$module}/{$action}/response/responseExtras"; if (Q::canHandle($event)) { Q::event($event); } }
/** * Adds a label to the system. Fills the "label" (and possibly "icon") slot. * @param {array} $_REQUEST * @param {string} $_REQUEST.title The title of the label * @param {string} [$_REQUEST.label] You can override the label to use * @param {string} [$_REQUEST.icon] Optional path to an icon * @param {string} [$_REQUEST.userId=Users::loggedInUser(true)->id] You can override the user id, if another plugin adds a hook that allows you to do this */ function Users_label_post($params = array()) { $req = array_merge($_REQUEST, $params); Q_Request::requireFields(array('title'), $req, true); $loggedInUserId = Users::loggedInUser(true)->id; $userId = Q::ifset($req, 'userId', $loggedInUserId); $icon = Q::ifset($req, 'icon', null); $title = $req['title']; $l = Q::ifset($req, 'label', 'Users/' . Q_Utils::normalize($title)); Users::canManageLabels($loggedInUserId, $userId, $l, true); $label = new Users_Label(); $label->userId = $userId; $label->label = $l; if ($label->retrieve()) { throw new Users_Exception_LabelExists(); } $label->title = $title; if (is_array($icon)) { // Process any icon that was posted $icon['path'] = 'uploads/Users'; $icon['subpath'] = "{$userId}/label/{$label}/icon"; $data = Q::event("Q/image/post", $icon); Q_Response::setSlot('icon', $data); $label->icon = Q_Request::baseUrl() . '/' . $data['']; } else { $label->icon = 'default'; } $label->save(); Q_Response::setSlot('label', $label->exportArray()); }
/** * Override Q/noModule handler. * just goes on to render our app's response, * which will echo a 404 view. */ function Q_noModule($params) { header("HTTP/1.0 404 Not Found"); Q_Dispatcher::uri()->module = Q_Config::expect('Q', 'app'); Q_Dispatcher::uri()->action = 'notFound'; Q::event('Q/response', $params); }
function Users_account_validate() { Q_Valid::nonce(true); $birthday_year = $birthday_month = $birthday_day = null; extract($_REQUEST); $field_names = array('firstName' => 'First name', 'lastName' => 'Last name', 'username' => 'Username', 'gender' => 'Your gender', 'desired_gender' => 'Gender preference', 'orientation' => 'Orientation', 'relationship_status' => 'Status', 'zipcode' => 'Zipcode'); foreach ($field_names as $name => $label) { if (isset($_POST[$name]) and !$_POST[$name]) { Q_Response::addError(new Q_Exception_RequiredField(array('field' => $label), $name)); } } if (isset($birthday_year)) { if (!checkdate($birthday_month, $birthday_day, $birthday_year)) { $field = 'Birthday'; $range = 'a valid date'; Q_Response::addError(new Q_Exception_WrongValue(compact('field', 'range'), 'birthday')); } } global $Q_installing; if (isset($username) and isset($Q_installing)) { try { Q::event('Users/validate/username', compact('username')); } catch (Exception $e) { Q_Response::addError($e); } } }
/** * Add contact with one or more labels * @method addContact * @static * @param {string} $userId * The id of the user whose contact will be added * @param {string} $contactUserId * The id of the user who is the contact * @param {string|array} $label * The label of the contact. This can be a string or an array of strings, in which case * multiple contact rows are saved. * @param {string} [$nickname=''] * Optional nickname to assign to the contact * @optional * @throws {Q_Exception_RequiredField} * if $label is missing * @return {array} Array of contacts that are saved */ static function addContact($userId, $label, $contactUserId, $nickname = '') { foreach (array('userId', 'label', 'contactUserId') as $field) { if (empty(${$field})) { throw new Q_Exception_RequiredField(compact('field')); } } $labels = is_array($label) ? $label : array($label); $contacts = array(); foreach ($labels as $l) { // Insert the contacts one by one $contact = new Users_Contact(); $contact->userId = $userId; $contact->contactUserId = $contactUserId; $contact->label = $l; if ($nickname) { $contact->nickname = $nickname; } $contact->save(true); $contacts[] = $contact; } /** * @event Users/Contact/addContact {after} * @param {string} contactUserId * @param {string} label * @param {array} contacts */ Q::event('Users/Contact/addContact', compact('contactUserId', 'label', 'contacts'), 'after'); return $contacts; }
function Users_activate_response() { $content = Q::event('Users/activate/response/content'); Q_Response::setSlot('content', $content); Q_Response::setSlot('column0', $content); // for SmartApp }
function Q_post($params) { $uri = Q_Dispatcher::uri(); $module = $uri->module; $action = $uri->action; if (!Q::canHandle("{$module}/{$action}/post")) { throw new Q_Exception_MethodNotSupported(array('method' => 'POST')); } if (isset($_SERVER['CONTENT_LENGTH'])) { $contentLength = (int) $_SERVER['CONTENT_LENGTH']; foreach (array('upload_max_filesize', 'post_max_size') as $name) { $value = ini_get($name); switch (substr($value, -1)) { case 'K': $value *= 1024; break; case 'M': $value *= 1024 * 1024; break; case 'B': $value *= 1024 * 1024 * 1024; break; } if ($contentLength > $value) { throw new Q_Exception_ContentLength(array('contentLength' => $contentLength, 'exceeds' => $name)); } } } return Q::event("{$module}/{$action}/post", $params); }
function Streams_publisher_validate($params) { // Protect against CSRF attacks: Q_Valid::nonce(true); $type = Streams::requestedType(); if ($type && Q::canHandle("Streams/validate/{$type}")) { return Q::event("Streams/validate/{$type}", $params); } }
function Q_validate($params) { $uri = Q_Dispatcher::uri(); $module = $uri->module; $action = $uri->action; if (!Q::canHandle("{$module}/{$action}/validate")) { return null; } return Q::event("{$module}/{$action}/validate", $params); }
function Q_put($params) { $uri = Q_Dispatcher::uri(); $module = $uri->module; $action = $uri->action; if (!Q::canHandle("{$module}/{$action}/put")) { throw new Q_Exception_MethodNotSupported(array('method' => 'PUT')); } return Q::event("{$module}/{$action}/put", $params); }
function Q_delete($params) { $uri = Q_Dispatcher::uri(); $module = $uri->module; $action = $uri->action; if (!Q::canHandle("{$module}/{$action}/delete")) { throw new Q_Exception_MethodNotSupported(array('method' => 'DELETE')); } Q_Request::requireValidNonce(); return Q::event("{$module}/{$action}/delete", $params); }
function Streams_stream_validate($params) { // Protect against CSRF attacks: if (Q_Request::method() !== 'GET') { Q_Valid::nonce(true); } $type = Streams::requestedType(); if ($type && Q::canHandle("Streams/validate/{$type}")) { return Q::event("Streams/validate/{$type}", $params); } }
/** * Assigns 'id' * @method beforeSave * @param {array} $modifiedFields * @return {array} */ function beforeSave($updatedFields) { if (isset($updatedFields['userId'])) { $this->userId = $updatedFields['userId']; } if (!$this->retrieved) { if (!isset($updatedFields['id'])) { $this->id = $updatedFields['id'] = self::db()->uniqueId(self::table(), 'id', array('userId' => $this->userId)); } } Q::event('Assets/Charge/save', array('charge' => $this), 'before'); return parent::beforeSave($updatedFields); }
function beforeSave($modifiedFields) { $stream = null; $uri = Q_Uri::from($this->uri); if ($uri->module === 'Streams' and $uri->action === 'stream') { $publisherId = Streams::requestedPublisherId(false, $uri); $streamName = Streams::requestedName(false, 'original', $uri); $stream = Streams::fetchOne(null, $publisherId, $streamName); } Q::event('Websites/permalink', array('permalink' => $this, 'modifiedFields' => $modifiedFields, 'stream' => &$stream), 'before'); if ($stream and $stream instanceof Streams_Stream) { $stream->setAttribute("Websites/url", $this->url); $stream->changed(); } return parent::beforeSave($modifiedFields); }
function Q_response_content() { $app = Q_Config::expect('Q', 'app'); $url = Q_Request::url(); $module = Q_Dispatcher::uri()->module; if (empty($module)) { return Q::event("{$app}/notFound/response/content"); } $action = Q_Dispatcher::uri()->action; $event = "{$module}/{$action}/response/content"; if (!Q::canHandle($event)) { return Q::event("{$app}/notFound/response/content"); } // Go ahead and fire the event, returning the result. return Q::event($event); }
function Streams_froala_post($params = array()) { $params = array_merge($_REQUEST, $params); try { $p = $params; if (!$p['icon']) { $p['icon'] = array(); } $p['icon']['data'] = $_REQUEST['image']; $p['icon']['save'] = array('x' => 'x.png'); Q::event('Streams/stream/post', $p); Q_Response::output(json_encode(array('link' => Streams::$cache['stream']->iconUrl('x.png')))); } catch (Exception $e) { Q_Response::output(json_encode(array('error' => $e->getMessage()))); } }
function Q_response_content() { $app = Q_Config::expect('Q', 'app'); $url = Q_Request::url(); $module = Q_Dispatcher::uri()->module; if (empty($module)) { return Q::event("{$app}/notFound/response/content"); } $action = Q_Dispatcher::uri()->action; $event = "{$module}/{$action}/response/content"; if (!Q::canHandle($event)) { return Q::event("{$app}/notFound/response/content"); } Q_Response::setMeta('format-detection', 'telephone=no,date=no,address=no,email=no,url=no'); // Go ahead and fire the event, returning the result. return Q::event($event); }
/** * Saves a file, usually sent by the client * @method save * @static * @param {array} $params * @param {string} [$params.data] the file data * @param {string} [$params.path="uploads"] parent path under web dir (see subpath) * @param {string} [$params.subpath=""] subpath that should follow the path, to save the image under * @param {string} [$params.name] override the name of the file, after the subpath * @param {string} [$params.skipAccess=false] if true, skips the check for authorization to write files there * @param {boolean} [$params.audio] set this to true if the file is an audio file * @return {array} Returns array containing ($name => $tailUrl) pair */ static function save($params) { if (empty($params['data'])) { throw new Q_Exception(array('field' => 'file'), 'data'); } // check whether we can write to this path, and create dirs if needed $data = $params['data']; $audio = $params['audio']; $path = isset($params['path']) ? $params['path'] : 'uploads'; $subpath = isset($params['subpath']) ? $params['subpath'] : ''; $realPath = Q::realPath(APP_WEB_DIR . DS . $path); if ($realPath === false) { throw new Q_Exception_MissingFile(array('filename' => APP_WEB_DIR . DS . $path)); } $name = isset($params['name']) ? $params['name'] : 'file'; if (!preg_match('/^[\\w.-]+$/', $name)) { $info = pathinfo($name); $name = Q_Utils::normalize($info['filename']) . '.' . $info['extension']; } // TODO: recognize some extensions maybe $writePath = $realPath . ($subpath ? DS . $subpath : ''); $lastChar = substr($writePath, -1); if ($lastChar !== DS and $lastChar !== '/') { $writePath .= DS; } $skipAccess = !empty($params['skipAccess']); Q_Utils::canWriteToPath($writePath, $skipAccess ? null : true, true); file_put_contents($writePath . $name, $data); $size = filesize($writePath . $name); $tailUrl = $subpath ? "{$path}/{$subpath}/{$name}" : "{$path}/{$name}"; /** * @event Q/file/save {after} * @param {string} user the user * @param {string} path the path in the url * @param {string} subpath the subpath in the url * @param {string} name the actual name of the file * @param {string} writePath the actual folder where the path is written * @param {string} data the data written to the file * @param {string} tailUrl consists of $path/[$subpath/]$name * @param {integer} size the size of the file that was written * @param {boolean} skipAccess whether we are skipping access checks * @param {boolean} audio whether the file is audio */ Q::event('Q/file/save', compact('path', 'subpath', 'name', 'writePath', 'data', 'tailUrl', 'size', 'skipAccess', 'audio'), 'after'); return array($name => $tailUrl); }
/** * Excecute web request * @method execute * @static */ static function execute() { // Fixes for different platforms: if (isset($_SERVER['HTTP_X_REWRITE_URL'])) { // ISAPI 3.0 $_SERVER['REQUEST_URI'] = $_SERVER['HTTP_X_REWRITE_URL']; } // Get the base URL $base_url = Q_Request::baseUrl(); if (Q::$controller === 'Q_ActionController') { // we detected action.php in the URL, but // a misconfigured web server executed index.php instead return Q_ActionController::execute(); } // Set the controller that is being used if (!isset(Q::$controller)) { Q::$controller = 'Q_WebController'; } try { $slots = Q_Request::slotNames(false); $slots = $slots ? ' slots: (' . implode(',', $slots) . ') from' : ''; $method = Q_Request::method(); Q::log("{$method}{$slots} url: " . Q_Request::url(true), null, null, array('maxLength' => 10000)); Q_Dispatcher::dispatch(); $dispatchResult = Q_Dispatcher::result(); if (!isset($dispatchResult)) { $dispatchResult = 'Ran dispatcher'; } $uri = Q_Request::uri(); $module = $uri->module; $action = $uri->action; if ($module and $action) { $slotNames = Q_Request::slotNames(); $returned_slots = empty($slotNames) ? '' : implode(',', $slotNames); Q::log("~" . ceil(Q::milliseconds()) . 'ms+' . ceil(memory_get_peak_usage() / 1000) . 'kb.' . " {$dispatchResult} for {$module}/{$action}" . " ({$returned_slots})", null, null, array('maxLength' => 10000)); } else { Q::log("~" . ceil(Q::milliseconds()) . 'ms+' . ceil(memory_get_peak_usage() / 1000) . 'kb.' . " {$dispatchResult} No route for " . $_SERVER['REQUEST_URI'], null, null, array('maxLength' => 10000)); } } catch (Exception $exception) { /** * @event Q/exception * @param {Exception} exception */ Q::event('Q/exception', compact('exception')); } }
function Users_authorize_post() { if (empty($_REQUEST['authorize'])) { return null; } // If we are here, the logged-in user requested to authorize the client $terms_uri = Q_Config::get('Users', 'authorize', 'terms', 'uri', null); $terms_label = Q_Config::get('Users', 'authorize', 'terms', 'label', null); $terms_title = Q_Config::get('Users', 'authorize', 'terms', 'title', null); if ($terms_uri and $terms_title and $terms_label) { if (empty($_REQUEST['agree'])) { throw new Q_Exception("First you must agree to the {$terms_title}", 'agree'); } } $user = Users::loggedInUser(true); $client_id = $_REQUEST['client_id']; $redirect_url = $_REQUEST['redirect_uri']; $state = $_REQUEST['state']; // for now we ignore the scope requested and always authorize "user" $oa = new Users_OAuth(); $oa->client_id = $client_id; $oa->userId = $user->id; $oa->state = $state; if ($oa->retrieve()) { if ($oa->scope !== 'user' || $oa->redirect_uri !== $redirect_url) { throw new Q_Exception("Different parameters were requested with the same state string before", 'state'); } Users::$cache['oAuth'] = $oa; return; } $duration_name = Q_Config::expect('Users', 'authorize', 'duration'); $duration = Q_Config::expect('Q', 'session', 'durations', $duration_name); $access_token = Users::copyToNewSession($duration); $oa->scope = 'user'; // for now the scope of authorization is always "user" $oa->redirect_uri = $redirect_url; // just saving it $oa->access_token = $access_token; // the session token $oa->token_expires_seconds = $duration; // session actually expires after $duration seconds of inactivity $oa->save(); Q::event('Users/authorize/success', array('oAuth' => $oa, 'duration' => $duration), 'after'); Users::$cache['oAuth'] = $oa; }
function Users_user_response_batch($params = array()) { $req = array_merge($_REQUEST, $params); Q_Valid::requireFields(array('batch'), $req, true); $batch = $req['batch']; $batch = json_decode($batch, true); if (!isset($batch)) { throw new Q_Exception_WrongValue(array('field' => 'batch', 'range' => '{userIds: [userId1, userId2, ...]}')); } Q_Valid::requireFields(array('userIds'), $batch, true); $userIds = $batch['userIds']; $users = Q::event('Users/user/response/users', compact('userIds')); $result = array(); foreach ($userIds as $userId) { $result[] = array('slots' => array('user' => isset($users[$userId]) ? $users[$userId] : null)); } Q_Response::setSlot('batch', $result); }
/** * Votes for something * @param {string} forType the type of thing to vote for * @param {string} forId string uniquely identifying that thing among others of its type * @param {integer} value the value the user has voted for, such as a rating etc. */ function Users_vote_post() { $user = Users::loggedInUser(true); $required = array('forType', 'forId'); foreach ($required as $field) { if (empty($_REQUEST[$field])) { throw new Q_Exception_RequiredField(compact('field')); } } $value = Q_Config::get('Users', 'vote', $_REQUEST['forType'], 'value', null); if (isset($value)) { $_REQUEST['value'] = $value; } else { if (!isset($_REQUEST['value'])) { $_REQUEST['value'] = 1; } } if ($_REQUEST['forType'] === 'Users/hinted') { $hinted = Q::ifset($_SESSION, 'Users', 'hinted', array()); if (!in_array($_REQUEST['forId'], $hinted)) { $_SESSION['Users']['hinted'][] = $_REQUEST['forId']; } } $vote = new Users_Vote(); $vote->userId = $user->id; $vote->forType = $_REQUEST['forType']; $vote->forId = $_REQUEST['forId']; $vote->value = $_REQUEST['value']; $retrieved = $vote->retrieve(); /** * @event Users/vote {before} * @return {string} */ if (false === Q::event('Users/vote', compact('user', 'vote'), 'before')) { return; } if (!$retrieved) { $vote->save(); } $vote = $vote->exportArray(); $vote['retrieved'] = $retrieved; Users::$cache['vote'] = $vote; }
function Users_contact_response_batch($params = array()) { $req = array_merge($_REQUEST, $params); Q_Valid::requireFields(array('batch'), $req, true); $batch = $req['batch']; $batch = json_decode($batch, true); if (!isset($batch)) { throw new Q_Exception_WrongValue(array('field' => 'batch', 'range' => '{userIds: [...], labels: [...], contactUserIds: [...]}')); } Q_Valid::requireFields(array('userIds', 'labels', 'contactUserIds'), $batch, true); $userIds = $batch['userIds']; $labels = $batch['labels']; $contactUserIds = $batch['contactUserIds']; $contacts = Q::event('Users/contact/response/contacts', compact('userIds', 'labels', 'contactUserIds')); $result = array(); foreach ($contacts as $contact) { $result[] = array('slots' => array('contact' => $contact)); } Q_Response::setSlot('batch', $result); }
function Streams_player_tool($options) { extract($options); if (!isset($stream)) { throw new Q_Exception_MissingObject(array('name' => 'stream')); } if (!$stream->testReadLevel('content')) { $streamName_html = Q_Html::text($stream->name); return "<a href='#{$streamName_html}'>hidden</a>"; } $parts = explode('/', $stream->type); switch ($parts[0]) { case 'Streams/text/small': case 'Streams/text/medium': case 'Streams/text': return $stream->content; case 'Streams/date': // TODO: localize if (isset($parts[1]) and $parts[1] === 'birthday') { return date('M j', strtotime($stream->content)); } return date('M j, Y', strtotime($stream->content)); case 'Streams/number': if (isset($parts[1]) and $parts[1] === 'age') { if (!empty($streams['Streams/user/birthday']->content)) { return Db::ageFromDateTime($streams['Streams/user/birthday']->content); } return null; } return $strem->content; case 'Streams/category': // TODO: implement // TODO: implement case 'Streams/chat': // TODO: implement // TODO: implement default: return Q::event("Streams/player/{$stream->type}", $options); // return $stream->content; } }
function Streams_0_8_7_Streams_mysql() { $app = Q_Config::expect('Q', 'app'); $user = Users_User::fetch($app, true); $simulated = array('row' => $user, 'inserted' => true, 'modifiedFields' => $user->fields); Q::event('Db/Row/Users_User/saveExecute', $simulated, 'after'); $stream = array('publisherId' => '', 'name' => "Streams/images/", 'type' => 'Streams/template', 'title' => 'Image Gallery', 'icon' => 'default', 'content' => '', 'attributes' => null, 'readLevel' => Streams::$READ_LEVEL['messages'], 'writeLevel' => Streams::$WRITE_LEVEL['close'], 'adminLevel' => Streams::$ADMIN_LEVEL['invite']); $access = array('publisherId' => '', 'streamName' => "Streams/images/", 'ofUserId' => '', 'grantedByUserId' => null, 'ofContactLabel' => "{$app}/admins", 'readLevel' => Streams::$READ_LEVEL['messages'], 'writeLevel' => Streams::$WRITE_LEVEL['close'], 'adminLevel' => Streams::$ADMIN_LEVEL['invite']); Streams_Stream::insert($stream)->execute(); Streams_Access::insert($access)->execute(); $stream['name'] = $access['streamName'] = 'Streams/image/'; $stream['icon'] = 'Streams/image'; $stream['title'] = 'Untitled Image'; Streams_Stream::insert($stream)->execute(); Streams_Access::insert($access)->execute(); $stream['name'] = $access['streamName'] = 'Streams/file/'; $stream['icon'] = 'files/_blank'; $stream['title'] = 'Untitled File'; Streams_Stream::insert($stream)->execute(); Streams_Access::insert($access)->execute(); }
/** * Saves a file, usually sent by the client * @method save * @static * @param {array} $params * @param {string} [$params.data] the file data * @param {string} [$params.path="uploads"] parent path under web dir (see subpath) * @param {string} [$params.subpath=""] subpath that should follow the path, to save the image under * @param {string} [$params.name] override the name of the file, after the subpath * @param {string} [$params.skipAccess=false] if true, skips the check for authorization to write files there * @return {array} Returns array containing ($name => $tailUrl) pair */ static function save($params) { if (empty($params['data'])) { throw new Q_Exception(array('field' => 'file'), 'data'); } // check whether we can write to this path, and create dirs if needed $data = $params['data']; $path = isset($params['path']) ? $params['path'] : 'uploads'; $subpath = isset($params['subpath']) ? $params['subpath'] : ''; $realPath = Q::realPath(APP_WEB_DIR . DS . $path); if ($realPath === false) { throw new Q_Exception_MissingFile(array('filename' => APP_WEB_DIR . DS . $path)); } $name = isset($params['name']) ? $params['name'] : 'file'; if (!preg_match('/^[\\w.-]+$/', $name)) { $info = pathinfo($name); $name = Q_Utils::normalize($info['filename']) . '.' . $info['extension']; } // TODO: recognize some extensions maybe $writePath = $realPath . ($subpath ? DS . $subpath : ''); $lastChar = substr($writePath, -1); if ($lastChar !== DS and $lastChar !== '/') { $writePath .= DS; } $throwIfNotWritable = empty($params['skipAccess']) ? true : null; Q_Utils::canWriteToPath($writePath, $throwIfNotWritable, true); file_put_contents($writePath . DS . $name, $data); $tailUrl = $subpath ? "{$path}/{$subpath}/{$name}" : "{$path}/{$name}"; /** * @event Q/file/save {after} * @param {string} user * @param {string} path * @param {string} subpath * @param {string} name * @param {string} writePath * @param {string} data */ Q::event('Q/file/save', compact('path', 'subpath', 'name', 'writePath', 'data', 'tailUrl'), 'after'); return array($name => $tailUrl); }
function Trump_before_Q_responseExtras() { $app = Q_Config::expect('Q', 'app'); Q_Response::addStylesheet('plugins/Q/css/Q.css'); Q_Response::addStylesheet('css/html.css', '@end'); if (Q_Config::get('Q', 'firebug', false)) { Q_Response::addScript("https://getfirebug.com/firebug-lite-debug.js"); } Q_Response::addScript('js/Trump.js'); if (Q_Request::isIE()) { header("X-UA-Compatible: IE=edge"); } header('Vary: User-Agent'); // running an event for loading action-specific extras (if there are any) $uri = Q_Dispatcher::uri(); $module = $uri->module; $action = $uri->action; $event = "{$module}/{$action}/response/responseExtras"; if (Q::canHandle($event)) { Q::event($event); } }
function Streams_after_Q_objects() { $user = Users::loggedInUser(); if (!$user) { return; } $invite = Streams::$followedInvite; if (!$invite) { return; } $displayName = $user->displayName(); $showDialog = !$displayName; $p = compact('user', 'invite', 'displayName'); Q::event('Streams/inviteDialog', $p, 'before', false, $showDialog); if (!$showDialog) { return; } $stream = new Streams_Stream(); $stream->publisherId = $invite->publisherId; $stream->name = $invite->streamName; if (!$stream->retrieve()) { throw new Q_Exception_MissingRow(array('table' => 'stream', 'criteria' => 'with that name'), 'streamName'); } // Prepare the complete invite dialog $invitingUser = Users_User::fetch($invite->invitingUserId); list($relations, $related) = Streams::related($user->id, $stream->publisherId, $stream->name, false); $templateName = Streams_Stream::getConfigField($stream->type, array('invite', 'dialog', 'templateName'), 'Streams/invite/complete'); $params = array('displayName' => $displayName, 'action' => 'Streams/basic', 'icon' => $user->iconUrl(), 'token' => $invite->token, 'user' => array('icon' => $invitingUser->iconUrl(), 'displayName' => $invitingUser->displayName(array('fullAccess' => true))), 'templateName' => $templateName, 'stream' => $stream->exportArray(), 'relations' => Db::exportArray($relations), 'related' => Db::exportArray($related)); $config = Streams_Stream::getConfigField($stream->type, 'invite', array()); $defaults = Q::ifset($config, 'dialog', array()); $tree = new Q_Tree($defaults); if ($tree->merge($params)) { $dialogData = $tree->getAll(); if ($dialogData) { Q_Response::setScriptData('Q.plugins.Streams.invite.dialog', $dialogData); Q_Response::addTemplate($templateName); } } }