Delete removed contacts
This commit is contained in:
parent
cb5362f499
commit
a331a8cf0a
7 changed files with 59 additions and 15 deletions
|
@ -147,14 +147,25 @@ class APContact
|
|||
$url = $apcontact['url'];
|
||||
}
|
||||
|
||||
$data = ActivityPub::fetchContent($url);
|
||||
if (empty($data)) {
|
||||
$curlResult = HTTPSignature::fetchRaw($url);
|
||||
$failed = empty($curlResult) || empty($curlResult->getBody()) ||
|
||||
(!$curlResult->isSuccess() && ($curlResult->getReturnCode() != 410));
|
||||
|
||||
if (!$failed) {
|
||||
$data = json_decode($curlResult->getBody(), true);
|
||||
$failed = empty($data) || !is_array($data);
|
||||
}
|
||||
|
||||
if (!$failed && ($curlResult->getReturnCode() == 410)) {
|
||||
$data = ['@context' => ActivityPub::CONTEXT, 'id' => $url, 'type' => 'Tombstone'];
|
||||
}
|
||||
|
||||
if ($failed) {
|
||||
self::markForArchival($fetched_contact ?: []);
|
||||
return $fetched_contact;
|
||||
}
|
||||
|
||||
$compacted = JsonLD::compact($data);
|
||||
|
||||
if (empty($compacted['@id'])) {
|
||||
return $fetched_contact;
|
||||
}
|
||||
|
@ -207,8 +218,11 @@ class APContact
|
|||
}
|
||||
|
||||
// Quit if none of the basic values are set
|
||||
if (empty($apcontact['url']) || empty($apcontact['inbox']) || empty($apcontact['type'])) {
|
||||
if (empty($apcontact['url']) || empty($apcontact['type']) || (($apcontact['type'] != 'Tombstone') && empty($apcontact['inbox']))) {
|
||||
return $fetched_contact;
|
||||
} elseif ($apcontact['type'] == 'Tombstone') {
|
||||
// The "inbox" field must have a content
|
||||
$apcontact['inbox'] = '';
|
||||
}
|
||||
|
||||
// Quit if this doesn't seem to be an account at all
|
||||
|
|
|
@ -724,7 +724,7 @@ class Contact
|
|||
{
|
||||
// We want just to make sure that we don't delete our "self" contact
|
||||
$contact = DBA::selectFirst('contact', ['uid'], ['id' => $id, 'self' => false]);
|
||||
if (!DBA::isResult($contact) || !intval($contact['uid'])) {
|
||||
if (!DBA::isResult($contact)) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1762,6 +1762,17 @@ class Contact
|
|||
DBA::update('contact', $fields, ['id' => $cids]);
|
||||
}
|
||||
|
||||
public static function deleteContactByUrl(string $url)
|
||||
{
|
||||
// Update contact data for all users
|
||||
$condition = ['self' => false, 'nurl' => Strings::normaliseLink($url)];
|
||||
$contacts = DBA::select('contact', ['id', 'uid'], $condition);
|
||||
while ($contact = DBA::fetch($contacts)) {
|
||||
Logger::info('Deleting contact', ['id' => $contact['id'], 'uid' => $contact['uid'], 'url' => $url]);
|
||||
self::remove($contact['id']);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper function for "updateFromProbe". Updates personal and public contact
|
||||
*
|
||||
|
@ -1914,6 +1925,15 @@ class Contact
|
|||
return false;
|
||||
}
|
||||
|
||||
if (!empty($ret['account-type']) && $ret['account-type'] == User::ACCOUNT_TYPE_DELETED) {
|
||||
Logger::info('Deleted account', ['id' => $id, 'url' => $ret['url'], 'ret' => $ret]);
|
||||
self::remove($id);
|
||||
|
||||
// Delete all contacts with the same URL
|
||||
self::deleteContactByUrl($ret['url']);
|
||||
return true;
|
||||
}
|
||||
|
||||
$uid = $contact['uid'];
|
||||
unset($contact['uid']);
|
||||
|
||||
|
|
|
@ -97,6 +97,7 @@ class User
|
|||
const ACCOUNT_TYPE_NEWS = 2;
|
||||
const ACCOUNT_TYPE_COMMUNITY = 3;
|
||||
const ACCOUNT_TYPE_RELAY = 4;
|
||||
const ACCOUNT_TYPE_DELETED = 127;
|
||||
/**
|
||||
* @}
|
||||
*/
|
||||
|
|
|
@ -104,7 +104,7 @@ class Proxy extends BaseModule
|
|||
|
||||
// It shouldn't happen but it does - spaces in URL
|
||||
$request['url'] = str_replace(' ', '+', $request['url']);
|
||||
$fetchResult = HTTPSignature::fetchRaw($request['url'], local_user(), true, ['timeout' => 10]);
|
||||
$fetchResult = HTTPSignature::fetchRaw($request['url'], local_user(), ['timeout' => 10]);
|
||||
$img_str = $fetchResult->getBody();
|
||||
|
||||
// If there is an error then return a blank image
|
||||
|
|
|
@ -68,7 +68,7 @@ class ActivityPub
|
|||
'manuallyApprovesFollowers' => 'as:manuallyApprovesFollowers',
|
||||
'sensitive' => 'as:sensitive', 'Hashtag' => 'as:Hashtag',
|
||||
'directMessage' => 'litepub:directMessage']];
|
||||
const ACCOUNT_TYPES = ['Person', 'Organization', 'Service', 'Group', 'Application'];
|
||||
const ACCOUNT_TYPES = ['Person', 'Organization', 'Service', 'Group', 'Application', 'Tombstone'];
|
||||
/**
|
||||
* Checks if the web request is done for the AP protocol
|
||||
*
|
||||
|
@ -113,7 +113,10 @@ class ActivityPub
|
|||
case 'Application':
|
||||
$accounttype = User::ACCOUNT_TYPE_RELAY;
|
||||
break;
|
||||
}
|
||||
case 'Tombstone':
|
||||
$accounttype = User::ACCOUNT_TYPE_DELETED;
|
||||
break;
|
||||
}
|
||||
|
||||
return $accounttype;
|
||||
}
|
||||
|
|
|
@ -376,8 +376,7 @@ class HTTPSignature
|
|||
*/
|
||||
public static function fetch($request, $uid)
|
||||
{
|
||||
$opts = ['accept_content' => 'application/activity+json, application/ld+json'];
|
||||
$curlResult = self::fetchRaw($request, $uid, false, $opts);
|
||||
$curlResult = self::fetchRaw($request, $uid);
|
||||
|
||||
if (empty($curlResult)) {
|
||||
return false;
|
||||
|
@ -410,7 +409,7 @@ class HTTPSignature
|
|||
* @return object CurlResult
|
||||
* @throws \Friendica\Network\HTTPException\InternalServerErrorException
|
||||
*/
|
||||
public static function fetchRaw($request, $uid = 0, $binary = false, $opts = [])
|
||||
public static function fetchRaw($request, $uid = 0, $opts = ['accept_content' => 'application/activity+json, application/ld+json'])
|
||||
{
|
||||
$header = [];
|
||||
|
||||
|
|
|
@ -31,15 +31,21 @@ use Friendica\Model\Photo;
|
|||
*/
|
||||
class RemoveContact {
|
||||
public static function execute($id) {
|
||||
|
||||
// Only delete if the contact is to be deleted
|
||||
$contact = DBA::selectFirst('contact', ['uid'], ['deleted' => true, 'id' => $id]);
|
||||
if (!DBA::isResult($contact)) {
|
||||
return;
|
||||
}
|
||||
|
||||
Logger::info('Start deleting contact', ['id' => $id]);
|
||||
// Now we delete the contact and all depending tables
|
||||
$condition = ['uid' => $contact['uid'], 'contact-id' => $id];
|
||||
if ($contact['uid'] == 0) {
|
||||
DBA::delete('post-tag', ['cid' => $id]);
|
||||
$condition = ["`author-id` = ? OR `owner-id` = ? OR `causer-id` = ? OR `contact-id` = ?",
|
||||
$id, $id, $id, $id];
|
||||
} else {
|
||||
$condition = ['uid' => $contact['uid'], 'contact-id' => $id];
|
||||
}
|
||||
do {
|
||||
$items = Item::select(['id', 'guid'], $condition, ['limit' => 100]);
|
||||
while ($item = Item::fetch($items)) {
|
||||
|
@ -49,7 +55,8 @@ class RemoveContact {
|
|||
DBA::close($items);
|
||||
} while (Item::exists($condition));
|
||||
|
||||
Photo::delete(['uid' => $contact['uid'], 'contact-id' => $id]);
|
||||
DBA::delete('contact', ['id' => $id]);
|
||||
Photo::delete(['contact-id' => $id]);
|
||||
$ret = DBA::delete('contact', ['id' => $id]);
|
||||
Logger::info('Deleted contact', ['id' => $id, 'result' => $ret]);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue