replace all tabs with four spaces

The PEAR coding standards decree: no tabs, but indent by four spaces.
I've done a global search-and-replace on all tabs, replacing them by
four spaces. This is a huge change, but it will go a long way to
getting us towards phpcs-compliance. And that means better code
readability, and that means more participation.

darcs-hash:20081223191907-84dde-21e8efe210e6d5d54e935a22d0cee5c7bbfc007d.gz
This commit is contained in:
Evan Prodromou
2008-12-23 14:19:07 -05:00
parent 17ece0777b
commit edbc0c665c
273 changed files with 53858 additions and 25794 deletions

View File

@@ -26,70 +26,70 @@ class Avatar extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
# We clean up the file, too
# We clean up the file, too
function delete() {
$filename = $this->filename;
if (parent::delete()) {
@unlink(common_avatar_path($filename));
}
}
function delete() {
$filename = $this->filename;
if (parent::delete()) {
@unlink(common_avatar_path($filename));
}
}
# Create and save scaled version of this avatar
# XXX: maybe break into different methods
# Create and save scaled version of this avatar
# XXX: maybe break into different methods
function scale($size) {
function scale($size) {
$image_s = imagecreatetruecolor($size, $size);
$image_a = $this->to_image();
$square = min($this->width, $this->height);
$image_s = imagecreatetruecolor($size, $size);
$image_a = $this->to_image();
$square = min($this->width, $this->height);
imagecolortransparent($image_s, imagecolorallocate($image_s, 0, 0, 0));
imagealphablending($image_s, false);
imagesavealpha($image_s, true);
imagecopyresampled($image_s, $image_a, 0, 0, 0, 0,
$size, $size, $square, $square);
imagecopyresampled($image_s, $image_a, 0, 0, 0, 0,
$size, $size, $square, $square);
$ext = ($this->mediattype == 'image/jpeg') ? ".jpeg" : ".png";
$ext = ($this->mediattype == 'image/jpeg') ? ".jpeg" : ".png";
$filename = common_avatar_filename($this->profile_id, $ext, $size, common_timestamp());
$filename = common_avatar_filename($this->profile_id, $ext, $size, common_timestamp());
if ($this->mediatype == 'image/jpeg') {
imagejpeg($image_s, common_avatar_path($filename));
} else {
imagepng($image_s, common_avatar_path($filename));
}
if ($this->mediatype == 'image/jpeg') {
imagejpeg($image_s, common_avatar_path($filename));
} else {
imagepng($image_s, common_avatar_path($filename));
}
$scaled = DB_DataObject::factory('avatar');
$scaled->profile_id = $this->profile_id;
$scaled->width = $size;
$scaled->height = $size;
$scaled->original = false;
$scaled->mediatype = ($this->mediattype == 'image/jpeg') ? 'image/jpeg' : 'image/png';
$scaled->filename = $filename;
$scaled->url = common_avatar_url($filename);
$scaled->created = DB_DataObject_Cast::dateTime(); # current time
$scaled = DB_DataObject::factory('avatar');
$scaled->profile_id = $this->profile_id;
$scaled->width = $size;
$scaled->height = $size;
$scaled->original = false;
$scaled->mediatype = ($this->mediattype == 'image/jpeg') ? 'image/jpeg' : 'image/png';
$scaled->filename = $filename;
$scaled->url = common_avatar_url($filename);
$scaled->created = DB_DataObject_Cast::dateTime(); # current time
if ($scaled->insert()) {
return $scaled;
} else {
return NULL;
}
}
if ($scaled->insert()) {
return $scaled;
} else {
return NULL;
}
}
function to_image() {
$filepath = common_avatar_path($this->filename);
if ($this->mediatype == 'image/gif') {
return imagecreatefromgif($filepath);
} else if ($this->mediatype == 'image/jpeg') {
return imagecreatefromjpeg($filepath);
} else if ($this->mediatype == 'image/png') {
return imagecreatefrompng($filepath);
} else {
return NULL;
}
}
function &pkeyGet($kv) {
return Memcached_DataObject::pkeyGet('Avatar', $kv);
}
function to_image() {
$filepath = common_avatar_path($this->filename);
if ($this->mediatype == 'image/gif') {
return imagecreatefromgif($filepath);
} else if ($this->mediatype == 'image/jpeg') {
return imagecreatefromjpeg($filepath);
} else if ($this->mediatype == 'image/png') {
return imagecreatefrompng($filepath);
} else {
return NULL;
}
}
function &pkeyGet($kv) {
return Memcached_DataObject::pkeyGet('Avatar', $kv);
}
}

View File

@@ -20,181 +20,181 @@
if (!defined('LACONICA')) { exit(1); }
class Channel {
function on($user) {
return false;
}
function on($user) {
return false;
}
function off($user) {
return false;
}
function off($user) {
return false;
}
function output($user, $text) {
return false;
}
function error($user, $text) {
return false;
}
function source() {
return NULL;
}
function output($user, $text) {
return false;
}
function error($user, $text) {
return false;
}
function source() {
return NULL;
}
}
class XMPPChannel extends Channel {
var $conn = NULL;
function source() {
return 'xmpp';
}
function __construct($conn) {
$this->conn = $conn;
}
function on($user) {
return $this->set_notify($user, 1);
}
function off($user) {
return $this->set_notify($user, 0);
}
var $conn = NULL;
function source() {
return 'xmpp';
}
function __construct($conn) {
$this->conn = $conn;
}
function on($user) {
return $this->set_notify($user, 1);
}
function off($user) {
return $this->set_notify($user, 0);
}
function output($user, $text) {
$text = '['.common_config('site', 'name') . '] ' . $text;
jabber_send_message($user->jabber, $text);
}
function error($user, $text) {
$text = '['.common_config('site', 'name') . '] ' . $text;
jabber_send_message($user->jabber, $text);
}
function set_notify(&$user, $notify) {
$orig = clone($user);
$user->jabbernotify = $notify;
$result = $user->update($orig);
if (!$result) {
$last_error = &PEAR::getStaticProperty('DB_DataObject','lastError');
common_log(LOG_ERR,
'Could not set notify flag to ' . $notify .
' for user ' . common_log_objstring($user) .
': ' . $last_error->message);
return false;
} else {
common_log(LOG_INFO,
'User ' . $user->nickname . ' set notify flag to ' . $notify);
return true;
}
}
function output($user, $text) {
$text = '['.common_config('site', 'name') . '] ' . $text;
jabber_send_message($user->jabber, $text);
}
function error($user, $text) {
$text = '['.common_config('site', 'name') . '] ' . $text;
jabber_send_message($user->jabber, $text);
}
function set_notify(&$user, $notify) {
$orig = clone($user);
$user->jabbernotify = $notify;
$result = $user->update($orig);
if (!$result) {
$last_error = &PEAR::getStaticProperty('DB_DataObject','lastError');
common_log(LOG_ERR,
'Could not set notify flag to ' . $notify .
' for user ' . common_log_objstring($user) .
': ' . $last_error->message);
return false;
} else {
common_log(LOG_INFO,
'User ' . $user->nickname . ' set notify flag to ' . $notify);
return true;
}
}
}
class WebChannel extends Channel {
function source() {
return 'web';
}
function on($user) {
return false;
}
function off($user) {
return false;
}
function source() {
return 'web';
}
function on($user) {
return false;
}
function off($user) {
return false;
}
function output($user, $text) {
# XXX: buffer all output and send it at the end
# XXX: even better, redirect to appropriate page
# depending on what command was run
common_show_header(_('Command results'));
common_element('p', NULL, $text);
common_show_footer();
}
function error($user, $text) {
common_user_error($text);
}
function output($user, $text) {
# XXX: buffer all output and send it at the end
# XXX: even better, redirect to appropriate page
# depending on what command was run
common_show_header(_('Command results'));
common_element('p', NULL, $text);
common_show_footer();
}
function error($user, $text) {
common_user_error($text);
}
}
class AjaxWebChannel extends WebChannel {
function output($user, $text) {
common_start_html('text/xml;charset=utf-8', true);
common_element_start('head');
common_element('title', null, _('Command results'));
common_element_end('head');
common_element_start('body');
common_element('p', array('id' => 'command_result'), $text);
common_element_end('body');
common_element_end('html');
}
function output($user, $text) {
common_start_html('text/xml;charset=utf-8', true);
common_element_start('head');
common_element('title', null, _('Command results'));
common_element_end('head');
common_element_start('body');
common_element('p', array('id' => 'command_result'), $text);
common_element_end('body');
common_element_end('html');
}
function error($user, $text) {
common_start_html('text/xml;charset=utf-8', true);
common_element_start('head');
common_element('title', null, _('Ajax Error'));
common_element_end('head');
common_element_start('body');
common_element('p', array('id' => 'error'), $text);
common_element_end('body');
common_element_end('html');
}
function error($user, $text) {
common_start_html('text/xml;charset=utf-8', true);
common_element_start('head');
common_element('title', null, _('Ajax Error'));
common_element_end('head');
common_element_start('body');
common_element('p', array('id' => 'error'), $text);
common_element_end('body');
common_element_end('html');
}
}
class MailChannel extends Channel {
var $addr = NULL;
var $addr = NULL;
function source() {
return 'mail';
}
function __construct($addr=NULL) {
$this->addr = $addr;
}
function on($user) {
return $this->set_notify($user, 1);
}
function off($user) {
return $this->set_notify($user, 0);
}
function source() {
return 'mail';
}
function __construct($addr=NULL) {
$this->addr = $addr;
}
function on($user) {
return $this->set_notify($user, 1);
}
function off($user) {
return $this->set_notify($user, 0);
}
function output($user, $text) {
function output($user, $text) {
$headers['From'] = $user->incomingemail;
$headers['To'] = $this->addr;
$headers['Subject'] = _('Command complete');
$headers['From'] = $user->incomingemail;
$headers['To'] = $this->addr;
$headers['Subject'] = _('Command complete');
return mail_send(array($this->addr), $headers, $text);
}
function error($user, $text) {
$headers['From'] = $user->incomingemail;
$headers['To'] = $this->addr;
$headers['Subject'] = _('Command failed');
return mail_send(array($this->addr), $headers, $text);
}
function error($user, $text) {
$headers['From'] = $user->incomingemail;
$headers['To'] = $this->addr;
$headers['Subject'] = _('Command failed');
return mail_send(array($this->addr), $headers, $text);
}
function set_notify($user, $value) {
$orig = clone($user);
$user->smsnotify = $value;
$result = $user->update($orig);
if (!$result) {
common_log_db_error($user, 'UPDATE', __FILE__);
return false;
}
return true;
}
return mail_send(array($this->addr), $headers, $text);
}
function set_notify($user, $value) {
$orig = clone($user);
$user->smsnotify = $value;
$result = $user->update($orig);
if (!$result) {
common_log_db_error($user, 'UPDATE', __FILE__);
return false;
}
return true;
}
}

View File

@@ -22,22 +22,22 @@ if (!defined('LACONICA')) { exit(1); }
require_once(INSTALLDIR.'/classes/Channel.php');
class Command {
var $user = NULL;
function __construct($user=NULL) {
$this->user = $user;
}
function execute($channel) {
return false;
}
var $user = NULL;
function __construct($user=NULL) {
$this->user = $user;
}
function execute($channel) {
return false;
}
}
class UnimplementedCommand extends Command {
function execute($channel) {
$channel->error($this->user, _("Sorry, this command is not yet implemented."));
}
function execute($channel) {
$channel->error($this->user, _("Sorry, this command is not yet implemented."));
}
}
class TrackingCommand extends UnimplementedCommand {
@@ -47,330 +47,330 @@ class TrackOffCommand extends UnimplementedCommand {
}
class TrackCommand extends UnimplementedCommand {
var $word = NULL;
function __construct($user, $word) {
parent::__construct($user);
$this->word = $word;
}
var $word = NULL;
function __construct($user, $word) {
parent::__construct($user);
$this->word = $word;
}
}
class UntrackCommand extends UnimplementedCommand {
var $word = NULL;
function __construct($user, $word) {
parent::__construct($user);
$this->word = $word;
}
var $word = NULL;
function __construct($user, $word) {
parent::__construct($user);
$this->word = $word;
}
}
class NudgeCommand extends UnimplementedCommand {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
}
class InviteCommand extends UnimplementedCommand {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
}
class StatsCommand extends Command {
function execute($channel) {
function execute($channel) {
$subs = new Subscription();
$subs->subscriber = $this->user->id;
$subs_count = (int) $subs->count() - 1;
$subs = new Subscription();
$subs->subscriber = $this->user->id;
$subs_count = (int) $subs->count() - 1;
$subbed = new Subscription();
$subbed->subscribed = $this->user->id;
$subbed_count = (int) $subbed->count() - 1;
$subbed = new Subscription();
$subbed->subscribed = $this->user->id;
$subbed_count = (int) $subbed->count() - 1;
$notices = new Notice();
$notices->profile_id = $this->user->id;
$notice_count = (int) $notices->count();
$channel->output($this->user, sprintf(_("Subscriptions: %1\$s\n".
"Subscribers: %2\$s\n".
"Notices: %3\$s"),
$subs_count,
$subbed_count,
$notice_count));
}
$notices = new Notice();
$notices->profile_id = $this->user->id;
$notice_count = (int) $notices->count();
$channel->output($this->user, sprintf(_("Subscriptions: %1\$s\n".
"Subscribers: %2\$s\n".
"Notices: %3\$s"),
$subs_count,
$subbed_count,
$notice_count));
}
}
class FavCommand extends Command {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
$recipient =
common_relative_profile($this->user, common_canonical_nickname($this->other));
if (!$recipient) {
$channel->error($this->user, _('No such user.'));
return;
}
$notice = $recipient->getCurrentNotice();
if (!$notice) {
$channel->error($this->user, _('User has no last notice'));
return;
}
$fave = Fave::addNew($this->user, $notice);
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
$recipient =
common_relative_profile($this->user, common_canonical_nickname($this->other));
if (!$recipient) {
$channel->error($this->user, _('No such user.'));
return;
}
$notice = $recipient->getCurrentNotice();
if (!$notice) {
$channel->error($this->user, _('User has no last notice'));
return;
}
$fave = Fave::addNew($this->user, $notice);
if (!$fave) {
$channel->error($this->user, _('Could not create favorite.'));
return;
}
if (!$fave) {
$channel->error($this->user, _('Could not create favorite.'));
return;
}
$other = User::staticGet('id', $recipient->id);
if ($other && $other->id != $user->id) {
if ($other->email && $other->emailnotifyfav) {
mail_notify_fave($other, $this->user, $notice);
}
}
$this->user->blowFavesCache();
$channel->output($this->user, _('Notice marked as fave.'));
}
$other = User::staticGet('id', $recipient->id);
if ($other && $other->id != $user->id) {
if ($other->email && $other->emailnotifyfav) {
mail_notify_fave($other, $this->user, $notice);
}
}
$this->user->blowFavesCache();
$channel->output($this->user, _('Notice marked as fave.'));
}
}
class WhoisCommand extends Command {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
$recipient =
common_relative_profile($this->user, common_canonical_nickname($this->other));
if (!$recipient) {
$channel->error($this->user, _('No such user.'));
return;
}
$whois = sprintf(_("%1\$s (%2\$s)"), $recipient->nickname,
$recipient->profileurl);
if ($recipient->fullname) {
$whois .= "\n" . sprintf(_('Fullname: %s'), $recipient->fullname);
}
if ($recipient->location) {
$whois .= "\n" . sprintf(_('Location: %s'), $recipient->location);
}
if ($recipient->homepage) {
$whois .= "\n" . sprintf(_('Homepage: %s'), $recipient->homepage);
}
if ($recipient->bio) {
$whois .= "\n" . sprintf(_('About: %s'), $recipient->bio);
}
$channel->output($this->user, $whois);
}
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
$recipient =
common_relative_profile($this->user, common_canonical_nickname($this->other));
if (!$recipient) {
$channel->error($this->user, _('No such user.'));
return;
}
$whois = sprintf(_("%1\$s (%2\$s)"), $recipient->nickname,
$recipient->profileurl);
if ($recipient->fullname) {
$whois .= "\n" . sprintf(_('Fullname: %s'), $recipient->fullname);
}
if ($recipient->location) {
$whois .= "\n" . sprintf(_('Location: %s'), $recipient->location);
}
if ($recipient->homepage) {
$whois .= "\n" . sprintf(_('Homepage: %s'), $recipient->homepage);
}
if ($recipient->bio) {
$whois .= "\n" . sprintf(_('About: %s'), $recipient->bio);
}
$channel->output($this->user, $whois);
}
}
class MessageCommand extends Command {
var $other = NULL;
var $text = NULL;
function __construct($user, $other, $text) {
parent::__construct($user);
$this->other = $other;
$this->text = $text;
}
function execute($channel) {
$other = User::staticGet('nickname', common_canonical_nickname($this->other));
$len = mb_strlen($this->text);
if ($len == 0) {
$channel->error($this->user, _('No content!'));
return;
} else if ($len > 140) {
$content = common_shorten_links($content);
if (mb_strlen($content) > 140) {
$channel->error($this->user, sprintf(_('Message too long - maximum is 140 characters, you sent %d'), $len));
return;
}
}
if (!$other) {
$channel->error($this->user, _('No such user.'));
return;
} else if (!$this->user->mutuallySubscribed($other)) {
$channel->error($this->user, _('You can\'t send a message to this user.'));
return;
} else if ($this->user->id == $other->id) {
$channel->error($this->user, _('Don\'t send a message to yourself; just say it to yourself quietly instead.'));
return;
}
$message = Message::saveNew($this->user->id, $other->id, $this->text, $channel->source());
if ($message) {
$channel->output($this->user, sprintf(_('Direct message to %s sent'), $this->other));
} else {
$channel->error($this->user, _('Error sending direct message.'));
}
}
var $other = NULL;
var $text = NULL;
function __construct($user, $other, $text) {
parent::__construct($user);
$this->other = $other;
$this->text = $text;
}
function execute($channel) {
$other = User::staticGet('nickname', common_canonical_nickname($this->other));
$len = mb_strlen($this->text);
if ($len == 0) {
$channel->error($this->user, _('No content!'));
return;
} else if ($len > 140) {
$content = common_shorten_links($content);
if (mb_strlen($content) > 140) {
$channel->error($this->user, sprintf(_('Message too long - maximum is 140 characters, you sent %d'), $len));
return;
}
}
if (!$other) {
$channel->error($this->user, _('No such user.'));
return;
} else if (!$this->user->mutuallySubscribed($other)) {
$channel->error($this->user, _('You can\'t send a message to this user.'));
return;
} else if ($this->user->id == $other->id) {
$channel->error($this->user, _('Don\'t send a message to yourself; just say it to yourself quietly instead.'));
return;
}
$message = Message::saveNew($this->user->id, $other->id, $this->text, $channel->source());
if ($message) {
$channel->output($this->user, sprintf(_('Direct message to %s sent'), $this->other));
} else {
$channel->error($this->user, _('Error sending direct message.'));
}
}
}
class GetCommand extends Command {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
$target_nickname = common_canonical_nickname($this->other);
$target =
common_relative_profile($this->user, $target_nickname);
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
$target_nickname = common_canonical_nickname($this->other);
$target =
common_relative_profile($this->user, $target_nickname);
if (!$target) {
$channel->error($this->user, _('No such user.'));
return;
}
$notice = $target->getCurrentNotice();
if (!$notice) {
$channel->error($this->user, _('User has no last notice'));
return;
}
$notice_content = $notice->content;
$channel->output($this->user, $target_nickname . ": " . $notice_content);
}
if (!$target) {
$channel->error($this->user, _('No such user.'));
return;
}
$notice = $target->getCurrentNotice();
if (!$notice) {
$channel->error($this->user, _('User has no last notice'));
return;
}
$notice_content = $notice->content;
$channel->output($this->user, $target_nickname . ": " . $notice_content);
}
}
class SubCommand extends Command {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if (!$this->other) {
$channel->error($this->user, _('Specify the name of the user to subscribe to'));
return;
}
$result = subs_subscribe_user($this->user, $this->other);
if ($result == 'true') {
$channel->output($this->user, sprintf(_('Subscribed to %s'), $this->other));
} else {
$channel->error($this->user, $result);
}
}
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if (!$this->other) {
$channel->error($this->user, _('Specify the name of the user to subscribe to'));
return;
}
$result = subs_subscribe_user($this->user, $this->other);
if ($result == 'true') {
$channel->output($this->user, sprintf(_('Subscribed to %s'), $this->other));
} else {
$channel->error($this->user, $result);
}
}
}
class UnsubCommand extends Command {
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
var $other = NULL;
function __construct($user, $other) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if(!$this->other) {
$channel->error($this->user, _('Specify the name of the user to unsubscribe from'));
return;
}
$result=subs_unsubscribe_user($this->user, $this->other);
if ($result) {
$channel->output($this->user, sprintf(_('Unsubscribed from %s'), $this->other));
} else {
$channel->error($this->user, $result);
}
}
function execute($channel) {
if(!$this->other) {
$channel->error($this->user, _('Specify the name of the user to unsubscribe from'));
return;
}
$result=subs_unsubscribe_user($this->user, $this->other);
if ($result) {
$channel->output($this->user, sprintf(_('Unsubscribed from %s'), $this->other));
} else {
$channel->error($this->user, $result);
}
}
}
class OffCommand extends Command {
var $other = NULL;
function __construct($user, $other=NULL) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if ($other) {
$channel->error($this->user, _("Command not yet implemented."));
} else {
if ($channel->off($this->user)) {
$channel->output($this->user, _('Notification off.'));
} else {
$channel->error($this->user, _('Can\'t turn off notification.'));
}
}
}
var $other = NULL;
function __construct($user, $other=NULL) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if ($other) {
$channel->error($this->user, _("Command not yet implemented."));
} else {
if ($channel->off($this->user)) {
$channel->output($this->user, _('Notification off.'));
} else {
$channel->error($this->user, _('Can\'t turn off notification.'));
}
}
}
}
class OnCommand extends Command {
var $other = NULL;
function __construct($user, $other=NULL) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if ($other) {
$channel->error($this->user, _("Command not yet implemented."));
} else {
if ($channel->on($this->user)) {
$channel->output($this->user, _('Notification on.'));
} else {
$channel->error($this->user, _('Can\'t turn on notification.'));
}
}
}
var $other = NULL;
function __construct($user, $other=NULL) {
parent::__construct($user);
$this->other = $other;
}
function execute($channel) {
if ($other) {
$channel->error($this->user, _("Command not yet implemented."));
} else {
if ($channel->on($this->user)) {
$channel->output($this->user, _('Notification on.'));
} else {
$channel->error($this->user, _('Can\'t turn on notification.'));
}
}
}
}
class HelpCommand extends Command {
function execute($channel) {
$channel->output($this->user,
_("Commands:\n".
"on - turn on notifications\n".
"off - turn off notifications\n".
"help - show this help\n".
"follow <nickname> - subscribe to user\n".
"leave <nickname> - unsubscribe from user\n".
"d <nickname> <text> - direct message to user\n".
"get <nickname> - get last notice from user\n".
"whois <nickname> - get profile info on user\n".
"fav <nickname> - add user's last notice as a 'fave'\n".
"stats - get your stats\n".
"stop - same as 'off'\n".
"quit - same as 'off'\n".
"sub <nickname> - same as 'follow'\n".
"unsub <nickname> - same as 'leave'\n".
"last <nickname> - same as 'get'\n".
"on <nickname> - not yet implemented.\n".
"off <nickname> - not yet implemented.\n".
"nudge <nickname> - not yet implemented.\n".
"invite <phone number> - not yet implemented.\n".
"track <word> - not yet implemented.\n".
"untrack <word> - not yet implemented.\n".
"track off - not yet implemented.\n".
"untrack all - not yet implemented.\n".
"tracks - not yet implemented.\n".
"tracking - not yet implemented.\n"));
}
function execute($channel) {
$channel->output($this->user,
_("Commands:\n".
"on - turn on notifications\n".
"off - turn off notifications\n".
"help - show this help\n".
"follow <nickname> - subscribe to user\n".
"leave <nickname> - unsubscribe from user\n".
"d <nickname> <text> - direct message to user\n".
"get <nickname> - get last notice from user\n".
"whois <nickname> - get profile info on user\n".
"fav <nickname> - add user's last notice as a 'fave'\n".
"stats - get your stats\n".
"stop - same as 'off'\n".
"quit - same as 'off'\n".
"sub <nickname> - same as 'follow'\n".
"unsub <nickname> - same as 'leave'\n".
"last <nickname> - same as 'get'\n".
"on <nickname> - not yet implemented.\n".
"off <nickname> - not yet implemented.\n".
"nudge <nickname> - not yet implemented.\n".
"invite <phone number> - not yet implemented.\n".
"track <word> - not yet implemented.\n".
"untrack <word> - not yet implemented.\n".
"track off - not yet implemented.\n".
"untrack all - not yet implemented.\n".
"tracks - not yet implemented.\n".
"tracking - not yet implemented.\n"));
}
}

View File

@@ -22,174 +22,174 @@ if (!defined('LACONICA')) { exit(1); }
require_once(INSTALLDIR.'/classes/Command.php');
class CommandInterpreter {
function handle_command($user, $text) {
# XXX: localise
function handle_command($user, $text) {
# XXX: localise
$text = preg_replace('/\s+/', ' ', trim($text));
list($cmd, $arg) = explode(' ', $text, 2);
$text = preg_replace('/\s+/', ' ', trim($text));
list($cmd, $arg) = explode(' ', $text, 2);
# We try to support all the same commands as Twitter, see
# http://getsatisfaction.com/twitter/topics/what_are_the_twitter_commands
# There are a few compatibility commands from earlier versions of
# Laconica
switch(strtolower($cmd)) {
case 'help':
if ($arg) {
return NULL;
}
return new HelpCommand($user);
case 'on':
if ($arg) {
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new OnCommand($user, $other);
}
} else {
return new OnCommand($user);
}
case 'off':
if ($arg) {
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new OffCommand($user, $other);
}
} else {
return new OffCommand($user);
}
case 'stop':
case 'quit':
if ($arg) {
return NULL;
} else {
return new OffCommand($user);
}
case 'follow':
case 'sub':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new SubCommand($user, $other);
}
case 'leave':
case 'unsub':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new UnsubCommand($user, $other);
}
case 'get':
case 'last':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new GetCommand($user, $other);
}
case 'd':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if (!$extra) {
return NULL;
} else {
return new MessageCommand($user, $other, $extra);
}
case 'whois':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new WhoisCommand($user, $other);
}
case 'fav':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new FavCommand($user, $other);
}
case 'nudge':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new NudgeCommand($user, $other);
}
case 'stats':
if ($arg) {
return NULL;
}
return new StatsCommand($user);
case 'invite':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new InviteCommand($user, $other);
}
case 'track':
if (!$arg) {
return NULL;
}
list($word, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else if ($word == 'off') {
return new TrackOffCommand($user);
} else {
return new TrackCommand($user, $word);
}
case 'untrack':
if (!$arg) {
return NULL;
}
list($word, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else if ($word == 'all') {
return new TrackOffCommand($user);
} else {
return new UntrackCommand($user, $word);
}
case 'tracks':
case 'tracking':
if ($arg) {
return NULL;
}
return new TrackingCommand($user);
default:
return false;
}
}
# We try to support all the same commands as Twitter, see
# http://getsatisfaction.com/twitter/topics/what_are_the_twitter_commands
# There are a few compatibility commands from earlier versions of
# Laconica
switch(strtolower($cmd)) {
case 'help':
if ($arg) {
return NULL;
}
return new HelpCommand($user);
case 'on':
if ($arg) {
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new OnCommand($user, $other);
}
} else {
return new OnCommand($user);
}
case 'off':
if ($arg) {
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new OffCommand($user, $other);
}
} else {
return new OffCommand($user);
}
case 'stop':
case 'quit':
if ($arg) {
return NULL;
} else {
return new OffCommand($user);
}
case 'follow':
case 'sub':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new SubCommand($user, $other);
}
case 'leave':
case 'unsub':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new UnsubCommand($user, $other);
}
case 'get':
case 'last':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new GetCommand($user, $other);
}
case 'd':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if (!$extra) {
return NULL;
} else {
return new MessageCommand($user, $other, $extra);
}
case 'whois':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new WhoisCommand($user, $other);
}
case 'fav':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new FavCommand($user, $other);
}
case 'nudge':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new NudgeCommand($user, $other);
}
case 'stats':
if ($arg) {
return NULL;
}
return new StatsCommand($user);
case 'invite':
if (!$arg) {
return NULL;
}
list($other, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else {
return new InviteCommand($user, $other);
}
case 'track':
if (!$arg) {
return NULL;
}
list($word, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else if ($word == 'off') {
return new TrackOffCommand($user);
} else {
return new TrackCommand($user, $word);
}
case 'untrack':
if (!$arg) {
return NULL;
}
list($word, $extra) = explode(' ', $arg, 2);
if ($extra) {
return NULL;
} else if ($word == 'all') {
return new TrackOffCommand($user);
} else {
return new UntrackCommand($user, $word);
}
case 'tracks':
case 'tracking':
if ($arg) {
return NULL;
}
return new TrackingCommand($user);
default:
return false;
}
}
}

View File

@@ -20,18 +20,18 @@ class Fave extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
static function addNew($user, $notice) {
$fave = new Fave();
$fave->user_id = $user->id;
$fave->notice_id = $notice->id;
if (!$fave->insert()) {
common_log_db_error($fave, 'INSERT', __FILE__);
return false;
}
return $fave;
}
function &pkeyGet($kv) {
return Memcached_DataObject::pkeyGet('Fave', $kv);
}
static function addNew($user, $notice) {
$fave = new Fave();
$fave->user_id = $user->id;
$fave->notice_id = $notice->id;
if (!$fave->insert()) {
common_log_db_error($fave, 'INSERT', __FILE__);
return false;
}
return $fave;
}
function &pkeyGet($kv) {
return Memcached_DataObject::pkeyGet('Fave', $kv);
}
}

View File

@@ -26,51 +26,51 @@ class Foreign_link extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
// XXX: This only returns a 1->1 single obj mapping. Change? Or make
// a getForeignUsers() that returns more than one? --Zach
static function getByUserID($user_id, $service) {
$flink = new Foreign_link();
$flink->service = $service;
$flink->user_id = $user_id;
$flink->limit(1);
// XXX: This only returns a 1->1 single obj mapping. Change? Or make
// a getForeignUsers() that returns more than one? --Zach
static function getByUserID($user_id, $service) {
$flink = new Foreign_link();
$flink->service = $service;
$flink->user_id = $user_id;
$flink->limit(1);
if ($flink->find(TRUE)) {
return $flink;
}
if ($flink->find(TRUE)) {
return $flink;
}
return NULL;
}
static function getByForeignID($foreign_id, $service) {
$flink = new Foreign_link();
$flink->service = $service;
$flink->foreign_id = $foreign_id;
$flink->limit(1);
return NULL;
}
static function getByForeignID($foreign_id, $service) {
$flink = new Foreign_link();
$flink->service = $service;
$flink->foreign_id = $foreign_id;
$flink->limit(1);
if ($flink->find(TRUE)) {
return $flink;
}
if ($flink->find(TRUE)) {
return $flink;
}
return NULL;
}
# Convenience methods
function getForeignUser() {
$fuser = new Foreign_user();
$fuser->service = $this->service;
$fuser->id = $this->foreign_id;
$fuser->limit(1);
if ($fuser->find(TRUE)) {
return $fuser;
}
return NULL;
}
function getUser() {
return User::staticGet($this->user_id);
}
return NULL;
}
# Convenience methods
function getForeignUser() {
$fuser = new Foreign_user();
$fuser->service = $this->service;
$fuser->id = $this->foreign_id;
$fuser->limit(1);
if ($fuser->find(TRUE)) {
return $fuser;
}
return NULL;
}
function getUser() {
return User::staticGet($this->user_id);
}
}

View File

@@ -22,49 +22,49 @@ class Foreign_user extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
// XXX: This only returns a 1->1 single obj mapping. Change? Or make
// a getForeignUsers() that returns more than one? --Zach
static function getForeignUser($id, $service) {
$fuser = new Foreign_user();
$fuser->whereAdd("service = $service");
$fuser->whereAdd("id = $id");
$fuser->limit(1);
if ($fuser->find()) {
$fuser->fetch();
return $fuser;
}
return NULL;
}
function updateKeys(&$orig) {
$parts = array();
foreach (array('id', 'service', 'uri', 'nickname') as $k) {
if (strcmp($this->$k, $orig->$k) != 0) {
$parts[] = $k . ' = ' . $this->_quote($this->$k);
}
}
if (count($parts) == 0) {
# No changes
return true;
}
$toupdate = implode(', ', $parts);
// XXX: This only returns a 1->1 single obj mapping. Change? Or make
// a getForeignUsers() that returns more than one? --Zach
static function getForeignUser($id, $service) {
$fuser = new Foreign_user();
$fuser->whereAdd("service = $service");
$fuser->whereAdd("id = $id");
$fuser->limit(1);
if ($fuser->find()) {
$fuser->fetch();
return $fuser;
}
return NULL;
}
function updateKeys(&$orig) {
$parts = array();
foreach (array('id', 'service', 'uri', 'nickname') as $k) {
if (strcmp($this->$k, $orig->$k) != 0) {
$parts[] = $k . ' = ' . $this->_quote($this->$k);
}
}
if (count($parts) == 0) {
# No changes
return true;
}
$toupdate = implode(', ', $parts);
$table = $this->tableName();
if(common_config('db','quote_identifiers')) {
$table = '"' . $table . '"';
}
$qry = 'UPDATE ' . $table . ' SET ' . $toupdate .
' WHERE id = ' . $this->id;
$orig->decache();
$result = $this->query($qry);
if ($result) {
$this->encache();
}
return $result;
}
$table = $this->tableName();
if(common_config('db','quote_identifiers')) {
$table = '"' . $table . '"';
}
$qry = 'UPDATE ' . $table . ' SET ' . $toupdate .
' WHERE id = ' . $this->id;
$orig->decache();
$result = $this->query($qry);
if ($result) {
$this->encache();
}
return $result;
}
}

View File

@@ -24,151 +24,151 @@ require_once INSTALLDIR.'/classes/Memcached_DataObject.php';
class Memcached_DataObject extends DB_DataObject
{
function &staticGet($cls, $k, $v=NULL) {
if (is_null($v)) {
$v = $k;
# XXX: HACK!
$i = new $cls;
$keys = $i->keys();
$k = $keys[0];
unset($i);
}
$i = Memcached_DataObject::getcached($cls, $k, $v);
if ($i) {
return $i;
} else {
$i = DB_DataObject::staticGet($cls, $k, $v);
if ($i) {
$i->encache();
}
return $i;
}
}
function &pkeyGet($cls, $kv) {
$i = Memcached_DataObject::multicache($cls, $kv);
if ($i) {
return $i;
} else {
$i = new $cls();
foreach ($kv as $k => $v) {
$i->$k = $v;
}
if ($i->find(true)) {
$i->encache();
} else {
$i = NULL;
}
if (is_null($v)) {
$v = $k;
# XXX: HACK!
$i = new $cls;
$keys = $i->keys();
$k = $keys[0];
unset($i);
}
$i = Memcached_DataObject::getcached($cls, $k, $v);
if ($i) {
return $i;
}
}
} else {
$i = DB_DataObject::staticGet($cls, $k, $v);
if ($i) {
$i->encache();
}
return $i;
}
}
function insert() {
$result = parent::insert();
return $result;
}
function update($orig=NULL) {
if (is_object($orig) && $orig instanceof Memcached_DataObject) {
$orig->decache(); # might be different keys
}
$result = parent::update($orig);
if ($result) {
$this->encache();
}
return $result;
}
function delete() {
$this->decache(); # while we still have the values!
return parent::delete();
}
static function memcache() {
return common_memcache();
}
static function cacheKey($cls, $k, $v) {
return common_cache_key(strtolower($cls).':'.$k.':'.$v);
}
static function getcached($cls, $k, $v) {
$c = Memcached_DataObject::memcache();
if (!$c) {
return false;
} else {
return $c->get(Memcached_DataObject::cacheKey($cls, $k, $v));
}
}
function &pkeyGet($cls, $kv) {
$i = Memcached_DataObject::multicache($cls, $kv);
if ($i) {
return $i;
} else {
$i = new $cls();
foreach ($kv as $k => $v) {
$i->$k = $v;
}
if ($i->find(true)) {
$i->encache();
} else {
$i = NULL;
}
return $i;
}
}
function keyTypes() {
global $_DB_DATAOBJECT;
function insert() {
$result = parent::insert();
return $result;
}
function update($orig=NULL) {
if (is_object($orig) && $orig instanceof Memcached_DataObject) {
$orig->decache(); # might be different keys
}
$result = parent::update($orig);
if ($result) {
$this->encache();
}
return $result;
}
function delete() {
$this->decache(); # while we still have the values!
return parent::delete();
}
static function memcache() {
return common_memcache();
}
static function cacheKey($cls, $k, $v) {
return common_cache_key(strtolower($cls).':'.$k.':'.$v);
}
static function getcached($cls, $k, $v) {
$c = Memcached_DataObject::memcache();
if (!$c) {
return false;
} else {
return $c->get(Memcached_DataObject::cacheKey($cls, $k, $v));
}
}
function keyTypes() {
global $_DB_DATAOBJECT;
if (!isset($_DB_DATAOBJECT['INI'][$this->_database][$this->__table."__keys"])) {
$this->databaseStructure();
$this->databaseStructure();
}
return $_DB_DATAOBJECT['INI'][$this->_database][$this->__table."__keys"];
}
function encache() {
$c = $this->memcache();
if (!$c) {
return false;
} else {
$pkey = array();
$pval = array();
$types = $this->keyTypes();
ksort($types);
foreach ($types as $key => $type) {
if ($type == 'K') {
$pkey[] = $key;
$pval[] = $this->$key;
} else {
$c->set($this->cacheKey($this->tableName(), $key, $this->$key), $this);
}
}
# XXX: should work for both compound and scalar pkeys
$pvals = implode(',', $pval);
$pkeys = implode(',', $pkey);
$c->set($this->cacheKey($this->tableName(), $pkeys, $pvals), $this);
}
}
function decache() {
$c = $this->memcache();
if (!$c) {
return false;
} else {
$pkey = array();
$pval = array();
$types = $this->keyTypes();
ksort($types);
foreach ($types as $key => $type) {
if ($type == 'K') {
$pkey[] = $key;
$pval[] = $this->$key;
} else {
$c->delete($this->cacheKey($this->tableName(), $key, $this->$key));
}
}
# should work for both compound and scalar pkeys
# XXX: comma works for now but may not be safe separator for future keys
$pvals = implode(',', $pval);
$pkeys = implode(',', $pkey);
$c->delete($this->cacheKey($this->tableName(), $pkeys, $pvals));
}
}
return $_DB_DATAOBJECT['INI'][$this->_database][$this->__table."__keys"];
}
function encache() {
$c = $this->memcache();
if (!$c) {
return false;
} else {
$pkey = array();
$pval = array();
$types = $this->keyTypes();
ksort($types);
foreach ($types as $key => $type) {
if ($type == 'K') {
$pkey[] = $key;
$pval[] = $this->$key;
} else {
$c->set($this->cacheKey($this->tableName(), $key, $this->$key), $this);
}
}
# XXX: should work for both compound and scalar pkeys
$pvals = implode(',', $pval);
$pkeys = implode(',', $pkey);
$c->set($this->cacheKey($this->tableName(), $pkeys, $pvals), $this);
}
}
function decache() {
$c = $this->memcache();
if (!$c) {
return false;
} else {
$pkey = array();
$pval = array();
$types = $this->keyTypes();
ksort($types);
foreach ($types as $key => $type) {
if ($type == 'K') {
$pkey[] = $key;
$pval[] = $this->$key;
} else {
$c->delete($this->cacheKey($this->tableName(), $key, $this->$key));
}
}
# should work for both compound and scalar pkeys
# XXX: comma works for now but may not be safe separator for future keys
$pvals = implode(',', $pval);
$pkeys = implode(',', $pkey);
$c->delete($this->cacheKey($this->tableName(), $pkeys, $pvals));
}
}
function multicache($cls, $kv) {
ksort($kv);
$c = Memcached_DataObject::memcache();
if (!$c) {
return false;
} else {
$pkeys = implode(',', array_keys($kv));
$pvals = implode(',', array_values($kv));
return $c->get(Memcached_DataObject::cacheKey($cls, $pkeys, $pvals));
}
}
function multicache($cls, $kv) {
ksort($kv);
$c = Memcached_DataObject::memcache();
if (!$c) {
return false;
} else {
$pkeys = implode(',', array_keys($kv));
$pvals = implode(',', array_values($kv));
return $c->get(Memcached_DataObject::cacheKey($cls, $pkeys, $pvals));
}
}
function getSearchEngine($table) {
require_once INSTALLDIR.'/lib/search_engines.php';

View File

@@ -26,43 +26,43 @@ class Message extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
function getFrom() {
return Profile::staticGet('id', $this->from_profile);
}
function getTo() {
return Profile::staticGet('id', $this->to_profile);
}
static function saveNew($from, $to, $content, $source) {
$msg = new Message();
$msg->from_profile = $from;
$msg->to_profile = $to;
$msg->content = common_shorten_links($content);
$msg->rendered = common_render_text($content);
$msg->created = common_sql_now();
$msg->source = $source;
$result = $msg->insert();
if (!$result) {
common_log_db_error($msg, 'INSERT', __FILE__);
return _('Could not insert message.');
}
$orig = clone($msg);
$msg->uri = common_local_url('showmessage', array('message' => $msg->id));
$result = $msg->update($orig);
if (!$result) {
common_log_db_error($msg, 'UPDATE', __FILE__);
return _('Could not update message with new URI.');
}
return $msg;
}
function getFrom() {
return Profile::staticGet('id', $this->from_profile);
}
function getTo() {
return Profile::staticGet('id', $this->to_profile);
}
static function saveNew($from, $to, $content, $source) {
$msg = new Message();
$msg->from_profile = $from;
$msg->to_profile = $to;
$msg->content = common_shorten_links($content);
$msg->rendered = common_render_text($content);
$msg->created = common_sql_now();
$msg->source = $source;
$result = $msg->insert();
if (!$result) {
common_log_db_error($msg, 'INSERT', __FILE__);
return _('Could not insert message.');
}
$orig = clone($msg);
$msg->uri = common_local_url('showmessage', array('message' => $msg->id));
$result = $msg->update($orig);
if (!$result) {
common_log_db_error($msg, 'UPDATE', __FILE__);
return _('Could not update message with new URI.');
}
return $msg;
}
}

View File

@@ -10,11 +10,11 @@
*
* 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
* 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/>.
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
if (!defined('LACONICA')) { exit(1); }
@@ -31,69 +31,69 @@ define('NOTICE_CACHE_WINDOW', 61);
class Notice extends Memcached_DataObject
{
###START_AUTOCODE
/* the code below is auto generated do not remove the above tag */
###START_AUTOCODE
/* the code below is auto generated do not remove the above tag */
public $__table = 'notice'; // table name
public $id; // int(4) primary_key not_null
public $profile_id; // int(4) not_null
public $uri; // varchar(255) unique_key
public $content; // varchar(140)
public $rendered; // text()
public $url; // varchar(255)
public $created; // datetime() not_null
public $modified; // timestamp() not_null default_CURRENT_TIMESTAMP
public $reply_to; // int(4)
public $is_local; // tinyint(1)
public $source; // varchar(32)
public $__table = 'notice'; // table name
public $id; // int(4) primary_key not_null
public $profile_id; // int(4) not_null
public $uri; // varchar(255) unique_key
public $content; // varchar(140)
public $rendered; // text()
public $url; // varchar(255)
public $created; // datetime() not_null
public $modified; // timestamp() not_null default_CURRENT_TIMESTAMP
public $reply_to; // int(4)
public $is_local; // tinyint(1)
public $source; // varchar(32)
/* Static get */
function staticGet($k,$v=NULL) { return Memcached_DataObject::staticGet('Notice',$k,$v); }
/* Static get */
function staticGet($k,$v=NULL) { return Memcached_DataObject::staticGet('Notice',$k,$v); }
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
function getProfile() {
return Profile::staticGet('id', $this->profile_id);
}
function getProfile() {
return Profile::staticGet('id', $this->profile_id);
}
function delete() {
$this->blowCaches(true);
$this->blowFavesCache(true);
$this->blowInboxes();
return parent::delete();
}
function delete() {
$this->blowCaches(true);
$this->blowFavesCache(true);
$this->blowInboxes();
return parent::delete();
}
function saveTags() {
/* extract all #hastags */
$count = preg_match_all('/(?:^|\s)#([A-Za-z0-9_\-\.]{1,64})/', strtolower($this->content), $match);
if (!$count) {
return true;
}
function saveTags() {
/* extract all #hastags */
$count = preg_match_all('/(?:^|\s)#([A-Za-z0-9_\-\.]{1,64})/', strtolower($this->content), $match);
if (!$count) {
return true;
}
/* elide characters we don't want in the tag */
$match[1] = str_replace(array('-', '_', '.'), '', $match[1]);
/* elide characters we don't want in the tag */
$match[1] = str_replace(array('-', '_', '.'), '', $match[1]);
/* Add them to the database */
foreach(array_unique($match[1]) as $hashtag) {
$tag = DB_DataObject::factory('Notice_tag');
$tag->notice_id = $this->id;
$tag->tag = $hashtag;
$tag->created = $this->created;
$id = $tag->insert();
if (!$id) {
$last_error = PEAR::getStaticProperty('DB_DataObject','lastError');
common_log(LOG_ERR, 'DB error inserting hashtag: ' . $last_error->message);
common_server_error(sprintf(_('DB error inserting hashtag: %s'), $last_error->message));
return;
}
}
return true;
}
/* Add them to the database */
foreach(array_unique($match[1]) as $hashtag) {
$tag = DB_DataObject::factory('Notice_tag');
$tag->notice_id = $this->id;
$tag->tag = $hashtag;
$tag->created = $this->created;
$id = $tag->insert();
if (!$id) {
$last_error = PEAR::getStaticProperty('DB_DataObject','lastError');
common_log(LOG_ERR, 'DB error inserting hashtag: ' . $last_error->message);
common_server_error(sprintf(_('DB error inserting hashtag: %s'), $last_error->message));
return;
}
}
return true;
}
static function saveNew($profile_id, $content, $source=NULL, $is_local=1, $reply_to=NULL, $uri=NULL) {
static function saveNew($profile_id, $content, $source=NULL, $is_local=1, $reply_to=NULL, $uri=NULL) {
$profile = Profile::staticGet($profile_id);
$profile = Profile::staticGet($profile_id);
if (!$profile) {
common_log(LOG_ERR, 'Problem saving notice. Unknown user.');
@@ -102,69 +102,69 @@ class Notice extends Memcached_DataObject
if (common_config('throttle', 'enabled') && !Notice::checkEditThrottle($profile_id)) {
common_log(LOG_WARNING, 'Excessive posting by profile #' . $profile_id . '; throttled.');
return _('Too many notices too fast; take a breather and post again in a few minutes.');
return _('Too many notices too fast; take a breather and post again in a few minutes.');
}
$banned = common_config('profile', 'banned');
$banned = common_config('profile', 'banned');
if ( in_array($profile_id, $banned) || in_array($profile->nickname, $banned)) {
common_log(LOG_WARNING, "Attempted post from banned user: $profile->nickname (user id = $profile_id).");
if ( in_array($profile_id, $banned) || in_array($profile->nickname, $banned)) {
common_log(LOG_WARNING, "Attempted post from banned user: $profile->nickname (user id = $profile_id).");
return _('You are banned from posting notices on this site.');
}
}
$notice = new Notice();
$notice->profile_id = $profile_id;
$notice = new Notice();
$notice->profile_id = $profile_id;
$blacklist = common_config('public', 'blacklist');
$blacklist = common_config('public', 'blacklist');
# Blacklisted are non-false, but not 1, either
# Blacklisted are non-false, but not 1, either
if ($blacklist && in_array($profile_id, $blacklist)) {
$notice->is_local = -1;
} else {
$notice->is_local = $is_local;
}
if ($blacklist && in_array($profile_id, $blacklist)) {
$notice->is_local = -1;
} else {
$notice->is_local = $is_local;
}
$notice->reply_to = $reply_to;
$notice->created = common_sql_now();
$notice->content = common_shorten_links($content);
$notice->rendered = common_render_content($notice->content, $notice);
$notice->source = $source;
$notice->uri = $uri;
$notice->reply_to = $reply_to;
$notice->created = common_sql_now();
$notice->content = common_shorten_links($content);
$notice->rendered = common_render_content($notice->content, $notice);
$notice->source = $source;
$notice->uri = $uri;
$id = $notice->insert();
$id = $notice->insert();
if (!$id) {
common_log_db_error($notice, 'INSERT', __FILE__);
return _('Problem saving notice.');
}
if (!$id) {
common_log_db_error($notice, 'INSERT', __FILE__);
return _('Problem saving notice.');
}
# Update the URI after the notice is in the database
if (!$uri) {
$orig = clone($notice);
$notice->uri = common_notice_uri($notice);
# Update the URI after the notice is in the database
if (!$uri) {
$orig = clone($notice);
$notice->uri = common_notice_uri($notice);
if (!$notice->update($orig)) {
common_log_db_error($notice, 'UPDATE', __FILE__);
return _('Problem saving notice.');
}
}
if (!$notice->update($orig)) {
common_log_db_error($notice, 'UPDATE', __FILE__);
return _('Problem saving notice.');
}
}
# XXX: do we need to change this for remote users?
# XXX: do we need to change this for remote users?
common_save_replies($notice);
$notice->saveTags();
common_save_replies($notice);
$notice->saveTags();
# Clear the cache for subscribed users, so they'll update at next request
# XXX: someone clever could prepend instead of clearing the cache
# Clear the cache for subscribed users, so they'll update at next request
# XXX: someone clever could prepend instead of clearing the cache
if (common_config('memcached', 'enabled')) {
$notice->blowCaches();
}
if (common_config('memcached', 'enabled')) {
$notice->blowCaches();
}
$notice->addToInboxes();
return $notice;
}
$notice->addToInboxes();
return $notice;
}
static function checkEditThrottle($profile_id) {
$profile = Profile::staticGet($profile_id);
@@ -184,356 +184,356 @@ class Notice extends Memcached_DataObject
return true;
}
function blowCaches($blowLast=false) {
$this->blowSubsCache($blowLast);
$this->blowNoticeCache($blowLast);
$this->blowRepliesCache($blowLast);
$this->blowPublicCache($blowLast);
$this->blowTagCache($blowLast);
}
function blowTagCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$tag = new Notice_tag();
$tag->notice_id = $this->id;
if ($tag->find()) {
while ($tag->fetch()) {
$cache->delete(common_cache_key('notice_tag:notice_stream:' . $tag->tag));
if ($blowLast) {
$cache->delete(common_cache_key('notice_tag:notice_stream:' . $tag->tag . ';last'));
}
}
}
$tag->free();
unset($tag);
}
}
function blowSubsCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$user = new User();
$user->query('SELECT id ' .
'FROM user JOIN subscription ON user.id = subscription.subscriber ' .
'WHERE subscription.subscribed = ' . $this->profile_id);
while ($user->fetch()) {
$cache->delete(common_cache_key('user:notices_with_friends:' . $user->id));
if ($blowLast) {
$cache->delete(common_cache_key('user:notices_with_friends:' . $user->id . ';last'));
}
}
$user->free();
unset($user);
}
}
function blowNoticeCache($blowLast=false) {
if ($this->is_local) {
$cache = common_memcache();
if ($cache) {
$cache->delete(common_cache_key('profile:notices:'.$this->profile_id));
if ($blowLast) {
$cache->delete(common_cache_key('profile:notices:'.$this->profile_id.';last'));
}
}
}
}
function blowRepliesCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$reply = new Reply();
$reply->notice_id = $this->id;
if ($reply->find()) {
while ($reply->fetch()) {
$cache->delete(common_cache_key('user:replies:'.$reply->profile_id));
if ($blowLast) {
$cache->delete(common_cache_key('user:replies:'.$reply->profile_id.';last'));
}
}
}
$reply->free();
unset($reply);
}
}
function blowPublicCache($blowLast=false) {
if ($this->is_local == 1) {
$cache = common_memcache();
if ($cache) {
$cache->delete(common_cache_key('public'));
if ($blowLast) {
$cache->delete(common_cache_key('public').';last');
}
}
}
}
function blowFavesCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$fave = new Fave();
$fave->notice_id = $this->id;
if ($fave->find()) {
while ($fave->fetch()) {
$cache->delete(common_cache_key('user:faves:'.$fave->user_id));
if ($blowLast) {
$cache->delete(common_cache_key('user:faves:'.$fave->user_id.';last'));
}
}
}
$fave->free();
unset($fave);
}
}
# XXX: too many args; we need to move to named params or even a separate
# class for notice streams
static function getStream($qry, $cachekey, $offset=0, $limit=20, $since_id=0, $before_id=0, $order=NULL, $since=NULL) {
if (common_config('memcached', 'enabled')) {
# Skip the cache if this is a since, since_id or before_id qry
if ($since_id > 0 || $before_id > 0 || $since) {
return Notice::getStreamDirect($qry, $offset, $limit, $since_id, $before_id, $order, $since);
} else {
return Notice::getCachedStream($qry, $cachekey, $offset, $limit, $order);
}
}
return Notice::getStreamDirect($qry, $offset, $limit, $since_id, $before_id, $order, $since);
}
static function getStreamDirect($qry, $offset, $limit, $since_id, $before_id, $order, $since) {
$needAnd = FALSE;
$needWhere = TRUE;
if (preg_match('/\bWHERE\b/i', $qry)) {
$needWhere = FALSE;
$needAnd = TRUE;
}
if ($since_id > 0) {
if ($needWhere) {
$qry .= ' WHERE ';
$needWhere = FALSE;
} else {
$qry .= ' AND ';
}
$qry .= ' notice.id > ' . $since_id;
}
if ($before_id > 0) {
if ($needWhere) {
$qry .= ' WHERE ';
$needWhere = FALSE;
} else {
$qry .= ' AND ';
}
$qry .= ' notice.id < ' . $before_id;
}
function blowCaches($blowLast=false) {
$this->blowSubsCache($blowLast);
$this->blowNoticeCache($blowLast);
$this->blowRepliesCache($blowLast);
$this->blowPublicCache($blowLast);
$this->blowTagCache($blowLast);
}
function blowTagCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$tag = new Notice_tag();
$tag->notice_id = $this->id;
if ($tag->find()) {
while ($tag->fetch()) {
$cache->delete(common_cache_key('notice_tag:notice_stream:' . $tag->tag));
if ($blowLast) {
$cache->delete(common_cache_key('notice_tag:notice_stream:' . $tag->tag . ';last'));
}
}
}
$tag->free();
unset($tag);
}
}
function blowSubsCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$user = new User();
$user->query('SELECT id ' .
'FROM user JOIN subscription ON user.id = subscription.subscriber ' .
'WHERE subscription.subscribed = ' . $this->profile_id);
while ($user->fetch()) {
$cache->delete(common_cache_key('user:notices_with_friends:' . $user->id));
if ($blowLast) {
$cache->delete(common_cache_key('user:notices_with_friends:' . $user->id . ';last'));
}
}
$user->free();
unset($user);
}
}
function blowNoticeCache($blowLast=false) {
if ($this->is_local) {
$cache = common_memcache();
if ($cache) {
$cache->delete(common_cache_key('profile:notices:'.$this->profile_id));
if ($blowLast) {
$cache->delete(common_cache_key('profile:notices:'.$this->profile_id.';last'));
}
}
}
}
function blowRepliesCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$reply = new Reply();
$reply->notice_id = $this->id;
if ($reply->find()) {
while ($reply->fetch()) {
$cache->delete(common_cache_key('user:replies:'.$reply->profile_id));
if ($blowLast) {
$cache->delete(common_cache_key('user:replies:'.$reply->profile_id.';last'));
}
}
}
$reply->free();
unset($reply);
}
}
function blowPublicCache($blowLast=false) {
if ($this->is_local == 1) {
$cache = common_memcache();
if ($cache) {
$cache->delete(common_cache_key('public'));
if ($blowLast) {
$cache->delete(common_cache_key('public').';last');
}
}
}
}
function blowFavesCache($blowLast=false) {
$cache = common_memcache();
if ($cache) {
$fave = new Fave();
$fave->notice_id = $this->id;
if ($fave->find()) {
while ($fave->fetch()) {
$cache->delete(common_cache_key('user:faves:'.$fave->user_id));
if ($blowLast) {
$cache->delete(common_cache_key('user:faves:'.$fave->user_id.';last'));
}
}
}
$fave->free();
unset($fave);
}
}
# XXX: too many args; we need to move to named params or even a separate
# class for notice streams
static function getStream($qry, $cachekey, $offset=0, $limit=20, $since_id=0, $before_id=0, $order=NULL, $since=NULL) {
if (common_config('memcached', 'enabled')) {
# Skip the cache if this is a since, since_id or before_id qry
if ($since_id > 0 || $before_id > 0 || $since) {
return Notice::getStreamDirect($qry, $offset, $limit, $since_id, $before_id, $order, $since);
} else {
return Notice::getCachedStream($qry, $cachekey, $offset, $limit, $order);
}
}
return Notice::getStreamDirect($qry, $offset, $limit, $since_id, $before_id, $order, $since);
}
static function getStreamDirect($qry, $offset, $limit, $since_id, $before_id, $order, $since) {
$needAnd = FALSE;
$needWhere = TRUE;
if (preg_match('/\bWHERE\b/i', $qry)) {
$needWhere = FALSE;
$needAnd = TRUE;
}
if ($since_id > 0) {
if ($needWhere) {
$qry .= ' WHERE ';
$needWhere = FALSE;
} else {
$qry .= ' AND ';
}
$qry .= ' notice.id > ' . $since_id;
}
if ($before_id > 0) {
if ($needWhere) {
$qry .= ' WHERE ';
$needWhere = FALSE;
} else {
$qry .= ' AND ';
}
$qry .= ' notice.id < ' . $before_id;
}
if ($since) {
if ($needWhere) {
$qry .= ' WHERE ';
$needWhere = FALSE;
} else {
$qry .= ' AND ';
}
if ($since) {
if ($needWhere) {
$qry .= ' WHERE ';
$needWhere = FALSE;
} else {
$qry .= ' AND ';
}
$qry .= ' notice.created > \'' . date('Y-m-d H:i:s', $since) . '\'';
}
$qry .= ' notice.created > \'' . date('Y-m-d H:i:s', $since) . '\'';
}
# Allow ORDER override
# Allow ORDER override
if ($order) {
$qry .= $order;
} else {
$qry .= ' ORDER BY notice.created DESC, notice.id DESC ';
}
if ($order) {
$qry .= $order;
} else {
$qry .= ' ORDER BY notice.created DESC, notice.id DESC ';
}
if (common_config('db','type') == 'pgsql') {
$qry .= ' LIMIT ' . $limit . ' OFFSET ' . $offset;
} else {
$qry .= ' LIMIT ' . $offset . ', ' . $limit;
}
if (common_config('db','type') == 'pgsql') {
$qry .= ' LIMIT ' . $limit . ' OFFSET ' . $offset;
} else {
$qry .= ' LIMIT ' . $offset . ', ' . $limit;
}
$notice = new Notice();
$notice = new Notice();
$notice->query($qry);
$notice->query($qry);
return $notice;
}
return $notice;
}
# XXX: this is pretty long and should probably be broken up into
# some helper functions
# XXX: this is pretty long and should probably be broken up into
# some helper functions
static function getCachedStream($qry, $cachekey, $offset, $limit, $order) {
static function getCachedStream($qry, $cachekey, $offset, $limit, $order) {
# If outside our cache window, just go to the DB
# If outside our cache window, just go to the DB
if ($offset + $limit > NOTICE_CACHE_WINDOW) {
return Notice::getStreamDirect($qry, $offset, $limit, NULL, NULL, $order, NULL);
}
if ($offset + $limit > NOTICE_CACHE_WINDOW) {
return Notice::getStreamDirect($qry, $offset, $limit, NULL, NULL, $order, NULL);
}
# Get the cache; if we can't, just go to the DB
# Get the cache; if we can't, just go to the DB
$cache = common_memcache();
$cache = common_memcache();
if (!$cache) {
return Notice::getStreamDirect($qry, $offset, $limit, NULL, NULL, $order, NULL);
}
if (!$cache) {
return Notice::getStreamDirect($qry, $offset, $limit, NULL, NULL, $order, NULL);
}
# Get the notices out of the cache
# Get the notices out of the cache
$notices = $cache->get(common_cache_key($cachekey));
$notices = $cache->get(common_cache_key($cachekey));
# On a cache hit, return a DB-object-like wrapper
# On a cache hit, return a DB-object-like wrapper
if ($notices !== FALSE) {
$wrapper = new NoticeWrapper(array_slice($notices, $offset, $limit));
return $wrapper;
}
if ($notices !== FALSE) {
$wrapper = new NoticeWrapper(array_slice($notices, $offset, $limit));
return $wrapper;
}
# If the cache was invalidated because of new data being
# added, we can try and just get the new stuff. We keep an additional
# copy of the data at the key + ';last'
# If the cache was invalidated because of new data being
# added, we can try and just get the new stuff. We keep an additional
# copy of the data at the key + ';last'
# No cache hit. Try to get the *last* cached version
# No cache hit. Try to get the *last* cached version
$last_notices = $cache->get(common_cache_key($cachekey) . ';last');
$last_notices = $cache->get(common_cache_key($cachekey) . ';last');
if ($last_notices) {
if ($last_notices) {
# Reverse-chron order, so last ID is last.
# Reverse-chron order, so last ID is last.
$last_id = $last_notices[0]->id;
$last_id = $last_notices[0]->id;
# XXX: this assumes monotonically increasing IDs; a fair
# bet with our DB.
# XXX: this assumes monotonically increasing IDs; a fair
# bet with our DB.
$new_notice = Notice::getStreamDirect($qry, 0, NOTICE_CACHE_WINDOW,
$last_id, NULL, $order, NULL);
$new_notice = Notice::getStreamDirect($qry, 0, NOTICE_CACHE_WINDOW,
$last_id, NULL, $order, NULL);
if ($new_notice) {
$new_notices = array();
while ($new_notice->fetch()) {
$new_notices[] = clone($new_notice);
}
$new_notice->free();
$notices = array_slice(array_merge($new_notices, $last_notices),
0, NOTICE_CACHE_WINDOW);
if ($new_notice) {
$new_notices = array();
while ($new_notice->fetch()) {
$new_notices[] = clone($new_notice);
}
$new_notice->free();
$notices = array_slice(array_merge($new_notices, $last_notices),
0, NOTICE_CACHE_WINDOW);
# Store the array in the cache for next time
# Store the array in the cache for next time
$result = $cache->set(common_cache_key($cachekey), $notices);
$result = $cache->set(common_cache_key($cachekey) . ';last', $notices);
$result = $cache->set(common_cache_key($cachekey), $notices);
$result = $cache->set(common_cache_key($cachekey) . ';last', $notices);
# return a wrapper of the array for use now
# return a wrapper of the array for use now
return new NoticeWrapper(array_slice($notices, $offset, $limit));
}
}
return new NoticeWrapper(array_slice($notices, $offset, $limit));
}
}
# Otherwise, get the full cache window out of the DB
# Otherwise, get the full cache window out of the DB
$notice = Notice::getStreamDirect($qry, 0, NOTICE_CACHE_WINDOW, NULL, NULL, $order, NULL);
$notice = Notice::getStreamDirect($qry, 0, NOTICE_CACHE_WINDOW, NULL, NULL, $order, NULL);
# If there are no hits, just return the value
# If there are no hits, just return the value
if (!$notice) {
return $notice;
}
if (!$notice) {
return $notice;
}
# Pack results into an array
# Pack results into an array
$notices = array();
$notices = array();
while ($notice->fetch()) {
$notices[] = clone($notice);
}
while ($notice->fetch()) {
$notices[] = clone($notice);
}
$notice->free();
$notice->free();
# Store the array in the cache for next time
# Store the array in the cache for next time
$result = $cache->set(common_cache_key($cachekey), $notices);
$result = $cache->set(common_cache_key($cachekey) . ';last', $notices);
$result = $cache->set(common_cache_key($cachekey), $notices);
$result = $cache->set(common_cache_key($cachekey) . ';last', $notices);
# return a wrapper of the array for use now
# return a wrapper of the array for use now
$wrapper = new NoticeWrapper(array_slice($notices, $offset, $limit));
$wrapper = new NoticeWrapper(array_slice($notices, $offset, $limit));
return $wrapper;
}
return $wrapper;
}
function publicStream($offset=0, $limit=20, $since_id=0, $before_id=0, $since=NULL) {
function publicStream($offset=0, $limit=20, $since_id=0, $before_id=0, $since=NULL) {
$parts = array();
$parts = array();
$qry = 'SELECT * FROM notice ';
$qry = 'SELECT * FROM notice ';
if (common_config('public', 'localonly')) {
$parts[] = 'is_local = 1';
} else {
# -1 == blacklisted
$parts[] = 'is_local != -1';
}
if (common_config('public', 'localonly')) {
$parts[] = 'is_local = 1';
} else {
# -1 == blacklisted
$parts[] = 'is_local != -1';
}
if ($parts) {
$qry .= ' WHERE ' . implode(' AND ', $parts);
}
if ($parts) {
$qry .= ' WHERE ' . implode(' AND ', $parts);
}
return Notice::getStream($qry,
'public',
$offset, $limit, $since_id, $before_id, NULL, $since);
}
return Notice::getStream($qry,
'public',
$offset, $limit, $since_id, $before_id, NULL, $since);
}
function addToInboxes() {
$enabled = common_config('inboxes', 'enabled');
function addToInboxes() {
$enabled = common_config('inboxes', 'enabled');
if ($enabled === true || $enabled === 'transitional') {
$inbox = new Notice_inbox();
$qry = 'INSERT INTO notice_inbox (user_id, notice_id, created) ' .
'SELECT user.id, ' . $this->id . ', "' . $this->created . '" ' .
'FROM user JOIN subscription ON user.id = subscription.subscriber ' .
'WHERE subscription.subscribed = ' . $this->profile_id . ' ' .
'AND NOT EXISTS (SELECT user_id, notice_id ' .
'FROM notice_inbox ' .
'WHERE user_id = user.id ' .
'AND notice_id = ' . $this->id . ' )';
if ($enabled === 'transitional') {
$qry .= ' AND user.inboxed = 1';
}
$inbox->query($qry);
}
return;
}
if ($enabled === true || $enabled === 'transitional') {
$inbox = new Notice_inbox();
$qry = 'INSERT INTO notice_inbox (user_id, notice_id, created) ' .
'SELECT user.id, ' . $this->id . ', "' . $this->created . '" ' .
'FROM user JOIN subscription ON user.id = subscription.subscriber ' .
'WHERE subscription.subscribed = ' . $this->profile_id . ' ' .
'AND NOT EXISTS (SELECT user_id, notice_id ' .
'FROM notice_inbox ' .
'WHERE user_id = user.id ' .
'AND notice_id = ' . $this->id . ' )';
if ($enabled === 'transitional') {
$qry .= ' AND user.inboxed = 1';
}
$inbox->query($qry);
}
return;
}
# Delete from inboxes if we're deleted.
# Delete from inboxes if we're deleted.
function blowInboxes() {
function blowInboxes() {
$enabled = common_config('inboxes', 'enabled');
$enabled = common_config('inboxes', 'enabled');
if ($enabled === true || $enabled === 'transitional') {
$inbox = new Notice_inbox();
$inbox->notice_id = $this->id;
$inbox->delete();
}
if ($enabled === true || $enabled === 'transitional') {
$inbox = new Notice_inbox();
$inbox->notice_id = $this->id;
$inbox->delete();
}
return;
}
return;
}
}

View File

@@ -35,25 +35,25 @@ class NoticeWrapper extends Notice {
public $is_local; // tinyint(1)
public $source; // varchar(32)
var $notices = NULL;
var $i = -1;
function __construct($arr) {
$this->notices = $arr;
}
function fetch() {
static $fields = array('id', 'profile_id', 'uri', 'content', 'rendered',
'url', 'created', 'modified', 'reply_to', 'is_local', 'source');
$this->i++;
if ($this->i >= count($this->notices)) {
return false;
} else {
$n = $this->notices[$this->i];
foreach ($fields as $f) {
$this->$f = $n->$f;
}
return true;
}
}
var $notices = NULL;
var $i = -1;
function __construct($arr) {
$this->notices = $arr;
}
function fetch() {
static $fields = array('id', 'profile_id', 'uri', 'content', 'rendered',
'url', 'created', 'modified', 'reply_to', 'is_local', 'source');
$this->i++;
if ($this->i >= count($this->notices)) {
return false;
} else {
$n = $this->notices[$this->i];
foreach ($fields as $f) {
$this->$f = $n->$f;
}
return true;
}
}
}

View File

@@ -34,22 +34,22 @@ class Notice_tag extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
static function getStream($tag, $offset=0, $limit=20) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN notice_tag ON notice.id = notice_tag.notice_id ' .
'WHERE notice_tag.tag = "%s" ';
static function getStream($tag, $offset=0, $limit=20) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN notice_tag ON notice.id = notice_tag.notice_id ' .
'WHERE notice_tag.tag = "%s" ';
return Notice::getStream(sprintf($qry, $tag),
'notice_tag:notice_stream:' . common_keyize($tag),
$offset, $limit);
}
function blowCache() {
$cache = common_memcache();
if ($cache) {
$cache->delete(common_cache_key('notice_tag:notice_stream:' . $this->tag));
}
}
return Notice::getStream(sprintf($qry, $tag),
'notice_tag:notice_stream:' . common_keyize($tag),
$offset, $limit);
}
function blowCache() {
$cache = common_memcache();
if ($cache) {
$cache->delete(common_cache_key('notice_tag:notice_stream:' . $this->tag));
}
}
}

View File

@@ -46,114 +46,114 @@ class Profile extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
function getAvatar($width, $height=NULL) {
if (is_null($height)) {
$height = $width;
}
return Avatar::pkeyGet(array('profile_id' => $this->id,
'width' => $width,
'height' => $height));
}
function getAvatar($width, $height=NULL) {
if (is_null($height)) {
$height = $width;
}
return Avatar::pkeyGet(array('profile_id' => $this->id,
'width' => $width,
'height' => $height));
}
function getOriginalAvatar() {
$avatar = DB_DataObject::factory('avatar');
$avatar->profile_id = $this->id;
$avatar->original = true;
if ($avatar->find(true)) {
return $avatar;
} else {
return NULL;
}
}
function getOriginalAvatar() {
$avatar = DB_DataObject::factory('avatar');
$avatar->profile_id = $this->id;
$avatar->original = true;
if ($avatar->find(true)) {
return $avatar;
} else {
return NULL;
}
}
function setOriginal($source) {
function setOriginal($source) {
$info = @getimagesize($source);
$info = @getimagesize($source);
if (!$info) {
return NULL;
}
if (!$info) {
return NULL;
}
$filename = common_avatar_filename($this->id,
image_type_to_extension($info[2]),
NULL, common_timestamp());
$filepath = common_avatar_path($filename);
$filename = common_avatar_filename($this->id,
image_type_to_extension($info[2]),
NULL, common_timestamp());
$filepath = common_avatar_path($filename);
copy($source, $filepath);
copy($source, $filepath);
$avatar = new Avatar();
$avatar = new Avatar();
$avatar->profile_id = $this->id;
$avatar->width = $info[0];
$avatar->height = $info[1];
$avatar->mediatype = image_type_to_mime_type($info[2]);
$avatar->filename = $filename;
$avatar->original = true;
$avatar->url = common_avatar_url($filename);
$avatar->created = DB_DataObject_Cast::dateTime(); # current time
$avatar->profile_id = $this->id;
$avatar->width = $info[0];
$avatar->height = $info[1];
$avatar->mediatype = image_type_to_mime_type($info[2]);
$avatar->filename = $filename;
$avatar->original = true;
$avatar->url = common_avatar_url($filename);
$avatar->created = DB_DataObject_Cast::dateTime(); # current time
# XXX: start a transaction here
# XXX: start a transaction here
if (!$this->delete_avatars()) {
@unlink($filepath);
return NULL;
}
if (!$this->delete_avatars()) {
@unlink($filepath);
return NULL;
}
if (!$avatar->insert()) {
@unlink($filepath);
return NULL;
}
if (!$avatar->insert()) {
@unlink($filepath);
return NULL;
}
foreach (array(AVATAR_PROFILE_SIZE, AVATAR_STREAM_SIZE, AVATAR_MINI_SIZE) as $size) {
# We don't do a scaled one if original is our scaled size
if (!($avatar->width == $size && $avatar->height == $size)) {
$s = $avatar->scale($size);
if (!$s) {
return NULL;
}
}
}
foreach (array(AVATAR_PROFILE_SIZE, AVATAR_STREAM_SIZE, AVATAR_MINI_SIZE) as $size) {
# We don't do a scaled one if original is our scaled size
if (!($avatar->width == $size && $avatar->height == $size)) {
$s = $avatar->scale($size);
if (!$s) {
return NULL;
}
}
}
return $avatar;
}
return $avatar;
}
function delete_avatars() {
$avatar = new Avatar();
$avatar->profile_id = $this->id;
$avatar->find();
while ($avatar->fetch()) {
$avatar->delete();
}
return true;
}
function delete_avatars() {
$avatar = new Avatar();
$avatar->profile_id = $this->id;
$avatar->find();
while ($avatar->fetch()) {
$avatar->delete();
}
return true;
}
function getBestName() {
return ($this->fullname) ? $this->fullname : $this->nickname;
}
function getBestName() {
return ($this->fullname) ? $this->fullname : $this->nickname;
}
# Get latest notice on or before date; default now
function getCurrentNotice($dt=NULL) {
$notice = new Notice();
$notice->profile_id = $this->id;
if ($dt) {
$notice->whereAdd('created < "' . $dt . '"');
}
$notice->orderBy('created DESC, notice.id DESC');
$notice->limit(1);
if ($notice->find(true)) {
return $notice;
}
return NULL;
}
function getCurrentNotice($dt=NULL) {
$notice = new Notice();
$notice->profile_id = $this->id;
if ($dt) {
$notice->whereAdd('created < "' . $dt . '"');
}
$notice->orderBy('created DESC, notice.id DESC');
$notice->limit(1);
if ($notice->find(true)) {
return $notice;
}
return NULL;
}
function getNotices($offset=0, $limit=NOTICES_PER_PAGE, $since_id=0, $before_id=0) {
$qry =
'SELECT * ' .
'FROM notice ' .
'WHERE profile_id = %d ';
function getNotices($offset=0, $limit=NOTICES_PER_PAGE, $since_id=0, $before_id=0) {
$qry =
'SELECT * ' .
'FROM notice ' .
'WHERE profile_id = %d ';
return Notice::getStream(sprintf($qry, $this->id),
'profile:notices:'.$this->id,
$offset, $limit, $since_id, $before_id);
}
return Notice::getStream(sprintf($qry, $this->id),
'profile:notices:'.$this->id,
$offset, $limit, $since_id, $before_id);
}
}

View File

@@ -21,81 +21,81 @@ class Profile_tag extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
static function getTags($tagger, $tagged) {
$tags = array();
static function getTags($tagger, $tagged) {
$tags = array();
# XXX: store this in memcached
$profile_tag = new Profile_tag();
$profile_tag->tagger = $tagger;
$profile_tag->tagged = $tagged;
$profile_tag->find();
while ($profile_tag->fetch()) {
$tags[] = $profile_tag->tag;
}
$profile_tag->free();
return $tags;
}
static function setTags($tagger, $tagged, $newtags) {
$oldtags = Profile_tag::getTags($tagger, $tagged);
# Delete stuff that's old that not in new
$to_delete = array_diff($oldtags, $newtags);
# Insert stuff that's in new and not in old
$to_insert = array_diff($newtags, $oldtags);
$profile_tag = new Profile_tag();
$profile_tag->tagger = $tagger;
$profile_tag->tagged = $tagged;
$profile_tag->query('BEGIN');
foreach ($to_delete as $deltag) {
$profile_tag->tag = $deltag;
$result = $profile_tag->delete();
if (!$result) {
common_log_db_error($profile_tag, 'DELETE', __FILE__);
return false;
}
}
foreach ($to_insert as $instag) {
$profile_tag->tag = $instag;
$result = $profile_tag->insert();
if (!$result) {
common_log_db_error($profile_tag, 'INSERT', __FILE__);
return false;
}
}
$profile_tag->query('COMMIT');
return true;
}
# Return profiles with a given tag
static function getTagged($tagger, $tag) {
$profile = new Profile();
$profile->query('SELECT profile.* ' .
'FROM profile JOIN profile_tag ' .
'ON profile.id = profile_tag.tagged ' .
'WHERE profile_tag.tagger = ' . $tagger . ' ' .
'AND profile_tag.tag = "' . $tag . '" ');
$tagged = array();
while ($profile->fetch()) {
$tagged[] = clone($profile);
}
return $tagged;
}
# XXX: store this in memcached
$profile_tag = new Profile_tag();
$profile_tag->tagger = $tagger;
$profile_tag->tagged = $tagged;
$profile_tag->find();
while ($profile_tag->fetch()) {
$tags[] = $profile_tag->tag;
}
$profile_tag->free();
return $tags;
}
static function setTags($tagger, $tagged, $newtags) {
$oldtags = Profile_tag::getTags($tagger, $tagged);
# Delete stuff that's old that not in new
$to_delete = array_diff($oldtags, $newtags);
# Insert stuff that's in new and not in old
$to_insert = array_diff($newtags, $oldtags);
$profile_tag = new Profile_tag();
$profile_tag->tagger = $tagger;
$profile_tag->tagged = $tagged;
$profile_tag->query('BEGIN');
foreach ($to_delete as $deltag) {
$profile_tag->tag = $deltag;
$result = $profile_tag->delete();
if (!$result) {
common_log_db_error($profile_tag, 'DELETE', __FILE__);
return false;
}
}
foreach ($to_insert as $instag) {
$profile_tag->tag = $instag;
$result = $profile_tag->insert();
if (!$result) {
common_log_db_error($profile_tag, 'INSERT', __FILE__);
return false;
}
}
$profile_tag->query('COMMIT');
return true;
}
# Return profiles with a given tag
static function getTagged($tagger, $tag) {
$profile = new Profile();
$profile->query('SELECT profile.* ' .
'FROM profile JOIN profile_tag ' .
'ON profile.id = profile_tag.tagged ' .
'WHERE profile_tag.tagger = ' . $tagger . ' ' .
'AND profile_tag.tag = "' . $tag . '" ');
$tagged = array();
while ($profile->fetch()) {
$tagged[] = clone($profile);
}
return $tagged;
}
}

View File

@@ -22,34 +22,34 @@ class Queue_item extends Memcached_DataObject
###END_AUTOCODE
function sequenceKey() { return array(false, false); }
static function top($transport) {
static function top($transport) {
$qi = new Queue_item();
$qi->transport = $transport;
$qi->orderBy('created');
$qi->whereAdd('claimed is NULL');
$qi = new Queue_item();
$qi->transport = $transport;
$qi->orderBy('created');
$qi->whereAdd('claimed is NULL');
$qi->limit(1);
$qi->limit(1);
$cnt = $qi->find(TRUE);
$cnt = $qi->find(TRUE);
if ($cnt) {
# XXX: potential race condition
# can we force it to only update if claimed is still NULL
# (or old)?
common_log(LOG_INFO, 'claiming queue item = ' . $qi->notice_id . ' for transport ' . $transport);
$orig = clone($qi);
$qi->claimed = common_sql_now();
$result = $qi->update($orig);
if ($result) {
common_log(LOG_INFO, 'claim succeeded.');
return $qi;
} else {
common_log(LOG_INFO, 'claim failed.');
}
}
$qi = NULL;
return NULL;
}
if ($cnt) {
# XXX: potential race condition
# can we force it to only update if claimed is still NULL
# (or old)?
common_log(LOG_INFO, 'claiming queue item = ' . $qi->notice_id . ' for transport ' . $transport);
$orig = clone($qi);
$qi->claimed = common_sql_now();
$result = $qi->update($orig);
if ($result) {
common_log(LOG_INFO, 'claim succeeded.');
return $qi;
} else {
common_log(LOG_INFO, 'claim failed.');
}
}
$qi = NULL;
return NULL;
}
}

View File

@@ -21,8 +21,8 @@ class Sms_carrier extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
function toEmailAddress($sms) {
return sprintf($this->email_pattern, $sms);
}
function toEmailAddress($sms) {
return sprintf($this->email_pattern, $sms);
}
}

View File

@@ -44,8 +44,8 @@ class Subscription extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
function &pkeyGet($kv) {
return Memcached_DataObject::pkeyGet('Subscription', $kv);
}
function &pkeyGet($kv) {
return Memcached_DataObject::pkeyGet('Subscription', $kv);
}
}

View File

@@ -67,82 +67,82 @@ class User extends Memcached_DataObject
/* the code above is auto generated do not remove the tag below */
###END_AUTOCODE
function getProfile() {
return Profile::staticGet('id', $this->id);
}
function getProfile() {
return Profile::staticGet('id', $this->id);
}
function isSubscribed($other) {
assert(!is_null($other));
# XXX: cache results of this query
$sub = Subscription::pkeyGet(array('subscriber' => $this->id,
'subscribed' => $other->id));
return (is_null($sub)) ? false : true;
}
function isSubscribed($other) {
assert(!is_null($other));
# XXX: cache results of this query
$sub = Subscription::pkeyGet(array('subscriber' => $this->id,
'subscribed' => $other->id));
return (is_null($sub)) ? false : true;
}
# 'update' won't write key columns, so we have to do it ourselves.
# 'update' won't write key columns, so we have to do it ourselves.
function updateKeys(&$orig) {
$parts = array();
foreach (array('nickname', 'email', 'jabber', 'incomingemail', 'sms', 'carrier', 'smsemail', 'language', 'timezone') as $k) {
if (strcmp($this->$k, $orig->$k) != 0) {
$parts[] = $k . ' = ' . $this->_quote($this->$k);
}
}
if (count($parts) == 0) {
# No changes
return true;
}
$toupdate = implode(', ', $parts);
function updateKeys(&$orig) {
$parts = array();
foreach (array('nickname', 'email', 'jabber', 'incomingemail', 'sms', 'carrier', 'smsemail', 'language', 'timezone') as $k) {
if (strcmp($this->$k, $orig->$k) != 0) {
$parts[] = $k . ' = ' . $this->_quote($this->$k);
}
}
if (count($parts) == 0) {
# No changes
return true;
}
$toupdate = implode(', ', $parts);
$table = $this->tableName();
if(common_config('db','quote_identifiers')) {
$table = '"' . $table . '"';
}
$qry = 'UPDATE ' . $table . ' SET ' . $toupdate .
' WHERE id = ' . $this->id;
$orig->decache();
$result = $this->query($qry);
if ($result) {
$this->encache();
}
return $result;
}
$table = $this->tableName();
if(common_config('db','quote_identifiers')) {
$table = '"' . $table . '"';
}
$qry = 'UPDATE ' . $table . ' SET ' . $toupdate .
' WHERE id = ' . $this->id;
$orig->decache();
$result = $this->query($qry);
if ($result) {
$this->encache();
}
return $result;
}
function allowed_nickname($nickname) {
# XXX: should already be validated for size, content, etc.
static $blacklist = array('rss', 'xrds', 'doc', 'main',
'settings', 'notice', 'user',
'search', 'avatar', 'tag', 'tags',
'api', 'message');
$merged = array_merge($blacklist, common_config('nickname', 'blacklist'));
return !in_array($nickname, $merged);
}
function allowed_nickname($nickname) {
# XXX: should already be validated for size, content, etc.
static $blacklist = array('rss', 'xrds', 'doc', 'main',
'settings', 'notice', 'user',
'search', 'avatar', 'tag', 'tags',
'api', 'message');
$merged = array_merge($blacklist, common_config('nickname', 'blacklist'));
return !in_array($nickname, $merged);
}
function getCurrentNotice($dt=NULL) {
$profile = $this->getProfile();
if (!$profile) {
return NULL;
}
return $profile->getCurrentNotice($dt);
}
function getCurrentNotice($dt=NULL) {
$profile = $this->getProfile();
if (!$profile) {
return NULL;
}
return $profile->getCurrentNotice($dt);
}
function getCarrier() {
return Sms_carrier::staticGet('id', $this->carrier);
}
function getCarrier() {
return Sms_carrier::staticGet('id', $this->carrier);
}
function subscribeTo($other) {
$sub = new Subscription();
$sub->subscriber = $this->id;
$sub->subscribed = $other->id;
function subscribeTo($other) {
$sub = new Subscription();
$sub->subscriber = $this->id;
$sub->subscribed = $other->id;
$sub->created = common_sql_now(); # current time
$sub->created = common_sql_now(); # current time
if (!$sub->insert()) {
return false;
}
if (!$sub->insert()) {
return false;
}
return true;
}
return true;
}
function hasBlocked($other) {
@@ -158,193 +158,193 @@ class User extends Memcached_DataObject
return $result;
}
static function register($fields) {
static function register($fields) {
# MAGICALLY put fields into current scope
# MAGICALLY put fields into current scope
extract($fields);
extract($fields);
$profile = new Profile();
$profile = new Profile();
$profile->query('BEGIN');
$profile->query('BEGIN');
$profile->nickname = $nickname;
$profile->profileurl = common_profile_url($nickname);
$profile->nickname = $nickname;
$profile->profileurl = common_profile_url($nickname);
if ($fullname) {
$profile->fullname = $fullname;
}
if ($homepage) {
$profile->homepage = $homepage;
}
if ($bio) {
$profile->bio = $bio;
}
if ($location) {
$profile->location = $location;
}
if ($fullname) {
$profile->fullname = $fullname;
}
if ($homepage) {
$profile->homepage = $homepage;
}
if ($bio) {
$profile->bio = $bio;
}
if ($location) {
$profile->location = $location;
}
$profile->created = common_sql_now();
$profile->created = common_sql_now();
$id = $profile->insert();
$id = $profile->insert();
if (!$id) {
common_log_db_error($profile, 'INSERT', __FILE__);
return FALSE;
}
if (!$id) {
common_log_db_error($profile, 'INSERT', __FILE__);
return FALSE;
}
$user = new User();
$user = new User();
$user->id = $id;
$user->nickname = $nickname;
$user->id = $id;
$user->nickname = $nickname;
if ($password) { # may not have a password for OpenID users
$user->password = common_munge_password($password, $id);
}
if ($password) { # may not have a password for OpenID users
$user->password = common_munge_password($password, $id);
}
# Users who respond to invite email have proven their ownership of that address
# Users who respond to invite email have proven their ownership of that address
if ($code) {
$invite = Invitation::staticGet($code);
if ($invite && $invite->address && $invite->address_type == 'email' && $invite->address == $email) {
$user->email = $invite->address;
}
}
if ($code) {
$invite = Invitation::staticGet($code);
if ($invite && $invite->address && $invite->address_type == 'email' && $invite->address == $email) {
$user->email = $invite->address;
}
}
$inboxes = common_config('inboxes', 'enabled');
$inboxes = common_config('inboxes', 'enabled');
if ($inboxes === true || $inboxes == 'transitional') {
$user->inboxed = 1;
}
if ($inboxes === true || $inboxes == 'transitional') {
$user->inboxed = 1;
}
$user->created = common_sql_now();
$user->uri = common_user_uri($user);
$user->created = common_sql_now();
$user->uri = common_user_uri($user);
$result = $user->insert();
$result = $user->insert();
if (!$result) {
common_log_db_error($user, 'INSERT', __FILE__);
return FALSE;
}
if (!$result) {
common_log_db_error($user, 'INSERT', __FILE__);
return FALSE;
}
# Everyone is subscribed to themself
# Everyone is subscribed to themself
$subscription = new Subscription();
$subscription->subscriber = $user->id;
$subscription->subscribed = $user->id;
$subscription->created = $user->created;
$subscription = new Subscription();
$subscription->subscriber = $user->id;
$subscription->subscribed = $user->id;
$subscription->created = $user->created;
$result = $subscription->insert();
$result = $subscription->insert();
if (!$result) {
common_log_db_error($subscription, 'INSERT', __FILE__);
return FALSE;
}
if (!$result) {
common_log_db_error($subscription, 'INSERT', __FILE__);
return FALSE;
}
if ($email && !$user->email) {
if ($email && !$user->email) {
$confirm = new Confirm_address();
$confirm->code = common_confirmation_code(128);
$confirm->user_id = $user->id;
$confirm->address = $email;
$confirm->address_type = 'email';
$confirm = new Confirm_address();
$confirm->code = common_confirmation_code(128);
$confirm->user_id = $user->id;
$confirm->address = $email;
$confirm->address_type = 'email';
$result = $confirm->insert();
if (!$result) {
common_log_db_error($confirm, 'INSERT', __FILE__);
return FALSE;
}
}
$result = $confirm->insert();
if (!$result) {
common_log_db_error($confirm, 'INSERT', __FILE__);
return FALSE;
}
}
if ($code && $user->email) {
$user->emailChanged();
}
if ($code && $user->email) {
$user->emailChanged();
}
$profile->query('COMMIT');
$profile->query('COMMIT');
if ($email && !$user->email) {
mail_confirm_address($user, $confirm->code, $profile->nickname, $email);
}
if ($email && !$user->email) {
mail_confirm_address($user, $confirm->code, $profile->nickname, $email);
}
return $user;
}
return $user;
}
# Things we do when the email changes
# Things we do when the email changes
function emailChanged() {
function emailChanged() {
$invites = new Invitation();
$invites->address = $this->email;
$invites->address_type = 'email';
$invites = new Invitation();
$invites->address = $this->email;
$invites->address_type = 'email';
if ($invites->find()) {
while ($invites->fetch()) {
$other = User::staticGet($invites->user_id);
subs_subscribe_to($other, $this);
}
}
}
if ($invites->find()) {
while ($invites->fetch()) {
$other = User::staticGet($invites->user_id);
subs_subscribe_to($other, $this);
}
}
}
function hasFave($notice) {
$cache = common_memcache();
function hasFave($notice) {
$cache = common_memcache();
# XXX: Kind of a hack.
if ($cache) {
# This is the stream of favorite notices, in rev chron
# order. This forces it into cache.
$faves = $this->favoriteNotices(0, NOTICE_CACHE_WINDOW);
$cnt = 0;
while ($faves->fetch()) {
if ($faves->id < $notice->id) {
# If we passed it, it's not a fave
return false;
} else if ($faves->id == $notice->id) {
# If it matches a cached notice, then it's a fave
return true;
}
$cnt++;
}
# If we're not past the end of the cache window,
# then the cache has all available faves, so this one
# is not a fave.
if ($cnt < NOTICE_CACHE_WINDOW) {
return false;
}
# Otherwise, cache doesn't have all faves;
# fall through to the default
}
$fave = Fave::pkeyGet(array('user_id' => $this->id,
'notice_id' => $notice->id));
return ((is_null($fave)) ? false : true);
}
function mutuallySubscribed($other) {
return $this->isSubscribed($other) &&
$other->isSubscribed($this);
}
# XXX: Kind of a hack.
if ($cache) {
# This is the stream of favorite notices, in rev chron
# order. This forces it into cache.
$faves = $this->favoriteNotices(0, NOTICE_CACHE_WINDOW);
$cnt = 0;
while ($faves->fetch()) {
if ($faves->id < $notice->id) {
# If we passed it, it's not a fave
return false;
} else if ($faves->id == $notice->id) {
# If it matches a cached notice, then it's a fave
return true;
}
$cnt++;
}
# If we're not past the end of the cache window,
# then the cache has all available faves, so this one
# is not a fave.
if ($cnt < NOTICE_CACHE_WINDOW) {
return false;
}
# Otherwise, cache doesn't have all faves;
# fall through to the default
}
$fave = Fave::pkeyGet(array('user_id' => $this->id,
'notice_id' => $notice->id));
return ((is_null($fave)) ? false : true);
}
function mutuallySubscribed($other) {
return $this->isSubscribed($other) &&
$other->isSubscribed($this);
}
function mutuallySubscribedUsers() {
# 3-way join; probably should get cached
$qry = 'SELECT user.* ' .
'FROM subscription sub1 JOIN user ON sub1.subscribed = user.id ' .
'JOIN subscription sub2 ON user.id = sub2.subscriber ' .
'WHERE sub1.subscriber = %d and sub2.subscribed = %d ' .
'ORDER BY user.nickname';
$user = new User();
$user->query(sprintf($qry, $this->id, $this->id));
# 3-way join; probably should get cached
$qry = 'SELECT user.* ' .
'FROM subscription sub1 JOIN user ON sub1.subscribed = user.id ' .
'JOIN subscription sub2 ON user.id = sub2.subscriber ' .
'WHERE sub1.subscriber = %d and sub2.subscribed = %d ' .
'ORDER BY user.nickname';
$user = new User();
$user->query(sprintf($qry, $this->id, $this->id));
return $user;
}
return $user;
}
function getReplies($offset=0, $limit=NOTICES_PER_PAGE, $since_id=0, $before_id=0, $since=NULL) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN reply ON notice.id = reply.notice_id ' .
'WHERE reply.profile_id = %d ';
return Notice::getStream(sprintf($qry, $this->id),
'user:replies:'.$this->id,
$offset, $limit, $since_id, $before_id, NULL, $since);
}
function getReplies($offset=0, $limit=NOTICES_PER_PAGE, $since_id=0, $before_id=0, $since=NULL) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN reply ON notice.id = reply.notice_id ' .
'WHERE reply.profile_id = %d ';
return Notice::getStream(sprintf($qry, $this->id),
'user:replies:'.$this->id,
$offset, $limit, $since_id, $before_id, NULL, $since);
}
function getNotices($offset=0, $limit=NOTICES_PER_PAGE, $since_id=0, $before_id=0, $since=NULL) {
$profile = $this->getProfile();
@@ -353,64 +353,64 @@ class User extends Memcached_DataObject
} else {
return $profile->getNotices($offset, $limit, $since_id, $before_id);
}
}
}
function favoriteNotices($offset=0, $limit=NOTICES_PER_PAGE) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN fave ON notice.id = fave.notice_id ' .
'WHERE fave.user_id = %d ';
return Notice::getStream(sprintf($qry, $this->id),
'user:faves:'.$this->id,
$offset, $limit);
}
$qry =
'SELECT notice.* ' .
'FROM notice JOIN fave ON notice.id = fave.notice_id ' .
'WHERE fave.user_id = %d ';
return Notice::getStream(sprintf($qry, $this->id),
'user:faves:'.$this->id,
$offset, $limit);
}
function noticesWithFriends($offset=0, $limit=NOTICES_PER_PAGE, $since_id=0, $before_id=0, $since=NULL) {
$enabled = common_config('inboxes', 'enabled');
$enabled = common_config('inboxes', 'enabled');
# Complicated code, depending on whether we support inboxes yet
# XXX: make this go away when inboxes become mandatory
# Complicated code, depending on whether we support inboxes yet
# XXX: make this go away when inboxes become mandatory
if ($enabled === false ||
($enabled == 'transitional' && $this->inboxed == 0)) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN subscription ON notice.profile_id = subscription.subscribed ' .
'WHERE subscription.subscriber = %d ';
$order = NULL;
} else if ($enabled === true ||
($enabled == 'transitional' && $this->inboxed == 1)) {
if ($enabled === false ||
($enabled == 'transitional' && $this->inboxed == 0)) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN subscription ON notice.profile_id = subscription.subscribed ' .
'WHERE subscription.subscriber = %d ';
$order = NULL;
} else if ($enabled === true ||
($enabled == 'transitional' && $this->inboxed == 1)) {
$qry =
'SELECT notice.* ' .
'FROM notice JOIN notice_inbox ON notice.id = notice_inbox.notice_id ' .
'WHERE notice_inbox.user_id = %d ';
# NOTE: we override ORDER
$order = 'ORDER BY notice_inbox.created DESC, notice_inbox.notice_id DESC ';
}
return Notice::getStream(sprintf($qry, $this->id),
'user:notices_with_friends:' . $this->id,
$offset, $limit, $since_id, $before_id,
$order, $since);
}
$qry =
'SELECT notice.* ' .
'FROM notice JOIN notice_inbox ON notice.id = notice_inbox.notice_id ' .
'WHERE notice_inbox.user_id = %d ';
# NOTE: we override ORDER
$order = 'ORDER BY notice_inbox.created DESC, notice_inbox.notice_id DESC ';
}
return Notice::getStream(sprintf($qry, $this->id),
'user:notices_with_friends:' . $this->id,
$offset, $limit, $since_id, $before_id,
$order, $since);
}
function blowFavesCache() {
$cache = common_memcache();
if ($cache) {
# Faves don't happen chronologically, so we need to blow
# ;last cache, too
$cache->delete(common_cache_key('user:faves:'.$this->id));
$cache->delete(common_cache_key('user:faves:'.$this->id).';last');
}
}
$cache = common_memcache();
if ($cache) {
# Faves don't happen chronologically, so we need to blow
# ;last cache, too
$cache->delete(common_cache_key('user:faves:'.$this->id));
$cache->delete(common_cache_key('user:faves:'.$this->id).';last');
}
}
function getSelfTags() {
return Profile_tag::getTags($this->id, $this->id);
}
return Profile_tag::getTags($this->id, $this->id);
}
function setSelfTags($newtags) {
return Profile_tag::setTags($this->id, $this->id, $newtags);
}
return Profile_tag::setTags($this->id, $this->id, $newtags);
}
function block($other) {
@@ -434,8 +434,8 @@ class User extends Memcached_DataObject
# Cancel their subscription, if it exists
$sub = Subscription::pkeyGet(array('subscriber' => $other->id,
'subscribed' => $this->id));
$sub = Subscription::pkeyGet(array('subscriber' => $other->id,
'subscribed' => $this->id));
if ($sub) {
$result = $sub->delete();