PluginProbe
ThinkRank AI SEO – AI SEO Plugin for WordPress: Schema, XML Sitemaps, Meta Tags, Search Console & Local SEO / 2.14.2
ThinkRank AI SEO – AI SEO Plugin for WordPress: Schema, XML Sitemaps, Meta Tags, Search Console & Local SEO v2.14.2
2.14.2 2.14.1 2.14.0 2.13.0 2.12.0 2.11.0 2.10.0 2.9.0 2.8.0 2.7.0 2.6.0 2.5.0 2.4.0 2.3.0 2.2.0 2.1.1 2.1.0 2.0.2 2.0.1 2.0.0 1.32.0 1.31.0 1.30.0 1.29.0 1.28.0 All 57 releases
← All changes | includes/integrations/class-google-search-console-client.php +22 -2 2.11.0 → 2.14.2 View file →
@@ -61,10 +61,16 @@
61 61 'message' => 'Google Search Console API connection successful',
62 62 'sites_count' => count($result['siteEntry'] ?? [])
63 63 ];
64 64 } catch (\Exception $e) {
65 + // `message` as well as `error`: the success branch above reports
66 + // its outcome as `message`, and every consumer reads that key, so
67 + // a failure that only set `error` was reported to the admin as an
68 + // error with no reason at all (#852). `error` is kept for any
69 + // caller that already reads it.
65 70 return [
66 71 'success' => false,
72 + 'message' => $e->getMessage(),
67 73 'error' => $e->getMessage()
68 74 ];
69 75 }
70 76 }
@@ -95,10 +101,15 @@
95 101 // Check if the site is already verified by listing sites
96 102 $sites = $this->list_sites();
97 103 $site_verified = false;
98 104
105 + // A domain property is compared in its punycode form, so an IDN
106 + // matches whichever form the account lists it in.
107 + $wanted = \ThinkRank\Core\Url_Validator::search_console_domain_property($site_url) ?? $site_url;
108 +
99 109 foreach ($sites['siteEntry'] ?? [] as $site) {
100 - if ($site['siteUrl'] === $site_url) {
110 + $listed = (string) ($site['siteUrl'] ?? '');
111 + if ($listed === $site_url || (\ThinkRank\Core\Url_Validator::search_console_domain_property($listed) ?? $listed) === $wanted) {
101 112 $site_verified = true;
102 113 break;
103 114 }
104 115 }
@@ -242,12 +253,15 @@
242 253 * @param string $site_url Site URL to get data for
243 254 * @param string $start_date Start date (Y-m-d)
244 255 * @param string $end_date End date (Y-m-d)
245 256 * @param int $row_limit Maximum rows to return
257 + * @param array $dimensions Dimensions to group by
258 + * @param array $filters Optional dimension filters (ANDed), each
259 + * {dimension, operator, expression}. @since 2.15.0
246 260 * @return array Raw rows from GSC API
247 261 * @throws \Exception If API request fails
248 262 */
249 - public function get_search_performance_by_dates(string $site_url, string $start_date, string $end_date, int $row_limit = 500, array $dimensions = ['query']): array {
263 + public function get_search_performance_by_dates(string $site_url, string $start_date, string $end_date, int $row_limit = 500, array $dimensions = ['query'], array $filters = []): array {
250 264 $endpoint = '/sites/' . rawurlencode($site_url) . '/searchAnalytics/query';
251 265
252 266 $request_body = [
253 267 'startDate' => $start_date,
@@ -258,8 +272,14 @@
258 272 // data — matches what the Search Console web UI displays, so the
259 273 // last 2-4 days aren't missing.
260 274 'dataState' => 'all',
261 275 ];
276 +
277 + // Optional dimension filters, ANDed, e.g. one page's queries:
278 + // [['dimension' => 'page', 'operator' => 'equals', 'expression' => $url]].
279 + if (!empty($filters)) {
280 + $request_body['dimensionFilterGroups'] = [['filters' => array_values($filters)]];
281 + }
262 282
263 283 $full_url = self::API_BASE_URL . $endpoint;
264 284 $response = $this->make_request($full_url, $request_body, 'POST');
265 285