-- ------------------------------------------
-- Friendica 2023.03-dev (Giant Rhubarb)
--- DB_UPDATE_VERSION 1506
+-- DB_UPDATE_VERSION 1507
-- ------------------------------------------
CREATE TABLE IF NOT EXISTS `inbox-status` (
`url` varbinary(383) NOT NULL COMMENT 'URL of the inbox',
`uri-id` int unsigned COMMENT 'Item-uri id of inbox url',
+ `gsid` int unsigned COMMENT 'ID of the related server',
`created` datetime NOT NULL DEFAULT '0001-01-01 00:00:00' COMMENT 'Creation date of this entry',
`success` datetime NOT NULL DEFAULT '0001-01-01 00:00:00' COMMENT 'Date of the last successful delivery',
`failure` datetime NOT NULL DEFAULT '0001-01-01 00:00:00' COMMENT 'Date of the last failed delivery',
`shared` boolean NOT NULL DEFAULT '0' COMMENT 'Is it a shared inbox?',
PRIMARY KEY(`url`),
INDEX `uri-id` (`uri-id`),
- FOREIGN KEY (`uri-id`) REFERENCES `item-uri` (`id`) ON UPDATE RESTRICT ON DELETE CASCADE
+ INDEX `gsid` (`gsid`),
+ FOREIGN KEY (`uri-id`) REFERENCES `item-uri` (`id`) ON UPDATE RESTRICT ON DELETE CASCADE,
+ FOREIGN KEY (`gsid`) REFERENCES `gserver` (`id`) ON UPDATE RESTRICT ON DELETE RESTRICT
) DEFAULT COLLATE utf8mb4_general_ci COMMENT='Status of ActivityPub inboxes';
--
| -------- | ------------------------------------ | -------------- | ---- | --- | ------------------- | ----- |
| url | URL of the inbox | varbinary(383) | NO | PRI | NULL | |
| uri-id | Item-uri id of inbox url | int unsigned | YES | | NULL | |
+| gsid | ID of the related server | int unsigned | YES | | NULL | |
| created | Creation date of this entry | datetime | NO | | 0001-01-01 00:00:00 | |
| success | Date of the last successful delivery | datetime | NO | | 0001-01-01 00:00:00 | |
| failure | Date of the last failed delivery | datetime | NO | | 0001-01-01 00:00:00 | |
| ------- | ------ |
| PRIMARY | url |
| uri-id | uri-id |
+| gsid | gsid |
Foreign Keys
------------
| Field | Target Table | Target Field |
|-------|--------------|--------------|
| uri-id | [item-uri](help/database/db_item-uri) | id |
+| gsid | [gserver](help/database/db_gserver) | id |
Return to [database documentation](help/database)
// Needed for the helper function to read from the legacy term table
const OBJECT_TYPE_POST = 1;
- const VERSION = 1484;
+ const VERSION = 1507;
/**
* Calls the post update functions
if (!self::update1484()) {
return false;
}
+ if (!self::update1507()) {
+ return false;
+ }
return true;
}
return false;
}
+
+ /**
+ * update the "gsid" (global server id) field in the inbox-status table
+ *
+ * @return bool "true" when the job is done
+ * @throws \Friendica\Network\HTTPException\InternalServerErrorException
+ * @throws \ImagickException
+ */
+ private static function update1507()
+ {
+ // Was the script completed?
+ if (DI::keyValue()->get('post_update_version') >= 1507) {
+ return true;
+ }
+
+ $id = DI::keyValue()->get('post_update_version_1507_id') ?? '';
+
+ Logger::info('Start', ['apcontact' => $id]);
+
+ $start_id = $id;
+ $rows = 0;
+ $condition = ["`url` > ? AND NOT `gsid` IS NULL", $id];
+ $params = ['order' => ['url'], 'limit' => 10000];
+ $apcontacts = DBA::select('apcontact', ['url', 'gsid', 'sharedinbox', 'inbox'], $condition, $params);
+
+ if (DBA::errorNo() != 0) {
+ Logger::error('Database error', ['no' => DBA::errorNo(), 'message' => DBA::errorMessage()]);
+ return false;
+ }
+
+ while ($apcontact = DBA::fetch($apcontacts)) {
+ $id = $apcontact['url'];
+
+ $inbox = [$apcontact['inbox']];
+ if (!empty($apcontact['sharedinbox'])) {
+ $inbox[] = $apcontact['sharedinbox'];
+ }
+ $condition = DBA::mergeConditions(['url' => $inbox], ["`gsid` IS NULL"]);
+ DBA::update('inbox-status', ['gsid' => $apcontact['gsid']], $condition);
+ ++$rows;
+ }
+ DBA::close($apcontacts);
+
+ DI::keyValue()->set('post_update_version_1507_id', $id);
+
+ Logger::info('Processed', ['rows' => $rows, 'last' => $id]);
+
+ if ($start_id == $id) {
+ DI::keyValue()->set('post_update_version', 1507);
+ Logger::info('Done');
+ return true;
+ }
+
+ return false;
+ }
}
$apcontact['following'] = JsonLD::fetchElement($compacted, 'as:following', '@id');
$apcontact['followers'] = JsonLD::fetchElement($compacted, 'as:followers', '@id');
$apcontact['inbox'] = (JsonLD::fetchElement($compacted, 'ldp:inbox', '@id') ?? '');
- self::unarchiveInbox($apcontact['inbox'], false);
-
$apcontact['outbox'] = JsonLD::fetchElement($compacted, 'as:outbox', '@id');
$apcontact['sharedinbox'] = '';
if (!empty($compacted['as:endpoints'])) {
$apcontact['sharedinbox'] = (JsonLD::fetchElement($compacted['as:endpoints'], 'as:sharedInbox', '@id') ?? '');
- self::unarchiveInbox($apcontact['sharedinbox'], true);
}
$apcontact['featured'] = JsonLD::fetchElement($compacted, 'toot:featured', '@id');
$apcontact['gsid'] = null;
}
+ self::unarchiveInbox($apcontact['inbox'], false, $apcontact['gsid']);
+
+ if (!empty($apcontact['sharedinbox'])) {
+ self::unarchiveInbox($apcontact['sharedinbox'], true, $apcontact['gsid']);
+ }
+
if ($apcontact['url'] == $apcontact['alias']) {
$apcontact['alias'] = null;
}
{
if (!empty($apcontact['inbox'])) {
Logger::info('Set inbox status to failure', ['inbox' => $apcontact['inbox']]);
- HTTPSignature::setInboxStatus($apcontact['inbox'], false);
+ HTTPSignature::setInboxStatus($apcontact['inbox'], false, false, $apcontact['gsid']);
}
if (!empty($apcontact['sharedinbox'])) {
if (!$available) {
// If all known personal inboxes are failing then set their shared inbox to failure as well
Logger::info('Set shared inbox status to failure', ['sharedinbox' => $apcontact['sharedinbox']]);
- HTTPSignature::setInboxStatus($apcontact['sharedinbox'], false, true);
+ HTTPSignature::setInboxStatus($apcontact['sharedinbox'], false, true, $apcontact['gsid']);
}
}
}
{
if (!empty($apcontact['inbox'])) {
Logger::info('Set inbox status to success', ['inbox' => $apcontact['inbox']]);
- HTTPSignature::setInboxStatus($apcontact['inbox'], true);
+ HTTPSignature::setInboxStatus($apcontact['inbox'], true, false, $apcontact['gsid']);
}
if (!empty($apcontact['sharedinbox'])) {
Logger::info('Set shared inbox status to success', ['sharedinbox' => $apcontact['sharedinbox']]);
- HTTPSignature::setInboxStatus($apcontact['sharedinbox'], true, true);
+ HTTPSignature::setInboxStatus($apcontact['sharedinbox'], true, true, $apcontact['gsid']);
}
}
*
* @param string $url inbox url
* @param boolean $shared Shared Inbox
+ * @param int $gsid Global server id
* @return void
*/
- private static function unarchiveInbox(string $url, bool $shared)
+ private static function unarchiveInbox(string $url, bool $shared, int $gsid = null)
{
if (empty($url)) {
return;
}
- HTTPSignature::setInboxStatus($url, true, $shared);
+ HTTPSignature::setInboxStatus($url, true, $shared, $gsid);
}
/**
['nurl' => Strings::normaliseLink($url)]);
Logger::info('Set failed status for existing server', ['url' => $url]);
if (self::isDefunct($gserver)) {
- Contact::update(['archive' => true], ['gsid' => $gserver['id']]);
+ self::archiveContacts($gserver['id']);
}
return;
}
Logger::info('Set failed status for new server', ['url' => $url]);
}
+ /**
+ * Archive server related contacts and inboxes
+ *
+ * @param integer $gsid
+ * @return void
+ */
+ private static function archiveContacts(int $gsid)
+ {
+ Contact::update(['archive' => true], ['gsid' => $gsid]);
+ DBA::update('inbox-status', ['archive' => true], ['gsid' => $gsid]);
+ }
+
/**
* Remove unwanted content from the given URL
*
* @param string $url The URL of the inbox
* @param boolean $success Transmission status
* @param boolean $shared The inbox is a shared inbox
+ * @param int $gsid Server ID
* @throws \Exception
*/
- static public function setInboxStatus(string $url, bool $success, bool $shared = false)
+ static public function setInboxStatus(string $url, bool $success, bool $shared = false, int $gsid = null)
{
$now = DateTimeFormat::utcNow();
$status = DBA::selectFirst('inbox-status', [], ['url' => $url]);
if (!DBA::isResult($status)) {
$insertFields = ['url' => $url, 'uri-id' => ItemURI::getIdByURI($url), 'created' => $now, 'shared' => $shared];
+ if (!empty($gsid)) {
+ $insertFields['gsid'] = $gsid;
+ }
if (!DBA::insert('inbox-status', $insertFields, Database::INSERT_IGNORE)) {
Logger::warning('Unable to insert inbox-status row', $insertFields);
return;
$fields = ['failure' => $now];
}
+ if (!empty($gsid)) {
+ $fields['gsid'] = $gsid;
+ }
+
if ($status['failure'] > DBA::NULL_DATETIME) {
$new_previous_stamp = strtotime($status['failure']);
$old_previous_stamp = strtotime($status['previous']);
use Friendica\Database\DBA;
if (!defined('DB_UPDATE_VERSION')) {
- define('DB_UPDATE_VERSION', 1506);
+ define('DB_UPDATE_VERSION', 1507);
}
return [
"fields" => [
"url" => ["type" => "varbinary(383)", "not null" => "1", "primary" => "1", "comment" => "URL of the inbox"],
"uri-id" => ["type" => "int unsigned", "foreign" => ["item-uri" => "id"], "comment" => "Item-uri id of inbox url"],
+ "gsid" => ["type" => "int unsigned", "foreign" => ["gserver" => "id", "on delete" => "restrict"], "comment" => "ID of the related server"],
"created" => ["type" => "datetime", "not null" => "1", "default" => DBA::NULL_DATETIME, "comment" => "Creation date of this entry"],
"success" => ["type" => "datetime", "not null" => "1", "default" => DBA::NULL_DATETIME, "comment" => "Date of the last successful delivery"],
"failure" => ["type" => "datetime", "not null" => "1", "default" => DBA::NULL_DATETIME, "comment" => "Date of the last failed delivery"],
"indexes" => [
"PRIMARY" => ["url"],
"uri-id" => ["uri-id"],
+ "gsid" => ["gsid"],
]
],
"intro" => [