From d4b7e990ce18bef4571012e270594fb559678927 Mon Sep 17 00:00:00 2001 From: Hugo Sales Date: Sun, 3 Apr 2022 21:40:32 +0100 Subject: [PATCH] [CORE][Event] Make all events return \EventResult, enforced at container build time --- components/Attachment/Attachment.php | 11 ++--- components/Avatar/Avatar.php | 10 +++-- components/Circle/Circle.php | 9 +++-- components/Collection/Collection.php | 5 ++- .../Collection/Util/MetaCollectionTrait.php | 5 ++- components/Conversation/Conversation.php | 19 ++++----- components/Feed/Feed.php | 3 +- components/FreeNetwork/FreeNetwork.php | 27 +++++++------ components/Group/Group.php | 11 ++--- components/Language/Language.php | 9 +++-- components/LeftPanel/LeftPanel.php | 5 ++- components/Link/Link.php | 7 ++-- components/Notification/Notification.php | 11 ++--- components/Person/Person.php | 3 +- components/Posting/Posting.php | 7 ++-- components/Search/Search.php | 9 +++-- components/Subscription/Subscription.php | 5 ++- components/Tag/Tag.php | 15 +++---- composer.json | 3 ++ config/services.yaml | 2 +- plugins/ActivityPub/ActivityPub.php | 25 ++++++------ .../AttachmentCollections.php | 5 ++- .../AttachmentShowRelated.php | 5 ++- plugins/AudioEncoder/AudioEncoder.php | 7 ++-- plugins/Blog/Blog.php | 7 ++-- plugins/Cover/Cover.php | 9 +++-- plugins/DeleteNote/DeleteNote.php | 11 ++--- plugins/Directory/Directory.php | 7 ++-- .../EmailNotifications/EmailNotifications.php | 3 +- plugins/Embed/Embed.php | 13 +++--- plugins/Favourite/Favourite.php | 19 ++++----- plugins/FileQuota/FileQuota.php | 5 ++- plugins/ImageEncoder/ImageEncoder.php | 11 ++--- plugins/LatexNotes/LatexNotes.php | 5 ++- plugins/MarkdownNotes/MarkdownNotes.php | 5 ++- .../NoteTypeFeedFilter/NoteTypeFeedFilter.php | 9 +++-- plugins/OAuth2/OAuth2.php | 8 ++-- plugins/Oomox/Oomox.php | 7 ++-- plugins/Pinboard/Pinboard.php | 5 ++- plugins/PinnedNotes/PinnedNotes.php | 19 ++++----- plugins/Poll/Poll.php | 9 +++-- plugins/ProfileColor/ProfileColor.php | 7 ++-- plugins/RelatedTags/RelatedTags.php | 3 +- plugins/RepeatNote/RepeatNote.php | 19 ++++----- plugins/StemWord/StemWord.php | 3 +- plugins/StoreRemoteMedia/StoreRemoteMedia.php | 5 ++- .../TagBasedFiltering/TagBasedFiltering.php | 10 +++-- plugins/TreeNotes/TreeNotes.php | 6 ++- plugins/UnboundGroup/UnboundGroup.php | 9 +++-- plugins/VideoEncoder/VideoEncoder.php | 11 ++--- plugins/WebHooks/WebHooks.php | 12 +++--- plugins/WebMonetization/WebMonetization.php | 11 ++--- .../XMPPNotifications/XMPPNotifications.php | 3 +- src/Core/Event.php | 40 +++++++++---------- src/Core/Event/EventResult.php | 13 ++++++ src/Core/Event/GSEvent.php | 23 +++++++++++ src/Core/ModuleManager.php | 15 +++++-- src/Core/Modules/Module.php | 12 +++--- src/Core/Modules/Plugin.php | 3 +- src/Core/Security.php | 9 ++--- 60 files changed, 345 insertions(+), 239 deletions(-) create mode 100644 src/Core/Event/EventResult.php create mode 100644 src/Core/Event/GSEvent.php diff --git a/components/Attachment/Attachment.php b/components/Attachment/Attachment.php index 5437ff1996..f3e1b3f03e 100644 --- a/components/Attachment/Attachment.php +++ b/components/Attachment/Attachment.php @@ -34,10 +34,11 @@ use Component\Attachment\Entity as E; use Doctrine\Common\Collections\ExpressionBuilder; use Doctrine\ORM\Query\Expr; use Doctrine\ORM\QueryBuilder; +use EventResult; class Attachment extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('note_attachment_show', '/object/note/{note_id<\d+>}/attachment/{attachment_id<\d+>}', [C\Attachment::class, 'attachmentShowWithNote']); $r->connect('note_attachment_view', '/object/note/{note_id<\d+>}/attachment/{attachment_id<\d+>}/view', [C\Attachment::class, 'attachmentViewWithNote']); @@ -51,13 +52,13 @@ class Attachment extends Component * * This can be used in the future to deduplicate images by visual content */ - public function onHashFile(string $filename, ?string &$out_hash): bool + public function onHashFile(string $filename, ?string &$out_hash): EventResult { $out_hash = hash_file(E\Attachment::FILEHASH_ALGO, $filename); return Event::stop; } - public function onNoteDeleteRelated(Note &$note, Actor $actor): bool + public function onNoteDeleteRelated(Note &$note, Actor $actor): EventResult { Cache::delete("note-attachments-{$note->getId()}"); foreach ($note->getAttachments() as $attachment) { @@ -68,7 +69,7 @@ class Attachment extends Component return Event::next; } - public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): bool + public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): EventResult { if (!\in_array('attachment_to_note', $note_qb->getAllAliases())) { $note_qb->leftJoin( @@ -84,7 +85,7 @@ class Attachment extends Component /** * Populate $note_expr with the criteria for looking for notes with attachments */ - public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): bool + public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): EventResult { $include_term = str_contains($term, ':') ? explode(':', $term)[1] : $term; if (Formatting::startsWith($term, ['note-types:', 'notes-incude:', 'note-filter:'])) { diff --git a/components/Avatar/Avatar.php b/components/Avatar/Avatar.php index ba27e5e1bb..6cebeadb0f 100644 --- a/components/Avatar/Avatar.php +++ b/components/Avatar/Avatar.php @@ -32,15 +32,17 @@ use Component\Attachment\Entity\Attachment; use Component\Attachment\Entity\AttachmentThumbnail; use Component\Avatar\Controller as C; use Component\Avatar\Exception\NoAvatarException; +use EventResult; use Symfony\Component\HttpFoundation\Request; class Avatar extends Component { - public function onInitializeComponent() + public function onInitializeComponent(): EventResult { + return EventResult::next; } - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('avatar_actor', '/actor/{actor_id<\d+>}/avatar/{size?medium}', [Controller\Avatar::class, 'avatar_view']); $r->connect('avatar_default', '/avatar/default/{size?medium}', [Controller\Avatar::class, 'default_avatar_view']); @@ -51,7 +53,7 @@ class Avatar extends Component /** * @throws \App\Util\Exception\ClientException */ - public function onPopulateSettingsTabs(Request $request, string $section, &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, &$tabs): EventResult { if ($section === 'profile') { $tabs[] = [ @@ -64,7 +66,7 @@ class Avatar extends Component return Event::next; } - public function onAvatarUpdate(int $actor_id): bool + public function onAvatarUpdate(int $actor_id): EventResult { Cache::delete("avatar-{$actor_id}"); foreach (['full', 'big', 'medium', 'small'] as $size) { diff --git a/components/Circle/Circle.php b/components/Circle/Circle.php index 5ed7d2414c..d9b2f3019c 100644 --- a/components/Circle/Circle.php +++ b/components/Circle/Circle.php @@ -39,6 +39,7 @@ use Component\Circle\Entity\ActorCircleSubscription; use Component\Circle\Entity\ActorTag; use Component\Collection\Util\MetaCollectionTrait; use Component\Tag\Tag; +use EventResult; use Functional as F; use Symfony\Component\HttpFoundation\Request; @@ -58,7 +59,7 @@ class Circle extends Component protected const SLUG = 'circle'; protected const PLURAL_SLUG = 'circles'; - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('actor_circle_view_by_circle_id', '/circle/{circle_id<\d+>}', [CircleController\Circle::class, 'circleById']); // View circle members by (tagger id or nickname) and tag @@ -93,7 +94,7 @@ class Circle extends Component ]; } - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'profile' && \in_array($request->get('_route'), ['person_actor_settings', 'group_actor_settings'])) { $tabs[] = [ @@ -106,7 +107,7 @@ class Circle extends Component return Event::next; } - public function onPostingFillTargetChoices(Request $request, Actor $actor, array &$targets): bool + public function onPostingFillTargetChoices(Request $request, Actor $actor, array &$targets): EventResult { $circles = $actor->getCircles(); foreach ($circles as $circle) { @@ -218,7 +219,7 @@ class Circle extends Component return $ids_only ? array_map(fn ($x) => $x->getId(), $circles) : $circles; } - public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering) + public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): EventResult { DB::persist(Feed::create([ 'actor_id' => $actor_id, diff --git a/components/Collection/Collection.php b/components/Collection/Collection.php index 5c04a1131e..6e8003a2eb 100644 --- a/components/Collection/Collection.php +++ b/components/Collection/Collection.php @@ -14,6 +14,7 @@ use Component\Subscription\Entity\ActorSubscription; use Doctrine\Common\Collections\ExpressionBuilder; use Doctrine\ORM\Query\Expr; use Doctrine\ORM\QueryBuilder; +use EventResult; class Collection extends Component { @@ -64,7 +65,7 @@ class Collection extends Component return ['notes' => $notes ?? null, 'actors' => $actors ?? null]; } - public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): bool + public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): EventResult { $note_aliases = $note_qb->getAllAliases(); if (!\in_array('subscription', $note_aliases)) { @@ -80,7 +81,7 @@ class Collection extends Component * Convert $term to $note_expr and $actor_expr, search criteria. Handles searching for text * notes, for different types of actors and for the content of text notes */ - public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr) + public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): EventResult { if (str_contains($term, ':')) { $term = explode(':', $term); diff --git a/components/Collection/Util/MetaCollectionTrait.php b/components/Collection/Util/MetaCollectionTrait.php index 03ec2551a4..935e8d07d3 100644 --- a/components/Collection/Util/MetaCollectionTrait.php +++ b/components/Collection/Util/MetaCollectionTrait.php @@ -39,6 +39,7 @@ use App\Entity\Actor; use App\Util\Common; use App\Util\Exception\RedirectException; use App\Util\Formatting; +use EventResult; use Symfony\Component\Form\Extension\Core\Type\ChoiceType; use Symfony\Component\Form\Extension\Core\Type\SubmitType; use Symfony\Component\Form\Extension\Core\Type\TextType; @@ -94,7 +95,7 @@ trait MetaCollectionTrait * It's compose of two forms: one to select collections to add * the current item to, and another to create a new collection. */ - public function onAppendRightPanelBlock(Request $request, $vars, &$res): bool + public function onAppendRightPanelBlock(Request $request, $vars, &$res): EventResult { $user = Common::actor(); if (\is_null($user)) { @@ -186,7 +187,7 @@ trait MetaCollectionTrait return Event::next; } - public function onEndShowStyles(array &$styles, string $route): bool + public function onEndShowStyles(array &$styles, string $route): EventResult { $styles[] = 'components/Collection/assets/css/widget.css'; $styles[] = 'components/Collection/assets/css/pages.css'; diff --git a/components/Conversation/Conversation.php b/components/Conversation/Conversation.php index 3396c99b2d..ac6c9ac9e5 100644 --- a/components/Conversation/Conversation.php +++ b/components/Conversation/Conversation.php @@ -40,12 +40,13 @@ use App\Util\Common; use App\Util\Formatting; use Component\Conversation\Entity\Conversation as ConversationEntity; use Component\Conversation\Entity\ConversationMute; +use EventResult; use Functional as F; use Symfony\Component\HttpFoundation\Request; class Conversation extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('conversation', '/conversation/{conversation_id<\d+>}', [Controller\Conversation::class, 'showConversation']); $r->connect('conversation_mute', '/conversation/{conversation_id<\d+>}/mute', [Controller\Conversation::class, 'muteConversation']); @@ -104,7 +105,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onAddNoteActions(Request $request, Note $note, array &$actions): bool + public function onAddNoteActions(Request $request, Note $note, array &$actions): EventResult { if (\is_null(Common::user())) { return Event::next; @@ -144,7 +145,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onAppendCardNote(array $vars, array &$result): bool + public function onAppendCardNote(array $vars, array &$result): EventResult { if (str_contains($vars['request']->getPathInfo(), 'conversation')) { return Event::next; @@ -197,7 +198,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onPostingGetContextActor(Request $request, Actor $actor, ?Actor &$context_actor): bool + public function onPostingGetContextActor(Request $request, Actor $actor, ?Actor &$context_actor): EventResult { $to_note_id = $this->getReplyToIdFromRequest($request); if (!\is_null($to_note_id)) { @@ -218,7 +219,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onPostingModifyData(Request $request, Actor $actor, array &$data): bool + public function onPostingModifyData(Request $request, Actor $actor, array &$data): EventResult { $to_note_id = $this->getReplyToIdFromRequest($request); if (!\is_null($to_note_id)) { @@ -232,7 +233,7 @@ class Conversation extends Component /** * Add minimal Note card to RightPanel template */ - public function onPrependPostingForm(Request $request, array &$elements): bool + public function onPrependPostingForm(Request $request, array &$elements): EventResult { $elements[] = Formatting::twigRenderFile('cards/blocks/note_compact_wrapper.html.twig', ['note' => Note::getById((int) $request->query->get('reply_to_id'))]); return Event::next; @@ -247,7 +248,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onNoteDeleteRelated(Note &$note, Actor $actor): bool + public function onNoteDeleteRelated(Note &$note, Actor $actor): EventResult { // Ensure we have the most up to date replies Cache::delete(Note::cacheKeys($note->getId())['replies']); @@ -266,7 +267,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onAddExtraNoteActions(Request $request, Note $note, array &$actions): bool + public function onAddExtraNoteActions(Request $request, Note $note, array &$actions): EventResult { if (\is_null($user = Common::user())) { return Event::next; @@ -302,7 +303,7 @@ class Conversation extends Component * * @return bool EventHook */ - public function onNewNotificationShould(Activity $activity, Actor $actor): bool + public function onNewNotificationShould(Activity $activity, Actor $actor): EventResult { if ($activity->getObjectType() === 'note' && ConversationMute::isMuted($activity, $actor)) { return Event::stop; diff --git a/components/Feed/Feed.php b/components/Feed/Feed.php index 6e8a134d2b..58c5a82f8b 100644 --- a/components/Feed/Feed.php +++ b/components/Feed/Feed.php @@ -27,10 +27,11 @@ use App\Core\Event; use App\Core\Modules\Component; use App\Core\Router; use Component\Feed\Controller as C; +use EventResult; class Feed extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('feed_public', '/feed/public', [C\Feeds::class, 'public']); $r->connect('feed_home', '/feed/home', [C\Feeds::class, 'home']); diff --git a/components/FreeNetwork/FreeNetwork.php b/components/FreeNetwork/FreeNetwork.php index 77bc78d92f..49e97358b1 100644 --- a/components/FreeNetwork/FreeNetwork.php +++ b/components/FreeNetwork/FreeNetwork.php @@ -54,6 +54,7 @@ use Component\FreeNetwork\Util\WebfingerResource; use Component\FreeNetwork\Util\WebfingerResource\WebfingerResourceActor; use Component\FreeNetwork\Util\WebfingerResource\WebfingerResourceNote; use Doctrine\Common\Collections\ExpressionBuilder; +use EventResult; use Exception; use const PREG_SET_ORDER; use Symfony\Component\HttpFoundation\JsonResponse; @@ -79,13 +80,13 @@ class FreeNetwork extends Component public const OAUTH_AUTHORIZE_REL = 'http://apinamespace.org/oauth/authorize'; private static array $protocols = []; - public function onInitializeComponent(): bool + public function onInitializeComponent(): EventResult { Event::handle('AddFreeNetworkProtocol', [&self::$protocols]); return Event::next; } - public function onAddRoute(Router $m): bool + public function onAddRoute(Router $m): EventResult { // Feeds $m->connect('feed_network', '/feed/network', [Feeds::class, 'network']); @@ -111,7 +112,7 @@ class FreeNetwork extends Component return Event::next; } - public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering) + public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): EventResult { DB::persist(\App\Entity\Feed::create(['actor_id' => $actor_id, 'url' => Router::url($route = 'feed_network'), 'route' => $route, 'title' => _m('Meteorites'), 'ordering' => $ordering++])); DB::persist(\App\Entity\Feed::create(['actor_id' => $actor_id, 'url' => Router::url($route = 'feed_clique'), 'route' => $route, 'title' => _m('Planetary System'), 'ordering' => $ordering++])); @@ -119,7 +120,7 @@ class FreeNetwork extends Component return Event::next; } - public function onStartGetProfileAcctUri(Actor $profile, &$acct): bool + public function onStartGetProfileAcctUri(Actor $profile, &$acct): EventResult { $wfr = new WebFingerResourceActor($profile); try { @@ -147,7 +148,7 @@ class FreeNetwork extends Component * @throws NoSuchActorException * @throws ServerException */ - public function onEndGetWebFingerResource(string $resource, ?WebfingerResource &$target = null, array $args = []): bool + public function onEndGetWebFingerResource(string $resource, ?WebfingerResource &$target = null, array $args = []): EventResult { // * Either we didn't find the profile, then we want to make // the $profile variable null for clarity. @@ -223,7 +224,7 @@ class FreeNetwork extends Component return Event::next; } - public function onStartHostMetaLinks(array &$links): bool + public function onStartHostMetaLinks(array &$links): EventResult { foreach (Discovery::supportedMimeTypes() as $type) { $links[] = new XML_XRD_Element_Link( @@ -244,7 +245,7 @@ class FreeNetwork extends Component /** * Add a link header for LRDD Discovery */ - public function onStartShowHTML($action): bool + public function onStartShowHTML($action): EventResult { if ($action instanceof ShowstreamAction) { $resource = $action->getTarget()->getUri(); @@ -257,13 +258,13 @@ class FreeNetwork extends Component return Event::next; } - public function onStartDiscoveryMethodRegistration(Discovery $disco): bool + public function onStartDiscoveryMethodRegistration(Discovery $disco): EventResult { $disco->registerMethod('\Component\FreeNetwork\Util\LrddMethod\LrddMethodWebfinger'); return Event::next; } - public function onEndDiscoveryMethodRegistration(Discovery $disco): bool + public function onEndDiscoveryMethodRegistration(Discovery $disco): EventResult { $disco->registerMethod('\Component\FreeNetwork\Util\LrddMethod\LrddMethodHostMeta'); $disco->registerMethod('\Component\FreeNetwork\Util\LrddMethod\LrddMethodLinkHeader'); @@ -275,7 +276,7 @@ class FreeNetwork extends Component * @throws ClientException * @throws ServerException */ - public function onControllerResponseInFormat(string $route, array $accept_header, array $vars, ?Response &$response = null): bool + public function onControllerResponseInFormat(string $route, array $accept_header, array $vars, ?Response &$response = null): EventResult { if (!\in_array($route, ['freenetwork_hostmeta', 'freenetwork_hostmeta_format', 'freenetwork_webfinger', 'freenetwork_webfinger_format', 'freenetwork_ownerxrd'])) { return Event::next; @@ -376,7 +377,7 @@ class FreeNetwork extends Component * @return bool hook return value * @example.com/mublog/user */ - public function onEndFindMentions(Actor $sender, string $text, array &$mentions): bool + public function onEndFindMentions(Actor $sender, string $text, array &$mentions): EventResult { $matches = []; @@ -517,7 +518,7 @@ class FreeNetwork extends Component * Add fediverse: query expression * // TODO: adding WebFinger would probably be nice */ - public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): bool + public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): EventResult { if (Formatting::startsWith($term, ['fediverse:'])) { foreach (self::$protocols as $protocol) { @@ -530,7 +531,7 @@ class FreeNetwork extends Component return Event::next; } - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = [ 'name' => 'WebFinger', diff --git a/components/Group/Group.php b/components/Group/Group.php index ff32d1bcbf..4ab6fbd13e 100644 --- a/components/Group/Group.php +++ b/components/Group/Group.php @@ -33,11 +33,12 @@ use App\Util\Nickname; use Component\Group\Controller as C; use Component\Group\Entity\LocalGroup; use Component\Notification\Notification; +use EventResult; use Symfony\Component\HttpFoundation\Request; class Group extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect(id: 'group_actor_view_id', uri_path: '/group/{id<\d+>}', target: [C\GroupFeed::class, 'groupViewId']); $r->connect(id: 'group_actor_view_nickname', uri_path: '/!{nickname<' . Nickname::DISPLAY_FMT . '>}', target: [C\GroupFeed::class, 'groupViewNickname']); @@ -50,7 +51,7 @@ class Group extends Component * Enqueues a notification for an Actor (such as person or group) which means * it shows up in their home feed and such. */ - public function onNewNotificationStart(Actor $sender, Activity $activity, array $targets = [], ?string $reason = null): bool + public function onNewNotificationStart(Actor $sender, Activity $activity, array $targets = [], ?string $reason = null): EventResult { foreach ($targets as $target) { if ($target->isGroup()) { @@ -70,7 +71,7 @@ class Group extends Component /** * Add an to the profile card for groups, if the current actor can access them */ - public function onAppendCardProfile(array $vars, array &$res): bool + public function onAppendCardProfile(array $vars, array &$res): EventResult { $actor = Common::actor(); $group = $vars['actor']; @@ -108,7 +109,7 @@ class Group extends Component return null; } - public function onPostingFillTargetChoices(Request $request, Actor $actor, array &$targets): bool + public function onPostingFillTargetChoices(Request $request, Actor $actor, array &$targets): EventResult { $group = $this->getGroupFromContext($request); if (!\is_null($group)) { @@ -127,7 +128,7 @@ class Group extends Component * * @param null|Actor $context_actor Actor group, if current route is part of an existing Group set of routes */ - public function onPostingGetContextActor(Request $request, Actor $actor, ?Actor &$context_actor): bool + public function onPostingGetContextActor(Request $request, Actor $actor, ?Actor &$context_actor): EventResult { $ctx = $this->getGroupFromContext($request); if (!\is_null($ctx)) { diff --git a/components/Language/Language.php b/components/Language/Language.php index 8bb00cfcca..a3cad0a2ca 100644 --- a/components/Language/Language.php +++ b/components/Language/Language.php @@ -33,18 +33,19 @@ use Component\Language\Entity\ActorLanguage; use Doctrine\Common\Collections\ExpressionBuilder; use Doctrine\ORM\Query\Expr; use Doctrine\ORM\QueryBuilder; +use EventResult; use Functional as F; use Symfony\Component\HttpFoundation\Request; class Language extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('settings_sort_languages', '/settings/sort_languages', [C\Language::class, 'sortLanguages']); return Event::next; } - public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): bool + public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): EventResult { if (\is_null($actor)) { return Event::next; @@ -60,7 +61,7 @@ class Language extends Component /** * Populate $note_expr or $actor_expr with an expression to match a language */ - public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): bool + public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): EventResult { $search_term = str_contains($term, ':') ? explode(':', $term)[1] : $term; @@ -103,7 +104,7 @@ class Language extends Component return Event::next; } - public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): bool + public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): EventResult { $note_aliases = $note_qb->getAllAliases(); if (!\in_array('note_language', $note_aliases)) { diff --git a/components/LeftPanel/LeftPanel.php b/components/LeftPanel/LeftPanel.php index 6cb885c3ad..6b3e73af0e 100644 --- a/components/LeftPanel/LeftPanel.php +++ b/components/LeftPanel/LeftPanel.php @@ -32,10 +32,11 @@ use App\Entity\Feed; use App\Util\Exception\ClientException; use App\Util\Exception\NotFoundException; use Component\LeftPanel\Controller as C; +use EventResult; class LeftPanel extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('edit_feeds', '/edit-feeds', C\EditFeeds::class); return Event::next; @@ -46,7 +47,7 @@ class LeftPanel extends Component * @throws \App\Util\Exception\ServerException * @throws ClientException */ - public function onAppendFeed(Actor $actor, string $title, string $route, array $route_params): bool + public function onAppendFeed(Actor $actor, string $title, string $route, array $route_params): EventResult { $cache_key = Feed::cacheKey($actor); $feeds = Feed::getFeeds($actor); diff --git a/components/Link/Link.php b/components/Link/Link.php index d8b0d5da43..2c01851875 100644 --- a/components/Link/Link.php +++ b/components/Link/Link.php @@ -31,6 +31,7 @@ use App\Entity\Note; use App\Util\Common; use App\Util\HTML; use Component\Link\Entity\NoteToLink; +use EventResult; use InvalidArgumentException; class Link extends Component @@ -54,7 +55,7 @@ class Link extends Component /** * Extract URLs from $content and create the appropriate Link and NoteToLink entities */ - public function onProcessNoteContent(Note $note, string $content, string $content_type, array $process_note_content_extra_args = []): bool + public function onProcessNoteContent(Note $note, string $content, string $content_type, array $process_note_content_extra_args = []): EventResult { $ignore = $process_note_content_extra_args['ignoreLinks'] ?? []; if (Common::config('attachments', 'process_links')) { @@ -71,7 +72,7 @@ class Link extends Component return Event::next; } - public function onRenderPlainTextNoteContent(string &$text): bool + public function onRenderPlainTextNoteContent(string &$text): EventResult { $text = $this->replaceURLs($text); return Event::next; @@ -275,7 +276,7 @@ class Link extends Component return HTML::html(['a' => ['attrs' => $attrs, $url]], options: ['indent' => false]); } - public function onNoteDeleteRelated(Note &$note, Actor $actor): bool + public function onNoteDeleteRelated(Note &$note, Actor $actor): EventResult { DB::wrapInTransaction(fn () => NoteToLink::removeWhereNoteId($note->getId())); return Event::next; diff --git a/components/Notification/Notification.php b/components/Notification/Notification.php index 6d2350ce0c..25ed3e62d7 100644 --- a/components/Notification/Notification.php +++ b/components/Notification/Notification.php @@ -34,12 +34,13 @@ use App\Entity\LocalUser; use App\Util\Exception\ServerException; use Component\FreeNetwork\FreeNetwork; use Component\Notification\Controller\Feed; +use EventResult; use Exception; use Throwable; class Notification extends Component { - public function onAddRoute(Router $m): bool + public function onAddRoute(Router $m): EventResult { $m->connect('feed_notifications', '/feed/notifications', [Feed::class, 'notifications']); return Event::next; @@ -48,7 +49,7 @@ class Notification extends Component /** * @throws ServerException */ - public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): bool + public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): EventResult { DB::persist(\App\Entity\Feed::create([ 'actor_id' => $actor_id, @@ -75,7 +76,7 @@ class Notification extends Component * @param array $targets Attentions, Mentions, any other source. Should never be empty, you usually want to register an attention to every $sender->getSubscribers() * @param null|string $reason An optional reason explaining why this notification exists */ - public function onNewNotification(Actor $sender, Activity $activity, array $targets, ?string $reason = null): bool + public function onNewNotification(Actor $sender, Activity $activity, array $targets, ?string $reason = null): EventResult { // Ensure targets are all actor objects and unique $effective_targets = []; @@ -102,13 +103,13 @@ class Notification extends Component return Event::next; } - public function onQueueNotificationLocal(Actor $sender, Activity $activity, Actor $target, ?string $reason, array &$retry_args): bool + public function onQueueNotificationLocal(Actor $sender, Activity $activity, Actor $target, ?string $reason, array &$retry_args): EventResult { // TODO: use https://symfony.com/doc/current/notifier.html return Event::stop; } - public function onQueueNotificationRemote(Actor $sender, Activity $activity, array $targets, ?string $reason, array &$retry_args): bool + public function onQueueNotificationRemote(Actor $sender, Activity $activity, array $targets, ?string $reason, array &$retry_args): EventResult { if (FreeNetwork::notify($sender, $activity, $targets, $reason)) { return Event::stop; diff --git a/components/Person/Person.php b/components/Person/Person.php index 3d5847aa14..aa8ea14bee 100644 --- a/components/Person/Person.php +++ b/components/Person/Person.php @@ -26,10 +26,11 @@ use App\Core\Modules\Component; use App\Core\Router; use App\Util\Nickname; use Component\Person\Controller as C; +use EventResult; class Person extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect(id: 'person_actor_view_id', uri_path: '/person/{id<\d+>}', target: [C\PersonFeed::class, 'personViewId']); $r->connect(id: 'person_actor_view_nickname', uri_path: '/@{nickname<' . Nickname::DISPLAY_FMT . '>}', target: [C\PersonFeed::class, 'personViewNickname'], options: ['is_system_path' => false]); diff --git a/components/Posting/Posting.php b/components/Posting/Posting.php index e50c7f7999..2193e816ef 100644 --- a/components/Posting/Posting.php +++ b/components/Posting/Posting.php @@ -47,6 +47,7 @@ use Component\Attachment\Entity\AttachmentToNote; use Component\Conversation\Conversation; use Component\Language\Entity\Language; use Component\Notification\Entity\Attention; +use EventResult; use Symfony\Component\HttpFoundation\File\UploadedFile; use Symfony\Component\HttpFoundation\Request; @@ -54,7 +55,7 @@ class Posting extends Component { public const route = 'posting_form_action'; - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect(self::route, '/form/posting', Controller\Posting::class); return Event::next; @@ -70,7 +71,7 @@ class Posting extends Component * @throws RedirectException * @throws ServerException */ - public function onAddMainRightPanelBlock(Request $request, array &$res): bool + public function onAddMainRightPanelBlock(Request $request, array &$res): EventResult { if (\is_null($user = Common::user()) || preg_match('(feed|conversation|group|view)', $request->get('_route')) === 0) { return Event::next; @@ -298,7 +299,7 @@ class Posting extends Component return [$activity, $note, $effective_attentions]; } - public function onRenderNoteContent(string $content, string $content_type, ?string &$rendered, Actor $author, ?string $language = null, array &$mentions = []) + public function onRenderNoteContent(string $content, string $content_type, ?string &$rendered, Actor $author, ?string $language = null, array &$mentions = []): EventResult { switch ($content_type) { case 'text/plain': diff --git a/components/Search/Search.php b/components/Search/Search.php index bc8e38f9e6..ad8c836e64 100644 --- a/components/Search/Search.php +++ b/components/Search/Search.php @@ -27,10 +27,12 @@ use App\Core\Event; use App\Core\Form; use function App\Core\I18n\_m; use App\Core\Modules\Component; +use App\Core\Router; use App\Util\Common; use App\Util\Exception\ClientException; use App\Util\Exception\RedirectException; use App\Util\Formatting; +use EventResult; use Symfony\Component\Form\Extension\Core\Type\SubmitType; use Symfony\Component\Form\Extension\Core\Type\TextType; use Symfony\Component\Form\FormView; @@ -39,9 +41,10 @@ use Symfony\Component\HttpFoundation\Request; class Search extends Component { - public function onAddRoute($r) + public function onAddRoute(Router $r): EventResult { $r->connect('search', '/search', Controller\Search::class); + return EventResult::next; } /** @@ -133,7 +136,7 @@ class Search extends Component * * @throws RedirectException */ - public function onPrependRightPanelBlock(Request $request, array &$elements): bool + public function onPrependRightPanelBlock(Request $request, array &$elements): EventResult { $elements[] = Formatting::twigRenderFile('cards/search/view.html.twig', ['search' => self::searchForm($request)]); return Event::next; @@ -146,7 +149,7 @@ class Search extends Component * * @return bool hook value; true means continue processing, false means stop */ - public function onEndShowStyles(array &$styles, string $route): bool + public function onEndShowStyles(array &$styles, string $route): EventResult { $styles[] = 'components/Search/assets/css/view.css'; return Event::next; diff --git a/components/Subscription/Subscription.php b/components/Subscription/Subscription.php index 7ac978c3ff..8781427a5c 100644 --- a/components/Subscription/Subscription.php +++ b/components/Subscription/Subscription.php @@ -39,11 +39,12 @@ use App\Util\Exception\ServerException; use Component\Notification\Entity\Attention; use Component\Subscription\Controller\Subscribers as SubscribersController; use Component\Subscription\Controller\Subscriptions as SubscriptionsController; +use EventResult; use Symfony\Component\HttpFoundation\Request; class Subscription extends Component { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect(id: 'actor_subscribe_add', uri_path: '/actor/subscribe/{object_id<\d+>}', target: [SubscribersController::class, 'subscribersAdd']); $r->connect(id: 'actor_subscribe_remove', uri_path: '/actor/unsubscribe/{object_id<\d+>}', target: [SubscribersController::class, 'subscribersRemove']); @@ -186,7 +187,7 @@ class Subscription extends Component * * @return bool EventHook */ - public function onAddProfileActions(Request $request, Actor $object, array &$actions): bool + public function onAddProfileActions(Request $request, Actor $object, array &$actions): EventResult { // Action requires a user to be logged in // We know it's a LocalUser, which has the same id as Actor diff --git a/components/Tag/Tag.php b/components/Tag/Tag.php index f6fe16788d..1edb313650 100644 --- a/components/Tag/Tag.php +++ b/components/Tag/Tag.php @@ -42,6 +42,7 @@ use Component\Tag\Entity\NoteTag; use Doctrine\Common\Collections\ExpressionBuilder; use Doctrine\ORM\Query\Expr; use Doctrine\ORM\QueryBuilder; +use EventResult; use Functional as F; use Symfony\Component\Form\Extension\Core\Type\CheckboxType; use Symfony\Component\HttpFoundation\Request; @@ -60,7 +61,7 @@ class Tag extends Component public const TAG_REGEX = '/(^|\\s)(#[\\pL\\pN_\\-]{1,64})/u'; // Brion Vibber 2011-02-23 v2:classes/Notice.php:367 function saveTags public const TAG_SLUG_REGEX = '[A-Za-z0-9]{1,64}'; - public function onAddRoute($r): bool + public function onAddRoute($r): EventResult { $r->connect('single_note_tag', '/note-tag/{tag<' . self::TAG_SLUG_REGEX . '>}', [Controller\Tag::class, 'single_note_tag']); $r->connect('multi_note_tags', '/note-tags/{tags<(' . self::TAG_SLUG_REGEX . ',)+' . self::TAG_SLUG_REGEX . '>}', [Controller\Tag::class, 'multi_note_tags']); @@ -118,7 +119,7 @@ class Tag extends Component /** * Process note by extracting any tags present */ - public function onProcessNoteContent(Note $note, string $content, string $content_type, array $extra_args): bool + public function onProcessNoteContent(Note $note, string $content, string $content_type, array $extra_args): EventResult { if ($extra_args['TagProcessed'] ?? false) { return Event::next; @@ -135,7 +136,7 @@ class Tag extends Component return Event::next; } - public function onRenderPlainTextNoteContent(string &$text, ?string $locale = null): bool + public function onRenderPlainTextNoteContent(string &$text, ?string $locale = null): EventResult { $text = preg_replace_callback(self::TAG_REGEX, fn ($m) => $m[1] . self::tagLink($m[2], $locale), $text); return Event::next; @@ -213,7 +214,7 @@ class Tag extends Component * * $term /^(note|tag|people|actor)/ means we want to match only either a note or an actor */ - public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): bool + public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $locale, ?Actor $actor, &$note_expr, &$actor_expr): EventResult { if (!str_contains($term, ':')) { return Event::next; @@ -252,7 +253,7 @@ class Tag extends Component return Event::next; } - public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): bool + public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): EventResult { if (!\in_array('note_tag', $note_qb->getAllAliases())) { $note_qb->leftJoin(NoteTag::class, 'note_tag', Expr\Join::WITH, 'note_tag.note_id = note.id'); @@ -263,13 +264,13 @@ class Tag extends Component return Event::next; } - public function onPostingAddFormEntries(Request $request, Actor $actor, array &$form_params): bool + public function onPostingAddFormEntries(Request $request, Actor $actor, array &$form_params): EventResult { $form_params[] = ['tag_use_canonical', CheckboxType::class, ['required' => false, 'data' => true, 'label' => _m('Make note tags canonical'), 'help' => _m('Canonical tags will be treated as a version of an existing tag with the same root/stem (e.g. \'#great_tag\' will be considered as a version of \'#great\', if it already exists)')]]; return Event::next; } - public function onAddExtraArgsToNoteContent(Request $request, Actor $actor, array $data, array &$extra_args): bool + public function onAddExtraArgsToNoteContent(Request $request, Actor $actor, array $data, array &$extra_args): EventResult { if (!isset($data['tag_use_canonical'])) { throw new ClientException(_m('Missing Use Canonical preference for Tags.')); diff --git a/composer.json b/composer.json index 913f25889e..b829072fd6 100644 --- a/composer.json +++ b/composer.json @@ -103,6 +103,9 @@ "files": [ "src/Core/I18n/I18n.php" ], + "classmap": [ + "src/Core/Event/EventResult.php" + ], "psr-4": { "App\\": "src/", "Plugin\\": "plugins/", diff --git a/config/services.yaml b/config/services.yaml index 182b7e2a9e..51576e704f 100644 --- a/config/services.yaml +++ b/config/services.yaml @@ -13,7 +13,7 @@ services: # this creates a service per class whose id is the fully-qualified class name App\: resource: '../src/*' - exclude: '../src/{DependencyInjection,Entity,Migrations,Tests,Kernel.php,Routes}' + exclude: '../src/{DependencyInjection,Entity,Migrations,Tests,Kernel.php,Routes,Core/Event/EventResult.php}' App\Test\Fixtures\: resource: '../tests/fixtures/*' diff --git a/plugins/ActivityPub/ActivityPub.php b/plugins/ActivityPub/ActivityPub.php index 17692c763c..646c9ce5ca 100644 --- a/plugins/ActivityPub/ActivityPub.php +++ b/plugins/ActivityPub/ActivityPub.php @@ -50,6 +50,7 @@ use App\Util\Exception\BugFoundException; use Component\Collection\Util\Controller\OrderedCollection; use Component\FreeNetwork\Entity\FreeNetworkActorProtocol; use Component\FreeNetwork\Util\Discovery; +use EventResult; use Exception; use InvalidArgumentException; use Plugin\ActivityPub\Controller\Inbox; @@ -122,14 +123,14 @@ class ActivityPub extends Plugin ], ]; - public function onInitializePlugin(): bool + public function onInitializePlugin(): EventResult { Event::handle('ActivityStreamsTwoContext', [&self::$activity_streams_two_context]); self::$activity_streams_two_context = array_unique(self::$activity_streams_two_context, \SORT_REGULAR); return Event::next; } - public function onQueueActivitypubInbox(ActivitypubActor $ap_actor, Actor $actor, string|AbstractObject $type): bool + public function onQueueActivitypubInbox(ActivitypubActor $ap_actor, Actor $actor, string|AbstractObject $type): EventResult { // TODO: Check if Actor has authority over payload @@ -157,7 +158,7 @@ class ActivityPub extends Plugin * * @param Router $r the router that was initialized */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect( 'activitypub_inbox', @@ -183,7 +184,7 @@ class ActivityPub extends Plugin /** * Fill Actor->getUrl() calls with correct URL coming from ActivityPub */ - public function onStartGetActorUri(Actor $actor, int $type, ?string &$url): bool + public function onStartGetActorUri(Actor $actor, int $type, ?string &$url): EventResult { if ( // Is remote? @@ -203,7 +204,7 @@ class ActivityPub extends Plugin /** * Fill Actor->canAdmin() for Actors that came from ActivityPub */ - public function onFreeNetworkActorCanAdmin(Actor $actor, Actor $other, bool &$canAdmin): bool + public function onFreeNetworkActorCanAdmin(Actor $actor, Actor $other, bool &$canAdmin): EventResult { // Are both in AP? if ( @@ -223,7 +224,7 @@ class ActivityPub extends Plugin * * @throws Exception */ - public function onControllerResponseInFormat(string $route, array $accept_header, array $vars, ?TypeResponse &$response = null): bool + public function onControllerResponseInFormat(string $route, array $accept_header, array $vars, ?TypeResponse &$response = null): EventResult { if (\count(array_intersect(self::$accept_headers, $accept_header)) === 0) { return Event::next; @@ -262,7 +263,7 @@ class ActivityPub extends Plugin /** * Add ActivityStreams 2 Extensions */ - public function onActivityPubValidateActivityStreamsTwoData(string $type_name, array &$validators): bool + public function onActivityPubValidateActivityStreamsTwoData(string $type_name, array &$validators): EventResult { switch ($type_name) { case 'Person': @@ -280,7 +281,7 @@ class ActivityPub extends Plugin /** * Let FreeNetwork Component know we exist and which class to use to call the freeNetworkDistribute method */ - public function onAddFreeNetworkProtocol(array &$protocols): bool + public function onAddFreeNetworkProtocol(array &$protocols): EventResult { $protocols[] = '\Plugin\ActivityPub\ActivityPub'; return Event::next; @@ -321,7 +322,7 @@ class ActivityPub extends Plugin string $inbox, array $to_actors, array &$retry_args, - ): bool { + ): EventResult { try { $data = Model::toType($activity); if ($sender->isGroup()) { // When the sender is a group, @@ -426,7 +427,7 @@ class ActivityPub extends Plugin /** * Add activity+json mimetype to WebFinger */ - public function onEndWebFingerProfileLinks(XML_XRD $xrd, Actor $object): bool + public function onEndWebFingerProfileLinks(XML_XRD $xrd, Actor $object): EventResult { if ($object->isPerson()) { $link = new XML_XRD_Element_Link( @@ -442,7 +443,7 @@ class ActivityPub extends Plugin /** * When FreeNetwork component asks us to help with identifying Actors from XRDs */ - public function onFreeNetworkFoundXrd(XML_XRD $xrd, ?Actor &$actor = null): bool + public function onFreeNetworkFoundXrd(XML_XRD $xrd, ?Actor &$actor = null): EventResult { $addr = null; foreach ($xrd->aliases as $alias) { @@ -473,7 +474,7 @@ class ActivityPub extends Plugin /** * When FreeNetwork component asks us to help with identifying Actors from URIs */ - public function onFreeNetworkFindMentions(string $target, ?Actor &$actor = null): bool + public function onFreeNetworkFindMentions(string $target, ?Actor &$actor = null): EventResult { try { if (FreeNetworkActorProtocol::canIAddr('activitypub', $addr = Discovery::normalize($target))) { diff --git a/plugins/AttachmentCollections/AttachmentCollections.php b/plugins/AttachmentCollections/AttachmentCollections.php index 40fa0e3824..91f682c1bf 100644 --- a/plugins/AttachmentCollections/AttachmentCollections.php +++ b/plugins/AttachmentCollections/AttachmentCollections.php @@ -41,6 +41,7 @@ use App\Entity\Feed; use App\Entity\LocalUser; use App\Util\Nickname; use Component\Collection\Util\MetaCollectionTrait; +use EventResult; use Plugin\AttachmentCollections\Controller\AttachmentCollections as AttachmentCollectionsController; use Plugin\AttachmentCollections\Entity\AttachmentCollection; use Plugin\AttachmentCollections\Entity\AttachmentCollectionEntry; @@ -122,7 +123,7 @@ class AttachmentCollections extends Plugin return array_map(fn ($x) => $x['attachment_collection_id'], $res); } - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { // View all collections by actor id and nickname $r->connect( @@ -149,7 +150,7 @@ class AttachmentCollections extends Plugin return Event::next; } - public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering) + public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): EventResult { DB::persist(Feed::create([ 'actor_id' => $actor_id, diff --git a/plugins/AttachmentShowRelated/AttachmentShowRelated.php b/plugins/AttachmentShowRelated/AttachmentShowRelated.php index 77f3604e21..c99d352160 100644 --- a/plugins/AttachmentShowRelated/AttachmentShowRelated.php +++ b/plugins/AttachmentShowRelated/AttachmentShowRelated.php @@ -28,11 +28,12 @@ use App\Core\Event; use App\Core\Modules\Plugin; use App\Util\Common; use App\Util\Formatting; +use EventResult; use Symfony\Component\HttpFoundation\Request; class AttachmentShowRelated extends Plugin { - public function onAppendRightPanelBlock(Request $request, $vars, &$res): bool + public function onAppendRightPanelBlock(Request $request, $vars, &$res): EventResult { if ($vars['path'] === 'note_attachment_show') { $related_notes = DB::dql('select n from attachment_to_note an ' @@ -54,7 +55,7 @@ class AttachmentShowRelated extends Plugin * * @return bool hook value; true means continue processing, false means stop */ - public function onEndShowStyles(array &$styles, string $path): bool + public function onEndShowStyles(array &$styles, string $path): EventResult { if ($path === 'note_attachment_show') { $styles[] = '/assets/default_theme/pages/feeds.css'; diff --git a/plugins/AudioEncoder/AudioEncoder.php b/plugins/AudioEncoder/AudioEncoder.php index 7104a311d2..9280929b9d 100644 --- a/plugins/AudioEncoder/AudioEncoder.php +++ b/plugins/AudioEncoder/AudioEncoder.php @@ -38,6 +38,7 @@ use function App\Core\I18n\_m; use App\Core\Modules\Plugin; use App\Util\Exception\ServerException; use App\Util\Formatting; +use EventResult; use FFMpeg\FFProbe as ffprobe; use SplFileInfo; @@ -53,7 +54,7 @@ class AudioEncoder extends Plugin return GSFile::mimetypeMajor($mimetype) === 'audio'; } - public function onFileMetaAvailable(array &$event_map, string $mimetype): bool + public function onFileMetaAvailable(array &$event_map, string $mimetype): EventResult { if (!self::shouldHandle($mimetype)) { return Event::next; @@ -90,7 +91,7 @@ class AudioEncoder extends Plugin /** * Generates the view for attachments of type Video */ - public function onViewAttachment(array $vars, array &$res): bool + public function onViewAttachment(array $vars, array &$res): EventResult { if (!self::shouldHandle($vars['attachment']->getMimetype())) { return Event::next; @@ -110,7 +111,7 @@ class AudioEncoder extends Plugin /** * @throws ServerException */ - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = [ 'name' => 'AudioEncoder', diff --git a/plugins/Blog/Blog.php b/plugins/Blog/Blog.php index 4d4fdab3c1..d30ee52b76 100644 --- a/plugins/Blog/Blog.php +++ b/plugins/Blog/Blog.php @@ -23,22 +23,23 @@ declare(strict_types = 1); namespace Plugin\Blog; use App\Core\Event; +use function App\Core\I18n\_m; use App\Core\Modules\Plugin; use App\Core\Router; use App\Util\Common; use App\Util\HTML; +use EventResult; use Plugin\Blog\Controller as C; -use function App\Core\I18n\_m; class Blog extends Plugin { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect(id: 'blog_post', uri_path: '/blog/post', target: [C\Post::class, 'makePost']); return Event::next; } - public function onAppendCardProfile(array $vars, array &$res): bool + public function onAppendCardProfile(array $vars, array &$res): EventResult { $actor = Common::actor(); $group = $vars['actor']; diff --git a/plugins/Cover/Cover.php b/plugins/Cover/Cover.php index 7a76c00a62..1bc692a07e 100644 --- a/plugins/Cover/Cover.php +++ b/plugins/Cover/Cover.php @@ -27,6 +27,7 @@ use App\Core\Event; use App\Core\Modules\Plugin; use App\Core\Router; use App\Util\Common; +use EventResult; use Plugin\Cover\Controller as C; use Symfony\Component\HttpFoundation\Request; @@ -47,14 +48,14 @@ class Cover extends Plugin * * @return bool hook value; true means continue processing, false means stop */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('settings_profile_cover', 'settings/cover', [Controller\Cover::class, 'coversettings']); $r->connect('cover', '/cover', [Controller\Cover::class, 'cover']); return Event::next; } - public function onPopulateSettingsTabs(Request $request, string $section, &$tabs) + public function onPopulateSettingsTabs(Request $request, string $section, &$tabs): EventResult { if ($section === 'profile') { $tabs[] = [ @@ -72,7 +73,7 @@ class Cover extends Plugin * * @return bool hook value; true means continue processing, false means stop. * - * public function onStartTwigPopulateVars(array &$vars): bool + * public function onStartTwigPopulateVars(array &$vars): \EventResult * { * if (Common::user() != null) { * $cover = DB::find('cover', ['actor_id' => Common::user()->getId()]); @@ -92,7 +93,7 @@ class Cover extends Plugin * * @return bool hook value; true means continue processing, false means stop */ - public function onStartShowStyles(array &$styles): bool + public function onStartShowStyles(array &$styles): EventResult { $styles[] = 'assets/css/cover.css'; return Event::next; diff --git a/plugins/DeleteNote/DeleteNote.php b/plugins/DeleteNote/DeleteNote.php index d3c395667a..a925ebd2da 100644 --- a/plugins/DeleteNote/DeleteNote.php +++ b/plugins/DeleteNote/DeleteNote.php @@ -34,6 +34,7 @@ use App\Entity\Note; use App\Util\Common; use App\Util\Exception\ClientException; use DateTime; +use EventResult; use Plugin\ActivityPub\Entity\ActivitypubActivity; use Symfony\Component\HttpFoundation\Request; @@ -135,7 +136,7 @@ class DeleteNote extends NoteHandlerPlugin * * @return bool Event hook */ - public function onAddRoute(Router $r) + public function onAddRoute(Router $r): EventResult { $r->connect(id: 'delete_note_action', uri_path: '/object/note/{note_id<\d+>}/delete', target: Controller\DeleteNote::class); @@ -154,7 +155,7 @@ class DeleteNote extends NoteHandlerPlugin * * @return bool Event hook */ - public function onAddExtraNoteActions(Request $request, Note $note, array &$actions) + public function onAddExtraNoteActions(Request $request, Note $note, array &$actions): EventResult { if (\is_null($actor = Common::actor())) { return Event::next; @@ -227,7 +228,7 @@ class DeleteNote extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onNewActivityPubActivity(Actor $actor, AbstractObject $type_activity, AbstractObject $type_object, ?ActivitypubActivity &$ap_act): bool + public function onNewActivityPubActivity(Actor $actor, AbstractObject $type_activity, AbstractObject $type_object, ?ActivitypubActivity &$ap_act): EventResult { return $this->activitypub_handler($actor, $type_activity, $type_object, $ap_act); } @@ -242,7 +243,7 @@ class DeleteNote extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onNewActivityPubActivityWithObject(Actor $actor, AbstractObject $type_activity, mixed $type_object, ?ActivitypubActivity &$ap_act): bool + public function onNewActivityPubActivityWithObject(Actor $actor, AbstractObject $type_activity, mixed $type_object, ?ActivitypubActivity &$ap_act): EventResult { return $this->activitypub_handler($actor, $type_activity, $type_object, $ap_act); } @@ -255,7 +256,7 @@ class DeleteNote extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onGSVerbToActivityStreamsTwoActivityType(string $verb, ?string &$gs_verb_to_activity_stream_two_verb): bool + public function onGSVerbToActivityStreamsTwoActivityType(string $verb, ?string &$gs_verb_to_activity_stream_two_verb): EventResult { if ($verb === 'delete') { $gs_verb_to_activity_stream_two_verb = 'Delete'; diff --git a/plugins/Directory/Directory.php b/plugins/Directory/Directory.php index 337bb5883d..b089b09d26 100644 --- a/plugins/Directory/Directory.php +++ b/plugins/Directory/Directory.php @@ -31,6 +31,7 @@ use App\Util\Exception\RedirectException; use App\Util\Exception\ServerException; use App\Util\Formatting; use Component\Group\Controller as ComponentGroupController; +use EventResult; use Symfony\Component\HttpFoundation\Request; class Directory extends Plugin @@ -40,7 +41,7 @@ class Directory extends Plugin * * @return bool */ - public function onAddRoute(Router $r) + public function onAddRoute(Router $r): EventResult { $r->connect('directory_people', '/directory/people', [Controller\Directory::class, 'people']); $r->connect('directory_groups', '/directory/groups', [Controller\Directory::class, 'groups']); @@ -55,7 +56,7 @@ class Directory extends Plugin * * @return bool hook value; true means continue processing, false means stop */ - public function onAddMainNavigationItem(array $vars, array &$res): bool + public function onAddMainNavigationItem(array $vars, array &$res): EventResult { $res[] = ['title' => 'People', 'path' => Router::url($path_id = 'directory_people', []), 'path_id' => $path_id]; $res[] = ['title' => 'Groups', 'path' => Router::url($path_id = 'directory_groups', []), 'path_id' => $path_id]; @@ -72,7 +73,7 @@ class Directory extends Plugin * * @return bool EventHook */ - public function onPrependActorsCollection(Request $request, array &$elements): bool + public function onPrependActorsCollection(Request $request, array &$elements): EventResult { if (\is_null($actor = Common::actor())) { return Event::next; diff --git a/plugins/EmailNotifications/EmailNotifications.php b/plugins/EmailNotifications/EmailNotifications.php index ab96291d3f..2ad1f3de53 100644 --- a/plugins/EmailNotifications/EmailNotifications.php +++ b/plugins/EmailNotifications/EmailNotifications.php @@ -36,10 +36,11 @@ namespace Plugin\EmailNotifications; use App\Core\Event; use App\Core\Modules\Plugin; +use EventResult; class EmailNotifications extends Plugin { - public function onAddNotificationTransport(&$form_defs): bool + public function onAddNotificationTransport(&$form_defs): EventResult { $form_defs['Email'] = $form_defs['placeholder']; $form_defs['Email'][] = $form_defs['placeholder']['save']('Email', 'save_email'); diff --git a/plugins/Embed/Embed.php b/plugins/Embed/Embed.php index d1edeebe78..3eff808b74 100644 --- a/plugins/Embed/Embed.php +++ b/plugins/Embed/Embed.php @@ -57,6 +57,7 @@ use App\Util\TemporaryFile; use Component\Attachment\Entity\Attachment; use Component\Link\Entity\Link; use Embed\Embed as LibEmbed; +use EventResult; use Exception; use Symfony\Component\HttpFoundation\Request; use Symfony\Contracts\HttpClient\Exception\ClientExceptionInterface; @@ -111,7 +112,7 @@ class Embed extends Plugin * * @throws Exception */ - public function onAddRoute(Router $m): bool + public function onAddRoute(Router $m): EventResult { $m->connect('oembed', 'main/oembed', Controller\OEmbed::class); return Event::next; @@ -120,7 +121,7 @@ class Embed extends Plugin /** * Insert oembed and opengraph tags in all HTML head elements */ - public function onShowHeadElements(Request $request, array &$result): bool + public function onShowHeadElements(Request $request, array &$result): EventResult { $matches = []; preg_match(',/?([^/]+)/?(.*),', $request->getPathInfo(), $matches); @@ -146,7 +147,7 @@ class Embed extends Plugin /** * Show this attachment enhanced with the corresponding Embed data, if available */ - public function onViewLink(array $vars, array &$res): bool + public function onViewLink(array $vars, array &$res): EventResult { $link = $vars['link']; try { @@ -177,7 +178,7 @@ class Embed extends Plugin * * @throws DuplicateFoundException */ - public function onNewLinkFromNote(Link $link, Note $note): bool + public function onNewLinkFromNote(Link $link, Note $note): EventResult { // Only handle text mime $mimetype = $link->getMimetype(); @@ -368,7 +369,7 @@ class Embed extends Plugin return HTTPClient::get($url)->getContent(); } - public function onAttachmentGetBestTitle(Attachment $attachment, Note $note, ?string &$title) + public function onAttachmentGetBestTitle(Attachment $attachment, Note $note, ?string &$title): EventResult { try { $embed = DB::findOneBy('attachment_embed', ['attachment_id' => $attachment->getId()]); @@ -389,7 +390,7 @@ class Embed extends Plugin * * @return bool true hook value */ - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = [ 'name' => 'Embed', diff --git a/plugins/Favourite/Favourite.php b/plugins/Favourite/Favourite.php index 60c924e439..d306d9fa23 100644 --- a/plugins/Favourite/Favourite.php +++ b/plugins/Favourite/Favourite.php @@ -45,6 +45,7 @@ use App\Util\Common; use App\Util\Nickname; use Component\Notification\Entity\Attention; use DateTime; +use EventResult; use Plugin\Favourite\Entity\NoteFavourite; use Symfony\Component\HttpFoundation\Request; @@ -125,7 +126,7 @@ class Favourite extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onAddNoteActions(Request $request, Note $note, array &$actions): bool + public function onAddNoteActions(Request $request, Note $note, array &$actions): EventResult { if (\is_null($user = Common::user())) { return Event::next; @@ -171,7 +172,7 @@ class Favourite extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onAppendCardNote(array $vars, array &$result): bool + public function onAppendCardNote(array $vars, array &$result): EventResult { // If note is the original and user isn't the one who repeated, append on end "user repeated this" // If user is the one who repeated, append on end "you repeated this, remove repeat?" @@ -197,7 +198,7 @@ class Favourite extends NoteHandlerPlugin /** * Deletes every favourite entity in table related to a deleted Note */ - public function onNoteDeleteRelated(Note &$note, Actor $actor): bool + public function onNoteDeleteRelated(Note &$note, Actor $actor): EventResult { $note_favourites_list = NoteFavourite::getNoteFavourites($note); foreach ($note_favourites_list as $favourite_entity) { @@ -210,7 +211,7 @@ class Favourite extends NoteHandlerPlugin /** * Maps Routes to their respective Controllers */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { // Add/remove note to/from favourites $r->connect(id: 'favourite_add', uri_path: '/object/note/{id<\d+>}/favour', target: [Controller\Favourite::class, 'favouriteAddNote']); @@ -233,7 +234,7 @@ class Favourite extends NoteHandlerPlugin * * @throws \App\Util\Exception\ServerException */ - public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): bool + public function onCreateDefaultFeeds(int $actor_id, LocalUser $user, int &$ordering): EventResult { DB::persist(Feed::create([ 'actor_id' => $actor_id, @@ -329,7 +330,7 @@ class Favourite extends NoteHandlerPlugin return Event::stop; } - public function onActivityPubNewNotification(Actor $sender, Activity $activity, array $targets, ?string $reason = null): bool + public function onActivityPubNewNotification(Actor $sender, Activity $activity, array $targets, ?string $reason = null): EventResult { switch ($activity->getVerb()) { case 'favourite': @@ -366,7 +367,7 @@ class Favourite extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onNewActivityPubActivity(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, \ActivityPhp\Type\AbstractObject $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): bool + public function onNewActivityPubActivity(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, \ActivityPhp\Type\AbstractObject $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): EventResult { return $this->activitypub_handler($actor, $type_activity, $type_object, $ap_act); } @@ -390,7 +391,7 @@ class Favourite extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onNewActivityPubActivityWithObject(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, mixed $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): bool + public function onNewActivityPubActivityWithObject(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, mixed $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): EventResult { return $this->activitypub_handler($actor, $type_activity, $type_object, $ap_act); } @@ -403,7 +404,7 @@ class Favourite extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onGSVerbToActivityStreamsTwoActivityType(string $verb, ?string &$gs_verb_to_activity_stream_two_verb): bool + public function onGSVerbToActivityStreamsTwoActivityType(string $verb, ?string &$gs_verb_to_activity_stream_two_verb): EventResult { if ($verb === 'favourite') { $gs_verb_to_activity_stream_two_verb = 'Like'; diff --git a/plugins/FileQuota/FileQuota.php b/plugins/FileQuota/FileQuota.php index cb0c5d6794..ae54108c5b 100644 --- a/plugins/FileQuota/FileQuota.php +++ b/plugins/FileQuota/FileQuota.php @@ -31,6 +31,7 @@ use App\Core\Modules\Plugin; use App\Util\Common; use App\Util\Exception\ClientException; use App\Util\Exception\ServerException; +use EventResult; /** * Check attachment file size quotas @@ -57,7 +58,7 @@ class FileQuota extends Plugin * @throws ClientException * @throws ServerException */ - public function onEnforceUserFileQuota(int $filesize, int $user_id): bool + public function onEnforceUserFileQuota(int $filesize, int $user_id): EventResult { $query = <<<'END' select sum(at.size) as total @@ -104,7 +105,7 @@ class FileQuota extends Plugin * * @return bool true hook value */ - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = [ 'name' => 'FileQuota', diff --git a/plugins/ImageEncoder/ImageEncoder.php b/plugins/ImageEncoder/ImageEncoder.php index a55265f076..2ef0e3dda9 100644 --- a/plugins/ImageEncoder/ImageEncoder.php +++ b/plugins/ImageEncoder/ImageEncoder.php @@ -32,6 +32,7 @@ use App\Util\Exception\ServerException; use App\Util\Exception\TemporaryFileException; use App\Util\Formatting; use App\Util\TemporaryFile; +use EventResult; use Exception; use Jcupitt\Vips; use SplFileInfo; @@ -59,7 +60,7 @@ class ImageEncoder extends Plugin return GSFile::mimetypeMajor($mimetype) === 'image'; } - public function onFileMetaAvailable(array &$event_map, string $mimetype): bool + public function onFileMetaAvailable(array &$event_map, string $mimetype): EventResult { if (!self::shouldHandle($mimetype)) { return Event::next; @@ -68,7 +69,7 @@ class ImageEncoder extends Plugin return Event::next; } - public function onFileSanitizerAvailable(array &$event_map, string $mimetype): bool + public function onFileSanitizerAvailable(array &$event_map, string $mimetype): EventResult { if (!self::shouldHandle($mimetype)) { return Event::next; @@ -77,7 +78,7 @@ class ImageEncoder extends Plugin return Event::next; } - public function onFileResizerAvailable(array &$event_map, string $mimetype): bool + public function onFileResizerAvailable(array &$event_map, string $mimetype): EventResult { if (!self::shouldHandle($mimetype)) { return Event::next; @@ -179,7 +180,7 @@ class ImageEncoder extends Plugin /** * Generates the view for attachments of type Image */ - public function onViewAttachment(array $vars, array &$res): bool + public function onViewAttachment(array $vars, array &$res): EventResult { if (!self::shouldHandle($vars['attachment']->getMimetype())) { return Event::next; @@ -260,7 +261,7 @@ class ImageEncoder extends Plugin * * @return bool true hook value */ - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = [ 'name' => 'ImageEncoder', diff --git a/plugins/LatexNotes/LatexNotes.php b/plugins/LatexNotes/LatexNotes.php index ddbe7f333a..35d8243451 100644 --- a/plugins/LatexNotes/LatexNotes.php +++ b/plugins/LatexNotes/LatexNotes.php @@ -33,17 +33,18 @@ namespace Plugin\LatexNotes; use App\Core\Event; use App\Core\Modules\Plugin; +use EventResult; use PhpLatex_Parser; use PhpLatex_Renderer_Html; class LatexNotes extends Plugin { - public function onPostingAvailableContentTypes(array &$types): bool + public function onPostingAvailableContentTypes(array &$types): EventResult { $types['LaTeX'] = 'application/x-latex'; return Event::next; } - public function onRenderNoteContent($content, $content_type, &$rendered): bool + public function onRenderNoteContent($content, $content_type, &$rendered): EventResult { if ($content_type !== 'application/x-latex') { return Event::next; diff --git a/plugins/MarkdownNotes/MarkdownNotes.php b/plugins/MarkdownNotes/MarkdownNotes.php index 7b5bbe426c..1ad50d9af3 100644 --- a/plugins/MarkdownNotes/MarkdownNotes.php +++ b/plugins/MarkdownNotes/MarkdownNotes.php @@ -33,16 +33,17 @@ namespace Plugin\MarkdownNotes; use App\Core\Event; use App\Core\Modules\Plugin; +use EventResult; use Parsedown; class MarkdownNotes extends Plugin { - public function onPostingAvailableContentTypes(array &$types): bool + public function onPostingAvailableContentTypes(array &$types): EventResult { $types['Markdown'] = 'text/markdown'; return Event::next; } - public function onRenderNoteContent($content, $content_type, &$rendered): bool + public function onRenderNoteContent($content, $content_type, &$rendered): EventResult { if ($content_type !== 'text/markdown') { return Event::next; diff --git a/plugins/NoteTypeFeedFilter/NoteTypeFeedFilter.php b/plugins/NoteTypeFeedFilter/NoteTypeFeedFilter.php index ad59e237be..4aa9d0fb5c 100644 --- a/plugins/NoteTypeFeedFilter/NoteTypeFeedFilter.php +++ b/plugins/NoteTypeFeedFilter/NoteTypeFeedFilter.php @@ -40,6 +40,7 @@ use App\Util\Exception\BugFoundException; use App\Util\Exception\ClientException; use App\Util\Formatting; use App\Util\Functional as GSF; +use EventResult; use Functional as F; use Symfony\Component\HttpFoundation\Request; @@ -94,7 +95,7 @@ class NoteTypeFeedFilter extends Plugin * * Includes if any positive type matches, but removes if any negated matches */ - public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): bool + public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): EventResult { $types = $this->normalizeTypesList(\is_null($request->get('note-types')) ? [] : explode(',', $request->get('note-types'))); $notes = F\select( @@ -108,7 +109,7 @@ class NoteTypeFeedFilter extends Plugin $include = false; foreach ($types as $type) { $is_negate = $type[0] === '!'; - $type = Formatting::removePrefix($type, '!'); + $type = Formatting::removePrefix($type, '!'); switch ($type) { case 'text': $ret = !\is_null($note->getContent()); @@ -139,7 +140,7 @@ class NoteTypeFeedFilter extends Plugin /** * Draw the media feed navigation. */ - public function onAddFeedActions(Request $request, bool $is_not_empty, &$res): bool + public function onAddFeedActions(Request $request, bool $is_not_empty, &$res): EventResult { $qs = []; $query_string = $request->getQueryString(); @@ -184,7 +185,7 @@ class NoteTypeFeedFilter extends Plugin * * @return bool hook value; true means continue processing, false means stop */ - public function onEndShowStyles(array &$styles, string $route): bool + public function onEndShowStyles(array &$styles, string $route): EventResult { $styles[] = 'plugins/NoteTypeFeedFilter/assets/css/noteTypeFeedFilter.css'; return Event::next; diff --git a/plugins/OAuth2/OAuth2.php b/plugins/OAuth2/OAuth2.php index a98db9f3aa..1d19b288e9 100644 --- a/plugins/OAuth2/OAuth2.php +++ b/plugins/OAuth2/OAuth2.php @@ -38,6 +38,7 @@ use App\Core\Modules\Plugin; use App\Core\Router; use App\Util\Common; use DateInterval; +use EventResult; use Exception; use League\OAuth2\Server\AuthorizationServer; use League\OAuth2\Server\CryptKey; @@ -67,7 +68,7 @@ class OAuth2 extends Plugin /** * @throws Exception */ - public function onInitializePlugin() + public function onInitializePlugin(): EventResult { self::$authorization_server = new AuthorizationServer( new Repository\Client, @@ -86,6 +87,7 @@ class OAuth2 extends Plugin ), new DateInterval('PT1H'), ); + return Event::next; } /** @@ -94,7 +96,7 @@ class OAuth2 extends Plugin * * @param Router $r the router that was initialized */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('oauth2_mastodon_api_apps', '/api/v1/apps', C\Client::class, ['http-methods' => ['POST']]); $r->connect('oauth2_client', '/oauth/client', C\Client::class, ['http-methods' => ['POST']]); @@ -103,7 +105,7 @@ class OAuth2 extends Plugin return Event::next; } - public function onEndHostMetaLinks(array &$links): bool + public function onEndHostMetaLinks(array &$links): EventResult { $links[] = new XML_XRD_Element_Link(self::OAUTH_REQUEST_TOKEN_REL, Router::url('oauth2_client', type: Router::ABSOLUTE_URL)); $links[] = new XML_XRD_Element_Link(self::OAUTH_AUTHORIZE_REL, Router::url('oauth2_authorize', type: Router::ABSOLUTE_URL)); diff --git a/plugins/Oomox/Oomox.php b/plugins/Oomox/Oomox.php index 1d07f3a298..e0a113891e 100644 --- a/plugins/Oomox/Oomox.php +++ b/plugins/Oomox/Oomox.php @@ -32,6 +32,7 @@ use App\Util\Common; use App\Util\Exception\NotFoundException; use App\Util\Exception\RedirectException; use App\Util\Exception\ServerException; +use EventResult; use Plugin\Oomox\Controller as C; use Symfony\Component\HttpFoundation\Request; @@ -50,7 +51,7 @@ class Oomox extends Plugin /** * Maps Routes to their respective Controllers */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('oomox_settings', 'settings/oomox', [Controller\Oomox::class, 'oomoxSettings']); $r->connect('oomox_css', 'plugins/oomox/colours', [Controller\Oomox::class, 'oomoxCSS']); @@ -65,7 +66,7 @@ class Oomox extends Plugin * @throws RedirectException * @throws ServerException */ - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'colours') { $tabs[] = [ @@ -108,7 +109,7 @@ class Oomox extends Plugin /** * Adds to array $styles the generated CSS according to user settings, if any are present. */ - public function onEndShowStyles(array &$styles, string $route): bool + public function onEndShowStyles(array &$styles, string $route): EventResult { $user = Common::user(); if ($user && Cache::get(self::cacheKey($user), static fn () => self::getEntity($user))) { diff --git a/plugins/Pinboard/Pinboard.php b/plugins/Pinboard/Pinboard.php index e93bbe4f34..33afb96e44 100644 --- a/plugins/Pinboard/Pinboard.php +++ b/plugins/Pinboard/Pinboard.php @@ -35,6 +35,7 @@ namespace Plugin\Pinboard; use App\Core\Event; use App\Core\Modules\Plugin; use App\Core\Router; +use EventResult; use Plugin\Pinboard\Controller as C; use Symfony\Component\HttpFoundation\Request; @@ -42,7 +43,7 @@ class Pinboard extends Plugin { public const controller_route = 'pinboard_settings'; - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect(self::controller_route, '/pinboard/settings', C\Settings::class, options: ['method' => 'post']); @@ -68,7 +69,7 @@ class Pinboard extends Plugin return Event::next; } - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'api') { $tabs[] = [ diff --git a/plugins/PinnedNotes/PinnedNotes.php b/plugins/PinnedNotes/PinnedNotes.php index 815c8bd21e..0e2e7d0e8c 100644 --- a/plugins/PinnedNotes/PinnedNotes.php +++ b/plugins/PinnedNotes/PinnedNotes.php @@ -46,14 +46,15 @@ use Doctrine\Common\Collections\ExpressionBuilder; use Doctrine\ORM\Query\Expr; use Doctrine\ORM\QueryBuilder; +use EventResult; use Plugin\PinnedNotes\Controller as C; -use Plugin\PinnedNotes\Entity as E; +use Plugin\PinnedNotes\Entity as E; use Symfony\Component\HttpFoundation\Request; class PinnedNotes extends Plugin { - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { // Pin and unpin notes $r->connect(id: 'toggle_note_pin', uri_path: '/object/note/{id<\d+>}/pin', target: [C\PinnedNotes::class, 'togglePin']); @@ -73,7 +74,7 @@ class PinnedNotes extends Plugin return Event::next; } - public function onBeforeFeed(Request $request, &$res): bool + public function onBeforeFeed(Request $request, &$res): EventResult { $path = $request->attributes->get('_route'); if ($path === 'actor_view_nickname') { @@ -92,7 +93,7 @@ class PinnedNotes extends Plugin return Event::next; } - public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): bool + public function onCollectionQueryAddJoins(QueryBuilder &$note_qb, QueryBuilder &$actor_qb): EventResult { if (!\in_array('pinned_notes', $note_qb->getAllAliases())) { $note_qb->leftJoin(E\PinnedNotes::class, 'pinned_notes', Expr\Join::WITH, 'note.id = pinned_notes.note_id'); @@ -100,7 +101,7 @@ class PinnedNotes extends Plugin return Event::next; } - public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $language, ?Actor $actor, &$note_expr, &$actor_expr): bool + public function onCollectionQueryCreateExpression(ExpressionBuilder $eb, string $term, ?string $language, ?Actor $actor, &$note_expr, &$actor_expr): EventResult { if ($term === 'pinned:true') { $note_expr = $eb->neq('pinned_notes', null); @@ -114,7 +115,7 @@ class PinnedNotes extends Plugin return Event::next; } - public function onAddNoteActions(Request $request, Note $note, array &$actions): bool + public function onAddNoteActions(Request $request, Note $note, array &$actions): EventResult { $user = Common::user(); if ($user->getId() !== $note->getActorId()) { @@ -139,7 +140,7 @@ class PinnedNotes extends Plugin return Event::next; } - public function onEndShowStyles(array &$styles, string $route): bool + public function onEndShowStyles(array &$styles, string $route): EventResult { $styles[] = 'plugins/PinnedNotes/assets/css/pinned-notes.css'; return Event::next; @@ -147,7 +148,7 @@ class PinnedNotes extends Plugin // Activity Pub handling stuff - public function onActivityStreamsTwoContext(array &$activity_streams_two_context): bool + public function onActivityStreamsTwoContext(array &$activity_streams_two_context): EventResult { $activity_streams_two_context[] = ['toot' => 'http://joinmastodon.org/ns#']; $activity_streams_two_context[] = [ @@ -159,7 +160,7 @@ class PinnedNotes extends Plugin return Event::next; } - public function onActivityPubAddActivityStreamsTwoData(string $type_name, &$type): bool + public function onActivityPubAddActivityStreamsTwoData(string $type_name, &$type): EventResult { if ($type_name === 'Person') { $actor = \Plugin\ActivityPub\Util\Explorer::getOneFromUri($type->get('id')); diff --git a/plugins/Poll/Poll.php b/plugins/Poll/Poll.php index dc0fe21f9b..afb1bc16ff 100644 --- a/plugins/Poll/Poll.php +++ b/plugins/Poll/Poll.php @@ -34,6 +34,7 @@ use App\Util\Exception\InvalidFormException; use App\Util\Exception\NotFoundException; use App\Util\Exception\RedirectException; use App\Util\Exception\ServerException; +use EventResult; use Symfony\Component\Form\Extension\Core\Type\ChoiceType; use Symfony\Component\Form\Extension\Core\Type\HiddenType; use Symfony\Component\Form\Extension\Core\Type\SubmitType; @@ -57,7 +58,7 @@ class Poll extends NoteHandlerPlugin * * @return bool hook value; true means continue processing, false means stop */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('newpoll', 'main/poll/new/{num<\\d+>?3}', [Controller\NewPoll::class, 'newpoll']); @@ -69,7 +70,7 @@ class Poll extends NoteHandlerPlugin * * @return bool hook value; true means continue processing, false means stop. * - * public function onStartTwigPopulateVars(array &$vars): bool + * public function onStartTwigPopulateVars(array &$vars): \EventResult * { * $vars['tabs'][] = ['title' => 'Poll', * 'href' => 'newpoll', @@ -84,7 +85,7 @@ class Poll extends NoteHandlerPlugin * * @return bool hook value; true means continue processing, false means stop */ - public function onStartShowStyles(array &$styles): bool + public function onStartShowStyles(array &$styles): EventResult { $styles[] = 'poll/poll.css'; return Event::next; @@ -102,7 +103,7 @@ class Poll extends NoteHandlerPlugin * * @return bool hook value; true means continue processing, false means stop */ - public function onShowNoteContent(Request $request, Note $note, array &$otherContent): bool + public function onShowNoteContent(Request $request, Note $note, array &$otherContent): EventResult { $responses = null; $formView = null; diff --git a/plugins/ProfileColor/ProfileColor.php b/plugins/ProfileColor/ProfileColor.php index 0d324d38b1..9c51e8e35b 100644 --- a/plugins/ProfileColor/ProfileColor.php +++ b/plugins/ProfileColor/ProfileColor.php @@ -30,6 +30,7 @@ use App\Core\Router; use App\Util\Exception\RedirectException; use App\Util\Exception\ServerException; use App\Util\Formatting; +use EventResult; use Plugin\ProfileColor\Controller as C; use Symfony\Component\HttpFoundation\Request; @@ -51,7 +52,7 @@ class ProfileColor extends Plugin * * @return bool hook value; true means continue processing, false means stop */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { $r->connect('settings_profile_color', 'settings/color', [Controller\ProfileColor::class, 'profileColorSettings']); return Event::next; @@ -61,7 +62,7 @@ class ProfileColor extends Plugin * @throws RedirectException * @throws ServerException */ - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'colours') { $tabs[] = [ @@ -77,7 +78,7 @@ class ProfileColor extends Plugin /** * Renders profileColorView, which changes the background color of that profile. */ - public function onAppendCardProfile(array $vars, array &$res): bool + public function onAppendCardProfile(array $vars, array &$res): EventResult { $actor = $vars['actor']; if ($actor !== null) { diff --git a/plugins/RelatedTags/RelatedTags.php b/plugins/RelatedTags/RelatedTags.php index bcbd482fea..c34bfd3f4a 100644 --- a/plugins/RelatedTags/RelatedTags.php +++ b/plugins/RelatedTags/RelatedTags.php @@ -27,6 +27,7 @@ use App\Core\Event; use App\Core\Modules\Plugin; use Component\Circle\Entity\ActorTag; use Component\Tag\Entity\NoteTag; +use EventResult; use Symfony\Component\HttpFoundation\Request; class RelatedTags extends Plugin @@ -34,7 +35,7 @@ class RelatedTags extends Plugin /** * Add a pinnned block containing tags related to the current page, be it note tags or actor tags */ - public function onAddPinnedFeedContent(Request $request, array &$pinned) + public function onAddPinnedFeedContent(Request $request, array &$pinned): EventResult { // Lets not use language, probably wouldn't make it more helpful //$locale = $request->attributes->get('locale'); diff --git a/plugins/RepeatNote/RepeatNote.php b/plugins/RepeatNote/RepeatNote.php index 1cdffcb8df..9e71aab036 100644 --- a/plugins/RepeatNote/RepeatNote.php +++ b/plugins/RepeatNote/RepeatNote.php @@ -45,6 +45,7 @@ use Component\Language\Entity\Language; use Component\Notification\Entity\Attention; use Component\Posting\Posting; use DateTime; +use EventResult; use Plugin\RepeatNote\Entity\NoteRepeat as RepeatEntity; use const SORT_REGULAR; use Symfony\Component\HttpFoundation\Request; @@ -211,7 +212,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): bool + public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): EventResult { // Replaces repeat with original note on Actor feed // it's pretty cool @@ -236,7 +237,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onAddNoteActions(Request $request, Note $note, array &$actions): bool + public function onAddNoteActions(Request $request, Note $note, array &$actions): EventResult { // Only logged users can repeat notes if (\is_null($user = Common::user())) { @@ -280,7 +281,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onAppendCardNote(array $vars, array &$result) + public function onAppendCardNote(array $vars, array &$result): EventResult { // If note is the original and user isn't the one who repeated, append on end "user repeated this" // If user is the one who repeated, append on end "you repeated this, remove repeat?" @@ -318,7 +319,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onNoteDeleteRelated(Note &$note, Actor $actor): bool + public function onNoteDeleteRelated(Note &$note, Actor $actor): EventResult { $note_repeats_list = RepeatEntity::getNoteRepeats($note); foreach ($note_repeats_list as $note_repeat) { @@ -340,7 +341,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Event hook, Event::next (true) is returned to allow Event to be handled by other handlers */ - public function onAddRoute(Router $r): bool + public function onAddRoute(Router $r): EventResult { // Add/remove note to/from repeats $r->connect(id: 'repeat_add', uri_path: '/object/note/{note_id<\d+>}/repeat', target: [Controller\Repeat::class, 'repeatAddNote']); @@ -427,7 +428,7 @@ class RepeatNote extends NoteHandlerPlugin return Event::stop; } - public function onActivityPubNewNotification(Actor $sender, Activity $activity, array $targets, ?string $reason = null): bool + public function onActivityPubNewNotification(Actor $sender, Activity $activity, array $targets, ?string $reason = null): EventResult { switch ($activity->getVerb()) { case 'repeat': @@ -465,7 +466,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onNewActivityPubActivity(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, \ActivityPhp\Type\AbstractObject $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): bool + public function onNewActivityPubActivity(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, \ActivityPhp\Type\AbstractObject $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): EventResult { return $this->activitypub_handler($actor, $type_activity, $type_object, $ap_act); } @@ -490,7 +491,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onNewActivityPubActivityWithObject(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, mixed $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): bool + public function onNewActivityPubActivityWithObject(Actor $actor, \ActivityPhp\Type\AbstractObject $type_activity, mixed $type_object, ?\Plugin\ActivityPub\Entity\ActivitypubActivity &$ap_act): EventResult { return $this->activitypub_handler($actor, $type_activity, $type_object, $ap_act); } @@ -503,7 +504,7 @@ class RepeatNote extends NoteHandlerPlugin * * @return bool Returns `Event::stop` if handled, `Event::next` otherwise */ - public function onGSVerbToActivityStreamsTwoActivityType(string $verb, ?string &$gs_verb_to_activity_stream_two_verb): bool + public function onGSVerbToActivityStreamsTwoActivityType(string $verb, ?string &$gs_verb_to_activity_stream_two_verb): EventResult { if ($verb === 'repeat') { $gs_verb_to_activity_stream_two_verb = 'Announce'; diff --git a/plugins/StemWord/StemWord.php b/plugins/StemWord/StemWord.php index b1c0d88fd5..d8e9bef369 100644 --- a/plugins/StemWord/StemWord.php +++ b/plugins/StemWord/StemWord.php @@ -25,12 +25,13 @@ namespace Plugin\StemWord; use App\Core\Event; use App\Core\Modules\Plugin; +use EventResult; use Wamania\Snowball\NotFoundException; use Wamania\Snowball\StemmerFactory; class StemWord extends Plugin { - public function onStemWord(string $language, string $word, ?string &$out) + public function onStemWord(string $language, string $word, ?string &$out): EventResult { $language = explode('_', $language)[0]; try { diff --git a/plugins/StoreRemoteMedia/StoreRemoteMedia.php b/plugins/StoreRemoteMedia/StoreRemoteMedia.php index 18cd6f0f51..5f0942ad54 100644 --- a/plugins/StoreRemoteMedia/StoreRemoteMedia.php +++ b/plugins/StoreRemoteMedia/StoreRemoteMedia.php @@ -37,6 +37,7 @@ use Component\Attachment\Entity\AttachmentThumbnail; use Component\Attachment\Entity\AttachmentToLink; use Component\Attachment\Entity\AttachmentToNote; use Component\Link\Entity\Link; +use EventResult; use Symfony\Contracts\HttpClient\Exception\ClientExceptionInterface; use Symfony\Contracts\HttpClient\Exception\RedirectionExceptionInterface; use Symfony\Contracts\HttpClient\Exception\ServerExceptionInterface; @@ -95,7 +96,7 @@ class StoreRemoteMedia extends Plugin * @throws ServerException * @throws TemporaryFileException */ - public function onNewLinkFromNote(Link $link, Note $note): bool + public function onNewLinkFromNote(Link $link, Note $note): EventResult { // Embed is the plugin to handle these if ($link->getMimetypeMajor() === 'text') { @@ -236,7 +237,7 @@ class StoreRemoteMedia extends Plugin * * @return bool true hook value */ - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = [ 'name' => 'StoreRemoteMedia', diff --git a/plugins/TagBasedFiltering/TagBasedFiltering.php b/plugins/TagBasedFiltering/TagBasedFiltering.php index 7bdc303d50..5c1be4b758 100644 --- a/plugins/TagBasedFiltering/TagBasedFiltering.php +++ b/plugins/TagBasedFiltering/TagBasedFiltering.php @@ -34,6 +34,7 @@ use App\Entity\LocalUser; use App\Entity\Note; use Component\Tag\Entity\NoteTag; use Component\Tag\Entity\NoteTagBlock; +use EventResult; use Functional as F; use Plugin\TagBasedFiltering\Controller as C; use Symfony\Component\HttpFoundation\Request; @@ -51,14 +52,14 @@ class TagBasedFiltering extends Plugin return ['note' => "blocked-note-tags-{$actor_id}", 'actor' => "blocked-actor-tags-{$actor_id}"]; } - public function onAddRoute(Router $r) + public function onAddRoute(Router $r): EventResult { $r->connect(id: self::NOTE_TAG_FILTER_ROUTE, uri_path: '/filter/edit-blocked-note-tags/{note_id<\d+>}', target: [Controller\AddBlocked::class, 'addBlockedNoteTags']); $r->connect(id: self::ACTOR_TAG_FILTER_ROUTE, uri_path: '/filter/edit-blocked-actor-tags/{actor_id<\d+>}', target: [Controller\AddBlocked::class, 'addBlockedActorTags']); return Event::next; } - public function onAddExtraNoteActions(Request $request, Note $note, array &$actions) + public function onAddExtraNoteActions(Request $request, Note $note, array &$actions): EventResult { $actions[] = [ 'title' => _m('Block note tags'), @@ -71,12 +72,13 @@ class TagBasedFiltering extends Plugin 'classes' => '', 'url' => Router::url(self::ACTOR_TAG_FILTER_ROUTE, ['actor_id' => $note->getActor()->getId()]), ]; + return Event::next; } /** * Filter out tags from notes or actors, per the user request */ - public function onFilterNoteList(?Actor $actor, array &$notes, Request $request) + public function onFilterNoteList(?Actor $actor, array &$notes, Request $request): EventResult { if (\is_null($actor)) { return Event::next; @@ -102,7 +104,7 @@ class TagBasedFiltering extends Plugin return Event::next; } - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'muting') { $tabs[] = [ diff --git a/plugins/TreeNotes/TreeNotes.php b/plugins/TreeNotes/TreeNotes.php index 974b07b1ba..3a6be82edb 100644 --- a/plugins/TreeNotes/TreeNotes.php +++ b/plugins/TreeNotes/TreeNotes.php @@ -26,6 +26,7 @@ use App\Core\Modules\Plugin; use App\Entity\Note; use App\Util\Common; use App\Util\Formatting; +use EventResult; use Symfony\Component\HttpFoundation\Request; class TreeNotes extends Plugin @@ -34,7 +35,7 @@ class TreeNotes extends Plugin * Formatting notes without taking a direct reply out of context * Show whole conversation in conversation related routes. */ - public function onFormatNoteList(array $notes_in, array &$notes_out, Request $request) + public function onFormatNoteList(array $notes_in, array &$notes_out, Request $request): EventResult { if (str_starts_with($request->get('_route'), 'conversation')) { $parents = $this->conversationFormat($notes_in); @@ -42,6 +43,7 @@ class TreeNotes extends Plugin } else { $notes_out = $this->feedFormatTree($notes_in); } + return Event::stop; } /** @@ -122,7 +124,7 @@ class TreeNotes extends Plugin ]; } - public function onAppendNoteBlock(Request $request, array $conversation, array &$res): bool + public function onAppendNoteBlock(Request $request, array $conversation, array &$res): EventResult { if (\array_key_exists('replies', $conversation)) { $res[] = Formatting::twigRenderFile( diff --git a/plugins/UnboundGroup/UnboundGroup.php b/plugins/UnboundGroup/UnboundGroup.php index a8653f1ef7..6c974e039c 100644 --- a/plugins/UnboundGroup/UnboundGroup.php +++ b/plugins/UnboundGroup/UnboundGroup.php @@ -36,6 +36,7 @@ use App\Core\DB; use App\Core\Event; use App\Core\Modules\Plugin; use App\Entity\Actor; +use EventResult; use Plugin\ActivityPub\Entity\ActivitypubActor; use Plugin\UnboundGroup\Controller\GroupSettings; use Plugin\UnboundGroup\Entity\activitypubGroupUnbound; @@ -49,7 +50,7 @@ use Symfony\Component\HttpFoundation\Request; */ class UnboundGroup extends Plugin { - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'profile' && $request->get('_route') === 'group_actor_settings') { $tabs[] = [ @@ -68,7 +69,7 @@ class UnboundGroup extends Plugin return Event::next; } - public function onActivityStreamsTwoContext(array &$activity_streams_two_context): bool + public function onActivityStreamsTwoContext(array &$activity_streams_two_context): EventResult { $activity_streams_two_context[] = [ 'unbound' => [ @@ -79,7 +80,7 @@ class UnboundGroup extends Plugin return Event::next; } - public function onActivityPubAddActivityStreamsTwoData(string $type_name, &$type): bool + public function onActivityPubAddActivityStreamsTwoData(string $type_name, &$type): EventResult { if ($type_name === 'Group' || $type_name === 'Organization') { $actor = \Plugin\ActivityPub\Util\Explorer::getOneFromUri($type->getId()); @@ -92,7 +93,7 @@ class UnboundGroup extends Plugin return Event::next; } - public function onActivityPubCreateOrUpdateActor(\ActivityPhp\Type\AbstractObject $object, Actor $actor, ActivitypubActor $ap_actor): bool + public function onActivityPubCreateOrUpdateActor(\ActivityPhp\Type\AbstractObject $object, Actor $actor, ActivitypubActor $ap_actor): EventResult { if ($object->has('unbound')) { $obj = DB::findOneBy(activitypubGroupUnbound::class, ['actor_id' => $actor->getId()], return_null: true); diff --git a/plugins/VideoEncoder/VideoEncoder.php b/plugins/VideoEncoder/VideoEncoder.php index 8bdc0ba87e..28f6390744 100644 --- a/plugins/VideoEncoder/VideoEncoder.php +++ b/plugins/VideoEncoder/VideoEncoder.php @@ -42,6 +42,7 @@ use App\Util\Exception\ServerException; use App\Util\Exception\TemporaryFileException; use App\Util\Formatting; use App\Util\TemporaryFile; +use EventResult; use Exception; use FFMpeg\FFMpeg as ffmpeg; use FFMpeg\FFProbe as ffprobe; @@ -59,7 +60,7 @@ class VideoEncoder extends Plugin return GSFile::mimetypeMajor($mimetype) === 'video' || $mimetype === 'image/gif'; } - public function onFileMetaAvailable(array &$event_map, string $mimetype): bool + public function onFileMetaAvailable(array &$event_map, string $mimetype): EventResult { if (!self::shouldHandle($mimetype)) { return Event::next; @@ -69,7 +70,7 @@ class VideoEncoder extends Plugin return Event::next; } - public function onFileSanitizerAvailable(array &$event_map, string $mimetype): bool + public function onFileSanitizerAvailable(array &$event_map, string $mimetype): EventResult { if ($mimetype !== 'image/gif') { return Event::next; @@ -79,7 +80,7 @@ class VideoEncoder extends Plugin return Event::next; } - public function onFileResizerAvailable(array &$event_map, string $mimetype): bool + public function onFileResizerAvailable(array &$event_map, string $mimetype): EventResult { if ($mimetype !== 'image/gif') { return Event::next; @@ -139,7 +140,7 @@ class VideoEncoder extends Plugin /** * Generates the view for attachments of type Video */ - public function onViewAttachment(array $vars, array &$res): bool + public function onViewAttachment(array $vars, array &$res): EventResult { if ($vars['attachment']->getMimetypeMajor() !== 'video') { return Event::next; @@ -289,7 +290,7 @@ class VideoEncoder extends Plugin /** * @throws ServerException */ - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $versions[] = ['name' => 'FFmpeg', 'version' => self::version(), diff --git a/plugins/WebHooks/WebHooks.php b/plugins/WebHooks/WebHooks.php index 3d8e608743..2dcbef10cf 100644 --- a/plugins/WebHooks/WebHooks.php +++ b/plugins/WebHooks/WebHooks.php @@ -33,6 +33,7 @@ use App\Entity\Actor; use App\Entity\LocalUser; use App\Util\Common; use App\Util\Exception\ServerException; +use EventResult; use Exception; use Functional as F; use Plugin\WebHooks\Controller as C; @@ -43,12 +44,13 @@ class WebHooks extends Plugin { public const controller_route = 'webhook'; - public function onAddRoute(Router $r) + public function onAddRoute(Router $r): EventResult { $r->connect(self::controller_route, '/webhook-settings', C\WebHooks::class, options: ['method' => 'post']); + return EventResult::next; } - public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): bool + public function onPopulateSettingsTabs(Request $request, string $section, array &$tabs): EventResult { if ($section === 'api') { $tabs[] = [ @@ -69,7 +71,7 @@ class WebHooks extends Plugin } } - public function onNewNotificationEnd(Actor $sender, Activity $activity, array $effective_targets, ?string $reason) + public function onNewNotificationEnd(Actor $sender, Activity $activity, array $effective_targets, ?string $reason): EventResult { foreach ($effective_targets as $actor) { $this->maybeEnqueue($actor, 'notifications', [$sender, $activity, $effective_targets, $reason]); @@ -77,7 +79,7 @@ class WebHooks extends Plugin return Event::next; } - public function onNewSubscriptionEnd(LocalUser|Actor $subscriber, Activity $activity, Actor $hook_target, ?string $reason) + public function onNewSubscriptionEnd(LocalUser|Actor $subscriber, Activity $activity, Actor $hook_target, ?string $reason): EventResult { $this->maybeEnqueue($hook_target, 'subscriptions', [$subscriber, $activity, $hook_target, $reason]); return Event::next; @@ -86,7 +88,7 @@ class WebHooks extends Plugin /** * @param array $args */ - public function onQueueWebhook(string $type, string $hook_target, Actor $actor, array $args) + public function onQueueWebhook(string $type, string $hook_target, Actor $actor, array $args): EventResult { switch ($type) { case 'notifications': diff --git a/plugins/WebMonetization/WebMonetization.php b/plugins/WebMonetization/WebMonetization.php index a7a6d2b5ba..a879de51e5 100644 --- a/plugins/WebMonetization/WebMonetization.php +++ b/plugins/WebMonetization/WebMonetization.php @@ -43,6 +43,7 @@ use App\Entity\LocalUser; use App\Util\Common; use App\Util\Exception\RedirectException; use App\Util\Formatting; +use EventResult; use Plugin\ActivityPub\Entity\ActivitypubActor; use Plugin\WebMonetization\Entity\Wallet; use Plugin\WebMonetization\Entity\WebMonetization as Monetization; @@ -52,7 +53,7 @@ use Symfony\Component\HttpFoundation\Request; class WebMonetization extends Plugin { - public function onAppendRightPanelBlock(Request $request, $vars, &$res): bool + public function onAppendRightPanelBlock(Request $request, $vars, &$res): EventResult { $user = Common::actor(); if (\is_null($user)) { @@ -209,7 +210,7 @@ class WebMonetization extends Plugin ]; } - public function onAppendToHead(Request $request, &$res): bool + public function onAppendToHead(Request $request, &$res): EventResult { $user = Common::user(); if (\is_null($user)) { @@ -241,7 +242,7 @@ class WebMonetization extends Plugin return Event::next; } - public function onActivityStreamsTwoContext(array &$activity_streams_two_context): bool + public function onActivityStreamsTwoContext(array &$activity_streams_two_context): EventResult { $activity_streams_two_context[] = [ 'webmonetizationWallet' => [ @@ -252,7 +253,7 @@ class WebMonetization extends Plugin return Event::next; } - public function onActivityPubAddActivityStreamsTwoData(string $type_name, &$type): bool + public function onActivityPubAddActivityStreamsTwoData(string $type_name, &$type): EventResult { if ($type_name === 'Person') { $actor = \Plugin\ActivityPub\Util\Explorer::getOneFromUri($type->getId()); @@ -265,7 +266,7 @@ class WebMonetization extends Plugin return Event::next; } - public function onActivityPubCreateOrUpdateActor(\ActivityPhp\Type\AbstractObject $object, Actor $actor, ActivitypubActor $ap_actor): bool + public function onActivityPubCreateOrUpdateActor(\ActivityPhp\Type\AbstractObject $object, Actor $actor, ActivitypubActor $ap_actor): EventResult { if ($object->has('webmonetizationWallet')) { $attr = ['actor_id' => $actor->getId(), 'address' => $object->get('webmonetizationWallet')]; diff --git a/plugins/XMPPNotifications/XMPPNotifications.php b/plugins/XMPPNotifications/XMPPNotifications.php index c4cc533d65..475dd41441 100644 --- a/plugins/XMPPNotifications/XMPPNotifications.php +++ b/plugins/XMPPNotifications/XMPPNotifications.php @@ -36,10 +36,11 @@ namespace Plugin\XMPPNotifications; use App\Core\Event; use App\Core\Modules\Plugin; +use EventResult; class XMPPNotifications extends Plugin { - public function onAddNotificationTransport(&$form_defs): bool + public function onAddNotificationTransport(&$form_defs): EventResult { $form_defs['XMPP'] = $form_defs['placeholder']; $form_defs['XMPP'][] = $form_defs['placeholder']['save']('XMPP', 'save_xmpp'); diff --git a/src/Core/Event.php b/src/Core/Event.php index a4b806ed18..feb1d77c89 100644 --- a/src/Core/Event.php +++ b/src/Core/Event.php @@ -33,20 +33,22 @@ declare(strict_types = 1); namespace App\Core; +use App\Core\Event\GSEvent; +use App\Util\Exception\BugFoundException; +use EventResult; use ReflectionFunction; use Symfony\Component\EventDispatcher\EventDispatcherInterface; -use Symfony\Component\EventDispatcher\GenericEvent; abstract class Event { /** - * Constants to be returned from event handlers, for increased clarity + * Constants to be returned from event handlers * - * bool stop - Stop other handlers from processing the event - * bool next - Allow the other handlers to process the event + * EventResult::stop - Stop other handlers from processing the event + * EventResult::next - Allow the other handlers to process the event */ - public const stop = false; - public const next = true; + public const stop = EventResult::stop; + public const next = EventResult::next; private static EventDispatcherInterface $dispatcher; @@ -83,20 +85,18 @@ abstract class Event ): void { self::$dispatcher->addListener( $ns . $name, - function ($event, $event_name, $dispatcher) use ($handler, $name) { - // Old style of events (preferred) - if ($event instanceof GenericEvent) { - if ($handler(...$event->getArguments()) === self::stop) { - $event->stopPropagation(); - } - return $event; + function ($event, $event_name, $dispatcher) use ($handler) { + $result = $handler(...$event->getArguments()); + if (\is_null($result) || !isset($result)) { + dd($handler, $event_name); + throw new BugFoundException("Events must return an \\EventResult, which a handler for {$event_name} does not"); } - // @codeCoverageIgnoreStart - // Symfony style of events - Log::warning("Event::addHandler for {$name} doesn't Conform to GNU social guidelines. Use of this style of event is discouraged."); - $handler($event, $event_name, $dispatcher); - // @codeCoverageIgnoreEnd + $event->setResult($result); + if ($result === EventResult::stop) { + $event->stopPropagation(); + } + return $event; }, $priority, ); @@ -119,9 +119,9 @@ abstract class Event * @return bool flag saying whether to continue processing, based * on results of handlers */ - public static function handle(string $name, array $args = [], string $ns = 'GNUsocial.'): bool + public static function handle(string $name, array $args = [], string $ns = 'GNUsocial.'): EventResult { - return !(self::$dispatcher->dispatch(new GenericEvent($name, $args), $ns . $name)->isPropagationStopped()); + return self::$dispatcher->dispatch(new GSEvent($name, $args), $ns . $name)->getResult(); } /** diff --git a/src/Core/Event/EventResult.php b/src/Core/Event/EventResult.php new file mode 100644 index 0000000000..0f66165ec9 --- /dev/null +++ b/src/Core/Event/EventResult.php @@ -0,0 +1,13 @@ +result = $result; + } + + public function getResult(): mixed + { + return $this->result ?? EventResult::next; + } +} diff --git a/src/Core/ModuleManager.php b/src/Core/ModuleManager.php index 7d02a2a5e2..ef23d2709e 100644 --- a/src/Core/ModuleManager.php +++ b/src/Core/ModuleManager.php @@ -36,6 +36,7 @@ declare(strict_types = 1); namespace App\Core; use App\Kernel; +use App\Util\Exception\BugFoundException; use App\Util\Formatting; use AppendIterator; use Exception; @@ -43,6 +44,7 @@ use FilesystemIterator; use Functional as F; use RecursiveDirectoryIterator; use RecursiveIteratorIterator; +use ReflectionMethod; use Symfony\Component\Config\Loader\LoaderInterface; use Symfony\Component\Config\Resource\GlobResource; use Symfony\Component\DependencyInjection\ContainerBuilder; @@ -85,10 +87,15 @@ class ModuleManager get_class_methods($obj), F\ary(F\partial_right('App\Util\Formatting::startsWith', 'on'), 1), ), - function (string $m) use ($obj) { - $ev = mb_substr($m, 2); - $this->events[$ev] ??= []; - $this->events[$ev][] = [$obj, $m]; + function (string $method) use ($obj) { + if (((string) (new ReflectionMethod($obj, $method))->getReturnType()) !== 'EventResult') { + $class = $obj::class; + dd("Return type of {$class}::{$method} is not the required EventResult"); + throw new BugFoundException("Return type of {$class}::{$method} is not the required EventResult"); + } + $event_name = mb_substr($method, 2); + $this->events[$event_name] ??= []; + $this->events[$event_name][] = [$obj, $method]; }, ); } diff --git a/src/Core/Modules/Module.php b/src/Core/Modules/Module.php index eb97959213..b0d93bc1f3 100644 --- a/src/Core/Modules/Module.php +++ b/src/Core/Modules/Module.php @@ -22,6 +22,7 @@ declare(strict_types = 1); namespace App\Core\Modules; use App\Util\Common; +use EventResult; /** * Base class for all GNU social modules (plugins and components) @@ -64,22 +65,23 @@ abstract class Module // ------- Module initialize and cleanup ---------- - private function defer(string $cycle) + private function defer(string $cycle): EventResult { $type = ucfirst(static::MODULE_TYPE); if (method_exists($this, $method = "on{$cycle}{$type}")) { $this->{$method}(); } + return EventResult::next; } // Can't use __call or it won't be found by our event function finder - public function onInitializeModule() + public function onInitializeModule(): EventResult { - $this->defer('Initialize'); + return $this->defer('Initialize'); } - public function onCleanupModule() + public function onCleanupModule(): EventResult { - $this->defer('Cleanup'); + return $this->defer('Cleanup'); } } diff --git a/src/Core/Modules/Plugin.php b/src/Core/Modules/Plugin.php index d269120fd8..3f50d17234 100644 --- a/src/Core/Modules/Plugin.php +++ b/src/Core/Modules/Plugin.php @@ -6,6 +6,7 @@ namespace App\Core\Modules; use App\Core\Event; use function App\Core\I18n\_m; +use EventResult; /** * TODO Plugins aren't tested yet @@ -21,7 +22,7 @@ abstract class Plugin extends Module return GNUSOCIAL_BASE_VERSION; } - public function onPluginVersion(array &$versions): bool + public function onPluginVersion(array &$versions): EventResult { $name = $this->name(); diff --git a/src/Core/Security.php b/src/Core/Security.php index 7f3d53f879..9a57613c0a 100644 --- a/src/Core/Security.php +++ b/src/Core/Security.php @@ -33,7 +33,6 @@ declare(strict_types = 1); namespace App\Core; use App\Entity\LocalUser; -use App\Util\Common; use App\Util\Formatting; use BadMethodCallException; use Functional as F; @@ -97,12 +96,12 @@ class Security implements EventSubscriberInterface //implements AuthenticatorInt // can be used to essentially override any class when such a // file is opened and thus provide code execution to an // attacker. Not a complete solution, since `file://`, - // `php://` and `glob://` get used _somewhere_, so we can't + // `php://` and `glob://`, 'compress.zlib' (symfony profiler) get used _somewhere_, so we can't // disable them F\each( - ['http', 'https', 'ftp', 'ftps', 'compress.zlib', 'data', 'phar'], // Making this configurable might be a nice feature, but it's tricky because this happens before general initialization - fn (string $protocol) => \stream_wrapper_unregister($protocol) - );; + ['http', 'https', 'ftp', 'ftps', 'data', 'phar'], // Making this configurable might be a nice feature, but it's tricky because this happens before general initialization + fn (string $protocol) => stream_wrapper_unregister($protocol), + ); } public static function __callStatic(string $name, array $args)