Commit e1961a37 authored by swentel's avatar swentel

Issue #3166193: add services, do not double send

parent 50b0e02f
...@@ -9,6 +9,11 @@ The default path can be overridden in settings.php via settings: ...@@ -9,6 +9,11 @@ The default path can be overridden in settings.php via settings:
$settings['activitypub_keys_path'] = '/your/path/'; $settings['activitypub_keys_path'] = '/your/path/';
``` ```
## Sending posts to followers
Activities in the outbox are stored in a queue and send either by
cron or drush.
## Default avatar ## Default avatar
The default avatar path can be overridden in settings.php via settings: The default avatar path can be overridden in settings.php via settings:
......
...@@ -52,6 +52,15 @@ function activitypub_nodeinfo_alter(&$data) { ...@@ -52,6 +52,15 @@ function activitypub_nodeinfo_alter(&$data) {
\Drupal::service('activitypub.utility')->alterNodeInfo($data); \Drupal::service('activitypub.utility')->alterNodeInfo($data);
} }
/**
* Implements hook_cron().
*/
function activitypub_cron() {
if (\Drupal::config('activitypub.settings')->get('send_outbox_handler') == 'cron') {
\Drupal::service('activitypub.outbox.client')->handleQueue();
}
}
/** /**
* Returns the path where the keys are stored. * Returns the path where the keys are stored.
* *
......
...@@ -25,3 +25,5 @@ services: ...@@ -25,3 +25,5 @@ services:
logger.channel.activitypub: logger.channel.activitypub:
parent: logger.channel_base parent: logger.channel_base
arguments: ['activitypub'] arguments: ['activitypub']
activitypub.outbox.client:
class: Drupal\activitypub\Services\ActivityPubOutboxClient
avatar_user_style: 'thumbnail' avatar_user_style: 'thumbnail'
avatar_user_field: 'user_picture' avatar_user_field: 'user_picture'
send_outbox_handler: ''
...@@ -33,7 +33,6 @@ activitypub.activitypub_object_mapping.*: ...@@ -33,7 +33,6 @@ activitypub.activitypub_object_mapping.*:
property: property:
type: string type: string
# schema for activitypub.settings # schema for activitypub.settings
activitypub.settings: activitypub.settings:
type: config_object type: config_object
...@@ -45,3 +44,6 @@ activitypub.settings: ...@@ -45,3 +44,6 @@ activitypub.settings:
avatar_user_field: avatar_user_field:
type: string type: string
label: 'Avatar user field' label: 'Avatar user field'
send_outbox_handler:
type: string
label: 'Send outbox handler'
...@@ -9,6 +9,18 @@ use Drush\Commands\DrushCommands; ...@@ -9,6 +9,18 @@ use Drush\Commands\DrushCommands;
*/ */
class ActivityPubCommands extends DrushCommands { class ActivityPubCommands extends DrushCommands {
/**
* Send activities.
*
* @command activitypub:send-activities
* @aliases asa,activitypub-send-activities
*/
public function sendActivities() {
if (\Drupal::config('activitypub.settings')->get('send_outbox_handler') == 'drush') {
\Drupal::service('activitypub.outbox.client')->handleQueue();
}
}
/** /**
* Get info about a name via WebFinger. * Get info about a name via WebFinger.
* *
......
...@@ -75,7 +75,12 @@ class ActivityPubSettingsForm extends ConfigFormBase { ...@@ -75,7 +75,12 @@ class ActivityPubSettingsForm extends ConfigFormBase {
$config = $this->config('activitypub.settings'); $config = $this->config('activitypub.settings');
$form['avatar_user_style'] = [ $form['media'] = [
'#type' => 'fieldset',
'#title' => $this->t('Media'),
];
$form['media']['avatar_user_style'] = [
'#title' => $this->t('Avatar image style'), '#title' => $this->t('Avatar image style'),
'#description' => $this->t('This image style will be used for the avatar for local and remote users.'), '#description' => $this->t('This image style will be used for the avatar for local and remote users.'),
'#default_value' => $config->get('avatar_user_style'), '#default_value' => $config->get('avatar_user_style'),
...@@ -92,7 +97,7 @@ class ActivityPubSettingsForm extends ConfigFormBase { ...@@ -92,7 +97,7 @@ class ActivityPubSettingsForm extends ConfigFormBase {
} }
} }
$form['avatar_user_field'] = [ $form['media']['avatar_user_field'] = [
'#title' => $this->t('Avatar field'), '#title' => $this->t('Avatar field'),
'#description' => $this->t('Select the field on the user which contains the user avatar.'), '#description' => $this->t('Select the field on the user which contains the user avatar.'),
'#default_value' => $config->get('avatar_user_field'), '#default_value' => $config->get('avatar_user_field'),
...@@ -100,6 +105,23 @@ class ActivityPubSettingsForm extends ConfigFormBase { ...@@ -100,6 +105,23 @@ class ActivityPubSettingsForm extends ConfigFormBase {
'#options' => $user_image_fields, '#options' => $user_image_fields,
]; ];
$form['outbox'] = [
'#type' => 'fieldset',
'#title' => $this->t('Outbox'),
];
$form['outbox']['send_outbox_handler'] = [
'#title' => $this->t('Send activities'),
'#type' => 'radios',
'#options' => [
'' => $this->t('Disabled'),
'cron' => $this->t('On cron run'),
'drush' => $this->t('With drush'),
],
'#default_value' => $config->get('send_outbox_handler'),
'#description' => $this->t('Activities in the Outbox are not send immediately, but are stored in a queue when the content is published.<br />The drush command is <strong>activitypub-send-activities</strong>')
];
return parent::buildForm($form, $form_state); return parent::buildForm($form, $form_state);
} }
...@@ -110,6 +132,7 @@ class ActivityPubSettingsForm extends ConfigFormBase { ...@@ -110,6 +132,7 @@ class ActivityPubSettingsForm extends ConfigFormBase {
$this->config('activitypub.settings') $this->config('activitypub.settings')
->set('avatar_user_style', $form_state->getValue('avatar_user_style')) ->set('avatar_user_style', $form_state->getValue('avatar_user_style'))
->set('avatar_user_field', $form_state->getValue('avatar_user_field')) ->set('avatar_user_field', $form_state->getValue('avatar_user_field'))
->set('send_outbox_handler', $form_state->getValue('send_outbox_handler'))
->save(); ->save();
parent::submitForm($form, $form_state); parent::submitForm($form, $form_state);
} }
......
...@@ -240,18 +240,30 @@ class ActivityPubFormAlter implements ActivityPubFormAlterInterface { ...@@ -240,18 +240,30 @@ class ActivityPubFormAlter implements ActivityPubFormAlterInterface {
return; return;
} }
$entities = $this->objectMapStorage->loadByProperties(['status' => TRUE, 'target_entity_type_id' => $entity->getEntityTypeId(), 'target_bundle' => $entity->bundle()]); $options = [];
if ($entities) { $outbox_selected = [];
$form['activitypub_wrapper'] = [ /** @var \Drupal\activitypub\Entity\ActivityPubActivityInterface[] $outboxEntities */
'#type' => 'details', if ($entity->id()) {
'#title' => t('ActivityPub outbox'), $outboxEntities = $this->activityStorage->loadByProperties(['entity_type_id' => $entity->getEntityTypeId(), 'entity_id' => $entity->id(), 'collection' => 'outbox']);
'#group' => 'advanced', foreach ($outboxEntities as $outboxEntity) {
]; $outbox_selected[$outboxEntity->getType()] = $outboxEntity->getType();
}
$options = ['' => $this->t('- Select -')]; }
foreach ($entities as $entity) { $mapEntities = $this->objectMapStorage->loadByProperties(['status' => TRUE, 'target_entity_type_id' => $entity->getEntityTypeId(), 'target_bundle' => $entity->bundle()]);
foreach ($mapEntities as $entity) {
if (!isset($outbox_selected[$entity->id()])) {
$options[$entity->id()] = $entity->label(); $options[$entity->id()] = $entity->label();
} }
}
$form['activitypub_wrapper'] = [
'#type' => 'details',
'#title' => t('ActivityPub outbox'),
'#group' => 'advanced',
];
if ($options) {
$options = ['' => $this->t('- Select -')] + $options;
$form['activitypub_wrapper']['activitypub_mapping'] = [ $form['activitypub_wrapper']['activitypub_mapping'] = [
'#type' => 'select', '#type' => 'select',
'#title' => $this->t('Object'), '#title' => $this->t('Object'),
...@@ -264,6 +276,11 @@ class ActivityPubFormAlter implements ActivityPubFormAlterInterface { ...@@ -264,6 +276,11 @@ class ActivityPubFormAlter implements ActivityPubFormAlterInterface {
} }
} }
} }
else {
$form['activitypub_wrapper']['activitypub_sent'] = [
'#markup' => $this->t('This post has been sent to the outbox.'),
];
}
} }
/** /**
......
<?php
namespace Drupal\activitypub\Services;
class ActivityPubOutboxClient implements ActivityPubOutboxClientInterface {
/**
* {@inheritdoc}
*/
public function handleQueue() {
}
}
<?php
namespace Drupal\activitypub\Services;
interface ActivityPubOutboxClientInterface {
/**
* Handles the Outbox queue.
*/
public function handleQueue();
}
...@@ -55,6 +55,8 @@ class OutboxTest extends ActivityPubTestBase { ...@@ -55,6 +55,8 @@ class OutboxTest extends ActivityPubTestBase {
]; ];
$this->drupalPostForm(NULL, $edit, 'Save'); $this->drupalPostForm(NULL, $edit, 'Save');
$assert_session->addressEquals('node/1'); $assert_session->addressEquals('node/1');
$this->drupalGet('node/1/edit');
$assert_session->pageTextContains('This post has been sent to the outbox.');
$this->drupalLogout(); $this->drupalLogout();
$this->drupalGet($outbox); $this->drupalGet($outbox);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment