| @@ -416,8 +416,14 @@ | ||
| 416 | 416 | * @return array Response data |
| 417 | 417 | * @throws \Exception If request fails |
| 418 | 418 | */ |
| 419 | 419 | private function make_request(string $endpoint, array $data): array { |
| 420 | + // The user's daily ceiling and kill switch are enforced here, at the | |
| 421 | + // one place every outbound Gemini call passes through, so no feature | |
| 422 | + // path can bypass them by forgetting to ask first (#448). | |
| 423 | + Spend_Guard::guard(); | |
| 424 | + Spend_Guard::record(); | |
| 425 | + | |
| 420 | 426 | // Send the API key in the x-goog-api-key header rather than the URL |
| 421 | 427 | // query string, which is logged by servers, proxies and referrers. |
| 422 | 428 | $url = "https://generativelanguage.googleapis.com/v1beta/models/{$this->model}:{$endpoint}"; |
| 423 | 429 | |
| @@ -870,9 +876,9 @@ | ||
| 870 | 876 | return [ |
| 871 | 877 | 'optimized_data' => [ |
| 872 | 878 | 'site_name' => sanitize_text_field($data['optimized_data']['site_name'] ?? ''), |
| 873 | 879 | 'project_overview' => sanitize_textarea_field($data['optimized_data']['project_overview'] ?? ''), |
| 874 | - 'key_features' => sanitize_textarea_field($data['optimized_data']['key_features'] ?? ''), | |
| 880 | + 'key_features' => \ThinkRank\SEO\LLMs_Txt_Manager::normalize_ai_key_features($data['optimized_data']['key_features'] ?? ''), | |
| 875 | 881 | 'architecture' => sanitize_textarea_field($data['optimized_data']['architecture'] ?? ''), |
| 876 | 882 | 'development_guidelines' => sanitize_textarea_field($data['optimized_data']['development_guidelines'] ?? ''), |
| 877 | 883 | 'ai_context' => sanitize_textarea_field($data['optimized_data']['ai_context'] ?? ''), |
| 878 | 884 | ], |