3 * StatusNet - the distributed open-source microblogging tool
4 * Copyright (C) 2010, StatusNet, Inc.
6 * Shows social activities in the output feed
10 * This program is free software: you can redistribute it and/or modify
11 * it under the terms of the GNU Affero General Public License as published by
12 * the Free Software Foundation, either version 3 of the License, or
13 * (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU Affero General Public License for more details.
20 * You should have received a copy of the GNU Affero General Public License
21 * along with this program. If not, see <http://www.gnu.org/licenses/>.
25 * @author Evan Prodromou <evan@status.net>
26 * @copyright 2010 StatusNet, Inc.
27 * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html AGPL 3.0
28 * @link http://status.net/
31 if (!defined('STATUSNET')) {
32 // This check helps protect against security problems;
33 // your code file can't be executed directly from the web.
38 * Activity plugin main class
42 * @author Evan Prodromou <evan@status.net>
43 * @copyright 2010 StatusNet, Inc.
44 * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html AGPL 3.0
45 * @link http://status.net/
47 class ActivityPlugin extends Plugin
49 const VERSION = '0.1';
50 const SOURCE = 'activity';
52 // Flags to switch off certain activity notices
53 public $StartFollowUser = true;
54 public $StopFollowUser = false;
55 public $JoinGroup = true;
56 public $LeaveGroup = false;
57 public $StartLike = false;
58 public $StopLike = false;
60 function onEndSubscribe(Profile $profile, Profile $other)
62 // Only do this if config is enabled
63 if(!$this->StartFollowUser) return true;
65 if (!$profile->isLocal()) {
66 // can't do anything with remote user anyway
70 $sub = Subscription::pkeyGet(array('subscriber' => $profile->id,
71 'subscribed' => $other->id));
72 // TRANS: Text for "started following" item in activity plugin.
73 // TRANS: %1$s is a profile URL, %2$s is a profile name,
74 // TRANS: %3$s is a profile URL, %4$s is a profile name.
75 $rendered = html_sprintf(_m('<a href="%1$s">%2$s</a> started following <a href="%3$s">%4$s</a>.'),
77 $profile->getBestName(),
79 $other->getBestName());
80 // TRANS: Text for "started following" item in activity plugin.
81 // TRANS: %1$s is a profile name, %2$s is a profile URL,
82 // TRANS: %3$s is a profile name, %4$s is a profile URL.
83 $content = sprintf(_m('%1$s (%2$s) started following %3$s (%4$s).'),
84 $profile->getBestName(),
86 $other->getBestName(),
89 $notice = Notice::saveNew($profile->id,
91 ActivityPlugin::SOURCE,
92 array('rendered' => $rendered,
94 'replies' => array($other->getUri()),
95 'verb' => ActivityVerb::FOLLOW,
96 'object_type' => ActivityObject::PERSON,
101 function onEndUnsubscribe(Profile $profile, Profile $other)
103 // Only do this if config is enabled
104 if(!$this->StopFollowUser) return true;
106 if (!$profile->isLocal()) {
110 // TRANS: Text for "stopped following" item in activity plugin.
111 // TRANS: %1$s is a profile URL, %2$s is a profile name,
112 // TRANS: %3$s is a profile URL, %4$s is a profile name.
113 $rendered = html_sprintf(_m('<a href="%1$s">%2$s</a> stopped following <a href="%3$s">%4$s</a>.'),
115 $profile->getBestName(),
117 $other->getBestName());
118 // TRANS: Text for "stopped following" item in activity plugin.
119 // TRANS: %1$s is a profile name, %2$s is a profile URL,
120 // TRANS: %3$s is a profile name, %4$s is a profile URL.
121 $content = sprintf(_m('%1$s (%2$s) stopped following %3$s (%4$s).'),
122 $profile->getBestName(),
124 $other->getBestName(),
127 $uri = TagURI::mint('stop-following:%d:%d:%s',
130 common_date_iso8601(common_sql_now()));
132 $notice = Notice::saveNew($profile->id,
134 ActivityPlugin::SOURCE,
135 array('rendered' => $rendered,
137 'replies' => array($other->getUri()),
139 'verb' => ActivityVerb::UNFOLLOW,
140 'object_type' => ActivityObject::PERSON));
145 function onEndDisfavorNotice($profile, $notice)
147 // Only do this if config is enabled
148 if(!$this->StopLike) return true;
150 if (!$profile->isLocal()) {
154 $author = Profile::getKV('id', $notice->profile_id);
155 // TRANS: Text for "stopped liking" item in activity plugin.
156 // TRANS: %1$s is a profile URL, %2$s is a profile name,
157 // TRANS: %3$s is a notice URL, %4$s is an author name.
158 $rendered = html_sprintf(_m('<a href="%1$s">%2$s</a> stopped liking <a href="%3$s">%4$s\'s update</a>.'),
160 $profile->getBestName(),
162 $author->getBestName());
163 // TRANS: Text for "stopped liking" item in activity plugin.
164 // TRANS: %1$s is a profile name, %2$s is a profile URL,
165 // TRANS: %3$s is an author name, %4$s is a notice URL.
166 $content = sprintf(_m('%1$s (%2$s) stopped liking %3$s\'s status (%4$s).'),
167 $profile->getBestName(),
169 $author->getBestName(),
172 $uri = TagURI::mint('unlike:%d:%d:%s',
175 common_date_iso8601(common_sql_now()));
177 $notice = Notice::saveNew($profile->id,
179 ActivityPlugin::SOURCE,
180 array('rendered' => $rendered,
182 'replies' => array($author->getUri()),
184 'verb' => ActivityVerb::UNFAVORITE,
185 'object_type' => (($notice->verb == ActivityVerb::POST) ?
186 $notice->object_type : null)));
191 function onEndJoinGroup($group, $profile)
193 // Only do this if config is enabled
194 if(!$this->JoinGroup) return true;
196 if (!$profile->isLocal()) {
200 // TRANS: Text for "joined group" item in activity plugin.
201 // TRANS: %1$s is a profile URL, %2$s is a profile name,
202 // TRANS: %3$s is a group URL, %4$s is a group name.
203 $rendered = html_sprintf(_m('<a href="%1$s">%2$s</a> joined the group <a href="%3$s">%4$s</a>.'),
205 $profile->getBestName(),
207 $group->getBestName());
208 // TRANS: Text for "joined group" item in activity plugin.
209 // TRANS: %1$s is a profile name, %2$s is a profile URL,
210 // TRANS: %3$s is a group name, %4$s is a group URL.
211 $content = sprintf(_m('%1$s (%2$s) joined the group %3$s (%4$s).'),
212 $profile->getBestName(),
214 $group->getBestName(),
217 $mem = Group_member::pkeyGet(array('group_id' => $group->id,
218 'profile_id' => $profile->id));
220 $notice = Notice::saveNew($profile->id,
222 ActivityPlugin::SOURCE,
223 array('rendered' => $rendered,
225 'groups' => array($group->id),
226 'uri' => $mem->getURI(),
227 'verb' => ActivityVerb::JOIN,
228 'object_type' => ActivityObject::GROUP));
232 function onEndLeaveGroup($group, $profile)
234 // Only do this if config is enabled
235 if(!$this->LeaveGroup) return true;
237 if (!$profile->isLocal()) {
241 // TRANS: Text for "left group" item in activity plugin.
242 // TRANS: %1$s is a profile URL, %2$s is a profile name,
243 // TRANS: %3$s is a group URL, %4$s is a group name.
244 $rendered = html_sprintf(_m('<a href="%1$s">%2$s</a> left the group <a href="%3$s">%4$s</a>.'),
246 $profile->getBestName(),
248 $group->getBestName());
249 // TRANS: Text for "left group" item in activity plugin.
250 // TRANS: %1$s is a profile name, %2$s is a profile URL,
251 // TRANS: %3$s is a group name, %4$s is a group URL.
252 $content = sprintf(_m('%1$s (%2$s) left the group %3$s (%4$s).'),
253 $profile->getBestName(),
255 $group->getBestName(),
258 $uri = TagURI::mint('leave:%d:%d:%s',
261 common_date_iso8601(common_sql_now()));
263 $notice = Notice::saveNew($profile->id,
265 ActivityPlugin::SOURCE,
266 array('rendered' => $rendered,
268 'groups' => array($group->id),
270 'verb' => ActivityVerb::LEAVE,
271 'object_type' => ActivityObject::GROUP));
275 function onStartShowNoticeItem($nli)
277 $notice = $nli->notice;
281 switch ($notice->verb) {
282 case ActivityVerb::JOIN:
283 $adapter = new JoinListItem($nli);
285 case ActivityVerb::LEAVE:
286 $adapter = new LeaveListItem($nli);
288 case ActivityVerb::FOLLOW:
289 $adapter = new FollowListItem($nli);
291 case ActivityVerb::UNFOLLOW:
292 $adapter = new UnfollowListItem($nli);
296 if (!empty($adapter)) {
297 $adapter->showNotice();
298 $adapter->showNoticeAttachments();
299 $adapter->showNoticeInfo();
300 $adapter->showNoticeOptions();
307 public function onEndNoticeAsActivity(Notice $stored, Activity $act, Profile $scoped=null)
309 switch ($stored->verb) {
310 case ActivityVerb::UNFAVORITE:
311 // FIXME: do something here
313 case ActivityVerb::JOIN:
314 $mem = Group_member::getKV('uri', $stored->getUri());
315 if ($mem instanceof Group_member) {
316 $group = $mem->getGroup();
317 $act->title = $stored->getTitle();
318 $act->objects = array(ActivityObject::fromGroup($group));
321 case ActivityVerb::LEAVE:
324 case ActivityVerb::FOLLOW:
325 $sub = Subscription::getKV('uri', $stored->uri);
326 if ($sub instanceof Subscription) {
327 $profile = Profile::getKV('id', $sub->subscribed);
328 if ($profile instanceof Profile) {
329 $act->title = $stored->getTitle();
330 $act->objects = array($profile->asActivityObject());
334 case ActivityVerb::UNFOLLOW:
342 function onPluginVersion(array &$versions)
344 $versions[] = array('name' => 'Activity',
345 'version' => self::VERSION,
346 'author' => 'Evan Prodromou',
347 'homepage' => 'https://git.gnu.io/gnu/gnu-social/tree/master/plugins/Activity',
349 // TRANS: Plugin description.
350 _m('Emits notices when social activities happen.'));