コード例 #1
0
ファイル: Contact.php プロジェクト: dmitriz/Platform
 /**
  * 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|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} $contactUserId
  *  The id of the user who is the contact
  * @param {string} [$nickname='']
  *  Optional nickname to assign to the contact
  * @param {string} [$asUserId=null] The user to do this operation as.
  *   Defaults to the logged-in user. Pass false to skip access checks.
  * @throws {Q_Exception_RequiredField}
  *	if $label is missing
  * @return {array} Array of contacts that are saved
  */
 static function addContact($userId, $label, $contactUserId, $nickname = '', $asUserId = null)
 {
     foreach (array('userId', 'label', 'contactUserId') as $field) {
         if (empty(${$field})) {
             throw new Q_Exception_RequiredField($field);
         }
     }
     Users::canManageContacts($asUserId, $userId, $label, true);
     Users_User::fetch($userId, true);
     Users_User::fetch($contactUserId, true);
     $labels = is_array($label) ? $label : array($label);
     // Insert the contacts one by one
     $contacts = array();
     foreach ($labels as $l) {
         $contact = new Users_Contact();
         $contact->userId = $userId;
         $contact->label = $l;
         $contact->contactUserId = $contactUserId;
         if (isset($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;
 }
コード例 #2
0
ファイル: tool.php プロジェクト: dmitriz/Platform
/**
 * This tool renders a user avatar
 *
 * @param {array} $options An associative array of parameters, containing:
 * @param {boolean} [$options.userId]
 *   "userId" => The user's id. Defaults to id of the logged-in user, if any.
 * @param {boolean} [$options.icon]
 *   "icon" => Optional. Render icon before the username.
 * @param {boolean} [$options.iconAttributes]
 *   "iconAttributes" => Optional. Array of attributes to render for the icon.
 * @param {boolean} [$options.editable]
 *   "editable" => Optional. Whether to provide an interface for editing the user's info. Can be array containing "icon", "name".
 * @param {array} [$options.inplaces] Additional fields to pass to the child Streams/inplace tools, if any
 * @param {boolean} [$options.renderOnClient]
 *    If true, only the html container is rendered, so the client will do the rest.
 */
function Users_avatar_tool($options)
{
    $defaults = array('icon' => false, 'editable' => false);
    $options = array_merge($defaults, $options);
    if (empty($options['userId'])) {
        $user = Users::loggedInUser();
        $options['userId'] = $user->id;
    } else {
        $user = Users_User::fetch($options['userId']);
    }
    Q_Response::addStylesheet('plugins/Q/css/Q.css');
    Q_Response::setToolOptions($options);
    if (!empty($options['renderOnClient'])) {
        return '';
    }
    if (!$user) {
        return '';
    }
    $user->addPreloaded();
    $p = $options;
    $p['userId'] = $user->id;
    Q_Response::setToolOptions($p);
    $result = '';
    $icon = $options['icon'];
    if ($icon) {
        if ($icon === true) {
            $icon = Q_Config::get('Users', 'icon', 'defaultSize', 40);
        }
        $attributes = isset($options['iconAttributes']) ? $options['iconAttributes'] : array();
        $attributes['class'] = isset($attributes['class']) ? $attributes['class'] . ' Users_avatar_icon' : 'Users_avatar_icon';
        $result .= Q_Html::img($user->iconUrl($icon), 'user icon', $attributes);
    }
    $result .= '<span class="Users_avatar_name">' . $user->username . '</span>';
    return $result;
}
コード例 #3
0
ファイル: post.php プロジェクト: AndreyTepaykin/Platform
function Users_identifier_post()
{
    $userId = Q::ifset($_REQUEST, 'userId', null);
    if (isset($userId)) {
        $user = Users_User::fetch($userId, true);
        if ($user->emailAddress or $user->mobileNumber) {
            throw new Q_Exception("This user is already able to log in and set their own email and mobile number.");
        }
    } else {
        $user = Users::loggedInUser(true);
    }
    $app = Q_Config::expect('Q', 'app');
    $fields = array();
    $identifier = Users::requestedIdentifier($type);
    if (!$type) {
        throw new Q_Exception("a valid email address or mobile number is required", array('identifier', 'mobileNumber', 'emailAddress'));
    }
    if ($type === 'email') {
        $subject = Q_Config::get('Users', 'transactional', 'identifier', 'subject', "Welcome! Verify your email address.");
        $view = Q_Config::get('Users', 'transactional', 'identifier', 'body', 'Users/email/addEmail.php');
        $user->addEmail($identifier, $subject, $view, array(), array('html' => true));
    } else {
        if ($type === 'mobile') {
            $view = Q_Config::get('Users', 'transactional', 'identifier', 'sms', 'Users/sms/addMobile.php');
            $user->addMobile($identifier, $view);
        }
    }
}
コード例 #4
0
function Streams_0_8_8_Streams_mysql()
{
    $communityId = Users::communityId();
    $user = Users_User::fetch($communityId, true);
    Streams::create($communityId, $communityId, 'Streams/resource', array('name' => 'Streams/invitations', 'readLevel' => 0, 'writeLevel' => 0, 'adminLevel' => 0));
    Streams_Access::insert(array('publisherId' => $communityId, 'streamName' => "Streams/invitations", 'ofUserId' => '', 'grantedByUserId' => null, 'ofContactLabel' => "{$app}/admins", 'readLevel' => Streams::$READ_LEVEL['messages'], 'writeLevel' => Streams::$WRITE_LEVEL['close'], 'adminLevel' => Streams::$ADMIN_LEVEL['invite']))->execute();
}
コード例 #5
0
ファイル: Q_objects.php プロジェクト: dmitriz/Platform
function Streams_after_Q_objects()
{
    $user = Users::loggedInUser();
    if (!$user) {
        return;
    }
    $invite = Streams::$followedInvite;
    if (!$invite) {
        return;
    }
    $displayName = $user->displayName();
    if ($displayName) {
        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);
    $params = array('displayName' => null, 'action' => 'Streams/basic', 'icon' => $user->iconUrl(), 'token' => $invite->token, 'user' => array('icon' => $invitingUser->iconUrl(), 'displayName' => $invitingUser->displayName(array('fullAccess' => true))), '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('Streams/invite/complete');
        }
    }
}
コード例 #6
0
function Streams_0_8_4_Streams_mysql()
{
    $app = Q_Config::expect('Q', 'app');
    $communityId = Users::communityId();
    $user = Users_User::fetch($communityId);
    // avatar for the App user
    $avatar = new Streams_Avatar();
    $avatar->toUserId = $communityId;
    $avatar->publisherId = $communityId;
    $avatar->username = $user->username;
    $avatar->firstName = Users::communityName();
    $avatar->lastName = Users::communitySuffix();
    $avatar->icon = $user->icon;
    $avatar->save();
    $avatar2 = new Streams_Avatar();
    $avatar2->copyFrom($avatar, null, false, true);
    $avatar->toUserId = '';
    $avatar->save();
    // access stream for managing app roles
    $stream = new Streams_Stream();
    $stream->publisherId = Users::communityId();
    $stream->name = 'Streams/contacts';
    $stream->type = 'Streams/resource';
    $stream->title = "Contacts";
    $stream->setAttribute('prefixes', array("Users/", "{$app}/"));
    $stream->save();
    // access stream for managing app roles
    $stream = new Streams_Stream();
    $stream->publisherId = $app;
    $stream->name = 'Streams/labels';
    $stream->type = 'Streams/resource';
    $stream->title = "Labels";
    $stream->setAttribute('prefixes', array("Users/", "{$app}/"));
    $stream->save();
    // access for managing app contacts
    $access = new Streams_Access();
    $access->publisherId = $communityId;
    $access->streamName = 'Streams/contacts';
    $access->ofUserId = '';
    $access->ofContactLabel = "{$app}/admins";
    $access->readLevel = Streams::$READ_LEVEL['messages'];
    $access->writeLevel = Streams::$WRITE_LEVEL['edit'];
    $access->adminLevel = Streams::$ADMIN_LEVEL['manage'];
    $access->save();
    // access for managing app roles
    $access = new Streams_Access();
    $access->publisherId = $communityId;
    $access->streamName = 'Streams/labels';
    $access->ofUserId = '';
    $access->ofContactLabel = "{$app}/admins";
    $access->readLevel = Streams::$READ_LEVEL['messages'];
    $access->writeLevel = Streams::$WRITE_LEVEL['edit'];
    $access->adminLevel = Streams::$ADMIN_LEVEL['manage'];
    $access->save();
}
コード例 #7
0
ファイル: response.php プロジェクト: AndreyTepaykin/Platform
/**
 * We are going to implement a subset of the OAuth 1.0a functionality for now,
 * and later we can expand it to match the full OAuth specification.
 */
function Users_authorize_response()
{
    if (Q_Response::getErrors()) {
        Q_Dispatcher::showErrors();
    }
    $response_type = 'token';
    $token_type = 'bearer';
    $client_id = $_REQUEST['client_id'];
    $state = $_REQUEST['state'];
    $skip = Q::ifset($_REQUEST, 'skip', false);
    $scope = Users_OAuth::requestedScope(true, $scopes);
    $client = Users_User::fetch($client_id, true);
    if (!$client) {
        throw new Q_Exception_MissingRow(array('table' => 'client user', 'criteria' => "id = '{$client_id}'"), 'client_id');
    }
    if (empty($client->url)) {
        throw new Q_Exception("Client app needs to register url", 'client_id');
    }
    $redirect_uri = Q::ifset($_REQUEST, 'redirect_uri', $client->url);
    $user = Users::loggedInUser();
    $oa = null;
    if (isset(Users::$cache['oAuth'])) {
        $oa = Users::$cache['oAuth'];
    } else {
        if ($user) {
            $oa = new Users_OAuth();
            $oa->client_id = $client_id;
            $oa->userId = $user->id;
            $oa->state = $state;
            $oa = $oa->retrieve();
        }
    }
    $remaining = $scope;
    if ($oa and $oa->wasRetrieved()) {
        // User is logged in and already has a token for this client_id and state
        $paths = Q_Config::get('Users', 'authorize', 'clients', Q::app(), 'redirectPaths', false);
        $path = substr($redirect_uri, strlen($client->url) + 1);
        $p = array('response_type' => $response_type, 'token_type' => $token_type, 'access_token' => $oa->access_token, 'expires_in' => $oa->token_expires_seconds, 'scope' => implode(' ', $scope), 'state' => $oa->state);
        $p = Q_Utils::sign($p, 'Q.Users.oAuth');
        // the redirect uri could be a native app url scheme
        $s = strpos($redirect_uri, '#') === false ? '#' : '&';
        $redirect_uri = Q_Uri::from($redirect_uri . $s . http_build_query($p), false)->toUrl();
        if (!Q::startsWith($redirect_uri, $client->url) or is_array($paths) and !in_array($path, $paths)) {
            throw new Users_Exception_Redirect(array('uri' => $redirect_uri));
        }
        Q_Response::redirect($redirect_uri);
        return false;
    }
    $terms_label = Users::termsLabel('authorize');
    Q_Response::setScriptData('Q.Users.authorize', compact('client_id', 'redirect_uri', 'scope', 'scopes', 'remaining', 'state', 'response_type', 'skip'));
    $content = Q::view('Users/content/authorize.php', compact('client', 'user', 'redirect_uri', 'scope', 'scopes', 'remaining', 'state', 'terms_label', 'response_type', 'skip'));
    Q_Response::setSlot('content', $content);
    Q_Response::setSlot('column0', $content);
    return true;
}
コード例 #8
0
ファイル: response.php プロジェクト: dmitriz/Platform
function Streams_invited_response()
{
    if (!($token = Q_Dispatcher::uri()->token)) {
        throw new Q_Exception_RequiredField(array('field' => 'token'), 'token');
    }
    if (!($invite = Streams_Invite::fromToken($token))) {
        throw new Q_Exception_MissingRow(array('table' => 'invite', 'criteria' => "token: {$token}"), 'token');
    }
    Users_User::fetch($invite->userId, true)->setVerified();
    Q_Response::redirect($invite->appUrl . "?" . http_build_query(array('Q.Streams.token' => $token), null, '&'));
}
コード例 #9
0
ファイル: interests.php プロジェクト: AndreyTepaykin/Platform
/**
 * Get a summary of streams related to the specified user's
 * "Streams/user/interests" stream
 *
 * @param {array} $_REQUEST 
 *   @param {string} [$_REQUEST.userId=loggedInUserId] userId
 * @return {void}
 */
function Streams_interest_response_interests()
{
    $user = Users::loggedInUser();
    $userId = Q::ifset($_REQUEST, 'userId', null);
    if ($user and $userId and $userId != $user->id and Q_Config::get('Streams', 'interests', 'allowClientQueries', false)) {
        throw new Q_Exception("Client queries are restricted, as per Streams/interests/allowClientQueries");
    }
    if ($userId) {
        $user = Users_User::fetch($userId);
    }
    if (!$user) {
        throw new Users_Exception_NotLoggedIn();
    }
    return Streams_Category::getRelatedTo($user->id, 'Streams/user/interests', 'Streams/interests');
}
コード例 #10
0
ファイル: tool.php プロジェクト: dmitriz/Platform
/**
 * This tool renders ways to get in touch
 *
 * @param array [$options] An associative array of options, containing:
 *   @param {string|Users_User} [$options.user] Required. The user object or id of the user exposing their primary identifiers for getting in touch.
 *   @param {boolean|string} [$options.email] Pass true here to use the primary verified email address, if any. Or pass the string label for this button.
 *   @param {string} [$options.emailSubject] Fill this if you want the email subject to be automatically filled in
 *   @param {string} [$options.emailBody] Fill this if you want the email body to be automatically filled in
 *   @param {boolean|string} [$options.sms] Pass true here to allow texting the primary verified mobile number, if any. Or pass the string label for this button.
 *   @param {boolean|string} [$options.call] Pass true here to allow calling the primary verified mobile number, if any. Or pass the string label for this button.
 *   @param {string} [$options.tag] The type of tag to use, defaults to "button"
 *   @param {string} [$options.class] Any classes to add to the tags
 *   @param {string} [$options.between] Any HTML to put between the elements
 */
function Users_getintouch_tool($options)
{
    $tag = 'button';
    $class = null;
    $between = '';
    $user = null;
    $emailSubject = '';
    $emailBody = '';
    extract($options, EXTR_IF_EXISTS);
    if (!$user) {
        throw new Q_Exception_RequiredField(array('field' => 'user'));
    }
    if (is_string($user)) {
        $userId = $user;
        $user = Users_User::fetch($userId);
        if (!$user) {
            throw new Q_Exception_MissingRow(array('table' => 'user', 'criteria' => "id={$userId}"));
        }
    }
    $ways = array();
    $email = $sms = $call = false;
    if (!empty($options['email']) and $user->emailAddress) {
        $email = is_string($options['email']) ? $options['email'] : "Email me";
        $email = Q_Html::img("plugins/Users/img/email.png") . $email;
        $ways['email'] = Q_Html::tag($tag, array('id' => 'email', 'class' => $class), $email);
        Q_Response::setToolOptions(array('emailAddress' => Q_Utils::obfuscate($user->emailAddress), 'emailSubject' => Q_Utils::obfuscate($emailSubject), 'emailBody' => Q_Utils::obfuscate($emailBody)));
    }
    if (Q_Request::isMobile()) {
        $obfuscated_mobileNumber = Q_Utils::obfuscate($user->mobileNumber);
        if (!empty($options['sms']) and $user->mobileNumber) {
            $sms = is_string($options['sms']) ? $options['sms'] : "Text me";
            $sms = Q_Html::img("plugins/Users/img/sms.png") . $sms;
            $ways['sms'] = Q_Html::tag($tag, array('id' => 'sms', 'class' => $class), $sms);
            Q_Response::setToolOptions(array('mobileNumber' => $obfuscated_mobileNumber));
        }
        if (!empty($options['call']) and $user->mobileNumber) {
            $call = is_string($options['call']) ? $options['call'] : "Call me";
            $call = Q_Html::img("plugins/Users/img/call.png") . $call;
            $ways['call'] = Q_Html::tag($tag, array('id' => 'call', 'class' => $class), $call);
            Q_Response::setToolOptions(array('mobileNumber' => $obfuscated_mobileNumber));
        }
    }
    return implode($between, $ways);
}
コード例 #11
0
ファイル: response.php プロジェクト: dmitriz/Platform
/**
 * We are going to implement a subset of the OAuth 1.0a functionality for now,
 * and later we can expand it to match the full OAuth specification.
 */
function Users_authorize_response()
{
    if (Q_Response::getErrors()) {
        Q_Dispatcher::showErrors();
    }
    $client_id = $_REQUEST['client_id'];
    $redirect_url = $_REQUEST['redirect_uri'];
    $state = $_REQUEST['state'];
    $client = Users_User::fetch($client_id);
    if (!$client) {
        throw new Q_Exception_MissingRow(array('table' => 'user', 'criteria' => "id = '{$client_id}'"), 'client_id');
    }
    if (empty($client->url)) {
        throw new Q_Exception("Client app needs to register url", 'client_id');
    }
    if (substr($redirect_url, 0, strlen($client->url)) !== $client->url) {
        throw new Q_Exception_WrongValue(array('field' => 'redirect_uri', 'range' => "a url prefixed by client user's url"));
    }
    $user = Users::loggedInUser();
    $oa = null;
    if (isset(Users::$cache['oAuth'])) {
        $oa = Users::$cache['oAuth'];
    } else {
        if ($user) {
            $oa = new Users_OAuth();
            $oa->client_id = $client_id;
            $oa->userId = $user->id;
            $oa->state = $state;
            $oa->retrieve();
        }
    }
    if ($oa and $oa->wasRetrieved()) {
        // User is logged in and already has a token for this client_id and state
        $separator = strpos($redirect_url, '?') === false ? '?' : '&';
        $url = $redirect_url . $separator . http_build_query(array('access_token' => $oa->access_token, 'token_type' => 'bearer', 'expires_in' => $oa->token_expires_seconds, 'scope' => 'user', 'state' => $oa->state));
        Q_Response::redirect(Q_Uri::from($url, false));
        return false;
    }
    $terms_label = Users::termsLabel('authorize');
    $content = Q::view('Users/content/authorize.php', compact('client', 'redirect_url', 'user', 'state', 'terms_label'));
    Q_Response::setSlot('content', $content);
    Q_Response::setSlot('column0', $content);
    return true;
}
コード例 #12
0
ファイル: Credits.php プロジェクト: dmitriz/Platform
 /**
  * Get the logged-in user's credits stream
  * @method userStream
  * @param {string} [$userId=null]
  *   The id of the user for which the stream is obtained. Defaults to logged-in user.
  * @param {string} [$asUserId=null]
  *   The id of the user who is trying to obtain it. Defaults to logged-in user.
  * @param {boolean} [$throwIfNotLoggedIn=false]
  *   Whether to throw a Users_Exception_NotLoggedIn if no user is logged in.
  * @return {Streams_Stream|null}
  * @throws {Users_Exception_NotLoggedIn} If user is not logged in and
  *   $throwIfNotLoggedIn is true
  */
 static function userStream($userId = null, $asUserId = null, $throwIfNotLoggedIn = false)
 {
     if (!isset($userId)) {
         $user = Users::loggedInUser($throwIfNotLoggedIn);
         if (!$user) {
             return null;
         }
     } else {
         $user = Users_User::fetch($userId, true);
     }
     $userId = $user->id;
     $streamName = 'Awards/user/credits';
     $stream = Streams::fetchOne($asUserId, $userId, $streamName);
     if (!$stream) {
         $amount = Q_Config::get('Awards', 'credits', 'amounts', 'Users/insertUser', self::DEFAULT_AMOUNT);
         $stream = Streams::create($userId, $userId, 'Awards/credits', array('name' => 'Awards/user/credits', 'title' => "Credits", 'icon' => 'plugins/Awards/img/credits.png', 'content' => '', 'attributes' => Q::json_encode(compact('amount'))));
     }
     return $stream;
 }
コード例 #13
0
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();
}
コード例 #14
0
ファイル: Access.php プロジェクト: AndreyTepaykin/Platform
 /**
  * Check if user "owns" a stream template for a publisher
  * @method isOwner
  * @static
  * @param {string} $publisherId
  * @param {string} $type
  * @param {string|Users_User} [$user=null]
  * @return {boolean}
  */
 static function isOwner($publisherId, $type, $user = null)
 {
     if (!isset($user)) {
         $user = Users::loggedInUser();
     } else {
         if (is_string($user)) {
             $user = Users_User::fetch($user);
         }
     }
     if (!isset($user)) {
         return false;
     }
     // check if user is owner of stream template
     $stream = new Streams_Stream();
     $stream->publisherId = $publisherId;
     $stream->name = $type . '/';
     if (!$stream->retrieve()) {
         return false;
     }
     $stream->calculateAccess($user->id);
     return $stream->testAdminLevel('own');
 }
コード例 #15
0
ファイル: post.php プロジェクト: atirjavid/Platform
/**
 * Adds contacts to the system. Fills the "contacts" slot.
 * @param {array} $_REQUEST
 * @param {string} $_REQUEST.label The label of the contact
 * @param {string} $_REQUEST.contactUserId The contactUserId of the contact
 * @param {string} [$_REQUEST.nickname] The nickname of the contact
 * @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_contact_post($params = array())
{
    $req = array_merge($_REQUEST, $params);
    Q_Request::requireFields(array('label', 'contactUserId'), $req, true);
    $loggedInUserId = Users::loggedInUser(true)->id;
    $userId = Q::ifset($req, 'userId', $loggedInUserId);
    $contactUserId = $req['contactUserId'];
    $nickname = Q::ifset($req, 'nickname', null);
    $l = $req['label'];
    if ($userId !== $loggedInUserId) {
        Users_User::fetch($userId, true);
    }
    Users_User::fetch($contactUserId, true);
    Users::canManageContacts($loggedInUserId, $userId, $l, true);
    $label = new Users_Label();
    $label->userId = $userId;
    $label->label = $l;
    if (!$label->retrieve()) {
        throw new Q_Exception_MissingRow(array('table' => 'Users_Label', 'criteria' => json_encode($label->fields)));
    }
    $contacts = Users_Contact::addContact($userId, $l, $contactUserId, $nickname);
    Q_Response::setSlot('contacts', Db::exportArray($contacts));
}
コード例 #16
0
ファイル: Streams.php プロジェクト: atirjavid/Platform
 /**
  * Invites a user (or a future user) to a stream .
  * @method invite
  * @static
  * @param {string} $publisherId The id of the stream publisher
  * @param {string} $streamName The name of the stream the user will be invited to
  * @param {array} $who Array that can contain the following keys:
  * @param {string|array} [$who.userId] user id or an array of user ids
  * @param {string|array} [$who.fb_uid]  fb user id or array of fb user ids
  * @param {string|array} [$who.label]  label or an array of labels, or tab-delimited string
  * @param {string|array} [$who.identifier]  identifier or an array of identifiers, or tab-delimited string
  * @param {integer} [$who.newFutureUsers] the number of new Users_User objects to create via Users::futureUser in order to invite them to this stream. This typically is used in conjunction with passing the "html" option to this function.
  * @param {array} [$options=array()]
  *  @param {string|array} [$options.label] label or an array of labels for adding publisher's contacts
  *  @param {string|array} [$options.myLabel] label or an array of labels for adding logged-in user's contacts
  *  @param {integer} [$options.readLevel] => the read level to grant those who are invited
  *  @param {integer} [$options.writeLevel] => the write level to grant those who are invited
  *  @param {integer} [$options.adminLevel] => the admin level to grant those who are invited
  *	@param {string} [$options.displayName] => the display name to use to represent the inviting user
  *  @param {string} [$options.appUrl] => Can be used to override the URL to which the invited user will be redirected and receive "Q.Streams.token" in the querystring.
  *	@param {array} [$options.html] => an array of ($template, $batchName) such as ("MyApp/foo.handlebars", "foo") for generating html snippets which can then be viewed from and printed via the action Streams/invitations?batchName=$batchName
  * @param {array} [$options.asUserId=null] Invite as this user id
  * @see Users::addLink()
  * @return {array} returns array with keys "success", "invited", "statuses", "identifierTypes", "alreadyParticipating"
  */
 static function invite($publisherId, $streamName, $who, $options = array())
 {
     if (isset($options['asUserId'])) {
         $asUserId = $options['asUserId'];
         $asUser = Users_User::fetch($asUserId);
     } else {
         $asUser = Users::loggedInUser(true);
         $asUserId = $asUser->id;
     }
     // Fetch the stream as the logged-in user
     $stream = Streams::fetch($asUserId, $publisherId, $streamName);
     if (!$stream) {
         throw new Q_Exception_MissingRow(array('table' => 'stream', 'criteria' => 'with that name'), 'streamName');
     }
     $stream = reset($stream);
     // Do we have enough admin rights to invite others to this stream?
     if (!$stream->testAdminLevel('invite') || !$stream->testWriteLevel('join')) {
         throw new Users_Exception_NotAuthorized();
     }
     if (isset($options['html'])) {
         $html = $options['html'];
         if (!is_array($html) or count($html) < 2) {
             throw new Q_Exception_WrongType(array('field' => "options.html", 'type' => 'array of 2 strings'));
         }
         list($template, $batchName) = $html;
         // validate these paths
         $filename = APP_VIEWS_DIR . DS . $template;
         if (!Q::realPath($filename)) {
             throw new Q_Exception_MissingFile(compact('filename'));
         }
         $ext = $pathinfo = pathinfo($template, PATHINFO_EXTENSION);
         if ($ext !== 'handlebars') {
             throw new Q_Exception_WrongValue(array('field' => 'options.html[0]', 'range' => 'a filename with extension .handlebars'));
         }
         $path = Streams::invitationsPath($asUserId) . DS . $batchName;
         Q_Utils::canWriteToPath($path, true, true);
     }
     // get user ids if any to array, throw if user not found
     $raw_userIds = isset($who['userId']) ? Users_User::verifyUserIds($who['userId'], true) : array();
     // merge labels if any
     if (isset($who['label'])) {
         $label = $who['label'];
         if (is_string($label)) {
             $label = array_map('trim', explode("\t", $labels));
         }
         $raw_userIds = array_merge($raw_userIds, Users_User::labelsToIds($asUserId, $label));
     }
     // merge identifiers if any
     $identifierType = null;
     $statuses = null;
     if (isset($who['identifier'])) {
         $identifier = $who['identifier'];
         if (is_string($identifier)) {
             if (Q_Valid::email($who['identifier'])) {
                 $identifierType = 'email';
             } else {
                 if (Q_Valid::phone($who['identifier'])) {
                     $identifierType = 'mobile';
                 }
             }
             $identifier = array_map('trim', explode("\t", $identifier));
         }
         $statuses = array();
         $identifier_ids = Users_User::idsFromIdentifiers($identifier, $statuses);
         $raw_userIds = array_merge($raw_userIds, $identifier_ids);
     }
     // merge fb uids if any
     if (isset($who['fb_uid'])) {
         $fb_uids = $who['fb_uid'];
         if (is_string($fb_uids)) {
             $fb_uids = array_map('trim', explode("\t", $fb_uids));
         }
         $raw_userIds = array_merge($raw_userIds, Users_User::idsFromFacebook($fb_uids));
     }
     if (!empty($who['newFutureUsers'])) {
         $nfu = $who['newFutureUsers'];
         for ($i = 0; $i < $nfu; ++$i) {
             $raw_userIds[] = Users::futureUser('none', null)->id;
         }
     }
     // ensure that each userId is included only once
     // and remove already participating users
     $raw_userIds = array_unique($raw_userIds);
     $total = count($raw_userIds);
     $userIds = Streams_Participant::filter($raw_userIds, $stream);
     $to_invite = count($userIds);
     $appUrl = !empty($options['appUrl']) ? $options['appUrl'] : Q_Request::baseUrl() . '/' . Q_Config::get("Streams", "types", $stream->type, "invite", "url", "plugins/Streams/stream");
     // now check and define levels for invited user
     $readLevel = isset($options['readLevel']) ? $options['readLevel'] : null;
     if (isset($readLevel)) {
         if (!$stream->testReadLevel($readLevel)) {
             // We can't assign greater read level to other people than we have ourselves!
             throw new Users_Exception_NotAuthorized();
         }
     }
     $writeLevel = isset($options['writeLevel']) ? $options['writeLevel'] : null;
     if (isset($writeLevel)) {
         if (!$stream->testWriteLevel($writeLevel)) {
             // We can't assign greater write level to other people than we have ourselves!
             throw new Users_Exception_NotAuthorized();
         }
     }
     $adminLevel = isset($options['adminLevel']) ? $options['adminLevel'] : null;
     if (isset($adminLevel)) {
         if (!$stream->testAdminLevel($adminLevel + 1)) {
             // We can't assign an admin level greater, or equal, to our own!
             // A stream's publisher can assign owners. Owners can assign admins.
             // Admins can confer powers to invite others, to some people.
             // Those people can confer the privilege to publish a message re this stream.
             // But admins can't assign other admins, and even stream owners
             // can't assign other owners.
             throw new Users_Exception_NotAuthorized();
         }
     }
     // calculate expiry time
     $duration = Q_Config::get("Streams", "types", $stream->type, "invite", "duration", false);
     $expiry = $duration ? strtotime($duration) : null;
     // let node handle the rest, and get the result
     $params = array("Q/method" => "Streams/Stream/invite", "invitingUserId" => $asUserId, "username" => $asUser->username, "userIds" => Q::json_encode($userIds), "stream" => Q::json_encode($stream->toArray()), "appUrl" => $appUrl, "label" => Q::ifset($options, 'label', null), "myLabel" => Q::ifset($options, 'myLabel', null), "readLevel" => $readLevel, "writeLevel" => $writeLevel, "adminLevel" => $adminLevel, "displayName" => isset($options['displayName']) ? $options['displayName'] : Streams::displayName($asUser), "expiry" => $expiry);
     if ($template) {
         $params['template'] = $template;
         $params['batchName'] = $batchName;
     }
     $result = Q_Utils::queryInternal('Q/node', $params);
     return array('success' => $result, 'invited' => $userIds, 'statuses' => $statuses, 'identifierType' => $identifierType, 'alreadyParticipating' => $total - $to_invite);
 }
コード例 #17
0
ファイル: Q_objects.php プロジェクト: dmitriz/Platform
function Streams_before_Q_objects()
{
    $token = Q_Request::special('Streams.token', null);
    if ($token === null) {
        return;
    }
    $invite = Streams_Invite::fromToken($token);
    if (!$invite) {
        throw new Q_Exception_MissingRow(array('table' => 'invite', 'criteria' => "token = '{$token}"), 'token');
    }
    // did invite expire?
    $ts = Streams_Invite::db()->select("CURRENT_TIMESTAMP")->fetchAll(PDO::FETCH_NUM);
    if (isset($invite->expireTime) and $invite->expireTime < $ts[0][0]) {
        $invite->state = 'expired';
        $invite->save();
    }
    // is invite still pending?
    if ($invite->state !== 'pending') {
        switch ($invite->state) {
            case 'expired':
                $exception = new Streams_Exception_AlreadyExpired(null, 'token');
                break;
            case 'accepted':
                $exception = new Streams_Exception_AlreadyAccepted(null, 'token');
                break;
            case 'declined':
                $exception = new Streams_Exception_AlreadyDeclined(null, 'token');
                break;
            case 'forwarded':
                $exception = new Streams_Exception_AlreadyForwarded(null, 'token');
                break;
            default:
                $exception = new Q_Exception("This invite has already been " . $invite->state, 'token');
                break;
        }
        $shouldThrow = Q::event('Streams/objects/inviteException', compact('invite', 'exception'), 'before');
        if ($shouldThrow === null) {
            Q_Response::setNotice('Streams/objects', $exception->getMessage(), true);
        } else {
            if ($shouldThrow === true) {
                throw $exception;
            }
        }
    }
    // now process the invite
    $invitedUser = Users_User::fetch($invite->userId, true);
    $stream = Streams::fetchOne($invitedUser->id, $invite->publisherId, $invite->streamName);
    if (!$stream) {
        throw new Q_Exception_MissingRow(array('table' => 'stream', 'criteria' => "publisherId = '{$invite->publisherId}', name = '{$invite->streamName}'"));
    }
    $byUser = Users_User::fetch($invite->invitingUserId, true);
    $byStream = Streams::fetchOne($byUser->id, $invite->publisherId, $invite->streamName);
    if (!$byStream) {
        throw new Q_Exception_MissingRow(array('table' => 'stream', 'criteria' => "publisherId = '{$invite->publisherId}', name = '{$invite->streamName}'"));
    }
    $access = new Streams_Access();
    $access->publisherId = $byStream->publisherId;
    $access->streamName = $byStream->name;
    $access->ofUserId = $invite->userId;
    $specified_access = false;
    foreach (array('readLevel', 'writeLevel', 'adminLevel') as $level_type) {
        $access->{$level_type} = -1;
        if (empty($invite->{$level_type})) {
            continue;
        }
        // Give access level from the invite.
        // However, if inviting user has a lower access level now,
        // then give that level instead, unless it is lower than
        // what the invited user would have had otherwise.
        $min = min($invite->{$level_type}, $byStream->get($level_type, 0));
        if ($min > $stream->get($level_type, 0)) {
            $access->{$level_type} = $min;
            $specified_access = true;
        }
    }
    if ($specified_access) {
        $access->save(true);
    }
    // now log invited user in
    $user = Users::loggedInUser();
    if (empty($user) or $user->id !== $invite->userId) {
        $user = new Users_User();
        $user->id = $invite->userId;
        if (!$user->retrieve()) {
            // The user who was invited doesn't exist
            // This shouldn't happen. We just silently log it and return.
            Q::log("Sanity check failed: invite with {$invite->token} pointed to nonexistent user");
            return;
        }
        Users::setLoggedInUser($user);
    }
    // accept invite and autosubscribe if first time
    if ($invite->accept() and !$stream->subscription($user->id)) {
        $stream->subscribe();
    }
    // retain the invite object for further processing
    Streams::$followedInvite = $invite;
}
コード例 #18
0
ファイル: Users.php プロジェクト: AndreyTepaykin/Platform
 /**
  * Use with caution! This bypasses authentication.
  * This functionality should not be exposed externally.
  * @method setLoggedInUser
  * @static
  * @param {Users_User|string} $user The user object or user id
  */
 static function setLoggedInUser($user = null)
 {
     if (!$user) {
         return Users::logout();
     }
     if (is_string($user)) {
         $user = Users_User::fetch($user);
     }
     if (isset($_SESSION['Users']['loggedInUser']['id'])) {
         if ($user->id == $_SESSION['Users']['loggedInUser']['id']) {
             // This user is already the logged-in user.
             return;
         }
     }
     if ($sessionId = Q_Session::id()) {
         // Change the session id to prevent session fixation attacks
         $sessionId = Q_Session::regenerateId(true);
     }
     // Store the new information in the session
     $snf = Q_Config::get('Q', 'session', 'nonceField', 'nonce');
     $_SESSION['Users']['loggedInUser']['id'] = $user->id;
     Q_Session::setNonce(true);
     $user->sessionCount = isset($user->sessionCount) ? $user->sessionCount + 1 : 1;
     // Do we need to update it?
     if (Q_Config::get('Users', 'setLoggedInUser', 'updateSessionKey', true)) {
         /**
          * @event Users/setLoggedInUser/updateSessionKey {before}
          * @param {Users_User} user
          */
         Q::event('Users/setLoggedInUser/updateSessionKey', compact('user'), 'before');
         $user->sessionId = $sessionId;
         $user->save();
         // update sessionId in user
         /**
          * @event Users/setLoggedInUser/updateSessionKey {after}
          * @param {Users_User} user
          */
         Q::event('Users/setLoggedInUser/updateSessionKey', compact('user'), 'after');
     }
     $votes = Users_Vote::select('*')->where(array('userId' => $user->id, 'forType' => 'Users/hinted'))->fetchDbRows(null, null, 'forId');
     // Cache already shown hints in the session.
     // The consistency of this mechanism across sessions is not perfect, i.e.
     // the same hint may repeat in multiple concurrent sessions, but it's ok.
     $_SESSION['Users']['hinted'] = array_keys($votes);
     /**
      * @event Users/setLoggedInUser {after}
      * @param {Users_User} user
      */
     Q::event('Users/setLoggedInUser', compact('user'), 'after');
     self::$loggedOut = false;
 }
コード例 #19
0
ファイル: Assets.php プロジェクト: AndreyTepaykin/Platform
 /**
  * Starts a recurring subscription
  * @param {Streams_Stream} $plan The subscription plan stream
  * @param {string} [$payments=null] The type of payments processor, could be "authnet" or "stripe". If omitted, the subscription proceeds without any payments.
  * @param {array} [$options=array()] Options for the subscription
  * @param {date} [$options.startDate=today] The start date of the subscription
  * @param {date} [$options.endDate=today+year] The end date of the subscription
  * @param {Users_User} [$options.user=Users::loggedInUser()] Allows us to set the user to subscribe
  * @param {Users_User} [$options.publisherId=Users::communityId()] Allows us to override the publisher to subscribe to
  * @param {string} [$options.description=null] description of the charge, to be sent to customer
  * @param {string} [$options.metadata=null] any additional metadata to store with the charge
  * @param {string} [$options.subscription=null] if this charge is related to a subscription stream
  * @param {string} [$options.subscription.publisherId]
  * @param {string} [$options.subscription.streamName]
  * @throws Assets_Exception_DuplicateTransaction
  * @throws Assets_Exception_HeldForReview
  * @throws Assets_Exception_ChargeFailed
  * @return {Streams_Stream} A stream of type 'Assets/subscription' representing this subscription
  */
 static function startSubscription($plan, $payments = null, $options = array())
 {
     if (!isset($options['user'])) {
         $options['user'] = Users::loggedInUser(true);
     }
     $app = Q_Config::expect('Q', 'app');
     $user = Q::ifset($options, 'user', Users::loggedInUser(true));
     $currency = 'USD';
     // TODO: may want to implement support for currency conversion
     $startDate = Q::ifset($options, 'startDate', date("Y-m-d"));
     $startDate = date('Y-m-d', strtotime($startDate));
     $months = $plan->getAttribute('months', 12);
     $amount = $plan->getAttribute('amount');
     $endDate = date("Y-m-d", strtotime("-1 day", strtotime("+{$months} month", strtotime($startDate))));
     $endDate = date('Y-m-d', strtotime($endDate));
     $publisherId = Q::ifset($options, 'publisherId', Users::communityId());
     $publisher = Users_User::fetch($publisherId);
     $streamName = "Assets/subscription/{$user->id}/{$plan->name}";
     if ($subscription = Streams::fetchOne($publisherId, $publisherId, $streamName)) {
         return $subscription;
         // it already started
     }
     $attributes = Q::json_encode(array('payments' => $payments, 'planPublisherId' => $plan->publisherId, 'planStreamName' => $plan->name, 'startDate' => $startDate, 'endDate' => $endDate, 'months' => $months, 'amount' => $amount, 'currency' => $currency));
     $stream = Streams::create($publisherId, $publisherId, "Assets/subscription", array('name' => $streamName, 'title' => $plan->title, 'readLevel' => Streams::$READ_LEVEL['none'], 'writeLevel' => Streams::$WRITE_LEVEL['none'], 'adminLevel' => Streams::$ADMIN_LEVEL['none'], 'attributes' => $attributes));
     $access = new Streams_Access(array('publisherId' => $publisherId, 'streamName' => $streamName, 'ofUserId' => $user->id, 'grantedByUserId' => $app, 'readLevel' => Streams::$READ_LEVEL['max'], 'writeLevel' => -1, 'adminLevel' => -1));
     $access->save();
     $amount = $plan->getAttribute('amount', null);
     if (!is_numeric($amount)) {
         throw new Q_Exception_WrongValue(array('field' => 'amount', 'range' => 'an integer'));
     }
     $options['stream'] = $stream;
     if ($payments) {
         Assets::charge($payments, $amount, $currency, $options);
     }
     /**
      * @event Assets/startSubscription {before}
      * @param {Streams_Stream} plan
      * @param {Streams_Stream} subscription
      * @param {string} startDate
      * @param {string} endDate
      * @return {Users_User}
      */
     Q::event('Assets/startSubscription', compact('plan', 'user', 'publisher', 'stream', 'startDate', 'endDate', 'months', 'currency'), 'after');
     return $stream;
 }
コード例 #20
0
ファイル: Credits.php プロジェクト: atirjavid/Platform
 /**
  * Send credits, as the logged-in user, to another user
  * @method send
  * @static
  * @param {integer} $amount The amount of credits to send.
  * @param {string} $toUserId The id of the user to whom you will send the credits
  * @param {array} $more An array supplying more info, including
  *  "reason" => Identifies the reason for sending, if any
  */
 static function send($amount, $toUserId, $more = array())
 {
     if (!is_int($amount) or $amount <= 0) {
         throw new Q_Exception_WrongType(array('field' => 'amount', 'type' => 'integer'));
     }
     $user = Users::loggedInUser(true);
     $from_stream = new Streams_Stream();
     $from_stream->publisherId = $user->id;
     $from_stream->name = 'Awards/credits';
     if (!$from_stream->retrieve()) {
         $from_stream = self::createStream($user);
     }
     $existing_amount = $from_stream->getAttribute('amount');
     if ($existing_amount < $amount) {
         throw new Awards_Exception_NotEnoughCredits(array('missing' => $amount - $existing_amount));
     }
     $to_user = Users_User::fetch($toUserId, true);
     $to_stream = new Streams_Stream();
     $to_stream->publisherId = $toUserId;
     $to_stream->name = 'Awards/credits';
     if (!$to_stream->retrieve()) {
         $to_stream = self::createStream($to_user);
     }
     $to_stream->setAttribute('amount', $to_stream->getAttribute('amount') - $amount);
     $to_stream->save();
     // NOTE: we are not doing transactions here mainly because of sharding.
     // If if we reached this point without exceptions, that means everything worked.
     // But if the following statement fails, then someone will get free credits.
     $from_stream->setAttribute('amount', $from_stream->getAttribute('amount') - $amount);
     $from_stream->save();
     $instructions_json = Q::json_encode(array_merge(array('app' => Q_Config::expect('Q', 'app')), $more));
     Streams_Message::post($user->id, $userId, array('type' => 'Awards/credits/sent', 'content' => $amount, 'instructions' => $instructions_json));
     Streams_Message::post($user->id, $toUserId, array('type' => 'Awards/credits/received', 'content' => $amount, 'instructions' => $instructions_json));
 }
コード例 #21
0
ファイル: Stream.php プロジェクト: AndreyTepaykin/Platform
 protected function _verifyUser($options, &$user = null)
 {
     if (isset($options['userId'])) {
         $user = Users_User::fetch($options['userId'], true);
     } else {
         $user = Users::loggedInUser(true);
     }
     $stream = Streams::fetchOne($user->id, $this->publisherId, $this->name, true, array('refetch' => true));
     return $user->id;
 }
コード例 #22
0
ファイル: Stream.php プロジェクト: dmitriz/Platform
 protected function fetchAsUser($options, &$userId, &$user = null)
 {
     if (isset($options['userId'])) {
         $user = Users_User::fetch($options['userId']);
         if (!$user) {
             throw new Q_Exception_MissingRow(array('table' => 'user', 'criteria' => "id = " . $options['userId']));
         }
     } else {
         $user = Users::loggedInUser(true);
     }
     $userId = $user->id;
     if (!empty($options['skipAccess']) or $userId === $this->get('asUserId', null)) {
         return $this;
     }
     $stream = Streams::fetchOne($userId, $this->publisherId, $this->name, '*', array('refetch' => true));
     if (!$stream) {
         // this should never happen
         throw new Q_Exception("Error getting {$this->name} stream published by {$this->publisherId} for user '{$userId}'");
     }
     return $stream;
 }
コード例 #23
0
function Assets_after_Assets_charge($params)
{
    $user = $payments = $amount = $currency = $charge = $adapter = $options = null;
    extract($params, EXTR_OVERWRITE);
    $description = 'a product or service';
    $stream = Q::ifset($options, 'stream', null);
    if ($stream) {
        $publisherId = $stream->publisherId;
        $publisher = Users_User::fetch($publisherId, true);
        if ($stream->type === 'Assets/subscription') {
            $plan = Streams::fetchOne($stream->getAttribute('planPublisherId'), $stream->getAttribute('planPublisherId'), $stream->getAttribute('planStreamName'), true);
            $months = $stream->getAttribute('months');
            $startDate = $stream->getAttribute('startDate');
            $endDate = $stream->getAttribute('endDate');
        }
        $description = $stream->title;
    } else {
        $publisherId = Users::communityId();
        $publisher = Users_User::fetch($publisherId, true);
    }
    if (isset($options['description'])) {
        $description = $options['description'];
    }
    $currencies = Q::json_decode(file_get_contents(ASSETS_PLUGIN_CONFIG_DIR . DS . 'currencies.json'), true);
    if (!isset($currencies['symbols'][$currency])) {
        throw new Q_Exception_BadValue(array('internal' => 'currency', 'problem' => 'no symbol found'), 'currency');
    }
    if (!isset($currencies['names'][$currency])) {
        throw new Q_Exception_BadValue(array('internal' => 'currency', 'problem' => 'no name found'), 'currency');
    }
    $symbol = $currencies['symbols'][$currency];
    $currencyName = $currencies['names'][$currency];
    $communityId = Users::communityId();
    $communityName = Users::communityName();
    $communitySuffix = Users::communitySuffix();
    $link = Q_Request::baseUrl('action.php') . "/Assets/payment?publisherId={$publisherId}&userId=" . $user->id;
    $fields = compact('user', 'publisher', 'publisherId', 'communityId', 'communityName', 'communitySuffix', 'description', 'subscription', 'stream', 'plan', 'currency', 'name', 'symbol', 'currencyName', 'amount', 'months', 'startDate', 'endDate', 'link');
    if ($user->emailAddress) {
        $email = new Users_Email();
        $email->address = $user->emailAddress;
        $email->retrieve(true);
        $emailSubject = Q_Config::get('Assets', 'transactional', 'charged', 'subject', false);
        $emailView = Q_Config::get('Assets', 'transactional', 'charged', 'body', false);
        if ($emailSubject !== false and $emailView) {
            $email->sendMessage($emailSubject, $emailView, $fields);
        }
    } else {
        if ($user->mobileNumber) {
            $mobile = new Users_Mobile();
            $mobile->number = $user->mobileNumber;
            $mobile->retrieve(true);
            if ($mobileView = Q_Config::get('Assets', 'transactional', 'charged', 'sms', false)) {
                $mobile->sendMessage($mobileView, $fields);
            }
        }
    }
    if ($publisher->emailAddress) {
        $email = new Users_Email();
        $email->address = $publisher->emailAddress;
        $email->retrieve(true);
        $emailSubject = Q_Config::get('Assets', 'transactional', 'charge', 'subject', false);
        $emailView = Q_Config::get('Assets', 'transactional', 'charge', 'body', false);
        if ($emailSubject !== false and $emailView) {
            $email->sendMessage($emailSubject, $emailView, $fields);
        }
    } else {
        if ($publisher->mobileNumber) {
            $mobile = new Users_Mobile();
            $mobile->number = $publisher->mobileNumber;
            $mobile->retrieve(true);
            if ($mobileView = Q_Config::get('Assets', 'transactional', 'charge', 'sms', false)) {
                $mobile->sendMessage($mobileView, $fields);
            }
        }
    }
}