PluginProbe ʕ •ᴥ•ʔ
AI Engine – The Chatbot, AI Framework & MCP for WordPress / 0.3.1
AI Engine – The Chatbot, AI Framework & MCP for WordPress v0.3.1
3.5.9 3.5.8 3.5.7 3.5.6 3.5.5 3.5.4 3.5.3 3.5.2 3.5.1 3.5.0 3.4.9 3.4.8 3.4.7 0.2.1 1.6.91 0.2.2 1.6.92 0.2.3 1.6.93 0.2.4 1.6.94 0.2.5 1.6.95 0.2.6 1.6.96 0.2.7 1.6.97 0.2.8 1.6.98 0.2.9 1.6.99 0.3.0 1.7.0 0.3.1 1.7.1 0.3.2 1.7.2 0.3.3 1.7.3 0.3.4 1.7.4 0.3.5 1.7.5 0.3.6 1.7.6 0.4.0 1.7.7 0.4.1 1.7.8 0.4.2 1.7.9 0.4.3 1.8.0 0.4.4 1.8.1 0.4.5 1.8.2 0.4.6 1.8.3 0.4.7 1.8.4 0.4.8 1.8.5 0.4.9 1.8.6 0.5.0 1.8.7 0.5.1 1.8.8 0.5.2 1.8.9 0.5.3 1.9.0 0.5.4 1.9.1 0.5.5 1.9.2 0.5.6 1.9.3 0.5.7 1.9.4 0.5.8 1.9.5 0.5.9 1.9.6 0.6.0 1.9.7 0.6.1 1.9.8 0.6.2 1.9.81 0.6.3 1.9.82 0.6.4 1.9.83 0.6.5 1.9.84 0.6.6 1.9.85 0.6.7 1.9.86 0.6.8 1.9.87 0.6.9 1.9.88 0.7.0 1.9.89 0.7.1 1.9.90 0.7.2 1.9.91 0.7.3 1.9.92 0.7.4 1.9.93 0.7.5 1.9.94 0.7.6 1.9.95 0.7.7 1.9.96 0.7.8 1.9.97 0.7.9 1.9.98 0.8.0 1.9.99 0.8.1 2.0.0 0.8.2 2.0.1 0.8.3 2.0.2 0.8.4 2.0.3 0.8.5 2.0.4 0.8.6 2.0.5 0.8.7 2.0.6 0.8.8 2.0.7 0.8.9 2.0.8 0.9.0 2.0.9 0.9.2 2.1.0 0.9.3 2.1.1 0.9.4 2.1.2 0.9.5 2.1.3 0.9.6 2.1.4 0.9.7 2.1.5 0.9.8 2.1.6 0.9.81 2.1.7 0.9.82 2.1.8 0.9.83 2.1.9 0.9.84 2.2.0 0.9.85 2.2.1 0.9.86 2.2.2 0.9.87 2.2.3 0.9.88 2.2.4 0.9.89 2.2.5 0.9.9 2.2.51 0.9.91 2.2.52 0.9.92 2.2.53 0.9.93 2.2.54 0.9.94 2.2.56 0.9.95 2.2.57 0.9.96 2.2.6 0.9.97 2.2.60 0.9.98 2.2.61 0.9.99 2.2.62 1.0.0 2.2.63 1.0.01 2.2.70 1.0.1 2.2.80 1.0.2 2.2.81 1.0.3 2.2.90 1.0.4 2.2.91 1.0.5 2.2.92 1.0.6 2.2.93 1.0.7 2.2.94 1.0.8 2.2.95 1.0.9 2.3.0 1.1.0 2.3.1 1.1.1 2.3.2 1.1.2 2.3.3 1.1.3 2.3.4 1.1.4 2.3.5 1.1.5 2.3.6 1.1.6 2.3.7 1.1.7 2.3.8 1.1.8 2.3.9 1.1.9 2.4.0 1.2.0 2.4.1 1.2.1 2.4.2 1.2.2 2.4.3 1.2.21 2.4.4 1.2.3 2.4.5 1.2.30 2.4.6 1.3.0 2.4.7 1.3.1 2.4.8 1.3.2 2.4.9 1.3.3 2.5.0 1.3.31 2.5.1 1.3.32 2.5.2 1.3.33 2.5.3 1.3.34 2.5.4 1.3.35 2.5.5 1.3.36 2.5.6 1.3.37 2.5.7 1.3.38 2.5.8 1.3.39 2.5.9 1.3.40 2.6.0 1.3.41 2.6.1 1.3.42 2.6.2 1.3.43 2.6.3 1.3.44 2.6.5 1.3.45 2.6.6 1.3.46 2.6.7 1.3.47 2.6.8 1.3.48 2.6.9 1.3.49 2.7.0 1.3.50 2.7.1 1.3.51 2.7.2 1.3.52 2.7.3 1.3.53 2.7.4 1.3.54 2.7.5 1.3.56 2.7.6 1.3.57 2.7.7 1.3.58 2.7.8 1.3.59 2.7.9 1.3.60 2.8.0 1.3.61 2.8.1 1.3.62 2.8.2 1.3.63 2.8.3 1.3.64 2.8.4 1.3.65 2.8.5 1.3.66 2.8.6 1.3.67 2.8.7 1.3.68 2.8.8 1.3.69 2.8.9 1.3.70 2.9.0 1.3.71 2.9.1 1.3.72 2.9.2 1.3.73 2.9.3 1.3.74 2.9.4 1.3.75 2.9.5 1.3.76 2.9.6 1.3.77 2.9.7 1.3.78 2.9.8 1.3.79 2.9.9 1.3.80 3.0.0 1.3.81 3.0.1 1.3.82 3.0.2 1.3.83 3.0.3 1.3.84 3.0.4 1.3.85 3.0.5 1.3.86 3.0.6 1.3.87 3.0.7 1.3.88 3.0.8 1.3.89 3.0.9 1.3.90 3.1.0 1.3.91 3.1.1 1.3.92 3.1.2 1.3.93 3.1.3 1.3.94 3.1.4 1.3.95 3.1.5 1.3.96 3.1.6 1.3.97 3.1.7 1.3.98 3.1.8 1.3.99 3.1.9 1.4.0 3.2.0 1.4.1 3.2.1 1.4.2 3.2.2 1.4.3 3.2.3 1.4.4 3.2.4 1.4.5 3.2.5 1.4.6 3.2.6 1.4.7 3.2.7 1.4.8 3.2.8 1.4.9 3.2.9 1.5.0 3.3.0 1.5.1 3.3.1 1.5.2 3.3.2 1.5.3 3.3.3 1.5.4 3.3.4 1.5.5 3.3.5 1.5.6 3.3.6 1.5.7 3.3.7 1.5.8 3.3.8 1.5.9 3.3.9 1.6.0 3.4.0 1.6.1 3.4.1 1.6.2 3.4.2 1.6.3 3.4.3 1.6.5 3.4.4 1.6.51 3.4.5 1.6.52 3.4.6 1.6.53 1.6.54 1.6.55 1.6.56 1.6.57 1.6.58 1.6.59 1.6.60 1.6.61 1.6.62 1.6.63 1.6.64 1.6.65 1.6.66 1.6.67 1.6.68 trunk 1.6.69 0.0.1 1.6.70 0.0.2 1.6.71 0.0.3 1.6.72 0.0.4 1.6.73 0.0.5 1.6.74 0.0.6 1.6.75 0.0.7 1.6.76 0.0.8 1.6.77 0.0.9 1.6.78 0.1.0 1.6.79 0.1.1 1.6.81 0.1.2 1.6.82 0.1.3 1.6.83 0.1.4 1.6.84 0.1.5 1.6.85 0.1.6 1.6.86 0.1.7 1.6.87 0.1.8 1.6.88 0.1.9 1.6.89 0.2.0 1.6.90
ai-engine / classes / modules / chatbot.php
ai-engine / classes / modules Last commit date
chatbot-chatgpt.css 3 years ago chatbot-chatgpt.scss 3 years ago chatbot.php 3 years ago contentaware.php 3 years ago imagesbot.php 3 years ago statistics.php 3 years ago
chatbot.php
358 lines
1 <?php
2
3 class Meow_MWAI_Modules_Chatbot {
4 private $core = null;
5 private $namespace = 'ai-engine/v1';
6
7 public function __construct() {
8 global $mwai_core;
9 $this->core = $mwai_core;
10 if ( is_admin() ) { return; }
11 add_shortcode( 'mwai_chat', array( $this, 'chat' ) );
12 add_shortcode( 'mwai_chatbot', array( $this, 'chat' ) );
13 add_action( 'rest_api_init', array( $this, 'rest_api_init' ) );
14 if ( $this->core->get_option( 'shortcode_chat_inject' ) ) {
15 add_action( 'wp_body_open', array( $this, 'inject_chat' ) );
16 }
17
18 // Only for test now, but later we should probably import the JS/CSS
19 if ( $this->core->get_option( 'shortcode_chat_syntax_highlighting' ) ) {
20 wp_enqueue_script( 'mwai_chatbot',
21 '//cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/highlight.min.js', [], null, false );
22 wp_enqueue_style( 'mwai_chatbot',
23 '//cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/styles/stackoverflow-dark.min.css' );
24 }
25 }
26
27 function rest_api_init() {
28 try {
29 register_rest_route( $this->namespace, '/chat', array(
30 'methods' => 'POST',
31 'callback' => array( $this, 'rest_chat' ),
32 'permission_callback' => '__return_true'
33 ) );
34 }
35 catch ( Exception $e ) {
36 var_dump( $e );
37 }
38 }
39
40 function chatgpt_style( $id ) {
41 $css = file_get_contents( MWAI_PATH . '/classes/modules/chatbot-chatgpt.css' );
42 $css = str_replace( '#mwai-chat-id', "#mwai-chat-{$id}", $css );
43 return "<style>" . $css . "</style>";
44 }
45
46 function rest_chat( $request ) {
47 try {
48 $params = $request->get_json_params();
49 $prompt = $params['prompt'];
50 $model = $params['model'];
51 $temperature = $params['temperature'];
52 $maxTokens = intval( $params['maxTokens'] );
53 $apiKey = $params['apiKey'];
54 $stop = $params['stop'];
55 $query = new Meow_MWAI_QueryText( $prompt, 1024 );
56 if ( $model ) {
57 $query->setModel( $model );
58 }
59 if ( $temperature ) {
60 $query->setTemperature( $temperature );
61 }
62 if ( $maxTokens ) {
63 $query->setMaxTokens( $maxTokens );
64 }
65 if ( $stop ) {
66 $query->setStop( $stop );
67 }
68 if ( $apiKey ) {
69 $query->setApiKey( $apiKey );
70 }
71 $answer = $this->core->ai->run( $query );
72 $rawText = $answer->result;
73 $html = apply_filters( 'mwai_chatbot_answer', $rawText );
74 $html = $this->core->markdown_to_html( $rawText );
75 return new WP_REST_Response([ 'success' => true, 'answer' => $rawText, 'html' => $html, 'usage' => $answer->usage ], 200 );
76 }
77 catch ( Exception $e ) {
78 return new WP_REST_Response([ 'success' => false, 'message' => $e->getMessage() ], 500 );
79 }
80 }
81
82 function inject_chat() {
83 $params = $this->core->get_option( 'shortcode_chat_params' );
84 echo $this->chat( $params );
85 }
86
87 function chat( $atts ) {
88 // Use the core default parameters, or the user default parameters
89 $override = $this->core->get_option( 'shortcode_chat_params_override' );
90 $defaults_params = $override ? $this->core->get_option( 'shortcode_chat_params' ) :
91 $this->core->get_option( 'shortcode_chat_default_params' );
92 $defaults_params['id'] = uniqid();
93
94 // Give a chance to modify the default parameters one last time
95 $defaults = apply_filters( 'mwai_chatbot_params_defaults', $defaults_params );
96
97 // Make sure all the mandatory params are set
98 foreach ( $this->core->defaultChatbotParams as $key => $value ) {
99 if ( !isset( $defaults[$key] ) ) {
100 $defaults[$key] = $value;
101 }
102 }
103
104 // Override with the shortcode, and before/after filters
105 $atts = apply_filters( 'mwai_chatbot_params_before', $atts );
106 $atts = shortcode_atts( $defaults, $atts );
107 $atts = apply_filters( 'mwai_chatbot_params', $atts );
108 $apiUrl = get_rest_url( null, 'ai-engine/v1/chat' );
109 $id = $atts['id'];
110
111 // Named functions
112 $onSentClickFn = "mwai_{$id}_onSendClick";
113 $addReplyFn = "mwai_{$id}_addReply";
114 $initChatBotFn = "mwai_{$id}_initChatBot";
115
116 // UI Parameters
117 $aiName = addslashes( trim($atts['ai_name']) );
118 $userName = addslashes( trim($atts['user_name']) );
119 $sysName = addslashes( trim($atts['sys_name']) );
120 $context = addslashes( $atts['context'] );
121 $textSend = addslashes( trim( $atts['text_send'] ) );
122 $textInputPlaceholder = addslashes( trim( $atts['text_input_placeholder'] ) );
123 $startSentence = addslashes( trim( $atts['start_sentence'] ) );
124 $window = filter_var( $atts['window'], FILTER_VALIDATE_BOOLEAN );
125 $fullscreen = filter_var( $atts['fullscreen'], FILTER_VALIDATE_BOOLEAN );
126 $style = $atts['style'];
127
128 // Chatbot System Parameters
129 $casuallyFineTuned = boolval( $atts['casually_fined_tuned'] );
130 $promptEnding = addslashes( trim( $atts['prompt_ending'] ) );
131 $completionEnding = addslashes( trim( $atts['completion_ending'] ) );
132 if ( $casuallyFineTuned ) {
133 $promptEnding = "\\n\\n===\\n\\n";
134 $completionEnding = "\\n\\n";
135 }
136
137 // OpenAI Parameters
138 $model = $atts['model'];
139 $temperature = $atts['temperature'];
140 $maxTokens = $atts['max_tokens'];
141 $apiKey = $atts['api_key'];
142
143 // Variables
144 $onGoingPrompt = "mwai_{$id}_onGoingPrompt";
145 $baseClasses = "mwai-chat";
146 $baseClasses .= ( $window ? " mwai-window" : "" );
147 $baseClasses .= ( !$window && $fullscreen ? " mwai-fullscreen" : "" );
148
149 // Output CSS
150 ob_start();
151 $style_content = "";
152 if ( $style === 'chatgpt' ) {
153 $style_content = $this->chatgpt_style( $id, $style );
154 }
155 echo apply_filters( 'mwai_chatbot_style', $style_content, $id );
156
157 // Output HTML & CSS
158 ?>
159 <div id="mwai-chat-<?= $id ?>" class="<?= $baseClasses ?>">
160 <?php if ( $window ) { ?>
161 <div class="mwai-open-button">
162 <img width="64" height="64" src="<?= plugins_url( '../../images/chat-green.svg', __FILE__ ) ?>" />
163 </div>
164 <div class="mwai-header">
165 <?php if ( $window ) { ?>
166 <div class="mwai-resize-button"></div>
167 <?php } ?>
168 <div class="mwai-close-button"></div>
169 </div>
170 <?php } ?>
171 <div class="mwai-content">
172 <div class="mwai-conversation">
173 </div>
174 <div class="mwai-input">
175 <textarea rows="1" placeholder="<?= $textInputPlaceholder ?>"></textarea>
176 <button><span><?= $textSend ?></span></button>
177 </div>
178 </div>
179 </div>
180
181 <script>
182 var <?= $onGoingPrompt ?> = '<?= $context ?>' + '\n\n';
183 var isMobile = window.matchMedia("only screen and (max-width: 760px)").matches;
184 var isWindow = <?= $window ? 'true' : 'false' ?>;
185
186 // Push the reply in the conversation
187 function <?= $addReplyFn ?>(text, type = 'user') {
188 var conversation = document.querySelector('#mwai-chat-<?= $id ?> .mwai-conversation');
189 var mwaiClasses = 'mwai-reply';
190 if (type === 'ai') {
191 mwaiClasses += ' mwai-ai';
192 }
193 else if (type === 'system') {
194 mwaiClasses += ' mwai-system';
195 }
196 else {
197 mwaiClasses += ' mwai-user';
198 }
199 var html = '<div class="' + mwaiClasses + '">';
200 if (type === 'ai') {
201 html += '<span class="mwai-name"><?= $aiName ?></span>';
202 }
203 else if (type === 'system') {
204 html += '<span class="mwai-name"><?= $sysName ?></span>';
205 }
206 else {
207 html += '<span class="mwai-name"><?= $userName ?></span>';
208 }
209 html += '<span class="mwai-text">' + text + '</span>';
210 html += '</div>';
211 conversation.innerHTML += html;
212 conversation.scrollTop = conversation.scrollHeight;
213
214 // Syntax coloring
215 if (typeof hljs !== 'undefined') {
216 document.querySelectorAll('pre code').forEach((el) => {
217 hljs.highlightElement(el);
218 });
219 }
220 }
221
222 // Function to request the completion
223 function <?= $onSentClickFn ?>() {
224 let input = document.querySelector('#mwai-chat-<?= $id ?> .mwai-input textarea');
225 let inputText = input.value.trim();
226
227 if (inputText === '') {
228 return;
229 }
230
231 // Disable the button
232 var button = document.querySelector('#mwai-chat-<?= $id ?> .mwai-input button');
233 button.disabled = true;
234
235 // Add the user reply
236 <?= $addReplyFn ?>(inputText, 'user');
237 <?= $onGoingPrompt ?> += '<?= $userName ?>' + inputText + '\n';
238 input.value = '';
239 input.setAttribute('rows', 1);
240 input.disabled = true;
241
242 // Let's build the prompt depending on the "system"
243 <?= $onGoingPrompt ?> += '<?= $aiName ?>';
244 let prompt = <?= $onGoingPrompt ?>;
245 if (<?= $casuallyFineTuned ? 1 : 0 ?>) {
246 prompt = inputText + '<?= $promptEnding ?>';
247 }
248
249 // Request the completion
250 const data = {
251 prompt: prompt,
252 userName: '<?= $userName ?>',
253 aiName: '<?= $aiName ?>',
254 model: '<?= $model ?>',
255 temperature: '<?= $temperature ?>',
256 maxTokens: '<?= $maxTokens ?>',
257 stop: '<?= $completionEnding ?>',
258 apiKey: '<?= $apiKey ?>',
259 };
260 console.log('[BOT] Sent: ', data);
261 fetch('<?= $apiUrl ?>', { method: 'POST', headers: { 'Content-Type': 'application/json' },
262 body: JSON.stringify(data)
263 })
264 .then(response => response.json())
265 .then(data => {
266 console.log('[BOT] Recv: ', data);
267 if (!data.success) {
268 <?= $addReplyFn ?>(data.message, 'system');
269 }
270 else {
271 <?= $addReplyFn ?>(data.html, 'ai');
272 <?= $onGoingPrompt ?> += data.answer + '\n';
273 }
274 button.disabled = false;
275 input.disabled = false;
276
277 // Only focus only on desktop (to avoid the mobile keyboard to kick-in)
278 if (!isMobile) {
279 input.focus();
280 }
281 })
282 .catch(error => {
283 console.error(error);
284 button.disabled = false;
285 input.disabled = false;
286 });
287 }
288
289 // Keep the textarea height in sync with the content
290 function mwaiSetTextAreaHeight(textarea, lines) {
291 var rows = textarea.getAttribute('rows');
292 if (lines !== rows) {
293 textarea.setAttribute('rows', lines > 5 ? 5 : lines);
294 }
295 }
296
297 // Init the chatbot
298 function <?= $initChatBotFn ?>() {
299 var input = document.querySelector('#mwai-chat-<?= $id ?> .mwai-input textarea');
300 input.addEventListener('keypress', (event) => {
301 if (event.keyCode === 13 && !event.shiftKey) {
302 <?= $onSentClickFn ?>();
303 }
304 });
305 input.addEventListener('keydown', (event) => {
306 var rows = input.getAttribute('rows');
307 if (event.keyCode === 13 && event.shiftKey) {
308 var lines = input.value.split('\n').length + 1;
309 mwaiSetTextAreaHeight(input, lines);
310 }
311 });
312 input.addEventListener('keyup', (event) => {
313 var rows = input.getAttribute('rows');
314 var lines = input.value.split('\n').length ;
315 mwaiSetTextAreaHeight(input, lines);
316 });
317 var button = document.querySelector('#mwai-chat-<?= $id ?> .mwai-input button');
318 button.addEventListener('click', (event) => {
319 <?= $onSentClickFn ?>();
320 });
321
322 // If window, add event listener to mwai-open-button and mwai-close-button
323 if ( isWindow ) {
324 var openButton = document.querySelector('#mwai-chat-<?= $id ?> .mwai-open-button');
325 openButton.addEventListener('click', (event) => {
326 var chat = document.querySelector('#mwai-chat-<?= $id ?>');
327 chat.classList.add('mwai-open');
328 // Only focus only on desktop (to avoid the mobile keyboard to kick-in)
329 if (!isMobile) {
330 input.focus();
331 }
332 });
333 var closeButton = document.querySelector('#mwai-chat-<?= $id ?> .mwai-close-button');
334 closeButton.addEventListener('click', (event) => {
335 var chat = document.querySelector('#mwai-chat-<?= $id ?>');
336 chat.classList.remove('mwai-open');
337 });
338 var resizeButton = document.querySelector('#mwai-chat-<?= $id ?> .mwai-resize-button');
339 resizeButton.addEventListener('click', (event) => {
340 var chat = document.querySelector('#mwai-chat-<?= $id ?>');
341 chat.classList.toggle('mwai-fullscreen');
342 });
343 }
344
345 <?= $addReplyFn ?>('<?= $startSentence ?>', 'ai');
346 }
347
348 // Let's go totally meoooow on this!
349 <?= $initChatBotFn ?>();
350 </script>
351
352 <?php
353 $output = ob_get_contents();
354 ob_end_clean();
355 $output = apply_filters( 'mwai_chatbot', $output, $atts );
356 return $output;
357 }
358 }