PluginProbe
ActivityPub / 5.7.0
ActivityPub v5.7.0
9.3.1 9.3.0 9.2.2 9.2.1 9.2.0 9.1.0 9.0.2 9.0.1 9.0.0 8.3.0 8.2.1 8.2.0 8.1.1 1.0.5 1.0.6 1.0.7 1.0.8 1.0.9 1.1.0 1.2.0 1.3.0 2.0.0 2.0.1 2.1.0 2.1.1 All 160 releases
activitypub / includes / model / class-user.php

class-user.php in ActivityPub 5.7.0, at includes/model/class-user.php

475 lines 10.0 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * User model file.
4 *
5 * @package Activitypub
6 */
7
8 namespace Activitypub\Model;
9
10 use Activitypub\Activity\Actor;
11 use Activitypub\Collection\Extra_Fields;
12 use Activitypub\Http;
13 use Activitypub\Signature;
14
15 use function Activitypub\is_blog_public;
16 use function Activitypub\get_rest_url_by_path;
17 use function Activitypub\get_attribution_domains;
18 use function Activitypub\user_can_activitypub;
19
20 /**
21 * User class.
22 *
23 * @method int get__id() Gets the WordPress user ID.
24 */
25 class User extends Actor {
26 /**
27 * The local User-ID (WP_User).
28 *
29 * @var int
30 */
31 protected $_id; // phpcs:ignore PSR2.Classes.PropertyDeclaration.Underscore
32
33 /**
34 * The Featured-Posts.
35 *
36 * @see https://docs.joinmastodon.org/spec/activitypub/#featured
37 *
38 * @context {
39 * "@id": "http://joinmastodon.org/ns#featured",
40 * "@type": "@id"
41 * }
42 *
43 * @var string
44 */
45 protected $featured;
46
47 /**
48 * Whether the User is discoverable.
49 *
50 * @see https://docs.joinmastodon.org/spec/activitypub/#discoverable
51 *
52 * @context http://joinmastodon.org/ns#discoverable
53 *
54 * @var boolean
55 */
56 protected $discoverable = true;
57
58 /**
59 * Whether the User is indexable.
60 *
61 * @context http://joinmastodon.org/ns#indexable
62 *
63 * @var boolean
64 */
65 protected $indexable;
66
67 /**
68 * The WebFinger Resource.
69 *
70 * @var string
71 */
72 protected $webfinger;
73
74 /**
75 * Constructor.
76 *
77 * @param int $user_id Optional. The WordPress user ID. Default null.
78 */
79 public function __construct( $user_id = null ) {
80 if ( $user_id ) {
81 $this->_id = $user_id;
82
83 /**
84 * Fires when a model actor is constructed.
85 *
86 * @param User $this The User object.
87 */
88 \do_action( 'activitypub_construct_model_actor', $this );
89 }
90 }
91
92 /**
93 * The type of the object.
94 *
95 * @return string The type of the object.
96 */
97 public function get_type() {
98 return 'Person';
99 }
100
101 /**
102 * Generate a User object from a WP_User.
103 *
104 * @param int $user_id The user ID.
105 *
106 * @return \WP_Error|User The User object or \WP_Error if user not found.
107 */
108 public static function from_wp_user( $user_id ) {
109 if ( ! user_can_activitypub( $user_id ) ) {
110 return new \WP_Error(
111 'activitypub_user_not_found',
112 \__( 'User not found', 'activitypub' ),
113 array( 'status' => 404 )
114 );
115 }
116
117 return new static( $user_id );
118 }
119
120 /**
121 * Get the user ID.
122 *
123 * @return string The user ID.
124 */
125 public function get_id() {
126 $id = parent::get_id();
127
128 if ( $id ) {
129 return $id;
130 }
131
132 $permalink = \get_user_option( 'activitypub_use_permalink_as_id', $this->_id );
133
134 if ( '1' === $permalink ) {
135 return $this->get_url();
136 }
137
138 return \add_query_arg( 'author', $this->_id, \trailingslashit( \home_url() ) );
139 }
140
141 /**
142 * Get the Username.
143 *
144 * @return string The Username.
145 */
146 public function get_name() {
147 return \get_the_author_meta( 'display_name', $this->_id );
148 }
149
150 /**
151 * Get the User description.
152 *
153 * @return string The User description.
154 */
155 public function get_summary() {
156 $description = get_user_option( 'activitypub_description', $this->_id );
157 if ( empty( $description ) ) {
158 $description = get_user_meta( $this->_id, 'description', true );
159 }
160 return \wpautop( \wp_kses( $description, 'default' ) );
161 }
162
163 /**
164 * Get the User url.
165 *
166 * @return string The User url.
167 */
168 public function get_url() {
169 return \esc_url( \get_author_posts_url( $this->_id ) );
170 }
171
172 /**
173 * Returns the User URL with @-Prefix for the username.
174 *
175 * @return string The User URL with @-Prefix for the username.
176 */
177 public function get_alternate_url() {
178 return \esc_url( \trailingslashit( get_home_url() ) . '@' . $this->get_preferred_username() );
179 }
180
181 /**
182 * Get the preferred username.
183 *
184 * @return string The preferred username.
185 */
186 public function get_preferred_username() {
187 return \get_the_author_meta( 'login', $this->_id );
188 }
189
190 /**
191 * Get the User icon.
192 *
193 * @return string[] The User icon.
194 */
195 public function get_icon() {
196 $icon = \get_user_option( 'activitypub_icon', $this->_id );
197 if ( false !== $icon && wp_attachment_is_image( $icon ) ) {
198 return array(
199 'type' => 'Image',
200 'url' => esc_url( wp_get_attachment_url( $icon ) ),
201 );
202 }
203
204 $icon = \esc_url(
205 \get_avatar_url(
206 $this->_id,
207 array( 'size' => 120 )
208 )
209 );
210
211 return array(
212 'type' => 'Image',
213 'url' => $icon,
214 );
215 }
216
217 /**
218 * Returns the header image.
219 *
220 * @return string[]|null The header image.
221 */
222 public function get_image() {
223 $header_image = get_user_option( 'activitypub_header_image', $this->_id );
224 $image_url = null;
225
226 if ( ! $header_image && \has_header_image() ) {
227 $image_url = \get_header_image();
228 }
229
230 if ( $header_image ) {
231 $image_url = \wp_get_attachment_url( $header_image );
232 }
233
234 if ( $image_url ) {
235 return array(
236 'type' => 'Image',
237 'url' => esc_url( $image_url ),
238 );
239 }
240
241 return null;
242 }
243
244 /**
245 * Returns the date the user was created.
246 *
247 * @return false|string The date the user was created.
248 */
249 public function get_published() {
250 return \gmdate( ACTIVITYPUB_DATE_TIME_RFC3339, \strtotime( \get_the_author_meta( 'registered', $this->_id ) ) );
251 }
252
253 /**
254 * Returns the public key.
255 *
256 * @return string[] The public key.
257 */
258 public function get_public_key() {
259 return array(
260 'id' => $this->get_id() . '#main-key',
261 'owner' => $this->get_id(),
262 'publicKeyPem' => Signature::get_public_key_for( $this->get__id() ),
263 );
264 }
265
266 /**
267 * Returns the Inbox-API-Endpoint.
268 *
269 * @return string The Inbox-Endpoint.
270 */
271 public function get_inbox() {
272 return get_rest_url_by_path( sprintf( 'actors/%d/inbox', $this->get__id() ) );
273 }
274
275 /**
276 * Returns the Outbox-API-Endpoint.
277 *
278 * @return string The Outbox-Endpoint.
279 */
280 public function get_outbox() {
281 return get_rest_url_by_path( sprintf( 'actors/%d/outbox', $this->get__id() ) );
282 }
283
284 /**
285 * Returns the Followers-API-Endpoint.
286 *
287 * @return string The Followers-Endpoint.
288 */
289 public function get_followers() {
290 return get_rest_url_by_path( sprintf( 'actors/%d/followers', $this->get__id() ) );
291 }
292
293 /**
294 * Returns the Following-API-Endpoint.
295 *
296 * @return string The Following-Endpoint.
297 */
298 public function get_following() {
299 return get_rest_url_by_path( sprintf( 'actors/%d/following', $this->get__id() ) );
300 }
301
302 /**
303 * Returns the Featured-API-Endpoint.
304 *
305 * @return string The Featured-Endpoint.
306 */
307 public function get_featured() {
308 return get_rest_url_by_path( sprintf( 'actors/%d/collections/featured', $this->get__id() ) );
309 }
310
311 /**
312 * Returns the endpoints.
313 *
314 * @return string[]|null The endpoints.
315 */
316 public function get_endpoints() {
317 $endpoints = null;
318
319 if ( \get_option( 'activitypub_shared_inbox' ) ) {
320 $endpoints = array(
321 'sharedInbox' => get_rest_url_by_path( 'inbox' ),
322 );
323 }
324
325 return $endpoints;
326 }
327
328 /**
329 * Extend the User-Output with Attachments.
330 *
331 * @return array The extended User-Output.
332 */
333 public function get_attachment() {
334 $extra_fields = Extra_Fields::get_actor_fields( $this->_id );
335 return Extra_Fields::fields_to_attachments( $extra_fields );
336 }
337
338 /**
339 * Returns a user@domain type of identifier for the user.
340 *
341 * @return string The Webfinger-Identifier.
342 */
343 public function get_webfinger() {
344 return $this->get_preferred_username() . '@' . \wp_parse_url( \home_url(), \PHP_URL_HOST );
345 }
346
347 /**
348 * Returns the canonical URL.
349 *
350 * @return string The canonical URL.
351 */
352 public function get_canonical_url() {
353 return $this->get_url();
354 }
355
356 /**
357 * Returns the streams.
358 *
359 * @return null The streams.
360 */
361 public function get_streams() {
362 return null;
363 }
364
365 /**
366 * Returns the tag.
367 *
368 * @return array The tag.
369 */
370 public function get_tag() {
371 return array();
372 }
373
374 /**
375 * Returns the indexable state.
376 *
377 * @return bool Whether the user is indexable.
378 */
379 public function get_indexable() {
380 if ( is_blog_public() ) {
381 return true;
382 } else {
383 return false;
384 }
385 }
386
387 /**
388 * Update the username.
389 *
390 * @param string $value The new value.
391 * @return int|\WP_Error The updated user ID or \WP_Error on failure.
392 */
393 public function update_name( $value ) {
394 $userdata = array(
395 'ID' => $this->_id,
396 'display_name' => $value,
397 );
398 return \wp_update_user( $userdata );
399 }
400
401 /**
402 * Update the User description.
403 *
404 * @param string $value The new value.
405 * @return bool True if the attribute was updated, false otherwise.
406 */
407 public function update_summary( $value ) {
408 return \update_user_option( $this->_id, 'activitypub_description', $value );
409 }
410
411 /**
412 * Update the User icon.
413 *
414 * @param int $value The new value. Should be an attachment ID.
415 * @return bool True if the attribute was updated, false otherwise.
416 */
417 public function update_icon( $value ) {
418 if ( ! wp_attachment_is_image( $value ) ) {
419 return false;
420 }
421 return update_user_option( $this->_id, 'activitypub_icon', $value );
422 }
423
424 /**
425 * Update the User-Header-Image.
426 *
427 * @param int $value The new value. Should be an attachment ID.
428 * @return bool True if the attribute was updated, false otherwise.
429 */
430 public function update_header( $value ) {
431 if ( ! wp_attachment_is_image( $value ) ) {
432 return false;
433 }
434 return \update_user_option( $this->_id, 'activitypub_header_image', $value );
435 }
436
437 /**
438 * Returns the website hosts allowed to credit this blog.
439 *
440 * @return string[]|null The attribution domains or null if not found.
441 */
442 public function get_attribution_domains() {
443 return get_attribution_domains();
444 }
445
446 /**
447 * Returns the alsoKnownAs.
448 *
449 * @return string[] The alsoKnownAs.
450 */
451 public function get_also_known_as() {
452 $also_known_as = array(
453 \add_query_arg( 'author', $this->_id, \home_url( '/' ) ),
454 $this->get_url(),
455 $this->get_alternate_url(),
456 );
457
458 // phpcs:ignore Universal.Operators.DisallowShortTernary.Found
459 $also_known_as = array_merge( $also_known_as, \get_user_option( 'activitypub_also_known_as', $this->_id ) ?: array() );
460
461 return array_unique( $also_known_as );
462 }
463
464 /**
465 * Returns the movedTo.
466 *
467 * @return string The movedTo.
468 */
469 public function get_moved_to() {
470 $moved_to = \get_user_option( 'activitypub_moved_to', $this->_id );
471
472 return $moved_to && $moved_to !== $this->get_id() ? $moved_to : null;
473 }
474 }
475