[OStatus] Port remote-follow to the RemoteFollow plugin
OStatusPlugin: - Stop adding the remote-follow button - Subscribe to required RemoteFollow plugin events - Drop main/ostatussub route and update urls to the main/RemoteFollowSub route - Bump plugin minor version number actions/ostatusgroup, actions/ostatuspeopletag: - Update urls to the main/RemoteFollowSub route lib/util: - Port required functions from OStatusSubAction and adapt to be used with the new events
This commit is contained in:
parent
32ae48358d
commit
66c5d17469
@ -28,9 +28,11 @@
|
|||||||
|
|
||||||
if (!defined('GNUSOCIAL')) { exit(1); }
|
if (!defined('GNUSOCIAL')) { exit(1); }
|
||||||
|
|
||||||
|
require_once __DIR__ . DIRECTORY_SEPARATOR . 'lib' . DIRECTORY_SEPARATOR . 'util.php';
|
||||||
|
|
||||||
class OStatusPlugin extends Plugin
|
class OStatusPlugin extends Plugin
|
||||||
{
|
{
|
||||||
const PLUGIN_VERSION = '2.0.3';
|
const PLUGIN_VERSION = '2.1.0';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Hook for RouterInitialized event.
|
* Hook for RouterInitialized event.
|
||||||
@ -46,9 +48,6 @@ class OStatusPlugin extends Plugin
|
|||||||
$m->connect('main/ostatustag?nickname=:nickname',
|
$m->connect('main/ostatustag?nickname=:nickname',
|
||||||
['action' => 'ostatustag'],
|
['action' => 'ostatustag'],
|
||||||
['nickname' => '[A-Za-z0-9_-]+']);
|
['nickname' => '[A-Za-z0-9_-]+']);
|
||||||
$m->connect('main/ostatus/nickname/:nickname',
|
|
||||||
['action' => 'ostatusinit'],
|
|
||||||
['nickname' => '[A-Za-z0-9_-]+']);
|
|
||||||
$m->connect('main/ostatus/group/:group',
|
$m->connect('main/ostatus/group/:group',
|
||||||
['action' => 'ostatusinit'],
|
['action' => 'ostatusinit'],
|
||||||
['group' => '[A-Za-z0-9_-]+']);
|
['group' => '[A-Za-z0-9_-]+']);
|
||||||
@ -60,8 +59,6 @@ class OStatusPlugin extends Plugin
|
|||||||
['action' => 'ostatusinit']);
|
['action' => 'ostatusinit']);
|
||||||
|
|
||||||
// Remote subscription actions
|
// Remote subscription actions
|
||||||
$m->connect('main/ostatussub',
|
|
||||||
['action' => 'ostatussub']);
|
|
||||||
$m->connect('main/ostatusgroup',
|
$m->connect('main/ostatusgroup',
|
||||||
['action' => 'ostatusgroup']);
|
['action' => 'ostatusgroup']);
|
||||||
$m->connect('main/ostatuspeopletag',
|
$m->connect('main/ostatuspeopletag',
|
||||||
@ -176,12 +173,16 @@ class OStatusPlugin extends Plugin
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add in an OStatus subscribe button
|
* Add in an OStatus list button
|
||||||
|
*
|
||||||
|
* @param HTMLOutputter $output
|
||||||
|
* @param Profile $profile
|
||||||
|
* @return bool hook return value
|
||||||
*/
|
*/
|
||||||
function onStartProfileRemoteSubscribe($output, $profile)
|
function onStartProfileRemoteSubscribe(HTMLOutputter $output, Profile $profile): bool
|
||||||
{
|
{
|
||||||
$this->onStartProfileListItemActionElements($output, $profile);
|
$this->onStartProfileListItemActionElements($output);
|
||||||
return false;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
function onStartGroupSubscribe($widget, $group)
|
function onStartGroupSubscribe($widget, $group)
|
||||||
@ -547,7 +548,7 @@ class OStatusPlugin extends Plugin
|
|||||||
|
|
||||||
function onEndProfileSettingsActions($out) {
|
function onEndProfileSettingsActions($out) {
|
||||||
$siteName = common_config('site', 'name');
|
$siteName = common_config('site', 'name');
|
||||||
$js = 'navigator.registerContentHandler("application/vnd.mozilla.maybe.feed", "'.addslashes(common_local_url('ostatussub', null, array('profile' => '%s'))).'", "'.addslashes($siteName).'")';
|
$js = 'navigator.registerContentHandler("application/vnd.mozilla.maybe.feed", "'.addslashes(common_local_url('RemoteFollowSub', null, array('profile' => '%s'))).'", "'.addslashes($siteName).'")';
|
||||||
$out->elementStart('li');
|
$out->elementStart('li');
|
||||||
$out->element('a',
|
$out->element('a',
|
||||||
array('href' => 'javascript:'.$js),
|
array('href' => 'javascript:'.$js),
|
||||||
@ -1169,21 +1170,7 @@ class OStatusPlugin extends Plugin
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function onStartShowSubscriptionsContent($action)
|
|
||||||
{
|
|
||||||
$this->showEntityRemoteSubscribe($action);
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
function onStartShowUserGroupsContent($action)
|
function onStartShowUserGroupsContent($action)
|
||||||
{
|
|
||||||
$this->showEntityRemoteSubscribe($action, 'ostatusgroup');
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
function onEndShowSubscriptionsMiniList($action)
|
|
||||||
{
|
{
|
||||||
$this->showEntityRemoteSubscribe($action);
|
$this->showEntityRemoteSubscribe($action);
|
||||||
|
|
||||||
@ -1192,12 +1179,12 @@ class OStatusPlugin extends Plugin
|
|||||||
|
|
||||||
function onEndShowGroupsMiniList($action)
|
function onEndShowGroupsMiniList($action)
|
||||||
{
|
{
|
||||||
$this->showEntityRemoteSubscribe($action, 'ostatusgroup');
|
$this->showEntityRemoteSubscribe($action);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
function showEntityRemoteSubscribe($action, $target='ostatussub')
|
function showEntityRemoteSubscribe($action)
|
||||||
{
|
{
|
||||||
if (!$action->getScoped() instanceof Profile) {
|
if (!$action->getScoped() instanceof Profile) {
|
||||||
// early return if we're not logged in
|
// early return if we're not logged in
|
||||||
@ -1208,7 +1195,7 @@ class OStatusPlugin extends Plugin
|
|||||||
$action->elementStart('div', 'entity_actions');
|
$action->elementStart('div', 'entity_actions');
|
||||||
$action->elementStart('p', array('id' => 'entity_remote_subscribe',
|
$action->elementStart('p', array('id' => 'entity_remote_subscribe',
|
||||||
'class' => 'entity_subscribe'));
|
'class' => 'entity_subscribe'));
|
||||||
$action->element('a', array('href' => common_local_url($target),
|
$action->element('a', array('href' => common_local_url('ostatusgroup'),
|
||||||
'class' => 'entity_remote_subscribe'),
|
'class' => 'entity_remote_subscribe'),
|
||||||
// TRANS: Link text for link to remote subscribe.
|
// TRANS: Link text for link to remote subscribe.
|
||||||
_m('Remote'));
|
_m('Remote'));
|
||||||
@ -1306,7 +1293,11 @@ class OStatusPlugin extends Plugin
|
|||||||
if (common_logged_in()) {
|
if (common_logged_in()) {
|
||||||
// only non-logged in users get to see the "remote subscribe" form
|
// only non-logged in users get to see the "remote subscribe" form
|
||||||
return true;
|
return true;
|
||||||
} elseif (!$item->getTarget()->isLocal()) {
|
}
|
||||||
|
|
||||||
|
$target = $item->getTarget();
|
||||||
|
|
||||||
|
if (!$target->isLocal()) {
|
||||||
// we can (for now) only provide remote subscribe forms for local users
|
// we can (for now) only provide remote subscribe forms for local users
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -1320,22 +1311,12 @@ class OStatusPlugin extends Plugin
|
|||||||
throw new ServerException('Bad item type for onStartProfileListItemActionElements');
|
throw new ServerException('Bad item type for onStartProfileListItemActionElements');
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add an OStatus subscribe
|
|
||||||
$output->elementStart('li', 'entity_subscribe');
|
|
||||||
$url = common_local_url('ostatusinit',
|
|
||||||
array('nickname' => $item->getTarget()->getNickname()));
|
|
||||||
$output->element('a', array('href' => $url,
|
|
||||||
'class' => 'entity_remote_subscribe'),
|
|
||||||
// TRANS: Link text for a user to subscribe to an OStatus user.
|
|
||||||
_m('Subscribe'));
|
|
||||||
$output->elementEnd('li');
|
|
||||||
|
|
||||||
$output->elementStart('li', 'entity_tag');
|
$output->elementStart('li', 'entity_tag');
|
||||||
$url = common_local_url('ostatustag',
|
$url = common_local_url('ostatustag', ['nickname' => $target->getNickname()]);
|
||||||
array('nickname' => $item->getTarget()->getNickname()));
|
$output->element('a',
|
||||||
$output->element('a', array('href' => $url,
|
['href' => $url,
|
||||||
'class' => 'entity_remote_tag'),
|
'class' => 'entity_remote_tag'],
|
||||||
// TRANS: Link text for a user to list an OStatus user.
|
// TRANS: Link text for a user to list an OStatus user.
|
||||||
_m('List'));
|
_m('List'));
|
||||||
$output->elementEnd('li');
|
$output->elementEnd('li');
|
||||||
|
|
||||||
@ -1480,12 +1461,6 @@ class OStatusPlugin extends Plugin
|
|||||||
$xrd->links[] = new XML_XRD_Element_Link(Salmon::NS_REPLIES, $salmon_url);
|
$xrd->links[] = new XML_XRD_Element_Link(Salmon::NS_REPLIES, $salmon_url);
|
||||||
$xrd->links[] = new XML_XRD_Element_Link(Salmon::NS_MENTIONS, $salmon_url);
|
$xrd->links[] = new XML_XRD_Element_Link(Salmon::NS_MENTIONS, $salmon_url);
|
||||||
|
|
||||||
// TODO - finalize where the redirect should go on the publisher
|
|
||||||
$xrd->links[] = new XML_XRD_Element_Link('http://ostatus.org/schema/1.0/subscribe',
|
|
||||||
common_local_url('ostatussub') . '?profile={uri}',
|
|
||||||
null, // type not set
|
|
||||||
true); // isTemplate
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1611,4 +1586,31 @@ class OStatusPlugin extends Plugin
|
|||||||
$qm->enqueue($item, 'pushrenew');
|
$qm->enqueue($item, 'pushrenew');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Try to grab and store the remote profile by the given uri
|
||||||
|
*
|
||||||
|
* @param string $uri
|
||||||
|
* @param Profile &$profile
|
||||||
|
* @return bool
|
||||||
|
*/
|
||||||
|
public function onRemoteFollowPullProfile(string $uri, ?Profile &$profile): bool
|
||||||
|
{
|
||||||
|
$oprofile = pullRemoteProfile($uri);
|
||||||
|
if ($oprofile instanceof Ostatus_profile) {
|
||||||
|
|
||||||
|
// validation
|
||||||
|
if ($oprofile->isGroup()) {
|
||||||
|
$target = common_local_url('ostatusgroup', [], ['profile' => $uri]);
|
||||||
|
common_redirect($target, 303);
|
||||||
|
} else if ($oprofile->isPeopletag()) {
|
||||||
|
$target = common_local_url('ostatuspeopletag', [], ['profile' => $uri]);
|
||||||
|
common_redirect($target, 303);
|
||||||
|
}
|
||||||
|
|
||||||
|
$profile = $oprofile->localProfile();
|
||||||
|
}
|
||||||
|
|
||||||
|
return is_null($profile);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -8,6 +8,11 @@ currently non-WebSub feeds cannot be subscribed unless an external
|
|||||||
WebSub hub proxy is used.
|
WebSub hub proxy is used.
|
||||||
|
|
||||||
|
|
||||||
|
Additional functionality:
|
||||||
|
|
||||||
|
The RemoteFollow plugin is highly recommended as it is the only way to remote
|
||||||
|
follow a user in OStatus, it adds a remote follow button to user profiles.
|
||||||
|
|
||||||
Configuration options available:
|
Configuration options available:
|
||||||
|
|
||||||
$config['ostatus']['hub']
|
$config['ostatus']['hub']
|
||||||
|
@ -47,7 +47,7 @@ class OStatusGroupAction extends OStatusSubAction
|
|||||||
{
|
{
|
||||||
if (!$this->oprofile->isGroup()) {
|
if (!$this->oprofile->isGroup()) {
|
||||||
// Send us to the user subscription form for conf
|
// Send us to the user subscription form for conf
|
||||||
$target = common_local_url('ostatussub', array(), array('profile' => $this->profile_uri));
|
$target = common_local_url('RemoteFollowSub', array(), array('profile' => $this->profile_uri));
|
||||||
common_redirect($target, 303);
|
common_redirect($target, 303);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -47,7 +47,7 @@ class OStatusPeopletagAction extends OStatusSubAction
|
|||||||
{
|
{
|
||||||
if (!$this->oprofile->isPeopletag()) {
|
if (!$this->oprofile->isPeopletag()) {
|
||||||
// Send us to the user subscription form for conf
|
// Send us to the user subscription form for conf
|
||||||
$target = common_local_url('ostatussub', array(), array('profile' => $this->profile_uri));
|
$target = common_local_url('RemoteFollowSub', array(), array('profile' => $this->profile_uri));
|
||||||
common_redirect($target, 303);
|
common_redirect($target, 303);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
64
plugins/OStatus/lib/util.php
Normal file
64
plugins/OStatus/lib/util.php
Normal file
@ -0,0 +1,64 @@
|
|||||||
|
<?php
|
||||||
|
// This file is part of GNU social - https://www.gnu.org/software/social
|
||||||
|
//
|
||||||
|
// GNU social 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.
|
||||||
|
//
|
||||||
|
// GNU social 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 GNU social. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
defined('GNUSOCIAL') || die();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Pull (and store) remote profile from the its uri
|
||||||
|
*
|
||||||
|
* @param string $uri
|
||||||
|
* @return null|Ostatus_profile
|
||||||
|
*/
|
||||||
|
function pullRemoteProfile(string $uri): ?Ostatus_profile
|
||||||
|
{
|
||||||
|
$validate = new Validate();
|
||||||
|
|
||||||
|
try {
|
||||||
|
$uri = Discovery::normalize($uri);
|
||||||
|
} catch (Exception $e) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
if (Discovery::isAcct($uri) && $validate->email(mb_substr($uri, 5))) {
|
||||||
|
$profile = Ostatus_profile::ensureWebfinger($uri);
|
||||||
|
} else if ($validate->uri($uri)) {
|
||||||
|
$profile = Ostatus_profile::ensureProfileURL($uri);
|
||||||
|
} else {
|
||||||
|
common_log(LOG_ERR, 'Invalid address format.');
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return $profile;
|
||||||
|
} catch (FeedSubBadURLException $e) {
|
||||||
|
common_log(LOG_ERR, 'Invalid URL or could not reach server.');
|
||||||
|
} catch (FeedSubBadResponseException $e) {
|
||||||
|
common_log(LOG_ERR, 'Cannot read feed; server returned error.');
|
||||||
|
} catch (FeedSubEmptyException $e) {
|
||||||
|
common_log(LOG_ERR, 'Cannot read feed; server returned an empty page.');
|
||||||
|
} catch (FeedSubBadHTMLException $e) {
|
||||||
|
common_log(LOG_ERR, 'Bad HTML, could not find feed link.');
|
||||||
|
} catch (FeedSubNoFeedException $e) {
|
||||||
|
common_log(LOG_ERR, 'Could not find a feed linked from this URL.');
|
||||||
|
} catch (FeedSubUnrecognizedTypeException $e) {
|
||||||
|
common_log(LOG_ERR, 'Not a recognized feed type.');
|
||||||
|
} catch (FeedSubNoHubException $e) {
|
||||||
|
common_log(LOG_ERR, 'No hub found.');
|
||||||
|
} catch (Exception $e) {
|
||||||
|
common_log(LOG_ERR, sprintf('Bad feed URL: %s %s', get_class($e), $e->getMessage()));
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user