summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--actions/otp.php2
-rw-r--r--lib/apiauth.php6
-rw-r--r--lib/default.php2
-rw-r--r--plugins/OStatus/classes/HubSub.php2
-rw-r--r--plugins/OStatus/lib/feeddiscovery.php2
-rw-r--r--plugins/RSSCloud/RSSCloudNotifier.php2
-rw-r--r--plugins/RSSCloud/RSSCloudRequestNotify.php7
-rw-r--r--scripts/flushsite.php45
-rw-r--r--scripts/importtwitteratom.php192
9 files changed, 253 insertions, 7 deletions
diff --git a/actions/otp.php b/actions/otp.php
index acf84aee8..1e06603d4 100644
--- a/actions/otp.php
+++ b/actions/otp.php
@@ -126,6 +126,8 @@ class OtpAction extends Action
$this->lt->delete();
$this->lt = null;
+ common_real_login(true);
+
if ($this->rememberme) {
common_rememberme($this->user);
}
diff --git a/lib/apiauth.php b/lib/apiauth.php
index 5090871cf..f63c84d8f 100644
--- a/lib/apiauth.php
+++ b/lib/apiauth.php
@@ -235,7 +235,11 @@ class ApiAuthAction extends ApiAction
{
$this->basicAuthProcessHeader();
- $realm = common_config('site', 'name') . ' API';
+ $realm = common_config('api', 'realm');
+
+ if (empty($realm)) {
+ $realm = common_config('site', 'name') . ' API';
+ }
if (!isset($this->auth_user_nickname) && $required) {
header('WWW-Authenticate: Basic realm="' . $realm . '"');
diff --git a/lib/default.php b/lib/default.php
index bdd78d4d8..46d3d4774 100644
--- a/lib/default.php
+++ b/lib/default.php
@@ -293,4 +293,6 @@ $default =
array('crawldelay' => 0,
'disallow' => array('main', 'settings', 'admin', 'search', 'message')
),
+ 'api' =>
+ array('realm' => null),
);
diff --git a/plugins/OStatus/classes/HubSub.php b/plugins/OStatus/classes/HubSub.php
index 3120a70f9..c420b3eef 100644
--- a/plugins/OStatus/classes/HubSub.php
+++ b/plugins/OStatus/classes/HubSub.php
@@ -192,7 +192,7 @@ class HubSub extends Memcached_DataObject
// Any existing query string parameters must be preserved
$url = $this->callback;
- if (strpos('?', $url) !== false) {
+ if (strpos($url, '?') !== false) {
$url .= '&';
} else {
$url .= '?';
diff --git a/plugins/OStatus/lib/feeddiscovery.php b/plugins/OStatus/lib/feeddiscovery.php
index 7afb71bdc..ff76b229e 100644
--- a/plugins/OStatus/lib/feeddiscovery.php
+++ b/plugins/OStatus/lib/feeddiscovery.php
@@ -129,7 +129,7 @@ class FeedDiscovery
function initFromResponse($response)
{
if (!$response->isOk()) {
- throw new FeedSubBadResponseException($response->getCode());
+ throw new FeedSubBadResponseException($response->getStatus());
}
$sourceurl = $response->getUrl();
diff --git a/plugins/RSSCloud/RSSCloudNotifier.php b/plugins/RSSCloud/RSSCloudNotifier.php
index d454691c8..9e7b53680 100644
--- a/plugins/RSSCloud/RSSCloudNotifier.php
+++ b/plugins/RSSCloud/RSSCloudNotifier.php
@@ -152,7 +152,7 @@ class RSSCloudNotifier
function notify($profile)
{
$feed = common_path('api/statuses/user_timeline/') .
- $profile->nickname . '.rss';
+ $profile->id . '.rss';
$cloudSub = new RSSCloudSubscription();
diff --git a/plugins/RSSCloud/RSSCloudRequestNotify.php b/plugins/RSSCloud/RSSCloudRequestNotify.php
index d76c08d37..030529534 100644
--- a/plugins/RSSCloud/RSSCloudRequestNotify.php
+++ b/plugins/RSSCloud/RSSCloudRequestNotify.php
@@ -270,13 +270,14 @@ class RSSCloudRequestNotifyAction extends Action
function userFromFeed($feed)
{
- // We only do profile feeds
+ // We only do canonical RSS2 profile feeds (specified by ID), e.g.:
+ // http://www.example.com/api/statuses/user_timeline/2.rss
$path = common_path('api/statuses/user_timeline/');
- $valid = '%^' . $path . '(?<nickname>.*)\.rss$%';
+ $valid = '%^' . $path . '(?<id>.*)\.rss$%';
if (preg_match($valid, $feed, $matches)) {
- $user = User::staticGet('nickname', $matches['nickname']);
+ $user = User::staticGet('id', $matches['id']);
if (!empty($user)) {
return $user;
}
diff --git a/scripts/flushsite.php b/scripts/flushsite.php
new file mode 100644
index 000000000..b7f385ac4
--- /dev/null
+++ b/scripts/flushsite.php
@@ -0,0 +1,45 @@
+#!/usr/bin/env php
+<?php
+/*
+ * StatusNet - a distributed open-source microblogging tool
+ * Copyright (C) 2008, 2009, StatusNet, Inc.
+ *
+ * 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/>.
+ */
+
+define('INSTALLDIR', realpath(dirname(__FILE__) . '/..'));
+
+$shortoptions = 'd';
+$longoptions = array('delete');
+
+$helptext = <<<END_OF_FLUSHSITE_HELP
+flushsite.php -s<sitename>
+Flush the site with the given name from memcached.
+
+END_OF_FLUSHSITE_HELP;
+
+require_once INSTALLDIR.'/scripts/commandline.inc';
+
+$nickname = common_config('site', 'nickname');
+
+$sn = Status_network::memGet('nickname', $nickname);
+
+if (empty($sn)) {
+ print "No such site.\n";
+ exit(-1);
+}
+
+print "Flushing cache for {$nickname}...";
+$sn->decache();
+print "OK.\n"; \ No newline at end of file
diff --git a/scripts/importtwitteratom.php b/scripts/importtwitteratom.php
new file mode 100644
index 000000000..7316f2108
--- /dev/null
+++ b/scripts/importtwitteratom.php
@@ -0,0 +1,192 @@
+#!/usr/bin/env php
+<?php
+/*
+ * StatusNet - the distributed open-source microblogging tool
+ * Copyright (C) 2010 StatusNet, Inc.
+ *
+ * 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/>.
+ */
+
+define('INSTALLDIR', realpath(dirname(__FILE__) . '/..'));
+
+$shortoptions = 'i:n:f:';
+$longoptions = array('id=', 'nickname=', 'file=');
+
+$helptext = <<<END_OF_IMPORTTWITTERATOM_HELP
+importtwitteratom.php [options]
+import an Atom feed from Twitter as notices by a user
+
+ -i --id ID of user to update
+ -n --nickname nickname of the user to update
+ -f --file file to import (Atom-only for now)
+
+END_OF_IMPORTTWITTERATOM_HELP;
+
+require_once INSTALLDIR.'/scripts/commandline.inc';
+require_once INSTALLDIR.'/extlib/htmLawed/htmLawed.php';
+
+function getUser()
+{
+ $user = null;
+
+ if (have_option('i', 'id')) {
+ $id = get_option_value('i', 'id');
+ $user = User::staticGet('id', $id);
+ if (empty($user)) {
+ throw new Exception("Can't find user with id '$id'.");
+ }
+ } else if (have_option('n', 'nickname')) {
+ $nickname = get_option_value('n', 'nickname');
+ $user = User::staticGet('nickname', $nickname);
+ if (empty($user)) {
+ throw new Exception("Can't find user with nickname '$nickname'");
+ }
+ } else {
+ show_help();
+ exit(1);
+ }
+
+ return $user;
+}
+
+function getAtomFeedDocument()
+{
+ $filename = get_option_value('f', 'file');
+
+ if (empty($filename)) {
+ show_help();
+ exit(1);
+ }
+
+ if (!file_exists($filename)) {
+ throw new Exception("No such file '$filename'.");
+ }
+
+ if (!is_file($filename)) {
+ throw new Exception("Not a regular file: '$filename'.");
+ }
+
+ if (!is_readable($filename)) {
+ throw new Exception("File '$filename' not readable.");
+ }
+
+ $xml = file_get_contents($filename);
+
+ $dom = DOMDocument::loadXML($xml);
+
+ if ($dom->documentElement->namespaceURI != Activity::ATOM ||
+ $dom->documentElement->localName != 'feed') {
+ throw new Exception("'$filename' is not an Atom feed.");
+ }
+
+ return $dom;
+}
+
+function importActivityStream($user, $doc)
+{
+ $feed = $doc->documentElement;
+
+ $entries = $feed->getElementsByTagNameNS(Activity::ATOM, 'entry');
+
+ for ($i = $entries->length - 1; $i >= 0; $i--) {
+ $entry = $entries->item($i);
+ $activity = new Activity($entry, $feed);
+ $object = $activity->object;
+ if (!have_option('q', 'quiet')) {
+ print $activity->content . "\n";
+ }
+ $html = getTweetHtml($object->link);
+
+ $config = array('safe' => 1,
+ 'deny_attribute' => 'class,rel,id,style,on*');
+
+ $html = htmLawed($html, $config);
+
+ $content = html_entity_decode(strip_tags($html));
+
+ $notice = Notice::saveNew($user->id,
+ $content,
+ 'importtwitter',
+ array('uri' => $object->id,
+ 'url' => $object->link,
+ 'rendered' => $html,
+ 'created' => common_sql_date($activity->time),
+ 'replies' => array(),
+ 'groups' => array()));
+ }
+}
+
+function getTweetHtml($url)
+{
+ try {
+ $client = new HTTPClient();
+ $response = $client->get($url);
+ } catch (HTTP_Request2_Exception $e) {
+ print "ERROR: HTTP response " . $e->getMessage() . "\n";
+ return false;
+ }
+
+ if (!$response->isOk()) {
+ print "ERROR: HTTP response " . $response->getCode() . "\n";
+ return false;
+ }
+
+ $body = $response->getBody();
+
+ return tweetHtmlFromBody($body);
+}
+
+function tweetHtmlFromBody($body)
+{
+ $doc = DOMDocument::loadHTML($body);
+ $xpath = new DOMXPath($doc);
+
+ $spans = $xpath->query('//span[@class="entry-content"]');
+
+ if ($spans->length == 0) {
+ print "ERROR: No content in tweet page.\n";
+ return '';
+ }
+
+ $span = $spans->item(0);
+
+ $children = $span->childNodes;
+
+ $text = '';
+
+ for ($i = 0; $i < $children->length; $i++) {
+ $child = $children->item($i);
+ if ($child instanceof DOMElement &&
+ $child->tagName == 'a' &&
+ !preg_match('#^https?://#', $child->getAttribute('href'))) {
+ $child->setAttribute('href', 'http://twitter.com' . $child->getAttribute('href'));
+ }
+ $text .= $doc->saveXML($child);
+ }
+
+ return $text;
+}
+
+try {
+
+ $doc = getAtomFeedDocument();
+ $user = getUser();
+
+ importActivityStream($user, $doc);
+
+} catch (Exception $e) {
+ print $e->getMessage()."\n";
+ exit(1);
+}
+