| @@ -6,8 +6,10 @@ | ||
| 6 | 6 | */ |
| 7 | 7 | |
| 8 | 8 | /** |
| 9 | 9 | * An SEO expert walks into a bar, bars, pub, public house, Irish pub, drinks, beer, wine, liquor, Grey Goose, Cristal... |
| 10 | + * | |
| 11 | + * @phan-constructor-used-for-side-effects | |
| 10 | 12 | */ |
| 11 | 13 | class Jetpack_SEO { |
| 12 | 14 | /** |
| 13 | 15 | * Constructor. |
| @@ -56,11 +58,44 @@ | ||
| 56 | 58 | add_filter( 'jetpack_open_graph_tags', array( $this, 'set_custom_og_tags' ) ); |
| 57 | 59 | Jetpack_SEO_Posts::register_post_meta(); |
| 58 | 60 | // Exclude posts with 'jetpack_seo_noindex' set true from the Jetpack sitemap. |
| 59 | 61 | add_filter( 'jetpack_sitemap_skip_post', array( 'Jetpack_SEO_Posts', 'exclude_noindex_posts_from_jetpack_sitemap' ), 10, 2 ); |
| 62 | + add_action( 'rest_api_init', array( $this, 'add_custom_field_post_type_meta' ) ); | |
| 60 | 63 | } |
| 61 | 64 | |
| 62 | 65 | /** |
| 66 | + * Add custom field meta to all public post types that don't already have it. | |
| 67 | + */ | |
| 68 | + public function add_custom_field_post_type_meta() { | |
| 69 | + /** | |
| 70 | + * Filter the list of post types for which custom fields support is added. | |
| 71 | + * | |
| 72 | + * This filter allows modification of the post types that will be processed | |
| 73 | + * to add support for custom fields if they do not already support it. | |
| 74 | + * | |
| 75 | + * @since 14.2 | |
| 76 | + * | |
| 77 | + * @param array $post_types An array of post type names. | |
| 78 | + */ | |
| 79 | + $post_types = apply_filters( | |
| 80 | + 'jetpack_seo_custom_field_post_types', | |
| 81 | + get_post_types( | |
| 82 | + array( | |
| 83 | + 'public' => true, | |
| 84 | + 'show_ui' => true, | |
| 85 | + '_builtin' => false, | |
| 86 | + ) | |
| 87 | + ) | |
| 88 | + ); | |
| 89 | + | |
| 90 | + foreach ( $post_types as $post_type ) { | |
| 91 | + if ( ! post_type_supports( $post_type, 'custom-fields' ) ) { | |
| 92 | + add_post_type_support( $post_type, 'custom-fields' ); | |
| 93 | + } | |
| 94 | + } | |
| 95 | + } | |
| 96 | + | |
| 97 | + /** | |
| 63 | 98 | * Helper method to fetch authors. |
| 64 | 99 | */ |
| 65 | 100 | private function get_authors() { |
| 66 | 101 | global $wp_query; |
| @@ -67,8 +102,11 @@ | ||
| 67 | 102 | |
| 68 | 103 | $authors = array(); |
| 69 | 104 | |
| 70 | 105 | foreach ( $wp_query->posts as $post ) { |
| 106 | + if ( ! $post instanceof WP_Post ) { | |
| 107 | + continue; | |
| 108 | + } | |
| 71 | 109 | $authors[] = get_the_author_meta( 'display_name', (int) $post->post_author ); |
| 72 | 110 | } |
| 73 | 111 | |
| 74 | 112 | $authors = array_unique( $authors ); |
| @@ -88,9 +126,14 @@ | ||
| 88 | 126 | if ( ! empty( $custom_title ) ) { |
| 89 | 127 | $tags['og:title'] = $custom_title; |
| 90 | 128 | } |
| 91 | 129 | |
| 92 | - $post_custom_description = Jetpack_SEO_Posts::get_post_custom_description( get_post() ); | |
| 130 | + // On archives and a latest-posts homepage, get_post() returns the first post in | |
| 131 | + // the loop, whose description does not represent the page being viewed. Only use | |
| 132 | + // the per-post custom description when we are actually on that singular post/page. | |
| 133 | + $post_custom_description = is_singular() | |
| 134 | + ? Jetpack_SEO_Posts::get_post_custom_description( get_post() ) | |
| 135 | + : ''; | |
| 93 | 136 | $front_page_meta = Jetpack_SEO_Utils::get_front_page_meta_description(); |
| 94 | 137 | |
| 95 | 138 | if ( class_exists( 'woocommerce' ) && is_shop() ) { |
| 96 | 139 | $shop_page_id = get_option( 'woocommerce_shop_page_id' ); |
| @@ -160,9 +203,9 @@ | ||
| 160 | 203 | |
| 161 | 204 | $meta['description'] = sprintf( |
| 162 | 205 | /* translators: first property is an user's display name, the second is the site's title. */ |
| 163 | 206 | _x( 'Read all of the posts by %1$s on %2$s', 'Read all of the posts by Author Name on Blog Title', 'jetpack' ), |
| 164 | - isset( $obj->display_name ) ? $obj->display_name : __( 'the author', 'jetpack' ), | |
| 207 | + $obj->display_name ?? __( 'the author', 'jetpack' ), | |
| 165 | 208 | get_bloginfo( 'title' ) |
| 166 | 209 | ); |
| 167 | 210 | } elseif ( is_tag() || is_category() || is_tax() ) { |
| 168 | 211 | $obj = get_queried_object(); |
| @@ -241,8 +284,12 @@ | ||
| 241 | 284 | * |
| 242 | 285 | * @param array Array that consists of meta name and meta content pairs. |
| 243 | 286 | */ |
| 244 | 287 | $meta = apply_filters( 'jetpack_seo_meta_tags', $meta ); |
| 288 | + | |
| 289 | + if ( ! is_array( $meta ) ) { | |
| 290 | + return; | |
| 291 | + } | |
| 245 | 292 | |
| 246 | 293 | // Output them. |
| 247 | 294 | foreach ( $meta as $name => $content ) { |
| 248 | 295 | if ( ! empty( $content ) ) { |