77
88namespace Activitypub ;
99
10- use Activitypub \Collection \Actors ;
1110use Activitypub \Collection \Followers ;
1211use Activitypub \Collection \Following ;
13- use Activitypub \Collection \Outbox ;
1412
1513/**
1614 * ActivityPub Class.
@@ -22,15 +20,9 @@ class Activitypub {
2220 * Initialize the class, registering WordPress hooks.
2321 */
2422 public static function init () {
25- \add_action ( 'init ' , array ( self ::class, 'add_rewrite_rules ' ), 11 );
2623 \add_action ( 'init ' , array ( self ::class, 'theme_compat ' ), 11 );
2724 \add_action ( 'init ' , array ( self ::class, 'register_user_meta ' ), 11 );
2825
29- \add_filter ( 'template_include ' , array ( self ::class, 'render_activitypub_template ' ), 99 );
30- \add_action ( 'template_redirect ' , array ( self ::class, 'template_redirect ' ) );
31- \add_filter ( 'redirect_canonical ' , array ( self ::class, 'redirect_canonical ' ), 10 , 2 );
32- \add_filter ( 'redirect_canonical ' , array ( self ::class, 'no_trailing_redirect ' ), 10 , 2 );
33- \add_filter ( 'query_vars ' , array ( self ::class, 'add_query_vars ' ) );
3426 \add_filter ( 'pre_get_avatar_data ' , array ( self ::class, 'pre_get_avatar_data ' ), 11 , 2 );
3527
3628 \add_action ( 'wp_trash_post ' , array ( self ::class, 'trash_post ' ), 1 );
@@ -98,227 +90,6 @@ public static function uninstall() {
9890 Options::delete ();
9991 }
10092
101- /**
102- * Return a AS2 JSON version of an author, post or page.
103- *
104- * @param string $template The path to the template object.
105- *
106- * @return string The new path to the JSON template.
107- */
108- public static function render_activitypub_template ( $ template ) {
109- if ( \wp_is_serving_rest_request () || \wp_doing_ajax () ) {
110- return $ template ;
111- }
112-
113- self ::add_headers ();
114-
115- if ( ! is_activitypub_request () || ! should_negotiate_content () ) {
116- if ( \get_query_var ( 'p ' ) && Outbox::POST_TYPE === \get_post_type ( \get_query_var ( 'p ' ) ) ) {
117- \set_query_var ( 'is_404 ' , true );
118- \status_header ( 406 );
119- }
120- return $ template ;
121- }
122-
123- if ( Tombstone::exists_local ( Query::get_instance ()->get_request_url () ) ) {
124- \status_header ( 410 );
125- return ACTIVITYPUB_PLUGIN_DIR . 'templates/tombstone-json.php ' ;
126- }
127-
128- $ activitypub_template = false ;
129- $ activitypub_object = Query::get_instance ()->get_activitypub_object ();
130-
131- if ( $ activitypub_object ) {
132- if ( \get_query_var ( 'preview ' ) ) {
133- \define ( 'ACTIVITYPUB_PREVIEW ' , true );
134-
135- /**
136- * Filter the template used for the ActivityPub preview.
137- *
138- * @param string $activitypub_template Absolute path to the template file.
139- */
140- $ activitypub_template = apply_filters ( 'activitypub_preview_template ' , ACTIVITYPUB_PLUGIN_DIR . '/templates/post-preview.php ' );
141- } else {
142- $ activitypub_template = ACTIVITYPUB_PLUGIN_DIR . 'templates/activitypub-json.php ' ;
143- }
144- }
145-
146- /*
147- * Check if the request is authorized.
148- *
149- * @see https://www.w3.org/wiki/SocialCG/ActivityPub/Primer/Authentication_Authorization#Authorized_fetch
150- * @see https://swicg.github.io/activitypub-http-signature/#authorized-fetch
151- */
152- if ( $ activitypub_template && use_authorized_fetch () ) {
153- $ verification = Signature::verify_http_signature ( $ _SERVER );
154- if ( \is_wp_error ( $ verification ) ) {
155- \status_header ( 401 );
156-
157- // Fallback as template_loader can't return http headers.
158- return $ template ;
159- }
160- }
161-
162- if ( $ activitypub_template ) {
163- \set_query_var ( 'is_404 ' , false );
164-
165- // Check if header already sent.
166- if ( ! \headers_sent () ) {
167- // Send 200 status header.
168- \status_header ( 200 );
169- }
170-
171- return $ activitypub_template ;
172- }
173-
174- return $ template ;
175- }
176-
177- /**
178- * Add the 'self' link to the header.
179- */
180- public static function add_headers () {
181- $ id = Query::get_instance ()->get_activitypub_object_id ();
182-
183- if ( ! $ id ) {
184- return ;
185- }
186-
187- if ( ! headers_sent () ) {
188- \header ( 'Link: < ' . esc_url ( $ id ) . '>; title="ActivityPub (JSON)"; rel="alternate"; type="application/activity+json" ' , false );
189-
190- if ( \get_option ( 'activitypub_vary_header ' , '1 ' ) ) {
191- // Send Vary header for Accept header.
192- \header ( 'Vary: Accept ' , false );
193- }
194- }
195-
196- add_action (
197- 'wp_head ' ,
198- function () use ( $ id ) {
199- echo PHP_EOL . '<link rel="alternate" title="ActivityPub (JSON)" type="application/activity+json" href=" ' . esc_url ( $ id ) . '" /> ' . PHP_EOL ;
200- }
201- );
202- }
203-
204- /**
205- * Remove trailing slash from ActivityPub @username requests.
206- *
207- * @param string $redirect_url The URL to redirect to.
208- * @param string $requested_url The requested URL.
209- *
210- * @return string $redirect_url The possibly-unslashed redirect URL.
211- */
212- public static function no_trailing_redirect ( $ redirect_url , $ requested_url ) {
213- if ( get_query_var ( 'actor ' ) ) {
214- return $ requested_url ;
215- }
216-
217- return $ redirect_url ;
218- }
219-
220- /**
221- * Add support for `p` and `author` query vars.
222- *
223- * @param string $redirect_url The URL to redirect to.
224- * @param string $requested_url The requested URL.
225- *
226- * @return string $redirect_url
227- */
228- public static function redirect_canonical ( $ redirect_url , $ requested_url ) {
229- if ( ! is_activitypub_request () ) {
230- return $ redirect_url ;
231- }
232-
233- $ query = \wp_parse_url ( $ requested_url , PHP_URL_QUERY );
234-
235- if ( ! $ query ) {
236- return $ redirect_url ;
237- }
238-
239- $ query_params = \wp_parse_args ( $ query );
240- unset( $ query_params ['activitypub ' ] );
241-
242- if ( 1 !== count ( $ query_params ) ) {
243- return $ redirect_url ;
244- }
245-
246- if ( isset ( $ query_params ['p ' ] ) ) {
247- return null ;
248- }
249-
250- if ( isset ( $ query_params ['author ' ] ) ) {
251- return null ;
252- }
253-
254- return $ requested_url ;
255- }
256-
257- /**
258- * Custom redirects for ActivityPub requests.
259- *
260- * @return void
261- */
262- public static function template_redirect () {
263- global $ wp_query ;
264-
265- $ comment_id = get_query_var ( 'c ' , null );
266-
267- // Check if it seems to be a comment.
268- if ( $ comment_id ) {
269- $ comment = get_comment ( $ comment_id );
270-
271- // Load a 404-page if `c` is set but not valid.
272- if ( ! $ comment ) {
273- $ wp_query ->set_404 ();
274- return ;
275- }
276-
277- // Stop if it's not an ActivityPub comment.
278- if ( is_activitypub_request () && ! is_local_comment ( $ comment ) ) {
279- return ;
280- }
281-
282- wp_safe_redirect ( get_comment_link ( $ comment ) );
283- exit ;
284- }
285-
286- $ actor = get_query_var ( 'actor ' , null );
287- if ( $ actor ) {
288- $ actor = Actors::get_by_username ( $ actor );
289- if ( ! $ actor || \is_wp_error ( $ actor ) ) {
290- $ wp_query ->set_404 ();
291- return ;
292- }
293-
294- if ( is_activitypub_request () ) {
295- return ;
296- }
297-
298- \wp_safe_redirect ( $ actor ->get_url (), 301 );
299- exit ;
300- }
301- }
302-
303- /**
304- * Add the 'activitypub' query variable so WordPress won't mangle it.
305- *
306- * @param array $vars The query variables.
307- *
308- * @return array The query variables.
309- */
310- public static function add_query_vars ( $ vars ) {
311- $ vars [] = 'activitypub ' ;
312- $ vars [] = 'preview ' ;
313- $ vars [] = 'author ' ;
314- $ vars [] = 'actor ' ;
315- $ vars [] = 'type ' ;
316- $ vars [] = 'c ' ;
317- $ vars [] = 'p ' ;
318-
319- return $ vars ;
320- }
321-
32293 /**
32394 * Replaces the default avatar.
32495 *
@@ -393,43 +164,22 @@ public static function untrash_post( $post_id ) {
393164 }
394165
395166 /**
396- * Add rewrite rules.
167+ * Flush rewrite rules.
397168 */
398- public static function add_rewrite_rules () {
399- /*
400- * If another system needs to take precedence over the ActivityPub rewrite rules,
401- * they can define their own and will manually call the appropriate functions as required.
402- */
403- if ( ACTIVITYPUB_DISABLE_REWRITES ) {
404- return ;
405- }
406-
407- if ( ! \class_exists ( 'Webfinger ' ) ) {
408- \add_rewrite_rule (
409- '^.well-known/webfinger ' ,
410- 'index.php?rest_route=/ ' . ACTIVITYPUB_REST_NAMESPACE . '/webfinger ' ,
411- 'top '
412- );
413- }
414-
415- if ( ! \class_exists ( 'Nodeinfo_Endpoint ' ) && true === (bool ) \get_option ( 'blog_public ' , 1 ) ) {
416- \add_rewrite_rule (
417- '^.well-known/nodeinfo ' ,
418- 'index.php?rest_route=/ ' . ACTIVITYPUB_REST_NAMESPACE . '/nodeinfo ' ,
419- 'top '
420- );
421- }
422-
423- \add_rewrite_rule ( '^@([\w\-\.]+)\/?$ ' , 'index.php?actor=$matches[1] ' , 'top ' );
424- \add_rewrite_endpoint ( 'activitypub ' , EP_AUTHORS | EP_PERMALINK | EP_PAGES );
169+ public static function flush_rewrite_rules () {
170+ Router::add_rewrite_rules ();
171+ \flush_rewrite_rules ();
425172 }
426173
427174 /**
428- * Flush rewrite rules.
175+ * Add rewrite rules.
176+ *
177+ * @deprecated unreleased Use {@see Router::add_rewrite_rules()}.
429178 */
430- public static function flush_rewrite_rules () {
431- self ::add_rewrite_rules ();
432- \flush_rewrite_rules ();
179+ public static function add_rewrite_rules () {
180+ _deprecated_function ( __FUNCTION__ , 'unreleased ' , '\Activitypub\Router::add_rewrite_rules() ' );
181+
182+ Router::add_rewrite_rules ();
433183 }
434184
435185 /**
0 commit comments