From 0d635d5dd1c8bc7423493bc2fd68edf748fe2c47 Mon Sep 17 00:00:00 2001 From: Matthias Pfefferle Date: Fri, 22 Sep 2023 09:38:59 +0200 Subject: [PATCH] More Group meta-data to play nicely with existing platforms (#441) * more group friendly settings * change http code * Fix Actor-Type * fix check if value is set * only ignore null * better posting_restricted_to_mods handling * remove user namespace from moderators endpoint thanks for the feedback @mattwiebe --- includes/activity/class-activity.php | 7 ++++ includes/activity/class-base-object.php | 2 +- includes/model/class-application-user.php | 10 +++-- includes/model/class-blog-user.php | 45 ++++++++++++++++------- includes/model/class-user.php | 39 ++++++++++++++++++++ includes/rest/class-collection.php | 37 +++++++++++++++++++ 6 files changed, 122 insertions(+), 18 deletions(-) diff --git a/includes/activity/class-activity.php b/includes/activity/class-activity.php index c4bebaa..6c59866 100644 --- a/includes/activity/class-activity.php +++ b/includes/activity/class-activity.php @@ -28,6 +28,7 @@ class Activity extends Base_Object { 'toot' => 'http://joinmastodon.org/ns#', 'webfinger' => 'https://webfinger.net/#', 'litepub' => 'http://litepub.social/ns#', + 'lemmy' => 'https://join-lemmy.org/ns#', 'value' => 'schema:value', 'Hashtag' => 'as:Hashtag', 'featured' => array( @@ -42,7 +43,13 @@ class Activity extends Base_Object { '@id' => 'as:alsoKnownAs', '@type' => '@id', ), + 'moderators' => array( + '@id' => 'lemmy:moderators', + '@type' => '@id', + ), + 'postingRestrictedToMods' => 'lemmy:postingRestrictedToMods', 'discoverable' => 'toot:discoverable', + 'indexable' => 'toot:indexable', 'sensitive' => 'as:sensitive', 'resource' => 'webfinger:resource', ), diff --git a/includes/activity/class-base-object.php b/includes/activity/class-base-object.php index b830229..a75ed16 100644 --- a/includes/activity/class-base-object.php +++ b/includes/activity/class-base-object.php @@ -644,7 +644,7 @@ class Base_Object { } // if value is still empty, ignore it for the array and continue. - if ( $value ) { + if ( isset( $value ) ) { $array[ snake_to_camel_case( $key ) ] = $value; } } diff --git a/includes/model/class-application-user.php b/includes/model/class-application-user.php index 0042338..1cfcec0 100644 --- a/includes/model/class-application-user.php +++ b/includes/model/class-application-user.php @@ -55,14 +55,18 @@ class Application_User extends Blog_User { } public function get_attachment() { - return array(); + return null; } public function get_featured_tags() { - return array(); + return null; } public function get_featured() { - return array(); + return null; + } + + public function get_moderators() { + return null; } } diff --git a/includes/model/class-blog-user.php b/includes/model/class-blog-user.php index 25b19e9..3853da1 100644 --- a/includes/model/class-blog-user.php +++ b/includes/model/class-blog-user.php @@ -7,6 +7,7 @@ use Activitypub\Collection\Users; use function Activitypub\is_single_user; use function Activitypub\is_user_disabled; +use function Activitypub\get_rest_url_by_path; class Blog_User extends User { /** @@ -21,7 +22,7 @@ class Blog_User extends User { * * @var string */ - protected $type = 'Group'; + protected $type = null; /** * Is Account discoverable? @@ -45,6 +46,21 @@ class Blog_User extends User { return $object; } + /** + * Get the type of the object. + * + * If the Blog is in "single user" mode, return "Person" insted of "Group". + * + * @return string The type of the object. + */ + public function get_type() { + if ( is_single_user() ) { + return 'Person'; + } else { + return 'Group'; + } + } + /** * Get the User-Name. * @@ -188,25 +204,26 @@ class Blog_User extends User { } public function get_attachment() { - return array(); + return null; } public function get_canonical_url() { return \home_url(); } - /** - * Get the type of the object. - * - * If the Blog is in "single user" mode, return "Person" insted of "Group". - * - * @return string The type of the object. - */ - public function get_type() { - if ( is_single_user() ) { - return 'Person'; - } else { - return $this->type; + public function get_moderators() { + if ( is_single_user() || 'Group' !== $this->get_type() ) { + return null; } + + return get_rest_url_by_path( 'collections/moderators' ); + } + + public function get_posting_restricted_to_mods() { + if ( 'Group' === $this->get_type() ) { + return true; + } + + return null; } } diff --git a/includes/model/class-user.php b/includes/model/class-user.php index 8dfc575..d07534b 100644 --- a/includes/model/class-user.php +++ b/includes/model/class-user.php @@ -36,6 +36,15 @@ class User extends Actor { */ protected $featured; + /** + * Moderators endpoint. + * + * @see https://join-lemmy.org/docs/contributors/05-federation.html + * + * @var string + */ + protected $moderators; + /** * The User-Type * @@ -46,10 +55,19 @@ class User extends Actor { /** * If the User is discoverable. * + * @see https://docs.joinmastodon.org/spec/activitypub/#discoverable + * * @var boolean */ protected $discoverable = true; + /** + * If the User is indexable. + * + * @var boolean + */ + protected $indexable; + /** * The WebFinger Resource. * @@ -57,6 +75,15 @@ class User extends Actor { */ protected $resource; + /** + * Restrict posting to mods + * + * @see https://join-lemmy.org/docs/contributors/05-federation.html + * + * @var boolean + */ + protected $posting_restricted_to_mods = null; + public static function from_wp_user( $user_id ) { if ( is_user_disabled( $user_id ) ) { return new WP_Error( @@ -272,4 +299,16 @@ class User extends Actor { public function get_canonical_url() { return $this->get_url(); } + + public function get_streams() { + return null; + } + + public function get_indexable() { + if ( \get_option( 'blog_public', 1 ) ) { + return true; + } else { + return false; + } + } } diff --git a/includes/rest/class-collection.php b/includes/rest/class-collection.php index b29a090..9e50835 100644 --- a/includes/rest/class-collection.php +++ b/includes/rest/class-collection.php @@ -1,6 +1,7 @@ WP_REST_Server::READABLE, + 'callback' => array( self::class, 'moderators_get' ), + 'permission_callback' => '__return_true', + ), + ) + ); } /** @@ -158,6 +171,30 @@ class Collection { return new WP_REST_Response( $response, 200 ); } + /** + * Moderators endpoint + * + * @param WP_REST_Request $request The request object. + * + * @return WP_REST_Response The response object. + */ + public static function moderators_get( $request ) { + $response = array( + '@context' => Activity::CONTEXT, + 'id' => get_rest_url_by_path( 'collections/moderators' ), + 'type' => 'OrderedCollection', + 'orderedItems' => array(), + ); + + $users = User_Collection::get_collection(); + + foreach ( $users as $user ) { + $response['orderedItems'][] = $user->get_url(); + } + + return new WP_REST_Response( $response, 200 ); + } + /** * The supported parameters *