PluginProbe
WPBot – AI ChatBot for Live Support, Lead Generation, WordPress Automation, AI Services / 7.1.5
WPBot – AI ChatBot for Live Support, Lead Generation, WordPress Automation, AI Services v7.1.5
8.8.4 8.8.3 8.8.2 8.8.1 8.8.0 8.7.9 8.7.8 8.7.7 8.7.6 8.7.5 8.7.4 8.7.3 8.7.2 8.7.1 8.7.0 8.6.9 8.6.8 8.6.7 8.6.6 8.6.5 8.6.4 8.6.2 8.6.1 8.6.0 8.5.9 All 540 releases
chatbot / includes / integration / gemini / qcld-bot-gemini.php

qcld-bot-gemini.php in WPBot – AI ChatBot for Live Support, Lead Generation, WordPress Automation, AI Services 7.1.5, at includes/integration/gemini/qcld-bot-gemini.php

377 lines 14.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 if (!defined('ABSPATH')) exit; // Exit if accessed directly
3
4 if(!class_exists('qcld_wpgemini_addons')){
5
6
7 /**
8 * Main Class.
9 */
10 final class qcld_wpgemini_addons
11 {
12 private $id = 'Open AI';
13
14 /**
15 * WPBot Pro version.
16 *
17 * @var string
18 */
19 public $version = '1.0.6';
20
21 /**
22 * WPBot Pro helper.
23 *
24 * @var object
25 */
26 public $helper;
27
28 /**
29 * The single instance of the class.
30 *
31 * @var qcld_wb_Chatbot
32 * @since 1.0.0
33 */
34 protected static $_instance = null;
35
36 /**
37 * Main wpbot Instance.
38 *
39 * Ensures only one instance of wpbot is loaded or can be loaded.
40 *
41 * @return qcld_wb_Chatbot - Main instance.
42 * @since 1.0.0
43 * @static
44 */
45 public static function instance() {
46 if ( is_null( self::$_instance ) ) {
47 self::$_instance = new self();
48 }
49
50 return self::$_instance;
51 }
52
53 public $response_list;
54
55 /**
56 * Constructor
57 */
58 public function __construct()
59 {
60
61 $this->includes();
62 add_action('wp_ajax_gemini_response',[$this,'gemini_response_callback']);
63 add_action('wp_ajax_nopriv_gemini_response', [$this, 'gemini_response_callback']);
64 add_action('wp_ajax_qcld_gemini_settings_option',[$this,'qcld_gemini_settings_option_callback']);
65
66 add_action('wp_ajax_update_settings_option', [$this, 'update_settings_option_callback']);
67
68 if (is_admin() && !empty($_GET["page"]) && (($_GET["page"] == "openai-panel_dashboard") || ($_GET["page"] == "openai-panel_file") || ($_GET["page"] == "openai-panel_help"))) {
69 add_action('admin_enqueue_scripts', array($this, 'qcld_wb_chatbot_admin_scripts'));
70 }
71 //add_action('wp_enqueue_scripts', array($this, 'qcld_wb_chatbot_gemini_scripts'));
72 add_action('admin_enqueue_scripts', array($this, 'qcld_wb_chatbot_gemini_admin_scripts'));
73 }
74
75
76
77 public function qcld_wb_chatbot_gemini_admin_scripts() {
78 if ( ! current_user_can( 'manage_options' ) ) {
79 return ;
80 }
81 wp_register_script(
82 'qcld-wp-chatbot-gemini-admin-js',
83 QCLD_wpCHATBOT_PLUGIN_URL . 'includes/integration/gemini/assets/js/qcld-wp-gemini-admin.js',
84 array('jquery'),
85 QCLD_wpCHATBOT_VERSION,
86 true
87 );
88
89 // Localize the script with necessary data
90 wp_localize_script('qcld-wp-chatbot-gemini-admin-js', 'ajax_object', array(
91 'ajax_url' => admin_url('admin-ajax.php'),
92 'ajax_nonce' => wp_create_nonce('wp_chatbot'),
93 'gemini_api_key' => get_option('qcld_gemini_api_key'),
94 'gemini_enabled' => get_option('qcld_gemini_enabled'),
95 'qcld_gemini_append_content' => get_option('qcld_gemini_append_content'),
96 'qcld_gemini_prepend_content' => get_option('qcld_gemini_prepend_content')
97 ));
98
99 wp_enqueue_script('qcld-wp-chatbot-gemini-admin-js');
100 }
101
102 /**
103 * Define wpbot Constants.
104 *
105 * @return void
106 * @since 1.0.0
107 */
108 public function includes() {
109 require_once( QCLD_wpCHATBOT_PLUGIN_DIR_PATH . "includes/Parsedown.php" );
110 require_once( QCLD_wpCHATBOT_PLUGIN_DIR_PATH . "includes/class-common-function.php" );
111 }
112 public function qcld_gemini_settings_option_callback() {
113 $nonce = sanitize_text_field($_POST['nonce']);
114 if (!wp_verify_nonce($nonce, 'wp_chatbot')) {
115 wp_send_json(array('success' => false, 'msg' => esc_html__('Failed in Security check', 'sm')));
116 wp_die();
117 } else {
118 $gemini_api_key = sanitize_text_field($_POST['gemini_api_key']);
119 $gemini_enabled = sanitize_text_field($_POST['gemini_enabled']);
120 $qcld_gemini_page_suggestion_enabled = sanitize_text_field($_POST['qcld_gemini_page_suggestion_enabled']);
121 $gemini_is_context_awareness_enabled = sanitize_text_field($_POST['gemini_is_context_awareness_enabled']);
122 $qcld_gemini_append_content = sanitize_text_field($_POST['qcld_gemini_append_content']) ?? '';
123 $qcld_gemini_prepend_content = sanitize_text_field($_POST['qcld_gemini_prepend_content']) ?? '';
124 if($gemini_api_key != '') {
125 update_option('qcld_gemini_api_key', $gemini_api_key);
126 }
127 if($gemini_enabled != '') {
128 update_option('qcld_gemini_enabled', $gemini_enabled);
129 }
130 if($gemini_enabled == '1') {
131 update_option('ai_enabled', 0);
132 update_option('qcld_openrouter_enabled', 0);
133
134 } else {
135 update_option('ai_enabled', 1);
136 }
137 update_option('qcld_gemini_page_suggestion_enabled', $qcld_gemini_page_suggestion_enabled);
138 update_option('gemeni_context_awareness_enabled', $gemini_is_context_awareness_enabled);
139 update_option( 'qcld_openai_relevant_post', $_POST['openai_post_type'] );
140
141 update_option('qcld_gemini_append_content', $qcld_gemini_append_content);
142 update_option('qcld_gemini_prepend_content', $qcld_gemini_prepend_content);
143
144 }
145 echo json_encode($gemini_enabled);
146 wp_die();
147 }
148 public function gemini_response_callback() {
149
150 $gemini_api_key = get_option( 'qcld_gemini_api_key' );
151 $keyword = isset($_POST['keyword']) ? $_POST['keyword'] : ''; // phpcs:ignore WordPress.Security.NonceVerification.Missing
152
153 $relevant_pagelink = Qcld_WPBot_Common_Functions::qcpd_relevant_pagelink( $keyword );
154 $relevant_pagelink = array_slice( $relevant_pagelink, 0, 5, true );
155
156 if ( ( get_option( 'page_suggestion_enabled' ) == '1' ) && count( $relevant_pagelink ) > 0 ) {
157 $relevant_post_link = maybe_unserialize( get_option( 'qlcd_wp_chatbot_relevant_post_link_openai' ) );
158 // Always use get_locale() to avoid undefined function error
159 $locale = get_locale();
160 if ( is_array( $relevant_post_link ) && isset( $relevant_post_link[ $locale ] ) && is_array( $relevant_post_link[ $locale ] ) ) {
161 $relevant_pagelinks = '<br><br><p><em>' . implode( '', $relevant_post_link[ $locale ] ) . '</em><p>' . implode( '</br>', $relevant_pagelink );
162 } else {
163 // Fallback: try to use $locale, but check if key exists
164 $em_text = '';
165 if ( is_array( $relevant_post_link ) && isset( $relevant_post_link[ $locale ] ) ) {
166 $em_text = is_array( $relevant_post_link[ $locale ] ) ? implode( '', $relevant_post_link[ $locale ] ) : $relevant_post_link[ $locale ];
167 }
168 $relevant_pagelinks = '<br><br><p><em>' . $em_text . '</em><p>' . implode( '</br>', $relevant_pagelink );
169 }
170 } else {
171 $relevant_pagelinks = '';
172 }
173
174 $Parsedown = new Parsedown();
175
176 // Build context-aware content with system instructions
177 $system_instructions = '';
178 if ( get_option('gemeni_context_awareness_enabled') == '1' ) {
179 $site_name = get_bloginfo('name');
180 $site_desc = get_bloginfo('description');
181
182 // Get current page URL and title more reliably
183 $current_url = '';
184 $page_title = '';
185 $page_summary = '';
186
187 // Try to get from referrer first
188 $ref = wp_get_referer();
189 if ( ! $ref && isset($_SERVER['HTTP_REFERER']) ) {
190 $ref = esc_url_raw( $_SERVER['HTTP_REFERER'] );
191 }
192
193 if ( $ref ) {
194 $current_url = $ref;
195
196 // Try to get post/page by URL, fallback to query param if needed.
197 $post_id = url_to_postid( $ref );
198 if ( ! $post_id && isset( $_GET['p'] ) ) {
199 $post_id = intval( $_GET['p'] );
200 }
201 if ( $post_id ) {
202 $page_title = get_the_title( $post_id );
203 $raw_content = get_post_field( 'post_content', $post_id );
204 $text_content = wp_strip_all_tags( $raw_content );
205 $page_summary = wp_trim_words( $text_content, 120, '…' );
206 } else {
207 // If not a post/page, try to extract title from URL or use current page
208 $parsed_url = parse_url( $ref );
209 if ( isset($parsed_url['path']) ) {
210 $path = trim($parsed_url['path'], '/');
211 if ( ! empty($path) ) {
212 // Try to get title from current page if we're on it
213 if ( is_singular() ) {
214 $page_title = get_the_title();
215 $raw_content = get_the_content();
216 $text_content = wp_strip_all_tags( $raw_content );
217 $page_summary = wp_trim_words( $text_content, 120, '…' );
218 } elseif ( is_archive() ) {
219 $page_title = get_the_archive_title();
220 } elseif ( is_search() ) {
221 $page_title = 'Search Results';
222 } elseif ( is_404() ) {
223 $page_title = 'Page Not Found';
224 }
225 }
226 }
227 }
228 } else {
229 // Fallback to current page info
230 $current_url = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
231
232 if ( is_singular() ) {
233 $page_title = get_the_title();
234 $raw_content = get_the_content();
235 $text_content = wp_strip_all_tags( $raw_content );
236 $page_summary = wp_trim_words( $text_content, 120, '…' );
237 } elseif ( is_archive() ) {
238 $page_title = get_the_archive_title();
239 } elseif ( is_search() ) {
240 $page_title = 'Search Results';
241 } elseif ( is_404() ) {
242 $page_title = 'Page Not Found';
243 }
244 }
245
246 $context_bits = array();
247 if ( $site_name ) { $context_bits[] = 'Site: ' . $site_name; }
248 if ( $site_desc ) { $context_bits[] = 'Tagline: ' . $site_desc; }
249 if ( $page_title ) { $context_bits[] = 'Page title: ' . $page_title; }
250 if ( $current_url ) { $context_bits[] = 'URL: ' . $current_url; }
251 if ( $page_summary ) { $context_bits[] = 'Page summary: ' . $page_summary; }
252
253 if ( ! empty( $context_bits ) ) {
254 $system_instructions = 'Context Information: ' . implode( '. ', $context_bits ) . '. Please use this context to provide more relevant and accurate responses.';
255 }
256 }
257
258 if ( ( get_option( 'page_suggestion_enabled' ) == '1' ) && count( $relevant_pagelink ) > 0 ) {
259 $relevant_post_link = maybe_unserialize( get_option( 'qlcd_wp_chatbot_relevant_post_link_openai' ) );
260 // Always use get_locale() to avoid undefined function error
261 $locale = get_locale();
262 if ( is_array( $relevant_post_link ) && isset( $relevant_post_link[ $locale ] ) && is_array( $relevant_post_link[ $locale ] ) ) {
263 $relevant_pagelinks = '<br><br><p><em>' . implode( '', $relevant_post_link[ $locale ] ) . '</em><p>' . implode( '</br>', $relevant_pagelink );
264 } else {
265 // Fallback: try to use $locale, but check if key exists
266 $em_text = '';
267 if ( is_array( $relevant_post_link ) && isset( $relevant_post_link[ $locale ] ) ) {
268 $em_text = is_array( $relevant_post_link[ $locale ] ) ? implode( '', $relevant_post_link[ $locale ] ) : $relevant_post_link[ $locale ];
269 }
270 $relevant_pagelinks = '<br><br><p><em>' . $em_text . '</em><p>' . implode( '</br>', $relevant_pagelink );
271 }
272 } else {
273 $relevant_pagelinks = '';
274 }
275
276 // Gemini API expects a different payload and endpoint
277 $api_url = 'https://generativelanguage.googleapis.com/v1beta/models/gemini-2.0-flash' . ':generateContent';
278
279 // Build formatted messages with system instructions
280 $formatted_messages = [];
281
282 // Add system instructions as first user message if context is enabled
283 if ( ! empty( $system_instructions ) ) {
284 $formatted_messages[] = [
285 'role' => 'user',
286 'parts' => [
287 ['text' => "[System Instructions] " . $system_instructions]
288 ]
289 ];
290
291 // Add model response to acknowledge system instructions
292 $formatted_messages[] = [
293 'role' => 'model',
294 'parts' => [
295 ['text' => "I understand and will follow these instructions."]
296 ]
297 ];
298 }
299
300 // Add the actual user query
301 $formatted_messages[] = [
302 'role' => 'user',
303 'parts' => [
304 ['text' => $keyword]
305 ]
306 ];
307
308 $data = array(
309 'contents' => $formatted_messages,
310 );
311
312 // Use WordPress wp_remote_post for better error handling and consistency
313 $args = array(
314 'body' => json_encode($data),
315 'headers' => array(
316 'Content-Type' => 'application/json',
317 'X-goog-api-key' => $gemini_api_key,
318 ),
319 'timeout' => 60,
320 'redirection' => 5,
321 'blocking' => true,
322 'httpversion' => '1.0',
323 'sslverify' => true,
324 );
325
326 $result = wp_remote_post($api_url, $args);
327
328 // Check for WordPress errors
329 if (is_wp_error($result)) {
330 $response['status'] = 'error';
331 $response['message'] = 'API request failed: ' . $result->get_error_message();
332 } else {
333 $http_code = wp_remote_retrieve_response_code($result);
334 $response_body = wp_remote_retrieve_body($result);
335
336 if ($http_code === 200) {
337 $msg = json_decode($response_body);
338 // Gemini API returns candidates[0]->content->parts[0]->text
339 if (
340 isset($msg->candidates[0]->content->parts[0]->text)
341 && !empty($msg->candidates[0]->content->parts[0]->text)
342 ) {
343 $response['status'] = 'success';
344 $response['message'] = $Parsedown->text( $msg->candidates[0]->content->parts[0]->text ) . $relevant_pagelinks;
345 } else {
346 $response['status'] = 'error';
347 $response['message'] = 'Invalid response format from Gemini API';
348 }
349 } else {
350 $response['status'] = 'error';
351 $response['message'] = 'API request failed with HTTP code: ' . $http_code;
352 }
353 }
354 echo json_encode( $response );
355 wp_die();
356 }
357 public function update_settings_option_callback(){
358 update_option('disable_wp_chatbot_site_search',1);
359 update_option('enable_wp_chatbot_post_content', '');
360 }
361 }
362
363 /**
364 * @return qcld_wpopenai_addon
365 */
366 if(!function_exists('qcld_wpgemini_addons')){
367 function qcld_wpgemini_addons() {
368 $qcld_wpgemini_addon = new qcld_wpgemini_addons();
369 return $qcld_wpgemini_addon->instance();
370
371 }
372 }
373
374 //fire off the plugin
375 qcld_wpgemini_addons();
376
377 }