summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorCraig Andrews <candrews@integralblue.com>2010-02-16 10:25:57 -0500
committerCraig Andrews <candrews@integralblue.com>2010-02-16 10:25:57 -0500
commit32084e33a266797b306158df29e48f057651b410 (patch)
tree2a46e529783c8547aaae8ac00c8cac9bdfa61490 /lib
parent057ec1fceacbfec1f755a5bc6700a188aa70e33f (diff)
parentd4f6235d7b8a40bd1b51370e7eb405cdb14e61fb (diff)
Merge branch '0.9.x' into 1.0.x
Conflicts: lib/queuemanager.php
Diffstat (limited to 'lib')
-rw-r--r--lib/api.php21
-rw-r--r--lib/apiauth.php22
-rw-r--r--lib/atom10entry.php106
-rw-r--r--lib/atom10feed.php293
-rw-r--r--lib/atomnoticefeed.php103
-rw-r--r--lib/cache.php4
-rw-r--r--lib/default.php7
-rw-r--r--lib/error.php10
-rw-r--r--lib/grouptagcloudsection.php1
-rw-r--r--lib/httpclient.php5
-rw-r--r--lib/mysqlschema.php1
-rw-r--r--lib/oauthclient.php88
-rw-r--r--lib/oauthstore.php3
-rw-r--r--lib/personaltagcloudsection.php1
-rw-r--r--lib/popularnoticesection.php7
-rw-r--r--lib/queuemanager.php6
-rw-r--r--lib/right.php1
-rw-r--r--lib/spawningdaemon.php2
-rw-r--r--lib/statusnet.php11
-rw-r--r--lib/stompqueuemanager.php44
-rw-r--r--lib/util.php8
21 files changed, 660 insertions, 84 deletions
diff --git a/lib/api.php b/lib/api.php
index 7d94eaee4..7a99f48e8 100644
--- a/lib/api.php
+++ b/lib/api.php
@@ -77,6 +77,7 @@ class ApiAction extends Action
function prepare($args)
{
+ StatusNet::setApi(true); // reduce exception reports to aid in debugging
parent::prepare($args);
$this->format = $this->arg('format');
@@ -1103,7 +1104,7 @@ class ApiAction extends Action
}
}
- function serverError($msg, $code = 500, $content_type = 'json')
+ function serverError($msg, $code = 500, $content_type = 'xml')
{
$action = $this->trimmed('action');
@@ -1321,4 +1322,22 @@ class ApiAction extends Action
}
}
+ function getSelfUri($action, $aargs)
+ {
+ parse_str($_SERVER['QUERY_STRING'], $params);
+ $pstring = '';
+ if (!empty($params)) {
+ unset($params['p']);
+ $pstring = http_build_query($params);
+ }
+
+ $uri = common_local_url($action, $aargs);
+
+ if (!empty($pstring)) {
+ $uri .= '?' . $pstring;
+ }
+
+ return $uri;
+ }
+
}
diff --git a/lib/apiauth.php b/lib/apiauth.php
index 262f4b966..25e2196cf 100644
--- a/lib/apiauth.php
+++ b/lib/apiauth.php
@@ -55,6 +55,7 @@ class ApiAuthAction extends ApiAction
{
var $auth_user_nickname = null;
var $auth_user_password = null;
+ var $oauth_source = null;
/**
* Take arguments for running, looks for an OAuth request,
@@ -73,28 +74,23 @@ class ApiAuthAction extends ApiAction
// NOTE: $this->auth_user has to get set in prepare(), not handle(),
// because subclasses do stuff with it in their prepares.
- if ($this->requiresAuth()) {
+ $oauthReq = $this->getOAuthRequest();
- $oauthReq = $this->getOAuthRequest();
-
- if (!$oauthReq) {
+ if (!$oauthReq) {
+ if ($this->requiresAuth()) {
$this->checkBasicAuthUser(true);
} else {
- $this->checkOAuthRequest($oauthReq);
+ // Check to see if a basic auth user is there even
+ // if one's not required
+ $this->checkBasicAuthUser(false);
}
} else {
-
- // Check to see if a basic auth user is there even
- // if one's not required
- $this->checkBasicAuthUser(false);
+ $this->checkOAuthRequest($oauthReq);
}
// Reject API calls with the wrong access level
if ($this->isReadOnly($args) == false) {
-
- common_debug(get_class($this) . ' is not read-only!');
-
if ($this->access != self::READ_WRITE) {
$msg = _('API resource requires read-write access, ' .
'but you only have read access.');
@@ -111,7 +107,6 @@ class ApiAuthAction extends ApiAction
* This is to avoid doign any unnecessary DB lookups.
*
* @return mixed the OAuthRequest or false
- *
*/
function getOAuthRequest()
@@ -140,7 +135,6 @@ class ApiAuthAction extends ApiAction
* @param OAuthRequest $request the OAuth Request
*
* @return nothing
- *
*/
function checkOAuthRequest($request)
diff --git a/lib/atom10entry.php b/lib/atom10entry.php
new file mode 100644
index 000000000..5710c80fc
--- /dev/null
+++ b/lib/atom10entry.php
@@ -0,0 +1,106 @@
+<?php
+/**
+ * StatusNet, the distributed open-source microblogging tool
+ *
+ * Class for building / manipulating an Atom entry in memory
+ *
+ * PHP version 5
+ *
+ * LICENCE: This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * @category Feed
+ * @package StatusNet
+ * @author Zach Copley <zach@status.net>
+ * @copyright 2010 StatusNet, Inc.
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+
+if (!defined('STATUSNET')
+{
+ exit(1);
+}
+
+class Atom10EntryException extends Exception
+{
+}
+
+/**
+ * Class for manipulating an Atom entry in memory. Get the entry as an XML
+ * string with Atom10Entry::getString().
+ *
+ * @category Feed
+ * @package StatusNet
+ * @author Zach Copley <zach@status.net>
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+class Atom10Entry extends XMLStringer
+{
+ private $namespaces;
+ private $categories;
+ private $content;
+ private $contributors;
+ private $id;
+ private $links;
+ private $published;
+ private $rights;
+ private $source;
+ private $summary;
+ private $title;
+
+ function __construct($indent = true) {
+ parent::__construct($indent);
+ $this->namespaces = array();
+ }
+
+ function addNamespace($namespace, $uri)
+ {
+ $ns = array($namespace => $uri);
+ $this->namespaces = array_merge($this->namespaces, $ns);
+ }
+
+ function initEntry()
+ {
+
+ }
+
+ function endEntry()
+ {
+
+ }
+
+ /**
+ * Check that all required elements have been set, etc.
+ * Throws an Atom10EntryException if something's missing.
+ *
+ * @return void
+ */
+ function validate
+ {
+
+ }
+
+ function getString()
+ {
+ $this->validate();
+
+ $this->initEntry();
+ $this->renderEntries();
+ $this->endEntry();
+
+ return $this->xw->outputMemory();
+ }
+
+} \ No newline at end of file
diff --git a/lib/atom10feed.php b/lib/atom10feed.php
new file mode 100644
index 000000000..806a9684b
--- /dev/null
+++ b/lib/atom10feed.php
@@ -0,0 +1,293 @@
+<?php
+/**
+ * StatusNet, the distributed open-source microblogging tool
+ *
+ * Class for building an Atom feed in memory
+ *
+ * PHP version 5
+ *
+ * LICENCE: This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * @category Feed
+ * @package StatusNet
+ * @author Zach Copley <zach@status.net>
+ * @copyright 2010 StatusNet, Inc.
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+
+if (!defined('STATUSNET'))
+{
+ exit(1);
+}
+
+class Atom10FeedException extends Exception
+{
+}
+
+/**
+ * Class for building an Atom feed in memory. Get the finished doc
+ * as a string with Atom10Feed::getString().
+ *
+ * @category Feed
+ * @package StatusNet
+ * @author Zach Copley <zach@status.net>
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+class Atom10Feed extends XMLStringer
+{
+ public $xw;
+ private $namespaces;
+ private $authors;
+ private $subject;
+ private $categories;
+ private $contributors;
+ private $generator;
+ private $icon;
+ private $links;
+ private $logo;
+ private $rights;
+ private $subtitle;
+ private $title;
+ private $published;
+ private $updated;
+ private $entries;
+
+ /**
+ * Constructor
+ *
+ * @param boolean $indent flag to turn indenting on or off
+ *
+ * @return void
+ */
+ function __construct($indent = true) {
+ parent::__construct($indent);
+ $this->namespaces = array();
+ $this->authors = array();
+ $this->links = array();
+ $this->entries = array();
+ $this->addNamespace('xmlns', 'http://www.w3.org/2005/Atom');
+ }
+
+ /**
+ * Add another namespace to the feed
+ *
+ * @param string $namespace the namespace
+ * @param string $uri namspace uri
+ *
+ * @return void
+ */
+ function addNamespace($namespace, $uri)
+ {
+ $ns = array($namespace => $uri);
+ $this->namespaces = array_merge($this->namespaces, $ns);
+ }
+
+ function addAuthor($name, $uri = null, $email = null)
+ {
+ $xs = new XMLStringer(true);
+
+ $xs->elementStart('author');
+
+ if (!empty($name)) {
+ $xs->element('name', null, $name);
+ } else {
+ throw new Atom10FeedException(
+ 'author element must contain a name element.'
+ );
+ }
+
+ if (!is_null($uri)) {
+ $xs->element('uri', null, $uri);
+ }
+
+ if (!is_null(email)) {
+ $xs->element('email', null, $email);
+ }
+
+ $xs->elementEnd('author');
+
+ array_push($this->authors, $xs->getString());
+ }
+
+ /**
+ * Add an Author to the feed via raw XML string
+ *
+ * @param string $xmlAuthor An XML string representation author
+ *
+ * @return void
+ */
+ function addAuthorRaw($xmlAuthor)
+ {
+ array_push($this->authors, $xmlAuthor);
+ }
+
+ function renderAuthors()
+ {
+ foreach ($this->authors as $author) {
+ $this->raw($author);
+ }
+ }
+
+ /**
+ * Add a activity feed subject via raw XML string
+ *
+ * @param string $xmlSubject An XML string representation of the subject
+ *
+ * @return void
+ */
+ function setActivitySubject($xmlSubject)
+ {
+ $this->subject = $xmlSubject;
+ }
+
+ function getNamespaces()
+ {
+ return $this->namespaces;
+ }
+
+ function initFeed()
+ {
+ $this->xw->startDocument('1.0', 'UTF-8');
+ $commonAttrs = array('xml:lang' => 'en-US');
+ $commonAttrs = array_merge($commonAttrs, $this->namespaces);
+ $this->elementStart('feed', $commonAttrs);
+
+ $this->element('id', null, $this->id);
+ $this->element('title', null, $this->title);
+ $this->element('subtitle', null, $this->subtitle);
+
+ if (!empty($this->logo)) {
+ $this->element('logo', null, $this->logo);
+ }
+
+ $this->element('updated', null, $this->updated);
+
+ $this->renderLinks();
+ }
+
+ /**
+ * Check that all required elements have been set, etc.
+ * Throws an Atom10FeedException if something's missing.
+ *
+ * @return void
+ */
+ function validate()
+ {
+ }
+
+ function renderLinks()
+ {
+ foreach ($this->links as $attrs)
+ {
+ $this->element('link', $attrs, null);
+ }
+ }
+
+ function addEntryRaw($xmlEntry)
+ {
+ array_push($this->entries, $xmlEntry);
+ }
+
+ function addEntry($entry)
+ {
+ array_push($this->entries, $entry->getString());
+ }
+
+ function renderEntries()
+ {
+ foreach ($this->entries as $entry) {
+ $this->raw($entry);
+ }
+ }
+
+ function endFeed()
+ {
+ $this->elementEnd('feed');
+ $this->xw->endDocument();
+ }
+
+ function getString()
+ {
+ $this->validate();
+
+ $this->initFeed();
+ $this->renderAuthors();
+
+ if (!empty($this->subject)) {
+ $this->raw($this->subject);
+ }
+
+ $this->renderEntries();
+ $this->endFeed();
+
+ return $this->xw->outputMemory();
+ }
+
+ function setId($id)
+ {
+ $this->id = $id;
+ }
+
+ function setTitle($title)
+ {
+ $this->title = $title;
+ }
+
+ function setSubtitle($subtitle)
+ {
+ $this->subtitle = $subtitle;
+ }
+
+ function setLogo($logo)
+ {
+ $this->logo = $logo;
+ }
+
+ function setUpdated($dt)
+ {
+ $this->updated = common_date_iso8601($dt);
+ }
+
+ function setPublished($dt)
+ {
+ $this->published = common_date_iso8601($dt);
+ }
+
+ /**
+ * Adds a link element into the Atom document
+ *
+ * Assumes you want rel="alternate" and type="text/html" unless
+ * you send in $otherAttrs.
+ *
+ * @param string $uri the uri the href needs to point to
+ * @param array $otherAttrs other attributes to stick in
+ *
+ * @return void
+ */
+ function addLink($uri, $otherAttrs = null) {
+ $attrs = array('href' => $uri);
+
+ if (is_null($otherAttrs)) {
+ $attrs['rel'] = 'alternate';
+ $attrs['type'] = 'text/html';
+ } else {
+ $attrs = array_merge($attrs, $otherAttrs);
+ }
+
+ array_push($this->links, $attrs);
+ }
+
+}
diff --git a/lib/atomnoticefeed.php b/lib/atomnoticefeed.php
new file mode 100644
index 000000000..34ed44b2e
--- /dev/null
+++ b/lib/atomnoticefeed.php
@@ -0,0 +1,103 @@
+<?php
+/**
+ * StatusNet, the distributed open-source microblogging tool
+ *
+ * Class for building and Atom feed from a collection of notices
+ *
+ * PHP version 5
+ *
+ * LICENCE: This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * @category Feed
+ * @package StatusNet
+ * @author Zach Copley <zach@status.net>
+ * @copyright 2010 StatusNet, Inc.
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+
+if (!defined('STATUSNET'))
+{
+ exit(1);
+}
+
+/**
+ * Class for creating a feed that represents a collection of notices. Builds the
+ * feed in memory. Get the feed as a string with AtomNoticeFeed::getString().
+ *
+ * @category Feed
+ * @package StatusNet
+ * @author Zach Copley <zach@status.net>
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+class AtomNoticeFeed extends Atom10Feed
+{
+ function __construct($indent = true) {
+ parent::__construct($indent);
+
+ // Feeds containing notice info use these namespaces
+
+ $this->addNamespace(
+ 'xmlns:thr',
+ 'http://purl.org/syndication/thread/1.0'
+ );
+
+ $this->addNamespace(
+ 'xmlns:georss',
+ 'http://www.georss.org/georss'
+ );
+
+ $this->addNamespace(
+ 'xmlns:activity',
+ 'http://activitystrea.ms/spec/1.0/'
+ );
+
+ // XXX: What should the uri be?
+ $this->addNamespace(
+ 'xmlns:ostatus',
+ 'http://ostatus.org/schema/1.0'
+ );
+ }
+
+ /**
+ * Add more than one Notice to the feed
+ *
+ * @param mixed $notices an array of Notice objects or handle
+ *
+ */
+ function addEntryFromNotices($notices)
+ {
+ if (is_array($notices)) {
+ foreach ($notices as $notice) {
+ $this->addEntryFromNotice($notice);
+ }
+ } else {
+ while ($notices->fetch()) {
+ $this->addEntryFromNotice($notices);
+ }
+ }
+ }
+
+ /**
+ * Add a single Notice to the feed
+ *
+ * @param Notice $notice a Notice to add
+ */
+ function addEntryFromNotice($notice)
+ {
+ $this->addEntryRaw($notice->asAtomEntry());
+ }
+
+}
diff --git a/lib/cache.php b/lib/cache.php
index 635c96ad4..df6fc3649 100644
--- a/lib/cache.php
+++ b/lib/cache.php
@@ -47,6 +47,8 @@ class Cache
var $_items = array();
static $_inst = null;
+ const COMPRESSED = 1;
+
/**
* Singleton constructor
*
@@ -133,7 +135,7 @@ class Cache
*
* @param string $key The key to use for lookups
* @param string $value The value to store
- * @param integer $flag Flags to use, mostly ignored
+ * @param integer $flag Flags to use, may include Cache::COMPRESSED
* @param integer $expiry Expiry value, mostly ignored
*
* @return boolean success flag
diff --git a/lib/default.php b/lib/default.php
index 437f350dd..cc6863488 100644
--- a/lib/default.php
+++ b/lib/default.php
@@ -88,6 +88,7 @@ $default =
'stomp_manual_failover' => true, // if multiple servers are listed, treat them as separate (enqueue on one randomly, listen on all)
'monitor' => null, // URL to monitor ping endpoint (work in progress)
'softlimit' => '90%', // total size or % of memory_limit at which to restart queue threads gracefully
+ 'spawndelay' => 1, // Wait at least N seconds between (re)spawns of child processes to avoid slamming the queue server with subscription startup
'debug_memory' => false, // true to spit memory usage to log
'inboxes' => true, // true to do inbox distribution & output queueing from in background via 'distrib' queue
),
@@ -144,9 +145,11 @@ $default =
'invite' =>
array('enabled' => true),
'tag' =>
- array('dropoff' => 864000.0),
+ array('dropoff' => 864000.0, # controls weighting based on age
+ 'cutoff' => 86400 * 90), # only look at notices posted in last 90 days
'popular' =>
- array('dropoff' => 864000.0),
+ array('dropoff' => 864000.0, # controls weighting based on age
+ 'cutoff' => 86400 * 90), # only look at notices favorited in last 90 days
'daemon' =>
array('piddir' => '/var/run',
'user' => false,
diff --git a/lib/error.php b/lib/error.php
index 87a4d913b..a6a29119f 100644
--- a/lib/error.php
+++ b/lib/error.php
@@ -56,6 +56,7 @@ class ErrorAction extends Action
$this->code = $code;
$this->message = $message;
+ $this->minimal = StatusNet::isApi();
// XXX: hack alert: usually we aren't going to
// call this page directly, but because it's
@@ -102,7 +103,14 @@ class ErrorAction extends Action
function showPage()
{
- parent::showPage();
+ if ($this->minimal) {
+ // Even more minimal -- we're in a machine API
+ // and don't want to flood the output.
+ $this->extraHeaders();
+ $this->showContent();
+ } else {
+ parent::showPage();
+ }
// We don't want to have any more output after this
exit();
diff --git a/lib/grouptagcloudsection.php b/lib/grouptagcloudsection.php
index 14ceda085..f1106cc7b 100644
--- a/lib/grouptagcloudsection.php
+++ b/lib/grouptagcloudsection.php
@@ -59,6 +59,7 @@ class GroupTagCloudSection extends TagCloudSection
function getTags()
{
$weightexpr = common_sql_weight('notice_tag.created', common_config('tag', 'dropoff'));
+ // @fixme should we use the cutoff too? Doesn't help with indexing per-group.
$names = $this->group->getAliases();
diff --git a/lib/httpclient.php b/lib/httpclient.php
index 3f8262076..4c3af8d7d 100644
--- a/lib/httpclient.php
+++ b/lib/httpclient.php
@@ -81,12 +81,13 @@ class HTTPResponse extends HTTP_Request2_Response
}
/**
- * Check if the response is OK, generally a 200 status code.
+ * Check if the response is OK, generally a 200 or other 2xx status code.
* @return bool
*/
function isOk()
{
- return ($this->getStatus() == 200);
+ $status = $this->getStatus();
+ return ($status >= 200 && $status < 300);
}
}
diff --git a/lib/mysqlschema.php b/lib/mysqlschema.php
index 1f7c3d092..485096ac4 100644
--- a/lib/mysqlschema.php
+++ b/lib/mysqlschema.php
@@ -213,6 +213,7 @@ class MysqlSchema extends Schema
$sql .= "); ";
+ common_log(LOG_INFO, $sql);
$res = $this->conn->query($sql);
if (PEAR::isError($res)) {
diff --git a/lib/oauthclient.php b/lib/oauthclient.php
index b22fd7897..bc7587183 100644
--- a/lib/oauthclient.php
+++ b/lib/oauthclient.php
@@ -90,20 +90,47 @@ class OAuthClient
/**
* Gets a request token from the given url
*
- * @param string $url OAuth endpoint for grabbing request tokens
+ * @param string $url OAuth endpoint for grabbing request tokens
+ * @param string $callback authorized request token callback
*
* @return OAuthToken $token the request token
*/
- function getRequestToken($url)
+ function getRequestToken($url, $callback = null)
{
- $response = $this->oAuthGet($url);
+ $params = null;
+
+ if (!is_null($callback)) {
+ $params['oauth_callback'] = $callback;
+ }
+
+ $response = $this->oAuthGet($url, $params);
+
$arr = array();
parse_str($response, $arr);
- if (isset($arr['oauth_token']) && isset($arr['oauth_token_secret'])) {
- $token = new OAuthToken($arr['oauth_token'], @$arr['oauth_token_secret']);
+
+ $token = $arr['oauth_token'];
+ $secret = $arr['oauth_token_secret'];
+ $confirm = $arr['oauth_callback_confirmed'];
+
+ if (isset($token) && isset($secret)) {
+
+ $token = new OAuthToken($token, $secret);
+
+ if (isset($confirm)) {
+ if ($confirm == 'true') {
+ common_debug('Twitter bridge - callback confirmed.');
+ return $token;
+ } else {
+ throw new OAuthClientException(
+ 'Callback was not confirmed by Twitter.'
+ );
+ }
+ }
return $token;
} else {
- throw new OAuthClientException();
+ throw new OAuthClientException(
+ 'Could not get a request token from Twitter.'
+ );
}
}
@@ -113,49 +140,64 @@ class OAuthClient
*
* @param string $url endpoint for authorizing request tokens
* @param OAuthToken $request_token the request token to be authorized
- * @param string $oauth_callback optional callback url
*
* @return string $authorize_url the url to redirect to
*/
- function getAuthorizeLink($url, $request_token, $oauth_callback = null)
+ function getAuthorizeLink($url, $request_token)
{
$authorize_url = $url . '?oauth_token=' .
$request_token->key;
- if (isset($oauth_callback)) {
- $authorize_url .= '&oauth_callback=' . urlencode($oauth_callback);
- }
-
return $authorize_url;
}
/**
* Fetches an access token
*
- * @param string $url OAuth endpoint for exchanging authorized request tokens
- * for access tokens
+ * @param string $url OAuth endpoint for exchanging authorized request tokens
+ * for access tokens
+ * @param string $verifier 1.0a verifier
*
* @return OAuthToken $token the access token
*/
- function getAccessToken($url)
+ function getAccessToken($url, $verifier = null)
{
- $response = $this->oAuthPost($url);
- parse_str($response);
- $token = new OAuthToken($oauth_token, $oauth_token_secret);
- return $token;
+ $params = array();
+
+ if (!is_null($verifier)) {
+ $params['oauth_verifier'] = $verifier;
+ }
+
+ $response = $this->oAuthPost($url, $params);
+
+ $arr = array();
+ parse_str($response, $arr);
+
+ $token = $arr['oauth_token'];
+ $secret = $arr['oauth_token_secret'];
+
+ if (isset($token) && isset($secret)) {
+ $token = new OAuthToken($token, $secret);
+ return $token;
+ } else {
+ throw new OAuthClientException(
+ 'Could not get a access token from Twitter.'
+ );
+ }
}
/**
- * Use HTTP GET to make a signed OAuth request
+ * Use HTTP GET to make a signed OAuth requesta
*
- * @param string $url OAuth endpoint
+ * @param string $url OAuth request token endpoint
+ * @param array $params additional parameters
*
* @return mixed the request
*/
- function oAuthGet($url)
+ function oAuthGet($url, $params = null)
{
$request = OAuthRequest::from_consumer_and_token($this->consumer,
- $this->token, 'GET', $url, null);
+ $this->token, 'GET', $url, $params);
$request->sign_request($this->sha1_method,
$this->consumer, $this->token);
diff --git a/lib/oauthstore.php b/lib/oauthstore.php
index b30fb49d5..eabe37f9f 100644
--- a/lib/oauthstore.php
+++ b/lib/oauthstore.php
@@ -65,7 +65,7 @@ class StatusNetOAuthDataStore extends OAuthDataStore
{
$n = new Nonce();
$n->consumer_key = $consumer->key;
- $n->ts = $timestamp;
+ $n->ts = common_sql_date($timestamp);
$n->nonce = $nonce;
if ($n->find(true)) {
return true;
@@ -362,7 +362,6 @@ class StatusNetOAuthDataStore extends OAuthDataStore
array('is_local' => Notice::REMOTE_OMB,
'uri' => $omb_notice->getIdentifierURI()));
-
}
/**
diff --git a/lib/personaltagcloudsection.php b/lib/personaltagcloudsection.php
index 091425f92..5ea3f188d 100644
--- a/lib/personaltagcloudsection.php
+++ b/lib/personaltagcloudsection.php
@@ -59,6 +59,7 @@ class PersonalTagCloudSection extends TagCloudSection
function getTags()
{
$weightexpr = common_sql_weight('notice_tag.created', common_config('tag', 'dropoff'));
+ // @fixme should we use the cutoff too? Doesn't help with indexing per-user.
$qry = 'SELECT notice_tag.tag, '.
$weightexpr . ' as weight ' .
diff --git a/lib/popularnoticesection.php b/lib/popularnoticesection.php
index fbf9a60ab..296ddbbb5 100644
--- a/lib/popularnoticesection.php
+++ b/lib/popularnoticesection.php
@@ -59,12 +59,15 @@ class PopularNoticeSection extends NoticeSection
}
}
$weightexpr = common_sql_weight('fave.modified', common_config('popular', 'dropoff'));
+ $cutoff = sprintf("fave.modified > '%s'",
+ common_sql_date(time() - common_config('popular', 'cutoff')));
$qry = "SELECT notice.*, $weightexpr as weight ";
if(isset($tag)) {
$qry .= 'FROM notice_tag, notice JOIN fave ON notice.id = fave.notice_id ' .
- "WHERE notice.id = notice_tag.notice_id and '$tag' = notice_tag.tag";
+ "WHERE $cutoff and notice.id = notice_tag.notice_id and '$tag' = notice_tag.tag";
} else {
- $qry .= 'FROM notice JOIN fave ON notice.id = fave.notice_id';
+ $qry .= 'FROM notice JOIN fave ON notice.id = fave.notice_id ' .
+ "WHERE $cutoff";
}
$qry .= ' GROUP BY notice.id,notice.profile_id,notice.content,notice.uri,' .
'notice.rendered,notice.url,notice.created,notice.modified,' .
diff --git a/lib/queuemanager.php b/lib/queuemanager.php
index a0b13fe55..162c9f375 100644
--- a/lib/queuemanager.php
+++ b/lib/queuemanager.php
@@ -157,17 +157,17 @@ abstract class QueueManager extends IoManager
/**
* Encode an object for queued storage.
*
- * @param mixed $object
+ * @param mixed $item
* @return string
*/
- protected function encode($object)
+ protected function encode($item)
{
return serialize($object);
}
/**
* Decode an object from queued storage.
- * Accepts back-compat notice reference entries and strings for now.
+ * Accepts notice reference entries and serialized items.
*
* @param string
* @return mixed
diff --git a/lib/right.php b/lib/right.php
index 5e66eae0e..4e9c5a918 100644
--- a/lib/right.php
+++ b/lib/right.php
@@ -57,5 +57,6 @@ class Right
const EMAILONREPLY = 'emailonreply';
const EMAILONSUBSCRIBE = 'emailonsubscribe';
const EMAILONFAVE = 'emailonfave';
+ const MAKEGROUPADMIN = 'makegroupadmin';
}
diff --git a/lib/spawningdaemon.php b/lib/spawningdaemon.php
index b1961d688..862cbb4fa 100644
--- a/lib/spawningdaemon.php
+++ b/lib/spawningdaemon.php
@@ -83,6 +83,7 @@ abstract class SpawningDaemon extends Daemon
$this->log(LOG_INFO, "Spawned thread $i as pid $pid");
$children[$i] = $pid;
}
+ sleep(common_config('queue', 'spawndelay'));
}
$this->log(LOG_INFO, "Waiting for children to complete.");
@@ -111,6 +112,7 @@ abstract class SpawningDaemon extends Daemon
$this->log(LOG_INFO, "Respawned thread $i as pid $pid");
$children[$i] = $pid;
}
+ sleep(common_config('queue', 'spawndelay'));
} else {
$this->log(LOG_INFO, "Thread $i pid $pid exited with status $exitCode; closing out thread.");
}
diff --git a/lib/statusnet.php b/lib/statusnet.php
index 2654ba573..3951d9251 100644
--- a/lib/statusnet.php
+++ b/lib/statusnet.php
@@ -30,6 +30,7 @@ global $config, $_server, $_path;
class StatusNet
{
protected static $have_config;
+ protected static $is_api;
/**
* Configure and instantiate a plugin into the current configuration.
@@ -147,6 +148,16 @@ class StatusNet
return self::$have_config;
}
+ public function isApi()
+ {
+ return self::$is_api;
+ }
+
+ public function setApi($mode)
+ {
+ self::$is_api = $mode;
+ }
+
/**
* Build default configuration array
* @return array
diff --git a/lib/stompqueuemanager.php b/lib/stompqueuemanager.php
index 6730cd213..cd62c25bd 100644
--- a/lib/stompqueuemanager.php
+++ b/lib/stompqueuemanager.php
@@ -107,9 +107,10 @@ class StompQueueManager extends QueueManager
$message .= ':' . $param;
}
$this->_connect();
- $result = $this->_send($this->control,
- $message,
- array ('created' => common_sql_now()));
+ $con = $this->cons[$this->defaultIdx];
+ $result = $con->send($this->control,
+ $message,
+ array ('created' => common_sql_now()));
if ($result) {
$this->_log(LOG_INFO, "Sent control ping to queue daemons: $message");
return true;
@@ -368,17 +369,10 @@ class StompQueueManager extends QueueManager
foreach ($this->cons as $i => $con) {
if ($con) {
$this->rollback($i);
- $con->unsubscribe($this->control);
+ $con->disconnect();
+ $this->cons[$i] = null;
}
}
- if ($this->sites) {
- foreach ($this->sites as $server) {
- StatusNet::init($server);
- $this->doUnsubscribe();
- }
- } else {
- $this->doUnsubscribe();
- }
return true;
}
@@ -555,26 +549,14 @@ class StompQueueManager extends QueueManager
}
$host = $this->cons[$idx]->getServer();
- if (is_numeric($frame->body)) {
- $id = intval($frame->body);
- $info = "notice $id posted at {$frame->headers['created']} in queue $queue from $host";
-
- $notice = Notice::staticGet('id', $id);
- if (empty($notice)) {
- $this->_log(LOG_WARNING, "Skipping missing $info");
- $this->ack($idx, $frame);
- $this->commit($idx);
- $this->begin($idx);
- $this->stats('badnotice', $queue);
- return false;
- }
-
- $item = $notice;
- } else {
- // @fixme should we serialize, or json, or what here?
- $info = "string posted at {$frame->headers['created']} in queue $queue from $host";
- $item = $frame->body;
+ $item = $this->decode($frame->body);
+ if (empty($item)) {
+ $this->_log(LOG_ERR, "Skipping empty or deleted item in queue $queue from $host");
+ return true;
}
+ $info = $this->logrep($item) . " posted at " .
+ $frame->headers['created'] . " in queue $queue from $host";
+ $this->_log(LOG_DEBUG, "Dequeued $info");
$handler = $this->getHandler($queue);
if (!$handler) {
diff --git a/lib/util.php b/lib/util.php
index 9a24d268d..3f20e2ec7 100644
--- a/lib/util.php
+++ b/lib/util.php
@@ -367,7 +367,8 @@ function common_current_user()
if ($_cur === false) {
- if (isset($_REQUEST[session_name()]) || (isset($_SESSION['userid']) && $_SESSION['userid'])) {
+ if (isset($_COOKIE[session_name()]) || isset($_GET[session_name()])
+ || (isset($_SESSION['userid']) && $_SESSION['userid'])) {
common_ensure_session();
$id = isset($_SESSION['userid']) ? $_SESSION['userid'] : false;
if ($id) {
@@ -658,6 +659,9 @@ function common_valid_profile_tag($str)
function common_at_link($sender_id, $nickname)
{
$sender = Profile::staticGet($sender_id);
+ if (!$sender) {
+ return $nickname;
+ }
$recipient = common_relative_profile($sender, common_canonical_nickname($nickname));
if ($recipient) {
$user = User::staticGet('id', $recipient->id);
@@ -687,7 +691,7 @@ function common_group_link($sender_id, $nickname)
{
$sender = Profile::staticGet($sender_id);
$group = User_group::getForNickname($nickname);
- if ($group && $sender->isMember($group)) {
+ if ($sender && $group && $sender->isMember($group)) {
$attrs = array('href' => $group->permalink(),
'class' => 'url');
if (!empty($group->fullname)) {