1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
|
<?php
namespace Yoast\WP\SEO\Builders;
use Yoast\WP\SEO\Exceptions\Indexable\Invalid_Term_Exception; use Yoast\WP\SEO\Exceptions\Indexable\Term_Not_Found_Exception; use Yoast\WP\SEO\Helpers\Taxonomy_Helper; use Yoast\WP\SEO\Models\Indexable;
/** * Term Builder for the indexables. * * Formats the term meta to indexable format. */ class Indexable_Term_Builder { use Indexable_Social_Image_Trait;
/** * Holds the taxonomy helper instance. * * @var Taxonomy_Helper */ private $taxonomy;
/** * Indexable_Term_Builder constructor. * * @param Taxonomy_Helper $taxonomy The taxonomy helper. */ public function __construct( Taxonomy_Helper $taxonomy ) { $this->taxonomy = $taxonomy; }
/** * Formats the data. * * @param int $term_id ID of the term to save data for. * @param Indexable $indexable The indexable to format. * * @return bool|Indexable The extended indexable. False when unable to build. * * @throws Invalid_Term_Exception When the term is invalid. * @throws Term_Not_Found_Exception When the term is not found. */ public function build( $term_id, $indexable ) { $term = \get_term( $term_id );
if ( $term === null ) { throw new Term_Not_Found_Exception(); }
if ( \is_wp_error( $term ) ) { throw new Invalid_Term_Exception( $term->get_error_message() ); }
$term_link = \get_term_link( $term, $term->taxonomy );
if ( \is_wp_error( $term_link ) ) { throw new Invalid_Term_Exception( $term_link->get_error_message() ); }
$term_meta = $this->taxonomy->get_term_meta( $term );
$indexable->object_id = $term_id; $indexable->object_type = 'term'; $indexable->object_sub_type = $term->taxonomy; $indexable->permalink = $term_link; $indexable->blog_id = \get_current_blog_id();
$indexable->primary_focus_keyword_score = $this->get_keyword_score( $this->get_meta_value( 'wpseo_focuskw', $term_meta ), $this->get_meta_value( 'wpseo_linkdex', $term_meta ) );
$indexable->is_robots_noindex = $this->get_noindex_value( $this->get_meta_value( 'wpseo_noindex', $term_meta ) ); $indexable->is_public = ( $indexable->is_robots_noindex === null ) ? null : ! $indexable->is_robots_noindex;
$this->reset_social_images( $indexable );
foreach ( $this->get_indexable_lookup() as $meta_key => $indexable_key ) { $indexable->{$indexable_key} = $this->get_meta_value( $meta_key, $term_meta ); }
if ( empty( $indexable->breadcrumb_title ) ) { $indexable->breadcrumb_title = $term->name; }
$this->handle_social_images( $indexable );
$indexable->is_cornerstone = $this->get_meta_value( 'wpseo_is_cornerstone', $term_meta );
// Not implemented yet. $indexable->is_robots_nofollow = null; $indexable->is_robots_noarchive = null; $indexable->is_robots_noimageindex = null; $indexable->is_robots_nosnippet = null;
return $indexable; }
/** * Converts the meta noindex value to the indexable value. * * @param string $meta_value Term meta to base the value on. * * @return bool|null */ protected function get_noindex_value( $meta_value ) { if ( $meta_value === 'noindex' ) { return true; }
if ( $meta_value === 'index' ) { return false; }
return null; }
/** * Determines the focus keyword score. * * @param string $keyword The focus keyword that is set. * @param int $score The score saved on the meta data. * * @return null|int Score to use. */ protected function get_keyword_score( $keyword, $score ) { if ( empty( $keyword ) ) { return null; }
return $score; }
/** * Retrieves the lookup table. * * @return array Lookup table for the indexable fields. */ protected function get_indexable_lookup() { return [ 'wpseo_canonical' => 'canonical', 'wpseo_focuskw' => 'primary_focus_keyword', 'wpseo_title' => 'title', 'wpseo_desc' => 'description', 'wpseo_content_score' => 'readability_score', 'wpseo_bctitle' => 'breadcrumb_title', 'wpseo_opengraph-title' => 'open_graph_title', 'wpseo_opengraph-description' => 'open_graph_description', 'wpseo_opengraph-image' => 'open_graph_image', 'wpseo_opengraph-image-id' => 'open_graph_image_id', 'wpseo_twitter-title' => 'twitter_title', 'wpseo_twitter-description' => 'twitter_description', 'wpseo_twitter-image' => 'twitter_image', 'wpseo_twitter-image-id' => 'twitter_image_id', ]; }
/** * Retrieves a meta value from the given meta data. * * @param string $meta_key The key to extract. * @param array $term_meta The meta data. * * @return null|string The meta value. */ protected function get_meta_value( $meta_key, $term_meta ) { if ( ! $term_meta || ! \array_key_exists( $meta_key, $term_meta ) ) { return null; }
$value = $term_meta[ $meta_key ]; if ( \is_string( $value ) && $value === '' ) { return null; }
return $value; }
/** * Finds an alternative image for the social image. * * @param Indexable $indexable The indexable. * * @return array|bool False when not found, array with data when found. */ protected function find_alternative_image( Indexable $indexable ) { $content_image = $this->image->get_term_content_image( $indexable->object_id ); if ( $content_image ) { return [ 'image' => $content_image, 'source' => 'first-content-image', ]; }
return false; } }
|