Google Search Console - v1.0.0
GET /top-queries
Returns the top search queries by clicks for a rolling range.
- Route name:
google-search-console.top-queries - Middleware:
web,auth - Controller:
ArtisanPackUI\GoogleSearchConsole\Http\Controllers\TopQueriesController - Consumed by:
<TopQueriesTable />(React) and<TopQueriesTable />(Vue) viaresources/js/shared/top-queries.ts.
Query parameters
| Parameter | Type | Default | Clamp | Notes |
|---|---|---|---|---|
days |
int |
28 |
1..DateRange::MAX_DAYS |
Any non-scalar → 28. |
limit |
int |
TopQueriesFetcher::DEFAULT_LIMIT (50) |
1..1000 |
Number of rows to pull from Google. |
Behavior
One searchAnalytics.query call with dimension query, row limit limit. Rows come back sorted by clicks descending — the API doesn't accept an orderBys field, so the returned order is what Google chose. The React and Vue components sort client-side after the fetch; the shipped Livewire component sorts and paginates over the visible page in-memory.
Successful response
{
"range": {
"startDate": "2026-01-01",
"endDate": "2026-01-28"
},
"rows": [
{ "query": "buy shoes", "clicks": 50, "impressions": 200, "ctr": 0.25, "position": 2 },
{ "query": "cheap shoes", "clicks": 20, "impressions": 100, "ctr": 0.2, "position": 4 },
{ "query": "running shoes", "clicks": 15, "impressions": 90, "ctr": 0.16, "position": 5 }
]
}
An empty rows array is a valid response — it means Google returned zero queries in the range. The components render an empty state.
Error responses
Standard shape (see HTTP Endpoints#Error response shapes):
401 unauthenticated409 not_connected501 base_not_installed502 reporting_error
Example calls
# Default: last 28 days, top 50 queries
curl 'https://your-app.test/google-search-console/top-queries' \
--cookie 'laravel_session=...'
# Last 90 days, top 200 queries
curl 'https://your-app.test/google-search-console/top-queries?days=90&limit=200' \
--cookie 'laravel_session=...'
# Way over cap — clamps to 1000
curl 'https://your-app.test/google-search-console/top-queries?limit=999999' \
--cookie 'laravel_session=...'
Testing
Http::fake( [
'*' => Http::response( [
'rows' => [
[ 'keys' => [ 'high' ], 'clicks' => 50, 'impressions' => 200, 'ctr' => 0.25, 'position' => 2 ],
[ 'keys' => [ 'mid' ], 'clicks' => 20, 'impressions' => 100, 'ctr' => 0.2, 'position' => 4 ],
],
], 200 ),
] );
$this->actingAs( $user )
->getJson( '/google-search-console/top-queries?days=7&limit=25' )
->assertOk()
->assertJsonPath( 'rows.0.query', 'high' )
->assertJsonPath( 'rows.0.clicks', 50.0 );