diff options
Diffstat (limited to 'actions')
86 files changed, 2270 insertions, 567 deletions
diff --git a/actions/accesstoken.php b/actions/accesstoken.php index 46b43c702..2a8cd1713 100644 --- a/actions/accesstoken.php +++ b/actions/accesstoken.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/all.php b/actions/all.php index 03179a246..f06ead2a8 100644 --- a/actions/all.php +++ b/actions/all.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -98,7 +98,13 @@ class AllAction extends ProfileAction function showContent() { - $notice = $this->user->noticesWithFriends(($this->page-1)*NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1); + $cur = common_current_user(); + + if (!empty($cur) && $cur->id == $this->user->id) { + $notice = $this->user->noticeInbox(($this->page-1)*NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1); + } else { + $notice = $this->user->noticesWithFriends(($this->page-1)*NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1); + } $nl = new NoticeList($notice, $this); diff --git a/actions/allrss.php b/actions/allrss.php index 45f3946a6..885a67f61 100644 --- a/actions/allrss.php +++ b/actions/allrss.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -81,6 +81,14 @@ class AllrssAction extends Rss10Action */ function getNotices($limit=0) { + $cur = common_current_user(); + + if (!empty($cur) && $cur->id == $user->id) { + $notice = $this->user->noticeInbox(0, $limit); + } else { + $notice = $this->user->noticesWithFriends(0, $limit); + } + $user = $this->user; $notice = $user->noticesWithFriends(0, $limit); $notices = array(); diff --git a/actions/api.php b/actions/api.php index b8da852b5..1fe5875ad 100644 --- a/actions/api.php +++ b/actions/api.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/attachment.php b/actions/attachment.php index 16ee723d9..e4dc0e054 100644 --- a/actions/attachment.php +++ b/actions/attachment.php @@ -99,48 +99,6 @@ class AttachmentAction extends Action } /** - * Last-modified date for page - * - * When was the content of this page last modified? Based on notice, - * profile, avatar. - * - * @return int last-modified date as unix timestamp - */ -/* - function lastModified() - { - return max(strtotime($this->notice->created), - strtotime($this->profile->modified), - ($this->avatar) ? strtotime($this->avatar->modified) : 0); - } -*/ - - /** - * An entity tag for this page - * - * Shows the ETag for the page, based on the notice ID and timestamps - * for the notice, profile, and avatar. It's weak, since we change - * the date text "one hour ago", etc. - * - * @return string etag - */ -/* - function etag() - { - $avtime = ($this->avatar) ? - strtotime($this->avatar->modified) : 0; - - return 'W/"' . implode(':', array($this->arg('action'), - common_language(), - $this->notice->id, - strtotime($this->notice->created), - strtotime($this->profile->modified), - $avtime)) . '"'; - } -*/ - - - /** * Handle input * * Only handles get, so just show the page. diff --git a/actions/attachment_ajax.php b/actions/attachment_ajax.php index 3d83393c5..5d6773010 100644 --- a/actions/attachment_ajax.php +++ b/actions/attachment_ajax.php @@ -74,46 +74,5 @@ class Attachment_ajaxAction extends AttachmentAction } $this->elementEnd('div'); } - - /** - * Last-modified date for page - * - * When was the content of this page last modified? Based on notice, - * profile, avatar. - * - * @return int last-modified date as unix timestamp - */ -/* - function lastModified() - { - return max(strtotime($this->notice->created), - strtotime($this->profile->modified), - ($this->avatar) ? strtotime($this->avatar->modified) : 0); - } -*/ - - /** - * An entity tag for this page - * - * Shows the ETag for the page, based on the notice ID and timestamps - * for the notice, profile, and avatar. It's weak, since we change - * the date text "one hour ago", etc. - * - * @return string etag - */ -/* - function etag() - { - $avtime = ($this->avatar) ? - strtotime($this->avatar->modified) : 0; - - return 'W/"' . implode(':', array($this->arg('action'), - common_language(), - $this->notice->id, - strtotime($this->notice->created), - strtotime($this->profile->modified), - $avtime)) . '"'; - } -*/ } diff --git a/actions/avatarbynickname.php b/actions/avatarbynickname.php index e92a99372..3e615261f 100644 --- a/actions/avatarbynickname.php +++ b/actions/avatarbynickname.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/block.php b/actions/block.php index 34f991dc6..06f92254e 100644 --- a/actions/block.php +++ b/actions/block.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -125,16 +125,18 @@ class BlockAction extends Action function areYouSureForm() { $id = $this->profile->id; + $this->elementStart('form', array('id' => 'block-' . $id, + 'method' => 'post', + 'class' => 'form_settings form_entity_block', + 'action' => common_local_url('block'))); + $this->elementStart('fieldset'); + $this->hidden('token', common_session_token()); + $this->element('legend', _('Block user')); $this->element('p', null, _('Are you sure you want to block this user? '. 'Afterwards, they will be unsubscribed from you, '. 'unable to subscribe to you in the future, and '. 'you will not be notified of any @-replies from them.')); - $this->elementStart('form', array('id' => 'block-' . $id, - 'method' => 'post', - 'class' => 'block', - 'action' => common_local_url('block'))); - $this->hidden('token', common_session_token()); $this->element('input', array('id' => 'blockto-' . $id, 'name' => 'blockto', 'type' => 'hidden', @@ -144,8 +146,9 @@ class BlockAction extends Action $this->hidden($k, $v); } } - $this->submit('no', _('No')); - $this->submit('yes', _('Yes')); + $this->submit('form_action-no', _('No'), 'submit form_action-primary', 'no', _("Do not block this user from this group")); + $this->submit('form_action-yes', _('Yes'), 'submit form_action-secondary', 'yes', _('Block this user from this group')); + $this->elementEnd('fieldset'); $this->elementEnd('form'); } @@ -180,7 +183,7 @@ class BlockAction extends Action if ($action) { common_redirect(common_local_url($action, $args), 303); } else { - common_redirect(common_local_url('subscriptions', + common_redirect(common_local_url('subscribers', array('nickname' => $cur->nickname)), 303); } diff --git a/actions/blockedfromgroup.php b/actions/blockedfromgroup.php new file mode 100644 index 000000000..5c1eab354 --- /dev/null +++ b/actions/blockedfromgroup.php @@ -0,0 +1,315 @@ +<?php +/** + * Laconica, the distributed open-source microblogging tool + * + * List of group members + * + * PHP version 5 + * + * LICENCE: This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + * + * @category Group + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @copyright 2008-2009 Control Yourself, Inc. + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + */ + +if (!defined('LACONICA')) { + exit(1); +} + +/** + * List of profiles blocked from this group + * + * @category Group + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + */ + +class BlockedfromgroupAction extends GroupDesignAction +{ + var $page = null; + + function isReadOnly($args) + { + return true; + } + + function prepare($args) + { + parent::prepare($args); + $this->page = ($this->arg('page')) ? ($this->arg('page')+0) : 1; + + $nickname_arg = $this->arg('nickname'); + $nickname = common_canonical_nickname($nickname_arg); + + // Permanent redirect on non-canonical nickname + + if ($nickname_arg != $nickname) { + $args = array('nickname' => $nickname); + if ($this->page != 1) { + $args['page'] = $this->page; + } + common_redirect(common_local_url('blockedfromgroup', $args), 301); + return false; + } + + if (!$nickname) { + $this->clientError(_('No nickname'), 404); + return false; + } + + $this->group = User_group::staticGet('nickname', $nickname); + + if (!$this->group) { + $this->clientError(_('No such group'), 404); + return false; + } + + return true; + } + + function title() + { + if ($this->page == 1) { + return sprintf(_('%s blocked profiles'), + $this->group->nickname); + } else { + return sprintf(_('%s blocked profiles, page %d'), + $this->group->nickname, + $this->page); + } + } + + function handle($args) + { + parent::handle($args); + $this->showPage(); + } + + function showPageNotice() + { + $this->element('p', 'instructions', + _('A list of the users blocked from joining this group.')); + } + + function showLocalNav() + { + $nav = new GroupNav($this, $this->group); + $nav->show(); + } + + function showContent() + { + $offset = ($this->page-1) * PROFILES_PER_PAGE; + $limit = PROFILES_PER_PAGE + 1; + + $cnt = 0; + + $blocked = $this->group->getBlocked($offset, $limit); + + if ($blocked) { + $blocked_list = new GroupBlockList($blocked, $this->group, $this); + $cnt = $blocked_list->show(); + } + + $blocked->free(); + + $this->pagination($this->page > 1, $cnt > PROFILES_PER_PAGE, + $this->page, 'blockedfromgroup', + array('nickname' => $this->group->nickname)); + } +} + +class GroupBlockList extends ProfileList +{ + var $group = null; + + function __construct($profile, $group, $action) + { + parent::__construct($profile, $action); + + $this->group = $group; + } + + function newListItem($profile) + { + return new GroupBlockListItem($profile, $this->group, $this->action); + } +} + +class GroupBlockListItem extends ProfileListItem +{ + var $group = null; + + function __construct($profile, $group, $action) + { + parent::__construct($profile, $action); + + $this->group = $group; + } + + function showActions() + { + $this->startActions(); + $this->showGroupUnblockForm(); + $this->endActions(); + } + + function showGroupUnblockForm() + { + $user = common_current_user(); + + if (!empty($user) && $user->id != $this->profile->id && $user->isAdmin($this->group)) { + $this->out->elementStart('li', 'entity_block'); + $bf = new GroupUnblockForm($this->out, $this->profile, $this->group, + array('action' => 'blockedfromgroup', + 'nickname' => $this->group->nickname)); + $bf->show(); + $this->out->elementEnd('li'); + } + } +} + +/** + * Form for unblocking a user from a group + * + * @category Form + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @author Sarven Capadisli <csarven@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + * + * @see UnblockForm + */ + +class GroupUnblockForm extends Form +{ + /** + * Profile of user to block + */ + + var $profile = null; + + /** + * Group to block the user from + */ + + var $group = null; + + /** + * Return-to args + */ + + var $args = null; + + /** + * Constructor + * + * @param HTMLOutputter $out output channel + * @param Profile $profile profile of user to block + * @param User_group $group group to block user from + * @param array $args return-to args + */ + + function __construct($out=null, $profile=null, $group=null, $args=null) + { + parent::__construct($out); + + $this->profile = $profile; + $this->group = $group; + $this->args = $args; + } + + /** + * ID of the form + * + * @return int ID of the form + */ + + function id() + { + // This should be unique for the page. + return 'unblock-' . $this->profile->id; + } + + /** + * class of the form + * + * @return string class of the form + */ + + function formClass() + { + return 'form_group_unblock'; + } + + /** + * Action of the form + * + * @return string URL of the action + */ + + function action() + { + return common_local_url('groupunblock'); + } + + /** + * Legend of the Form + * + * @return void + */ + function formLegend() + { + $this->out->element('legend', null, _('Unblock user from group')); + } + + /** + * Data elements of the form + * + * @return void + */ + + function formData() + { + $this->out->hidden('unblockto-' . $this->profile->id, + $this->profile->id, + 'unblockto'); + $this->out->hidden('unblockgroup-' . $this->group->id, + $this->group->id, + 'unblockgroup'); + if ($this->args) { + foreach ($this->args as $k => $v) { + $this->out->hidden('returnto-' . $k, $v); + } + } + } + + /** + * Action elements + * + * @return void + */ + + function formActions() + { + $this->out->submit('submit', _('Unblock'), 'submit', null, _('Unblock this user')); + } +} diff --git a/actions/conversation.php b/actions/conversation.php index 20c68986c..654a670f5 100644 --- a/actions/conversation.php +++ b/actions/conversation.php @@ -63,6 +63,7 @@ class ConversationAction extends Action if (empty($this->id)) { return false; } + $this->id = $this->id+0; $this->page = $this->trimmed('page'); if (empty($this->page)) { $this->page = 1; @@ -106,18 +107,10 @@ class ConversationAction extends Action function showContent() { - // FIXME this needs to be a tree, not a list - - $qry = 'SELECT * FROM notice WHERE conversation = %s '; - $offset = ($this->page-1) * NOTICES_PER_PAGE; $limit = NOTICES_PER_PAGE + 1; - $txt = sprintf($qry, $this->id); - - $notices = Notice::getStream($txt, - 'notice:conversation:'.$this->id, - $offset, $limit); + $notices = Notice::conversationStream($this->id, $offset, $limit); $ct = new ConversationTree($notices, $this); @@ -126,7 +119,6 @@ class ConversationAction extends Action $this->pagination($this->page > 1, $cnt > NOTICES_PER_PAGE, $this->page, 'conversation', array('id' => $this->id)); } - } /** @@ -217,6 +209,8 @@ class ConversationTree extends NoticeList $this->out->elementStart('ol', array('class' => 'notices')); + sort($children); + foreach ($children as $child) { $this->showNoticePlus($child); } diff --git a/actions/designsettings.php b/actions/designsettings.php deleted file mode 100644 index 5774b8537..000000000 --- a/actions/designsettings.php +++ /dev/null @@ -1,264 +0,0 @@ -<?php -/** - * Laconica, the distributed open-source microblogging tool - * - * Change user password - * - * PHP version 5 - * - * LICENCE: This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU Affero General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU Affero General Public License for more details. - * - * You should have received a copy of the GNU Affero General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - * - * @category Settings - * @package Laconica - * @author Sarven Capadisli <csarven@controlyourself.ca> - * @copyright 2008-2009 Control Yourself, Inc. - * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 - * @link http://laconi.ca/ - */ - -if (!defined('LACONICA')) { - exit(1); -} - -require_once INSTALLDIR.'/lib/accountsettingsaction.php'; - - - -class DesignsettingsAction extends AccountSettingsAction -{ - /** - * Title of the page - * - * @return string Title of the page - */ - - function title() - { - return _('Profile design'); - } - - /** - * Instructions for use - * - * @return instructions for use - */ - - function getInstructions() - { - return _('Customize the way your profile looks with a background image and a colour palette of your choice.'); - } - - /** - * Content area of the page - * - * Shows a form for changing the password - * - * @return void - */ - - function showContent() - { - $user = common_current_user(); - $this->elementStart('form', array('method' => 'post', - 'id' => 'form_settings_design', - 'class' => 'form_settings', - 'action' => - common_local_url('designsettings'))); - $this->elementStart('fieldset'); - $this->hidden('token', common_session_token()); - - $this->elementStart('fieldset', array('id' => 'settings_design_background-image')); - $this->element('legend', null, _('Change background image')); - $this->elementStart('ul', 'form_data'); - $this->elementStart('li'); - $this->element('label', array('for' => 'design_background-image_file'), - _('Upload file')); - $this->element('input', array('name' => 'design_background-image_file', - 'type' => 'file', - 'id' => 'design_background-image_file')); - $this->element('p', 'form_guide', _('You can upload your personal background image. The maximum file size is 2Mb.')); - $this->element('input', array('name' => 'MAX_FILE_SIZE', - 'type' => 'hidden', - 'id' => 'MAX_FILE_SIZE', - 'value' => ImageFile::maxFileSizeInt())); - $this->elementEnd('li'); - $this->elementEnd('ul'); - $this->elementEnd('fieldset'); - - $this->elementStart('fieldset', array('id' => 'settings_design_color')); - $this->element('legend', null, _('Change colours')); - $this->elementStart('ul', 'form_data'); - - //This is a JSON object in the DB field. Here for testing. Remove later. - $userSwatch = '{"body":{"background-color":"#F0F2F5"}, - "#content":{"background-color":"#FFFFFF"}, - "#aside_primary":{"background-color":"#CEE1E9"}, - "html body":{"color":"#000000"}, - "a":{"color":"#002E6E"}}'; - - //Default theme swatch -- Where should this be stored? - $defaultSwatch = array('body' => array('background-color' => '#F0F2F5'), - '#content' => array('background-color' => '#FFFFFF'), - '#aside_primary' => array('background-color' => '#CEE1E9'), - 'html body' => array('color' => '#000000'), - 'a' => array('color' => '#002E6E')); - - $userSwatch = ($userSwatch) ? json_decode($userSwatch, true) : $defaultSwatch; - - $s = 0; - $labelSwatch = array('Background', - 'Content', - 'Sidebar', - 'Text', - 'Links'); - foreach($userSwatch as $propertyvalue => $value) { - $foo = array_values($value); - $this->elementStart('li'); - $this->element('label', array('for' => 'swatch-'.$s), _($labelSwatch[$s])); - $this->element('input', array('name' => 'swatch-'.$s, //prefer swatch[$s] ? - 'type' => 'text', - 'id' => 'swatch-'.$s, - 'class' => 'swatch', - 'maxlength' => '7', - 'size' => '7', - 'value' => $foo[0])); - $this->elementEnd('li'); - $s++; - } - - $this->elementEnd('ul'); - $this->elementEnd('fieldset'); - - $this->element('input', array('id' => 'settings_design_reset', - 'type' => 'reset', - 'value' => 'Reset', - 'class' => 'submit form_action-primary', - 'title' => _('Reset back to default'))); - $this->submit('save', _('Save'), 'submit form_action-secondary', 'save', _('Save design')); - -/*TODO: Check submitted form values: -json_encode(form values) -if submitted Swatch == DefaultSwatch, don't store in DB. -else store in BD -*/ - $this->elementEnd('fieldset'); - $this->elementEnd('form'); - - } - - /** - * Handle a post - * - * Validate input and save changes. Reload the form with a success - * or error message. - * - * @return void - */ - - function handlePost() - { - /* - // CSRF protection - - $token = $this->trimmed('token'); - if (!$token || $token != common_session_token()) { - $this->showForm(_('There was a problem with your session token. '. - 'Try again, please.')); - return; - } - - $user = common_current_user(); - assert(!is_null($user)); // should already be checked - - // FIXME: scrub input - - $newpassword = $this->arg('newpassword'); - $confirm = $this->arg('confirm'); - - # Some validation - - if (strlen($newpassword) < 6) { - $this->showForm(_('Password must be 6 or more characters.')); - return; - } else if (0 != strcmp($newpassword, $confirm)) { - $this->showForm(_('Passwords don\'t match.')); - return; - } - - if ($user->password) { - $oldpassword = $this->arg('oldpassword'); - - if (!common_check_user($user->nickname, $oldpassword)) { - $this->showForm(_('Incorrect old password')); - return; - } - } - - $original = clone($user); - - $user->password = common_munge_password($newpassword, $user->id); - - $val = $user->validate(); - if ($val !== true) { - $this->showForm(_('Error saving user; invalid.')); - return; - } - - if (!$user->update($original)) { - $this->serverError(_('Can\'t save new password.')); - return; - } - - $this->showForm(_('Password saved.'), true); - */ - } - - - /** - * Add the Farbtastic stylesheet - * - * @return void - */ - - function showStylesheets() - { - parent::showStylesheets(); - $farbtasticStyle = - common_path('theme/base/css/farbtastic.css?version='.LACONICA_VERSION); - - $this->element('link', array('rel' => 'stylesheet', - 'type' => 'text/css', - 'href' => $farbtasticStyle, - 'media' => 'screen, projection, tv')); - } - - /** - * Add the Farbtastic scripts - * - * @return void - */ - - function showScripts() - { - parent::showScripts(); - - $farbtasticPack = common_path('js/farbtastic/farbtastic.js'); - $farbtasticGo = common_path('js/farbtastic/farbtastic.go.js'); - - $this->element('script', array('type' => 'text/javascript', - 'src' => $farbtasticPack)); - $this->element('script', array('type' => 'text/javascript', - 'src' => $farbtasticGo)); - } -} diff --git a/actions/disfavor.php b/actions/disfavor.php index bc13b09da..740f7de93 100644 --- a/actions/disfavor.php +++ b/actions/disfavor.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/doc.php b/actions/doc.php index e6508030b..54ae13803 100644 --- a/actions/doc.php +++ b/actions/doc.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/editgroup.php b/actions/editgroup.php index 39dad0465..6aa6f8b11 100644 --- a/actions/editgroup.php +++ b/actions/editgroup.php @@ -23,6 +23,7 @@ * @package Laconica * @author Evan Prodromou <evan@controlyourself.ca> * @author Sarven Capadisli <csarven@controlyourself.ca> + * @author Zach Copley <zach@controlyourself.ca> * @copyright 2008-2009 Control Yourself, Inc. * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 * @link http://laconi.ca/ @@ -40,14 +41,15 @@ if (!defined('LACONICA')) { * @category Group * @package Laconica * @author Evan Prodromou <evan@controlyourself.ca> + * @author Zach Copley <zach@controlyourself.ca> * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 * @link http://laconi.ca/ */ -class EditgroupAction extends Action +class EditgroupAction extends GroupDesignAction { + var $msg; - var $group = null; function title() { @@ -171,6 +173,7 @@ class EditgroupAction extends Action $homepage = $this->trimmed('homepage'); $description = $this->trimmed('description'); $location = $this->trimmed('location'); + $aliasstring = $this->trimmed('aliases'); if (!Validate::string($nickname, array('min_length' => 1, 'max_length' => 64, @@ -201,6 +204,39 @@ class EditgroupAction extends Action return; } + if (!empty($aliasstring)) { + $aliases = array_map('common_canonical_nickname', array_unique(preg_split('/[\s,]+/', $aliasstring))); + } else { + $aliases = array(); + } + + if (count($aliases) > common_config('group', 'maxaliases')) { + $this->showForm(sprintf(_('Too many aliases! Maximum %d.'), + common_config('group', 'maxaliases'))); + return; + } + + foreach ($aliases as $alias) { + if (!Validate::string($alias, array('min_length' => 1, + 'max_length' => 64, + 'format' => NICKNAME_FMT))) { + $this->showForm(sprintf(_('Invalid alias: "%s"'), $alias)); + return; + } + if ($this->nicknameExists($alias)) { + $this->showForm(sprintf(_('Alias "%s" already in use. Try another one.'), + $alias)); + return; + } + // XXX assumes alphanum nicknames + if (strcmp($alias, $nickname) == 0) { + $this->showForm(_('Alias can\'t be the same as nickname.')); + return; + } + } + + $this->group->query('BEGIN'); + $orig = clone($this->group); $this->group->nickname = $nickname; @@ -217,6 +253,14 @@ class EditgroupAction extends Action $this->serverError(_('Could not update group.')); } + $result = $this->group->setAliases($aliases); + + if (!$result) { + $this->serverError(_('Could not create aliases.')); + } + + $this->group->query('COMMIT'); + if ($this->group->nickname != $orig->nickname) { common_redirect(common_local_url('editgroup', array('nickname' => $nickname)), @@ -229,9 +273,20 @@ class EditgroupAction extends Action function nicknameExists($nickname) { $group = User_group::staticGet('nickname', $nickname); - return (!is_null($group) && - $group != false && - $group->id != $this->group->id); + + if (!empty($group) && + $group->id != $this->group->id) { + return true; + } + + $alias = Group_alias::staticGet('alias', $nickname); + + if (!empty($alias) && + $alias->group_id != $this->group->id) { + return true; + } + + return false; } } diff --git a/actions/facebookhome.php b/actions/facebookhome.php index 00b35ef68..34989c978 100644 --- a/actions/facebookhome.php +++ b/actions/facebookhome.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -21,29 +21,28 @@ if (!defined('LACONICA')) { exit(1); } require_once INSTALLDIR.'/lib/facebookaction.php'; - class FacebookhomeAction extends FacebookAction { var $page = null; - + function prepare($argarray) - { + { parent::prepare($argarray); - + $this->page = $this->trimmed('page'); - + if (!$this->page) { $this->page = 1; } - + return true; } function handle($args) { - parent::handle($args); - + parent::handle($args); + // If the user has opted not to initially allow the app to have // Facebook status update permission, store that preference. Only // promt the user the first time she uses the app @@ -73,7 +72,7 @@ class FacebookhomeAction extends FacebookAction $this->updateProfileBox($notice); } - if ($this->arg('status_submit') == 'Send') { + if ($this->arg('status_submit') == 'Send') { $this->saveNewNotice(); } @@ -81,7 +80,7 @@ class FacebookhomeAction extends FacebookAction // Facebook status update permission? Then show the main page // of the app $this->showPage(); - + } else { // User hasn't authenticated yet, prompt for creds @@ -89,12 +88,12 @@ class FacebookhomeAction extends FacebookAction } } - + function login() { - + $this->showStylesheets(); - + $nickname = common_canonical_nickname($this->trimmed('nickname')); $password = $this->arg('password'); @@ -141,13 +140,12 @@ class FacebookhomeAction extends FacebookAction $this->facebook->api_client->data_setUserPreference( FACEBOOK_PROMPTED_UPDATE_PREF, 'false'); } - function showNoticeForm() { $post_action = "$this->app_uri/index.php"; - - $notice_form = new FacebookNoticeForm($this, $post_action, null, + + $notice_form = new FacebookNoticeForm($this, $post_action, null, $post_action, $this->user); $notice_form->show(); } @@ -163,9 +161,8 @@ class FacebookhomeAction extends FacebookAction function showContent() { - $notice = $this->user->noticesWithFriends(($this->page-1) * - NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1); - + $notice = $this->user->noticeInbox(($this->page-1) * NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1); + $nl = new NoticeList($notice, $this); $cnt = $nl->show(); @@ -176,7 +173,7 @@ class FacebookhomeAction extends FacebookAction function showNoticeList($notice) { - + $nl = new NoticeList($notice, $this); return $nl->show(); } @@ -201,16 +198,16 @@ class FacebookhomeAction extends FacebookAction $this->elementStart('ul', array('id' => 'fb-permissions-list')); $this->elementStart('li', array('id' => 'fb-permissions-item')); - + $next = urlencode("$this->app_uri/index.php"); $api_key = common_config('facebook', 'apikey'); - + $auth_url = 'http://www.facebook.com/authorize.php?api_key=' . - $api_key . '&v=1.0&ext_perm=status_update&next=' . $next . + $api_key . '&v=1.0&ext_perm=status_update&next=' . $next . '&next_cancel=' . $next . '&submit=skip'; - + $this->elementStart('span', array('class' => 'facebook-button')); - $this->element('a', array('href' => $auth_url), + $this->element('a', array('href' => $auth_url), sprintf(_('Okay, do it!'), $this->app_name)); $this->elementEnd('span'); @@ -225,7 +222,7 @@ class FacebookhomeAction extends FacebookAction $this->elementEnd('div'); } - + /** * Generate pagination links * @@ -239,11 +236,11 @@ class FacebookhomeAction extends FacebookAction */ function pagination($have_before, $have_after, $page, $action, $args=null) { - + // Does a little before-after block for next/prev page - + // XXX: Fix so this uses common_local_url() if possible. - + if ($have_before || $have_after) { $this->elementStart('div', array('class' => 'pagination')); $this->elementStart('dl', null); @@ -254,7 +251,7 @@ class FacebookhomeAction extends FacebookAction if ($have_before) { $pargs = array('page' => $page-1); $newargs = $args ? array_merge($args, $pargs) : $pargs; - $this->elementStart('li', array('class' => 'nav_prev')); + $this->elementStart('li', array('class' => 'nav_prev')); $this->element('a', array('href' => "$action?page=$newargs[page]", 'rel' => 'prev'), _('After')); $this->elementEnd('li'); @@ -274,6 +271,5 @@ class FacebookhomeAction extends FacebookAction $this->elementEnd('div'); } } - } diff --git a/actions/facebookinvite.php b/actions/facebookinvite.php index 2207580f7..f43d04e27 100644 --- a/actions/facebookinvite.php +++ b/actions/facebookinvite.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/facebooklogin.php b/actions/facebooklogin.php index 94d494a82..22007da4f 100644 --- a/actions/facebooklogin.php +++ b/actions/facebooklogin.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/facebookremove.php b/actions/facebookremove.php index 376e12a2e..9ca7a77a8 100644 --- a/actions/facebookremove.php +++ b/actions/facebookremove.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/facebooksettings.php b/actions/facebooksettings.php index 227e12316..ee2c279ab 100644 --- a/actions/facebooksettings.php +++ b/actions/facebooksettings.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/favor.php b/actions/favor.php index 3b7d979eb..ec86b17e6 100644 --- a/actions/favor.php +++ b/actions/favor.php @@ -15,7 +15,7 @@ /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/favoritesrss.php b/actions/favoritesrss.php index 6b46b8dec..c439a9a62 100644 --- a/actions/favoritesrss.php +++ b/actions/favoritesrss.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/featured.php b/actions/featured.php index 79eba2aa6..04365687d 100644 --- a/actions/featured.php +++ b/actions/featured.php @@ -32,7 +32,7 @@ if (!defined('LACONICA')) { exit(1); } -require_once(INSTALLDIR.'/lib/profilelist.php'); +require_once INSTALLDIR.'/lib/profilelist.php'; require_once INSTALLDIR.'/lib/publicgroupnav.php'; /** @@ -107,7 +107,6 @@ class FeaturedAction extends Action $featured_nicks = common_config('nickname', 'featured'); - if (count($featured_nicks) > 0) { $quoted = array(); @@ -136,7 +135,7 @@ class FeaturedAction extends Action $cnt = $profile->find(); if ($cnt > 0) { - $featured = new ProfileList($profile, null, $this); + $featured = new ProfileList($profile, $this); $featured->show(); } diff --git a/actions/file.php b/actions/file.php index 1179dbe9a..271f57ab9 100644 --- a/actions/file.php +++ b/actions/file.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -21,20 +21,40 @@ if (!defined('LACONICA')) { exit(1); } require_once(INSTALLDIR.'/actions/shownotice.php'); -class FileAction extends ShowNoticeAction +class FileAction extends Action { - function showPage() { - $source_url = common_local_url('file', array('notice' => $this->notice->id)); - $query = "select file_redirection.url as url from file join file_redirection on file.id = file_redirection.file_id where file.url = '$source_url'"; - $file = new File_redirection; - $file->query($query); - $file->fetch(); - if (empty($file->url)) { - die('nothing attached here'); - } else { - header("Location: {$file->url}"); - die(); + var $id = null; + var $filerec = null; + + function prepare($args) + { + parent::prepare($args); + $this->id = $this->trimmed('notice'); + if (empty($this->id)) { + $this->clientError(_('No notice id')); + } + $notice = Notice::staticGet('id', $this->id); + if (empty($notice)) { + $this->clientError(_('No notice')); + } + $atts = $notice->attachments(); + if (empty($atts)) { + $this->clientError(_('No attachments')); + } + foreach ($atts as $att) { + if (!empty($att->filename)) { + $this->filerec = $att; + break; + } } + if (empty($this->filerec)) { + $this->clientError(_('No uploaded attachments')); + } + return true; + } + + function handle() { + common_redirect($this->filerec->url); } } diff --git a/actions/finishopenidlogin.php b/actions/finishopenidlogin.php index b08b96df6..e9f7c746b 100644 --- a/actions/finishopenidlogin.php +++ b/actions/finishopenidlogin.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/finishremotesubscribe.php b/actions/finishremotesubscribe.php index 3e3a81715..5c764aeb0 100644 --- a/actions/finishremotesubscribe.php +++ b/actions/finishremotesubscribe.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/foaf.php b/actions/foaf.php index fb0172eb9..b481b2437 100644 --- a/actions/foaf.php +++ b/actions/foaf.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/groupblock.php b/actions/groupblock.php new file mode 100644 index 000000000..ce2c6c144 --- /dev/null +++ b/actions/groupblock.php @@ -0,0 +1,215 @@ +<?php +/** + * Block a user from a group action class. + * + * PHP version 5 + * + * @category Action + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://laconi.ca/ + * + * Laconica - a distributed open-source microblogging tool + * Copyright (C) 2008, 2009, Control Yourself, Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +if (!defined('LACONICA')) { + exit(1); +} + +/** + * Block a user from a group + * + * @category Action + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://laconi.ca/ + */ + +class GroupblockAction extends Action +{ + var $profile = null; + var $group = null; + + /** + * Take arguments for running + * + * @param array $args $_REQUEST args + * + * @return boolean success flag + */ + + function prepare($args) + { + parent::prepare($args); + if (!common_logged_in()) { + $this->clientError(_('Not logged in.')); + return false; + } + $token = $this->trimmed('token'); + if (empty($token) || $token != common_session_token()) { + $this->clientError(_('There was a problem with your session token. Try again, please.')); + return; + } + $id = $this->trimmed('blockto'); + if (empty($id)) { + $this->clientError(_('No profile specified.')); + return false; + } + $this->profile = Profile::staticGet('id', $id); + if (empty($this->profile)) { + $this->clientError(_('No profile with that ID.')); + return false; + } + $group_id = $this->trimmed('blockgroup'); + if (empty($group_id)) { + $this->clientError(_('No group specified.')); + return false; + } + $this->group = User_group::staticGet('id', $group_id); + if (empty($this->group)) { + $this->clientError(_('No such group.')); + return false; + } + $user = common_current_user(); + if (!$user->isAdmin($this->group)) { + $this->clientError(_('Only an admin can block group members.'), 401); + return false; + } + if (Group_block::isBlocked($this->group, $this->profile)) { + $this->clientError(_('User is already blocked from group.')); + return false; + } + // XXX: could have proactive blocks, but we don't have UI for it. + if (!$this->profile->isMember($this->group)) { + $this->clientError(_('User is not a member of group.')); + return false; + } + return true; + } + + /** + * Handle request + * + * Shows a page with list of favorite notices + * + * @param array $args $_REQUEST args; handled in prepare() + * + * @return void + */ + function handle($args) + { + parent::handle($args); + if ($_SERVER['REQUEST_METHOD'] == 'POST') { + if ($this->arg('no')) { + common_redirect(common_local_url('groupmembers', + array('nickname' => $this->group->nickname)), + 303); + } elseif ($this->arg('yes')) { + $this->blockProfile(); + } elseif ($this->arg('blockto')) { + $this->showPage(); + } + } + } + + function showContent() { + $this->areYouSureForm(); + } + + function title() { + return _('Block user from group'); + } + + function showNoticeForm() { + // nop + } + + /** + * Confirm with user. + * + * Shows a confirmation form. + * + * @return void + */ + + function areYouSureForm() + { + $id = $this->profile->id; + $this->element('p', null, + sprintf(_('Are you sure you want to block user "%s" from the group "%s"? '. + 'They will be removed from the group, unable to post, and '. + 'unable to subscribe to the group in the future.'), + $this->profile->getBestName(), + $this->group->getBestName())); + $this->elementStart('form', array('id' => 'block-' . $id, + 'method' => 'post', + 'class' => 'block', + 'action' => common_local_url('groupblock'))); + $this->hidden('token', common_session_token()); + $this->hidden('blockto-' . $this->profile->id, + $this->profile->id, + 'blockto'); + $this->hidden('blockgroup-' . $this->group->id, + $this->group->id, + 'blockgroup'); + foreach ($this->args as $k => $v) { + if (substr($k, 0, 9) == 'returnto-') { + $this->hidden($k, $v); + } + } + $this->submit('no', _('No')); + $this->submit('yes', _('Yes')); + $this->elementEnd('form'); + } + + /** + * Actually block a user. + * + * @return void + */ + + function blockProfile() + { + $block = Group_block::blockProfile($this->group, $this->profile, + common_current_user()); + + if (empty($block)) { + $this->serverError(_("Database error blocking user from group.")); + return false; + } + + // Now, gotta figure where we go back to + foreach ($this->args as $k => $v) { + if ($k == 'returnto-action') { + $action = $v; + } elseif (substr($k, 0, 9) == 'returnto-') { + $args[substr($k, 9)] = $v; + } + } + + if ($action) { + common_redirect(common_local_url($action, $args), 303); + } else { + common_redirect(common_local_url('groupmembers', + array('nickname' => $this->group->nickname)), + 303); + } + } +} + diff --git a/actions/groupdesignsettings.php b/actions/groupdesignsettings.php new file mode 100644 index 000000000..79c192ac4 --- /dev/null +++ b/actions/groupdesignsettings.php @@ -0,0 +1,328 @@ +<?php +/** + * Laconica, the distributed open-source microblogging tool + * + * Change user password + * + * PHP version 5 + * + * LICENCE: This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + * + * @category Settings + * @package Laconica + * @author Sarven Capadisli <csarven@controlyourself.ca> + * @author Zach Copley <zach@controlyourself.ca> + * @copyright 2008-2009 Control Yourself, Inc. + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + */ + +if (!defined('LACONICA')) { + exit(1); +} + +require_once INSTALLDIR . '/lib/designsettings.php'; + +class GroupDesignSettingsAction extends DesignSettingsAction +{ + var $group = null; + + /** + * Prepare to run + */ + + function prepare($args) + { + parent::prepare($args); + + if (!common_config('inboxes','enabled')) { + $this->serverError(_('Inboxes must be enabled for groups to work')); + return false; + } + + if (!common_logged_in()) { + $this->clientError(_('You must be logged in to edit a group.')); + return false; + } + + $nickname_arg = $this->trimmed('nickname'); + $nickname = common_canonical_nickname($nickname_arg); + + // Permanent redirect on non-canonical nickname + + if ($nickname_arg != $nickname) { + $args = array('nickname' => $nickname); + common_redirect(common_local_url('groupdesignsettings', $args), 301); + return false; + } + + if (!$nickname) { + $this->clientError(_('No nickname'), 404); + return false; + } + + $groupid = $this->trimmed('groupid'); + + if ($groupid) { + $this->group = User_group::staticGet('id', $groupid); + } else { + $this->group = User_group::staticGet('nickname', $nickname); + } + + if (!$this->group) { + $this->clientError(_('No such group'), 404); + return false; + } + + $cur = common_current_user(); + + if (!$cur->isAdmin($this->group)) { + $this->clientError(_('You must be an admin to edit the group'), 403); + return false; + } + + $this->submitaction = common_local_url('groupdesignsettings', + array('nickname' => $this->group->nickname)); + + return true; + } + + /** + * A design for this action + * + * if the group attribute has been set, returns that group's + * design. + * + * @return Design a design object to use + */ + + function getDesign() + { + + if (empty($this->group)) { + return null; + } + + return $this->group->getDesign(); + } + + /** + * Title of the page + * + * @return string Title of the page + */ + + function title() + { + return _('Group design'); + } + + /** + * Instructions for use + * + * @return instructions for use + */ + + function getInstructions() + { + return _('Customize the way your group looks ' . + 'with a background image and a colour palette of your choice.'); + } + + /** + * Override to show group nav stuff + * + * @return nothing + */ + + function showLocalNav() + { + $nav = new GroupNav($this, $this->group); + $nav->show(); + } + + /** + * Get the design we want to edit + * + * @return Design + */ + + function getWorkingDesign() { + + $design = null; + + if (isset($this->group)) { + $design = $this->group->getDesign(); + } + + if (empty($design)) { + $design = $this->defaultDesign(); + } + + return $design; + } + + /** + * Content area of the page + * + * Shows a form for changing the design + * + * @return void + */ + + function showContent() + { + $this->showDesignForm($this->getWorkingDesign()); + } + + /** + * Save or update the group's design settings + * + * @return void + */ + + function saveDesign() + { + try { + + $bgcolor = new WebColor($this->trimmed('design_background')); + $ccolor = new WebColor($this->trimmed('design_content')); + $sbcolor = new WebColor($this->trimmed('design_sidebar')); + $tcolor = new WebColor($this->trimmed('design_text')); + $lcolor = new WebColor($this->trimmed('design_links')); + + } catch (WebColorException $e) { + $this->showForm($e->getMessage()); + return; + } + + $onoff = $this->arg('design_background-image_onoff'); + + $on = false; + $off = false; + $tile = false; + + if ($onoff == 'on') { + $on = true; + } else { + $off = true; + } + + $repeat = $this->boolean('design_background-image_repeat'); + + if ($repeat) { + $tile = true; + } + + $design = $this->group->getDesign(); + + if (!empty($design)) { + + // update design + + $original = clone($design); + + $design->backgroundcolor = $bgcolor->intValue(); + $design->contentcolor = $ccolor->intValue(); + $design->sidebarcolor = $sbcolor->intValue(); + $design->textcolor = $tcolor->intValue(); + $design->linkcolor = $lcolor->intValue(); + + $design->setDisposition($on, $off, $tile); + + $result = $design->update($original); + + if ($result === false) { + common_log_db_error($design, 'UPDATE', __FILE__); + $this->showForm(_('Couldn\'t update your design.')); + return; + } + + } else { + + $this->group->query('BEGIN'); + + // save new design + + $design = new Design(); + + $design->backgroundcolor = $bgcolor->intValue(); + $design->contentcolor = $ccolor->intValue(); + $design->sidebarcolor = $sbcolor->intValue(); + $design->textcolor = $tcolor->intValue(); + $design->linkcolor = $lcolor->intValue(); + + $design->setDisposition($on, $off, $tile); + + $id = $design->insert(); + + if (empty($id)) { + common_log_db_error($id, 'INSERT', __FILE__); + $this->showForm(_('Unable to save your design settings!')); + return; + } + + $original = clone($this->group); + $this->group->design_id = $id; + $result = $this->group->update($original); + + if (empty($result)) { + common_log_db_error($original, 'UPDATE', __FILE__); + $this->showForm(_('Unable to save your design settings!')); + $this->group->query('ROLLBACK'); + return; + } + + $this->group->query('COMMIT'); + + } + + $this->saveBackgroundImage($design); + + $this->showForm(_('Design preferences saved.'), true); + } + + /** + * Handle input and output a page (overrided) + * + * @param array $args $_REQUEST arguments + * + * @return void + */ + + function handle($args) + { + parent::handle($args); + if (!common_logged_in()) { + $this->clientError(_('Not logged in.')); + return; + } else if (!common_is_real_login()) { + // Cookie theft means that automatic logins can't + // change important settings or see private info, and + // _all_ our settings are important + common_set_returnto($this->selfUrl()); + $user = common_current_user(); + if ($user->hasOpenID()) { + common_redirect(common_local_url('openidlogin'), 303); + } else { + common_redirect(common_local_url('login'), 303); + } + } else if ($_SERVER['REQUEST_METHOD'] == 'POST') { + $this->handlePost(); + } else { + $this->showForm(); + } + } + +} diff --git a/actions/grouplogo.php b/actions/grouplogo.php index fe6127da2..8f6158dac 100644 --- a/actions/grouplogo.php +++ b/actions/grouplogo.php @@ -50,7 +50,7 @@ define('MAX_ORIGINAL', 480); * @link http://laconi.ca/ */ -class GrouplogoAction extends Action +class GrouplogoAction extends GroupDesignAction { var $mode = null; var $imagefile = null; diff --git a/actions/groupmembers.php b/actions/groupmembers.php index 21e5ebbaa..d132cdf96 100644 --- a/actions/groupmembers.php +++ b/actions/groupmembers.php @@ -44,7 +44,7 @@ require_once INSTALLDIR.'/lib/publicgroupnav.php'; * @link http://laconi.ca/ */ -class GroupmembersAction extends Action +class GroupmembersAction extends GroupDesignAction { var $page = null; @@ -127,7 +127,7 @@ class GroupmembersAction extends Action $members = $this->group->getMembers($offset, $limit); if ($members) { - $member_list = new ProfileList($members, null, $this); + $member_list = new GroupMemberList($members, $this->group, $this); $cnt = $member_list->show(); } @@ -138,3 +138,326 @@ class GroupmembersAction extends Action array('nickname' => $this->group->nickname)); } } + +class GroupMemberList extends ProfileList +{ + var $group = null; + + function __construct($profile, $group, $action) + { + parent::__construct($profile, $action); + + $this->group = $group; + } + + function newListItem($profile) + { + return new GroupMemberListItem($profile, $this->group, $this->action); + } +} + +class GroupMemberListItem extends ProfileListItem +{ + var $group = null; + + function __construct($profile, $group, $action) + { + parent::__construct($profile, $action); + + $this->group = $group; + } + + function showActions() + { + $this->startActions(); + $this->showSubscribeButton(); + $this->showMakeAdminForm(); + $this->showGroupBlockForm(); + $this->endActions(); + } + + function showMakeAdminForm() + { + $user = common_current_user(); + + if (!empty($user) && $user->id != $this->profile->id && $user->isAdmin($this->group) && + !$this->profile->isAdmin($this->group)) { + $this->out->elementStart('li', 'entity_make_admin'); + $maf = new MakeAdminForm($this->out, $this->profile, $this->group, + array('action' => 'groupmembers', + 'nickname' => $this->group->nickname)); + $maf->show(); + $this->out->elementEnd('li'); + } + + } + function showGroupBlockForm() + { + $user = common_current_user(); + + if (!empty($user) && $user->id != $this->profile->id && $user->isAdmin($this->group)) { + $this->out->elementStart('li', 'entity_block'); + $bf = new GroupBlockForm($this->out, $this->profile, $this->group, + array('action' => 'groupmembers', + 'nickname' => $this->group->nickname)); + $bf->show(); + $this->out->elementEnd('li'); + } + + } +} + +/** + * Form for blocking a user from a group + * + * @category Form + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @author Sarven Capadisli <csarven@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + * + * @see BlockForm + */ + +class GroupBlockForm extends Form +{ + /** + * Profile of user to block + */ + + var $profile = null; + + /** + * Group to block the user from + */ + + var $group = null; + + /** + * Return-to args + */ + + var $args = null; + + /** + * Constructor + * + * @param HTMLOutputter $out output channel + * @param Profile $profile profile of user to block + * @param User_group $group group to block user from + * @param array $args return-to args + */ + + function __construct($out=null, $profile=null, $group=null, $args=null) + { + parent::__construct($out); + + $this->profile = $profile; + $this->group = $group; + $this->args = $args; + } + + /** + * ID of the form + * + * @return int ID of the form + */ + + function id() + { + // This should be unique for the page. + return 'block-' . $this->profile->id; + } + + /** + * class of the form + * + * @return string class of the form + */ + + function formClass() + { + return 'form_group_block'; + } + + /** + * Action of the form + * + * @return string URL of the action + */ + + function action() + { + return common_local_url('groupblock'); + } + + /** + * Legend of the Form + * + * @return void + */ + function formLegend() + { + $this->out->element('legend', null, _('Block user from group')); + } + + /** + * Data elements of the form + * + * @return void + */ + + function formData() + { + $this->out->hidden('blockto-' . $this->profile->id, + $this->profile->id, + 'blockto'); + $this->out->hidden('blockgroup-' . $this->group->id, + $this->group->id, + 'blockgroup'); + if ($this->args) { + foreach ($this->args as $k => $v) { + $this->out->hidden('returnto-' . $k, $v); + } + } + } + + /** + * Action elements + * + * @return void + */ + + function formActions() + { + $this->out->submit('submit', _('Block'), 'submit', null, _('Block this user')); + } +} + +/** + * Form for making a user an admin for a group + * + * @category Form + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @author Sarven Capadisli <csarven@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + */ + +class MakeAdminForm extends Form +{ + /** + * Profile of user to block + */ + + var $profile = null; + + /** + * Group to block the user from + */ + + var $group = null; + + /** + * Return-to args + */ + + var $args = null; + + /** + * Constructor + * + * @param HTMLOutputter $out output channel + * @param Profile $profile profile of user to block + * @param User_group $group group to block user from + * @param array $args return-to args + */ + + function __construct($out=null, $profile=null, $group=null, $args=null) + { + parent::__construct($out); + + $this->profile = $profile; + $this->group = $group; + $this->args = $args; + } + + /** + * ID of the form + * + * @return int ID of the form + */ + + function id() + { + // This should be unique for the page. + return 'makeadmin-' . $this->profile->id; + } + + /** + * class of the form + * + * @return string class of the form + */ + + function formClass() + { + return 'form_make_admin'; + } + + /** + * Action of the form + * + * @return string URL of the action + */ + + function action() + { + return common_local_url('makeadmin', array('nickname' => $this->group->nickname)); + } + + /** + * Legend of the Form + * + * @return void + */ + + function formLegend() + { + $this->out->element('legend', null, _('Make user an admin of the group')); + } + + /** + * Data elements of the form + * + * @return void + */ + + function formData() + { + $this->out->hidden('profileid-' . $this->profile->id, + $this->profile->id, + 'profileid'); + $this->out->hidden('groupid-' . $this->group->id, + $this->group->id, + 'groupid'); + if ($this->args) { + foreach ($this->args as $k => $v) { + $this->out->hidden('returnto-' . $k, $v); + } + } + } + + /** + * Action elements + * + * @return void + */ + + function formActions() + { + $this->out->submit('submit', _('Make Admin'), 'submit', null, _('Make this user an admin')); + } +} diff --git a/actions/groups.php b/actions/groups.php index 26b52a5fc..b49d80f37 100644 --- a/actions/groups.php +++ b/actions/groups.php @@ -100,11 +100,13 @@ class GroupsAction extends Action function showContent() { - $this->elementStart('p', array('id' => 'new_group')); - $this->element('a', array('href' => common_local_url('newgroup'), - 'class' => 'more'), - _('Create a new group')); - $this->elementEnd('p'); + if (common_logged_in()) { + $this->elementStart('p', array('id' => 'new_group')); + $this->element('a', array('href' => common_local_url('newgroup'), + 'class' => 'more'), + _('Create a new group')); + $this->elementEnd('p'); + } $offset = ($this->page-1) * GROUPS_PER_PAGE; $limit = GROUPS_PER_PAGE + 1; diff --git a/actions/groupsearch.php b/actions/groupsearch.php index 06b4a7755..c50466ce6 100644 --- a/actions/groupsearch.php +++ b/actions/groupsearch.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/groupunblock.php b/actions/groupunblock.php new file mode 100644 index 000000000..6beb46352 --- /dev/null +++ b/actions/groupunblock.php @@ -0,0 +1,149 @@ +<?php +/** + * Block a user from a group action class. + * + * PHP version 5 + * + * @category Action + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://laconi.ca/ + * + * Laconica - a distributed open-source microblogging tool + * Copyright (C) 2008, 2009, Control Yourself, Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +if (!defined('LACONICA')) { + exit(1); +} + +/** + * Unlock a user from a group + * + * @category Action + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://laconi.ca/ + */ + +class GroupunblockAction extends Action +{ + var $profile = null; + var $group = null; + + /** + * Take arguments for running + * + * @param array $args $_REQUEST args + * + * @return boolean success flag + */ + + function prepare($args) + { + parent::prepare($args); + if (!common_logged_in()) { + $this->clientError(_('Not logged in.')); + return false; + } + $token = $this->trimmed('token'); + if (empty($token) || $token != common_session_token()) { + $this->clientError(_('There was a problem with your session token. Try again, please.')); + return; + } + $id = $this->trimmed('unblockto'); + if (empty($id)) { + $this->clientError(_('No profile specified.')); + return false; + } + $this->profile = Profile::staticGet('id', $id); + if (empty($this->profile)) { + $this->clientError(_('No profile with that ID.')); + return false; + } + $group_id = $this->trimmed('unblockgroup'); + if (empty($group_id)) { + $this->clientError(_('No group specified.')); + return false; + } + $this->group = User_group::staticGet('id', $group_id); + if (empty($this->group)) { + $this->clientError(_('No such group.')); + return false; + } + $user = common_current_user(); + if (!$user->isAdmin($this->group)) { + $this->clientError(_('Only an admin can unblock group members.'), 401); + return false; + } + if (!Group_block::isBlocked($this->group, $this->profile)) { + $this->clientError(_('User is not blocked from group.')); + return false; + } + return true; + } + + /** + * Handle request + * + * @param array $args $_REQUEST args; handled in prepare() + * + * @return void + */ + + function handle($args) + { + parent::handle($args); + if ($_SERVER['REQUEST_METHOD'] == 'POST') { + $this->unblockProfile(); + } + } + + /** + * Unblock a user. + * + * @return void + */ + + function unblockProfile() + { + $result = Group_block::unblockProfile($this->group, $this->profile); + + if (!$result) { + $this->serverError(_('Error removing the block.')); + return; + } + + foreach ($this->args as $k => $v) { + if ($k == 'returnto-action') { + $action = $v; + } else if (substr($k, 0, 9) == 'returnto-') { + $args[substr($k, 9)] = $v; + } + } + + if ($action) { + common_redirect(common_local_url($action, $args), 303); + } else { + common_redirect(common_local_url('blockedfromgroup', + array('nickname' => $this->group->nickname)), + 303); + } + } +} + diff --git a/actions/invite.php b/actions/invite.php index 9631f7a7f..bdea4807d 100644 --- a/actions/invite.php +++ b/actions/invite.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -19,7 +19,7 @@ if (!defined('LACONICA')) { exit(1); } -class InviteAction extends Action +class InviteAction extends CurrentUserDesignAction { var $mode = null; var $error = null; diff --git a/actions/joingroup.php b/actions/joingroup.php index a5d82ddc7..0e4f96eaf 100644 --- a/actions/joingroup.php +++ b/actions/joingroup.php @@ -96,6 +96,11 @@ class JoingroupAction extends Action return false; } + if (Group_block::isBlocked($this->group, $cur->getProfile())) { + $this->clientError(_('You have been blocked from that group by the admin.'), 403); + return false; + } + return true; } diff --git a/actions/logout.php b/actions/logout.php index c34b10987..3fcfb4f4e 100644 --- a/actions/logout.php +++ b/actions/logout.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/makeadmin.php b/actions/makeadmin.php new file mode 100644 index 000000000..6fc2cf9ab --- /dev/null +++ b/actions/makeadmin.php @@ -0,0 +1,166 @@ +<?php +/** + * Make another user an admin of a group + * + * PHP version 5 + * + * @category Action + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://laconi.ca/ + * + * Laconica - a distributed open-source microblogging tool + * Copyright (C) 2008, 2009, Control Yourself, Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +if (!defined('LACONICA')) { + exit(1); +} + +/** + * Make another user an admin of a group + * + * @category Action + * @package Laconica + * @author Evan Prodromou <evan@controlyourself.ca> + * @license http://www.fsf.org/licensing/licenses/agpl.html AGPLv3 + * @link http://laconi.ca/ + */ + +class MakeadminAction extends Action +{ + var $profile = null; + var $group = null; + + /** + * Take arguments for running + * + * @param array $args $_REQUEST args + * + * @return boolean success flag + */ + + function prepare($args) + { + parent::prepare($args); + if (!common_logged_in()) { + $this->clientError(_('Not logged in.')); + return false; + } + $token = $this->trimmed('token'); + if (empty($token) || $token != common_session_token()) { + $this->clientError(_('There was a problem with your session token. Try again, please.')); + return; + } + $id = $this->trimmed('profileid'); + if (empty($id)) { + $this->clientError(_('No profile specified.')); + return false; + } + $this->profile = Profile::staticGet('id', $id); + if (empty($this->profile)) { + $this->clientError(_('No profile with that ID.')); + return false; + } + $group_id = $this->trimmed('groupid'); + if (empty($group_id)) { + $this->clientError(_('No group specified.')); + return false; + } + $this->group = User_group::staticGet('id', $group_id); + if (empty($this->group)) { + $this->clientError(_('No such group.')); + return false; + } + $user = common_current_user(); + if (!$user->isAdmin($this->group)) { + $this->clientError(_('Only an admin can make another user an admin.'), 401); + return false; + } + if ($this->profile->isAdmin($this->group)) { + $this->clientError(sprintf(_('%s is already an admin for group "%s".'), + $this->profile->getBestName(), + $this->group->getBestName()), + 401); + return false; + } + return true; + } + + /** + * Handle request + * + * @param array $args $_REQUEST args; handled in prepare() + * + * @return void + */ + + function handle($args) + { + parent::handle($args); + if ($_SERVER['REQUEST_METHOD'] == 'POST') { + $this->makeAdmin(); + } + } + + /** + * Make user an admin + * + * @return void + */ + + function makeAdmin() + { + $member = Group_member::pkeyGet(array('group_id' => $this->group->id, + 'profile_id' => $this->profile->id)); + + if (empty($member)) { + $this->serverError(_('Can\'t get membership record for %s in group %s'), + $this->profile->getBestName(), + $this->group->getBestName()); + } + + $orig = clone($member); + + $member->is_admin = 1; + + $result = $member->update($orig); + + if (!$result) { + common_log_db_error($member, 'UPDATE', __FILE__); + $this->serverError(_('Can\'t make %s an admin for group %s'), + $this->profile->getBestName(), + $this->group->getBestName()); + } + + foreach ($this->args as $k => $v) { + if ($k == 'returnto-action') { + $action = $v; + } else if (substr($k, 0, 9) == 'returnto-') { + $args[substr($k, 9)] = $v; + } + } + + if ($action) { + common_redirect(common_local_url($action, $args), 303); + } else { + common_redirect(common_local_url('groupmembers', + array('nickname' => $this->group->nickname)), + 303); + } + } +} diff --git a/actions/microsummary.php b/actions/microsummary.php index 0b408ec95..6884a919a 100644 --- a/actions/microsummary.php +++ b/actions/microsummary.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/newgroup.php b/actions/newgroup.php index 67cd6b2f1..0289e77c2 100644 --- a/actions/newgroup.php +++ b/actions/newgroup.php @@ -123,6 +123,7 @@ class NewgroupAction extends Action $homepage = $this->trimmed('homepage'); $description = $this->trimmed('description'); $location = $this->trimmed('location'); + $aliasstring = $this->trimmed('aliases'); if (!Validate::string($nickname, array('min_length' => 1, 'max_length' => 64, @@ -153,6 +154,37 @@ class NewgroupAction extends Action return; } + if (!empty($aliasstring)) { + $aliases = array_map('common_canonical_nickname', array_unique(preg_split('/[\s,]+/', $aliasstring))); + } else { + $aliases = array(); + } + + if (count($aliases) > common_config('group', 'maxaliases')) { + $this->showForm(sprintf(_('Too many aliases! Maximum %d.'), + common_config('group', 'maxaliases'))); + return; + } + + foreach ($aliases as $alias) { + if (!Validate::string($alias, array('min_length' => 1, + 'max_length' => 64, + 'format' => NICKNAME_FMT))) { + $this->showForm(sprintf(_('Invalid alias: "%s"'), $alias)); + return; + } + if ($this->nicknameExists($alias)) { + $this->showForm(sprintf(_('Alias "%s" already in use. Try another one.'), + $alias)); + return; + } + // XXX assumes alphanum nicknames + if (strcmp($alias, $nickname) == 0) { + $this->showForm(_('Alias can\'t be the same as nickname.')); + return; + } + } + $cur = common_current_user(); // Checked in prepare() above @@ -177,6 +209,12 @@ class NewgroupAction extends Action $this->serverError(_('Could not create group.')); } + $result = $group->setAliases($aliases); + + if (!$result) { + $this->serverError(_('Could not create aliases.')); + } + $member = new Group_member(); $member->group_id = $group->id; @@ -199,7 +237,18 @@ class NewgroupAction extends Action function nicknameExists($nickname) { $group = User_group::staticGet('nickname', $nickname); - return (!is_null($group) && $group != false); + + if (!empty($group)) { + return true; + } + + $alias = Group_alias::staticGet('alias', $nickname); + + if (!empty($alias)) { + return true; + } + + return false; } } diff --git a/actions/newnotice.php b/actions/newnotice.php index 02976a2ae..15caff6ea 100644 --- a/actions/newnotice.php +++ b/actions/newnotice.php @@ -116,6 +116,9 @@ class NewnoticeAction extends Action function getUploadedFileType() { require_once 'MIME/Type.php'; + $cmd = &PEAR::getStaticProperty('MIME_Type', 'fileCmd'); + $cmd = common_config('attachments', 'filecommand'); + $filetype = MIME_Type::autoDetect($_FILES['attach']['tmp_name']); if (in_array($filetype, common_config('attachments', 'supported'))) { return $filetype; @@ -221,17 +224,35 @@ class NewnoticeAction extends Action } } + if (isset($mimetype)) { + $filename = $this->saveFile($mimetype); + if (empty($filename)) { + $this->clientError(_('Couldn\'t save file.')); + } + $fileurl = File::url($filename); + $short_fileurl = common_shorten_url($fileurl); + $content_shortened .= ' ' . $short_fileurl; + if (mb_strlen($content_shortened) > 140) { + $this->deleteFile($filename); + $this->clientError(_('Max notice size is 140 chars, including attachment URL.')); + } + $fileRecord = $this->rememberFile($filename, $mimetype, $short_fileurl); + } + $notice = Notice::saveNew($user->id, $content_shortened, 'web', 1, ($replyto == 'false') ? null : $replyto); if (is_string($notice)) { + if (isset($filename)) { + $this->deleteFile($filename); + } $this->clientError($notice); } if (isset($mimetype)) { - $this->storeFile($notice, $mimetype); + $this->attachFile($notice, $fileRecord); } - $this->saveUrls($notice); + common_broadcast_notice($notice); if ($this->boolean('ajax')) { @@ -257,49 +278,82 @@ class NewnoticeAction extends Action } } - function storeFile($notice, $mimetype) { - $filename = basename($_FILES['attach']['name']); - $destination = "file/{$notice->id}-$filename"; - if (move_uploaded_file($_FILES['attach']['tmp_name'], INSTALLDIR . "/$destination")) { - $file = new File; - $file->url = common_local_url('file', array('notice' => $notice->id)); - $file->size = filesize(INSTALLDIR . "/$destination"); - $file->date = time(); - $file->mimetype = $mimetype; - if ($file_id = $file->insert()) { - $file_redir = new File_redirection; - $file_redir->url = common_path($destination); - $file_redir->file_id = $file_id; - $file_redir->insert(); - - $f2p = new File_to_post; - $f2p->file_id = $file_id; - $f2p->post_id = $notice->id; - $f2p->insert(); - } else { - $this->clientError(_('There was a database error while saving your file. Please try again.')); - } + function saveFile($mimetype) { + + $cur = common_current_user(); + + if (empty($cur)) { + $this->serverError(_('Somehow lost the login in saveFile')); + } + + $basename = basename($_FILES['attach']['name']); + + $filename = File::filename($cur->getProfile(), $basename, $mimetype); + + $filepath = File::path($filename); + + if (move_uploaded_file($_FILES['attach']['tmp_name'], $filepath)) { + return $filename; } else { $this->clientError(_('File could not be moved to destination directory.')); } } - /** save all urls in the notice to the db - * - * follow redirects and save all available file information - * (mimetype, date, size, oembed, etc.) - * - * @param class $notice Notice to pull URLs from - * - * @return void - */ - function saveUrls($notice, $uploaded = null) { - common_replace_urls_callback($notice->content, array($this, 'saveUrl'), $notice->id); + function deleteFile($filename) + { + $filepath = File::path($filename); + @unlink($filepath); + } + + function rememberFile($filename, $mimetype, $short) + { + $file = new File; + $file->filename = $filename; + + $file->url = File::url($filename); + + $filepath = File::path($filename); + + $file->size = filesize($filepath); + $file->date = time(); + $file->mimetype = $mimetype; + + $file_id = $file->insert(); + + if (!$file_id) { + common_log_db_error($file, "INSERT", __FILE__); + $this->clientError(_('There was a database error while saving your file. Please try again.')); + } + + $this->maybeAddRedir($file_id, $short); + + return $file; + } + + function maybeAddRedir($file_id, $url) + { + $file_redir = File_redirection::staticGet('url', $url); + + if (empty($file_redir)) { + $file_redir = new File_redirection; + $file_redir->url = $url; + $file_redir->file_id = $file_id; + + $result = $file_redir->insert(); + + if (!$result) { + common_log_db_error($file_redir, "INSERT", __FILE__); + $this->clientError(_('There was a database error while saving your file. Please try again.')); + } + } } - function saveUrl($data) { - list($url, $notice_id) = $data; - $zzz = File::processNew($url, $notice_id); + function attachFile($notice, $filerec) + { + File_to_post::processNew($filerec->id, $notice->id); + + $this->maybeAddRedir($filerec->id, + common_local_url('file', array('notice' => $notice->id))); } /** diff --git a/actions/noticesearch.php b/actions/noticesearch.php index d996998fc..49b473d9e 100644 --- a/actions/noticesearch.php +++ b/actions/noticesearch.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/noticesearchrss.php b/actions/noticesearchrss.php index f6da969ee..c1bf3bf5f 100644 --- a/actions/noticesearchrss.php +++ b/actions/noticesearchrss.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/nudge.php b/actions/nudge.php index c23d3e643..78c0ee566 100644 --- a/actions/nudge.php +++ b/actions/nudge.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/openidlogin.php b/actions/openidlogin.php index 1a4372d73..a8d052096 100644 --- a/actions/openidlogin.php +++ b/actions/openidlogin.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/opensearch.php b/actions/opensearch.php index d1f4895ce..4fe95c93b 100644 --- a/actions/opensearch.php +++ b/actions/opensearch.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/peoplesearch.php b/actions/peoplesearch.php index 65d970dd1..c61e0e273 100644 --- a/actions/peoplesearch.php +++ b/actions/peoplesearch.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/peopletag.php b/actions/peopletag.php index 5add75485..dd3c1c089 100644 --- a/actions/peopletag.php +++ b/actions/peopletag.php @@ -124,7 +124,7 @@ class PeopletagAction extends Action $profile->query(sprintf($qry, $this->tag, $lim)); - $pl = new ProfileList($profile, null, $this); + $pl = new ProfileList($profile, $this); $cnt = $pl->show(); $this->pagination($this->page > 1, diff --git a/actions/postnotice.php b/actions/postnotice.php index 3e98b3cd5..eb2d63b61 100644 --- a/actions/postnotice.php +++ b/actions/postnotice.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/public.php b/actions/public.php index 27153f131..9851285c4 100644 --- a/actions/public.php +++ b/actions/public.php @@ -35,6 +35,10 @@ require_once INSTALLDIR.'/lib/publicgroupnav.php'; require_once INSTALLDIR.'/lib/noticelist.php'; require_once INSTALLDIR.'/lib/feedlist.php'; +// Farther than any human will go + +define('MAX_PUBLIC_PAGE', 100); + /** * Action for displaying the public stream * @@ -74,6 +78,10 @@ class PublicAction extends Action parent::prepare($args); $this->page = ($this->arg('page')) ? ($this->arg('page')+0) : 1; + if ($this->page > MAX_PUBLIC_PAGE) { + $this->clientError(sprintf(_("Beyond the page limit (%s)"), MAX_PUBLIC_PAGE)); + } + common_set_returnto($this->selfUrl()); return true; diff --git a/actions/publicrss.php b/actions/publicrss.php index bc52f2952..7e8df9625 100644 --- a/actions/publicrss.php +++ b/actions/publicrss.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/publicxrds.php b/actions/publicxrds.php index 283a932ca..0a1421550 100644 --- a/actions/publicxrds.php +++ b/actions/publicxrds.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/recoverpassword.php b/actions/recoverpassword.php index 82263fcd5..2afd052a7 100644 --- a/actions/recoverpassword.php +++ b/actions/recoverpassword.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/remotesubscribe.php b/actions/remotesubscribe.php index 0b1174896..e658f8d37 100644 --- a/actions/remotesubscribe.php +++ b/actions/remotesubscribe.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/replies.php b/actions/replies.php index eac4d0a3a..d7ed440e9 100644 --- a/actions/replies.php +++ b/actions/replies.php @@ -45,9 +45,8 @@ require_once INSTALLDIR.'/lib/feedlist.php'; * @link http://laconi.ca/ */ -class RepliesAction extends Action +class RepliesAction extends OwnerDesignAction { - var $user = null; var $page = null; /** diff --git a/actions/repliesrss.php b/actions/repliesrss.php index 2017c4309..a87e2870d 100644 --- a/actions/repliesrss.php +++ b/actions/repliesrss.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/requesttoken.php b/actions/requesttoken.php index 9507e3d6c..8d1e3f004 100644 --- a/actions/requesttoken.php +++ b/actions/requesttoken.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/showfavorites.php b/actions/showfavorites.php index 865045337..b723924a5 100644 --- a/actions/showfavorites.php +++ b/actions/showfavorites.php @@ -45,7 +45,7 @@ require_once INSTALLDIR.'/lib/feedlist.php'; * @link http://laconi.ca/ */ -class ShowfavoritesAction extends Action +class ShowfavoritesAction extends CurrentUserDesignAction { /** User we're getting the faves of */ var $user = null; @@ -191,10 +191,21 @@ class ShowfavoritesAction extends Action function showContent() { - $notice = $this->user->favoriteNotices(($this->page-1)*NOTICES_PER_PAGE, - NOTICES_PER_PAGE + 1); + $cur = common_current_user(); - if (!$notice) { + if (!empty($cur) && $cur->id == $this->user->id) { + + // Show imported/gateway notices as well as local if + // the user is looking at his own favorites + + $notice = $this->user->favoriteNotices(($this->page-1)*NOTICES_PER_PAGE, + NOTICES_PER_PAGE + 1, true); + } else { + $notice = $this->user->favoriteNotices(($this->page-1)*NOTICES_PER_PAGE, + NOTICES_PER_PAGE + 1, false); + } + + if (empty($notice)) { $this->serverError(_('Could not retrieve favorite notices.')); return; } diff --git a/actions/showgroup.php b/actions/showgroup.php index 29b6fa1e6..b6a0f4844 100644 --- a/actions/showgroup.php +++ b/actions/showgroup.php @@ -47,10 +47,9 @@ define('MEMBERS_PER_SECTION', 27); * @link http://laconi.ca/ */ -class ShowgroupAction extends Action +class ShowgroupAction extends GroupDesignAction { - /** group we're viewing. */ - var $group = null; + /** page we're viewing. */ var $page = null; @@ -272,6 +271,17 @@ class ShowgroupAction extends Action $this->elementEnd('dl'); } + if (common_config('group', 'maxaliases') > 0) { + $aliases = $this->group->getAliases(); + + if (!empty($aliases)) { + $this->elementStart('dl', 'entity_aliases'); + $this->element('dt', null, _('Aliases')); + $this->element('dd', 'aliases', implode(' ', $aliases)); + $this->elementEnd('dl'); + } + } + $this->elementEnd('div'); $this->elementStart('div', 'entity_actions'); @@ -283,7 +293,7 @@ class ShowgroupAction extends Action if ($cur->isMember($this->group)) { $lf = new LeaveForm($this, $this->group); $lf->show(); - } else { + } else if (!Group_block::isBlocked($this->group, $cur->getProfile())) { $jf = new JoinForm($this, $this->group); $jf->show(); } @@ -344,7 +354,7 @@ class ShowgroupAction extends Action $this->element('h2', null, _('Members')); - $pml = new ProfileMiniList($member, null, $this); + $pml = new ProfileMiniList($member, $this); $cnt = $pml->show(); if ($cnt == 0) { $this->element('p', null, _('(None)')); diff --git a/actions/shownotice.php b/actions/shownotice.php index b0d973a99..0d89af5ac 100644 --- a/actions/shownotice.php +++ b/actions/shownotice.php @@ -209,7 +209,7 @@ class ShownoticeAction extends Action function showContent() { $this->elementStart('ol', array('class' => 'notices xoxo')); - $nli = new NoticeListItem($this->notice, $this); + $nli = new SingleNoticeItem($this->notice, $this); $nli->show(); $this->elementEnd('ol'); } @@ -264,3 +264,29 @@ class ShownoticeAction extends Action } } } + +class SingleNoticeItem extends NoticeListItem +{ + /** + * recipe function for displaying a single notice. + * + * We overload to show attachments. + * + * @return void + */ + + function show() + { + $this->showStart(); + $this->showNotice(); + $this->showNoticeAttachments(); + $this->showNoticeInfo(); + $this->showNoticeOptions(); + $this->showEnd(); + } + + function showNoticeAttachments() { + $al = new AttachmentList($this->notice, $this->out); + $al->show(); + } +} diff --git a/actions/showstream.php b/actions/showstream.php index e2f4e24d4..cd5d4bb70 100644 --- a/actions/showstream.php +++ b/actions/showstream.php @@ -320,10 +320,14 @@ class ShowstreamAction extends ProfileAction $blocked = $cur->hasBlocked($this->profile); $this->elementStart('li', 'entity_block'); if ($blocked) { - $ubf = new UnblockForm($this, $this->profile); + $ubf = new UnblockForm($this, $this->profile, + array('action' => 'showstream', + 'nickname' => $this->profile->nickname)); $ubf->show(); } else { - $bf = new BlockForm($this, $this->profile); + $bf = new BlockForm($this, $this->profile, + array('action' => 'showstream', + 'nickname' => $this->profile->nickname)); $bf->show(); } $this->elementEnd('li'); @@ -366,7 +370,7 @@ class ShowstreamAction extends ProfileAction { $notice = empty($this->tag) ? $this->user->getNotices(($this->page-1)*NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1) - : $this->user->getTaggedNotices(($this->page-1)*NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1, 0, 0, null, $this->tag); + : $this->user->getTaggedNotices($this->tag, ($this->page-1)*NOTICES_PER_PAGE, NOTICES_PER_PAGE + 1, 0, 0, null); $pnl = new ProfileNoticeList($notice, $this); $cnt = $pnl->show(); diff --git a/actions/subedit.php b/actions/subedit.php index 8ca2d7914..2e1bf5538 100644 --- a/actions/subedit.php +++ b/actions/subedit.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/subscribe.php b/actions/subscribe.php index 0bc522867..15b89a312 100644 --- a/actions/subscribe.php +++ b/actions/subscribe.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/subscribers.php b/actions/subscribers.php index 4482de9a7..66ac00fb1 100644 --- a/actions/subscribers.php +++ b/actions/subscribers.php @@ -130,18 +130,34 @@ class SubscribersAction extends GalleryAction } } -class SubscribersList extends ProfileList +class SubscribersList extends SubscriptionList { - function showBlockForm() + function newListItem($profile) { - $bf = new BlockForm($this->out, $this->profile, - array('action' => 'subscribers', - 'nickname' => $this->owner->nickname)); - $bf->show(); + return new SubscribersListItem($profile, $this->owner, $this->action); } +} - function isReadOnly($args) +class SubscribersListItem extends SubscriptionListItem +{ + function showActions() { - return true; + $this->startActions(); + $this->showSubscribeButton(); + // Relevant code! + $this->showBlockForm(); + $this->endActions(); + } + + function showBlockForm() + { + $user = common_current_user(); + + if (!empty($user) && $this->owner->id == $user->id) { + $bf = new BlockForm($this->out, $this->profile, + array('action' => 'subscribers', + 'nickname' => $this->owner->nickname)); + $bf->show(); + } } } diff --git a/actions/subscriptions.php b/actions/subscriptions.php index 095b18ad8..4124abea4 100644 --- a/actions/subscriptions.php +++ b/actions/subscriptions.php @@ -137,22 +137,46 @@ class SubscriptionsAction extends GalleryAction } } -class SubscriptionsList extends ProfileList +// XXX SubscriptionsList and SubscriptionList are dangerously close + +class SubscriptionsList extends SubscriptionList { - function showOwnerControls($profile) + function newListItem($profile) + { + return new SubscriptionsListItem($profile, $this->owner, $this->action); + } +} + +class SubscriptionsListItem extends SubscriptionListItem +{ + function showProfile() + { + $this->startProfile(); + $this->showAvatar(); + $this->showFullName(); + $this->showLocation(); + $this->showHomepage(); + $this->showBio(); + $this->showTags(); + // Relevant portion! + $this->showOwnerControls(); + $this->endProfile(); + } + + function showOwnerControls() { $sub = Subscription::pkeyGet(array('subscriber' => $this->owner->id, - 'subscribed' => $profile->id)); + 'subscribed' => $this->profile->id)); if (!$sub) { return; } - $this->out->elementStart('form', array('id' => 'subedit-' . $profile->id, + $this->out->elementStart('form', array('id' => 'subedit-' . $this->profile->id, 'method' => 'post', 'class' => 'form_subscription_edit', 'action' => common_local_url('subedit'))); $this->out->hidden('token', common_session_token()); - $this->out->hidden('profile', $profile->id); + $this->out->hidden('profile', $this->profile->id); $this->out->checkbox('jabber', _('Jabber'), $sub->jabber); $this->out->checkbox('sms', _('SMS'), $sub->sms); $this->out->submit('save', _('Save')); diff --git a/actions/sup.php b/actions/sup.php index 691153d6a..e446a7b0d 100644 --- a/actions/sup.php +++ b/actions/sup.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/tag.php b/actions/tag.php index d0ad797eb..888aba062 100644 --- a/actions/tag.php +++ b/actions/tag.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/tagother.php b/actions/tagother.php index 0c5bb7cf3..96246f799 100644 --- a/actions/tagother.php +++ b/actions/tagother.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/tagrss.php b/actions/tagrss.php index 83cf3afe2..f69374fca 100644 --- a/actions/tagrss.php +++ b/actions/tagrss.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapiaccount.php b/actions/twitapiaccount.php index b5e7b91da..f2a7534a2 100644 --- a/actions/twitapiaccount.php +++ b/actions/twitapiaccount.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapiblocks.php b/actions/twitapiblocks.php index 0e3509162..d8e72efb1 100644 --- a/actions/twitapiblocks.php +++ b/actions/twitapiblocks.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapidirect_messages.php b/actions/twitapidirect_messages.php index 85c788d6a..bd27e9d20 100644 --- a/actions/twitapidirect_messages.php +++ b/actions/twitapidirect_messages.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapifavorites.php b/actions/twitapifavorites.php index 8656adbe8..8256668f3 100644 --- a/actions/twitapifavorites.php +++ b/actions/twitapifavorites.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -34,6 +34,11 @@ class TwitapifavoritesAction extends TwitterapiAction $user = $this->get_user($apidata['api_arg'], $apidata); if (empty($user)) { + if ($apidata['content-type'] == 'xml') { + $this->show_single_xml_status($notice); + } elseif ($apidata['content-type'] == 'json') { + $this->show_single_json_status($notice); + } $this->clientError('Not Found', 404, $apidata['content-type']); return; } @@ -56,7 +61,11 @@ class TwitapifavoritesAction extends TwitterapiAction $since_id = (int)$this->arg('since_id', 0); $since = $this->arg('since'); - $notice = $user->favoriteNotices(($page-1)*$count, $count); + if (!empty($this->auth_user) && $this->auth_user->id == $user->id) { + $notice = $user->favoriteNotices(($page-1)*$count, $count, true); + } else { + $notice = $user->favoriteNotices(($page-1)*$count, $count, false); + } switch($apidata['content-type']) { case 'xml': @@ -91,7 +100,6 @@ class TwitapifavoritesAction extends TwitterapiAction // Check for RESTfulness if (!in_array($_SERVER['REQUEST_METHOD'], array('POST', 'DELETE'))) { - // XXX: Twitter just prints the err msg, no XML / JSON. $this->clientError(_('This method requires a POST or DELETE.'), 400, $apidata['content-type']); return; @@ -102,10 +110,9 @@ class TwitapifavoritesAction extends TwitterapiAction return; } - $user = $apidata['user']; // Always the auth user - + $user = $apidata['user']; // Always the auth user $notice_id = $apidata['api_arg']; - $notice = Notice::staticGet($notice_id); + $notice = Notice::staticGet($notice_id); if (empty($notice)) { $this->clientError(_('No status found with that ID.'), @@ -115,7 +122,7 @@ class TwitapifavoritesAction extends TwitterapiAction // XXX: Twitter lets you fave things repeatedly via api. if ($user->hasFave($notice)) { - $this->clientError(_('This notice is already a favorite!'), + $this->clientError(_('This status is already a favorite!'), 403, $apidata['content-type']); return; } @@ -123,7 +130,7 @@ class TwitapifavoritesAction extends TwitterapiAction $fave = Fave::addNew($user, $notice); if (empty($fave)) { - $this->serverError(_('Could not create favorite.')); + $this->clientError(_('Could not create favorite.')); return; } @@ -141,7 +148,55 @@ class TwitapifavoritesAction extends TwitterapiAction function destroy($args, $apidata) { parent::handle($args); - $this->serverError(_('API method under construction.'), $code=501); + + // Check for RESTfulness + if (!in_array($_SERVER['REQUEST_METHOD'], array('POST', 'DELETE'))) { + $this->clientError(_('This method requires a POST or DELETE.'), + 400, $apidata['content-type']); + return; + } + + if (!in_array($apidata['content-type'], array('xml', 'json'))) { + $this->clientError(_('API method not found!'), $code = 404); + return; + } + + $user = $apidata['user']; // Always the auth user + $notice_id = $apidata['api_arg']; + $notice = Notice::staticGet($notice_id); + + if (empty($notice)) { + $this->clientError(_('No status found with that ID.'), + 404, $apidata['content-type']); + return; + } + + $fave = new Fave(); + $fave->user_id = $this->id; + $fave->notice_id = $notice->id; + + if (!$fave->find(true)) { + $this->clientError(_('That status is not a favorite!'), + 403, $apidata['content-type']); + return; + } + + $result = $fave->delete(); + + if (!$result) { + common_log_db_error($fave, 'DELETE', __FILE__); + $this->clientError(_('Could not delete favorite.'), 404); + return; + } + + $user->blowFavesCache(); + + if ($apidata['content-type'] == 'xml') { + $this->show_single_xml_status($notice); + } elseif ($apidata['content-type'] == 'json') { + $this->show_single_json_status($notice); + } + } // XXX: these two funcs swiped from faves. diff --git a/actions/twitapifriendships.php b/actions/twitapifriendships.php index b1c277748..29eb4cc0f 100644 --- a/actions/twitapifriendships.php +++ b/actions/twitapifriendships.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapihelp.php b/actions/twitapihelp.php index bdef1314a..dab2b34f9 100644 --- a/actions/twitapihelp.php +++ b/actions/twitapihelp.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapinotifications.php b/actions/twitapinotifications.php index 411971af1..09b11766b 100644 --- a/actions/twitapinotifications.php +++ b/actions/twitapinotifications.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/twitapistatuses.php b/actions/twitapistatuses.php index 94f624afb..555c746cb 100644 --- a/actions/twitapistatuses.php +++ b/actions/twitapistatuses.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -75,8 +75,8 @@ class TwitapistatusesAction extends TwitterapiAction { parent::handle($args); + $this->auth_user = $apidata['user']; $user = $this->get_user($apidata['api_arg'], $apidata); - $this->auth_user = $user; if (empty($user)) { $this->clientError(_('No such user!'), 404, @@ -100,8 +100,13 @@ class TwitapistatusesAction extends TwitterapiAction $since_id = (int)$this->arg('since_id', 0); $since = $this->arg('since'); - $notice = $user->noticesWithFriends(($page-1)*$count, - $count, $since_id, $max_id,$since); + if (!empty($this->auth_user) && $this->auth_user->id == $user->id) { + $notice = $user->noticeInbox(($page-1)*$count, + $count, $since_id, $max_id, $since); + } else { + $notice = $user->noticesWithFriends(($page-1)*$count, + $count, $since_id, $max_id, $since); + } switch($apidata['content-type']) { case 'xml': diff --git a/actions/twitapiusers.php b/actions/twitapiusers.php index 13a8746cd..4057b63e7 100644 --- a/actions/twitapiusers.php +++ b/actions/twitapiusers.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -58,7 +58,7 @@ class TwitapiusersAction extends TwitterapiAction return; } - $twitter_user = $this->twitter_user_array($profile, true); + $twitter_user = $this->twitter_user_array($user->getProfile(), true); if ($apidata['content-type'] == 'xml') { $this->init_document('xml'); diff --git a/actions/unblock.php b/actions/unblock.php index 8573b2a87..05d57c60d 100644 --- a/actions/unblock.php +++ b/actions/unblock.php @@ -12,7 +12,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by @@ -118,7 +118,7 @@ class UnblockAction extends Action if ($action) { common_redirect(common_local_url($action, $args), 303); } else { - common_redirect(common_local_url('subscriptions', + common_redirect(common_local_url('subscribers', array('nickname' => $cur->nickname)), 303); } diff --git a/actions/unsubscribe.php b/actions/unsubscribe.php index 7dcab04c0..19275041a 100644 --- a/actions/unsubscribe.php +++ b/actions/unsubscribe.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/updateprofile.php b/actions/updateprofile.php index 08cb31ae0..d8b62fb09 100644 --- a/actions/updateprofile.php +++ b/actions/updateprofile.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/userauthorization.php b/actions/userauthorization.php index 168019149..8dc2c808d 100644 --- a/actions/userauthorization.php +++ b/actions/userauthorization.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/userbyid.php b/actions/userbyid.php index 4a985fcd7..8b686ae10 100644 --- a/actions/userbyid.php +++ b/actions/userbyid.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/userdesignsettings.php b/actions/userdesignsettings.php new file mode 100644 index 000000000..6e745e96f --- /dev/null +++ b/actions/userdesignsettings.php @@ -0,0 +1,206 @@ +<?php +/** + * Laconica, the distributed open-source microblogging tool + * + * Change user password + * + * PHP version 5 + * + * LICENCE: This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + * + * @category Settings + * @package Laconica + * @author Sarven Capadisli <csarven@controlyourself.ca> + * @author Zach Copley <zach@controlyourself.ca> + * @copyright 2008-2009 Control Yourself, Inc. + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://laconi.ca/ + */ + +if (!defined('LACONICA')) { + exit(1); +} + +require_once INSTALLDIR . '/lib/designsettings.php'; + +class UserDesignSettingsAction extends DesignSettingsAction +{ + + function prepare($args) + { + parent::prepare($args); + $this->submitaction = common_local_url('userdesignsettings'); + return true; + } + + /** + * Title of the page + * + * @return string Title of the page + */ + + function title() + { + return _('Profile design'); + } + + /** + * Instructions for use + * + * @return instructions for use + */ + + function getInstructions() + { + return _('Customize the way your profile looks ' . + 'with a background image and a colour palette of your choice.'); + } + + /** + * Get the design we want to edit + * + * @return Design + */ + + function getWorkingDesign() { + + $user = common_current_user(); + $design = $user->getDesign(); + + if (empty($design)) { + $design = $this->defaultDesign(); + } + + return $design; + } + + /** + * Content area of the page + * + * Shows a form for changing the design + * + * @return void + */ + + function showContent() + { + $this->showDesignForm($this->getWorkingDesign()); + } + + /** + * Save or update the user's design settings + * + * @return void + */ + + function saveDesign() + { + try { + + $bgcolor = new WebColor($this->trimmed('design_background')); + $ccolor = new WebColor($this->trimmed('design_content')); + $sbcolor = new WebColor($this->trimmed('design_sidebar')); + $tcolor = new WebColor($this->trimmed('design_text')); + $lcolor = new WebColor($this->trimmed('design_links')); + + } catch (WebColorException $e) { + $this->showForm($e->getMessage()); + return; + } + + $onoff = $this->arg('design_background-image_onoff'); + + $on = false; + $off = false; + $tile = false; + + if ($onoff == 'on') { + $on = true; + } else { + $off = true; + } + + $repeat = $this->boolean('design_background-image_repeat'); + + if ($repeat) { + $tile = true; + } + + $user = common_current_user(); + $design = $user->getDesign(); + + if (!empty($design)) { + + $original = clone($design); + + $design->backgroundcolor = $bgcolor->intValue(); + $design->contentcolor = $ccolor->intValue(); + $design->sidebarcolor = $sbcolor->intValue(); + $design->textcolor = $tcolor->intValue(); + $design->linkcolor = $lcolor->intValue(); + + $design->setDisposition($on, $off, $tile); + + $result = $design->update($original); + + if ($result === false) { + common_log_db_error($design, 'UPDATE', __FILE__); + $this->showForm(_('Couldn\'t update your design.')); + return; + } + + // update design + } else { + + $user->query('BEGIN'); + + // save new design + $design = new Design(); + + $design->backgroundcolor = $bgcolor->intValue(); + $design->contentcolor = $ccolor->intValue(); + $design->sidebarcolor = $sbcolor->intValue(); + $design->textcolor = $tcolor->intValue(); + $design->linkcolor = $lcolor->intValue(); + + $design->setDisposition($on, $off, $tile); + + $id = $design->insert(); + + if (empty($id)) { + common_log_db_error($id, 'INSERT', __FILE__); + $this->showForm(_('Unable to save your design settings!')); + return; + } + + $original = clone($user); + $user->design_id = $id; + $result = $user->update($original); + + if (empty($result)) { + common_log_db_error($original, 'UPDATE', __FILE__); + $this->showForm(_('Unable to save your design settings!')); + $user->query('ROLLBACK'); + return; + } + + $user->query('COMMIT'); + + } + + $this->saveBackgroundImage($design); + + $this->showForm(_('Design preferences saved.'), true); + } +} diff --git a/actions/usergroups.php b/actions/usergroups.php index e3088dcbd..7ead6e6e4 100644 --- a/actions/usergroups.php +++ b/actions/usergroups.php @@ -46,9 +46,8 @@ require_once INSTALLDIR.'/lib/grouplist.php'; * @link http://laconi.ca/ */ -class UsergroupsAction extends Action +class UsergroupsAction extends OwnerDesignAction { - var $user = null; var $page = null; var $profile = null; diff --git a/actions/userrss.php b/actions/userrss.php index 2280509b2..8a940865f 100644 --- a/actions/userrss.php +++ b/actions/userrss.php @@ -1,7 +1,7 @@ <?php /* * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by diff --git a/actions/xrds.php b/actions/xrds.php index 1335b6b80..9327a3c83 100644 --- a/actions/xrds.php +++ b/actions/xrds.php @@ -13,7 +13,7 @@ * @link http://laconi.ca/ * * Laconica - a distributed open-source microblogging tool - * Copyright (C) 2008, Controlez-Vous, Inc. + * Copyright (C) 2008, 2009, Control Yourself, Inc. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by |