PluginProbe ʕ •ᴥ•ʔ
AI Engine – The Chatbot, AI Framework & MCP for WordPress / 2.4.8
AI Engine – The Chatbot, AI Framework & MCP for WordPress v2.4.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 / reply.php
ai-engine / classes Last commit date
engines 1 year ago modules 1 year ago queries 1 year ago admin.php 2 years ago api.php 1 year ago core.php 1 year ago init.php 2 years ago reply.php 1 year ago rest.php 1 year ago
reply.php
258 lines
1 <?php
2
3 class Meow_MWAI_Reply implements JsonSerializable {
4 public $id = null;
5 public $result = '';
6 public $results = [];
7 public $usage = [
8 'prompt_tokens' => 0,
9 'completion_tokens' => 0,
10 'total_tokens' => 0,
11 'price' => null,
12 ];
13 public $query = null;
14 public $type = 'text';
15
16 // This is when models return a message that needs to be executed (functions, tools, etc)
17 public $needFeedbacks = [];
18 public $needClientActions = [];
19
20 public function __construct( $query = null ) {
21 $this->query = $query;
22 }
23
24 #[\ReturnTypeWillChange]
25 public function jsonSerialize() {
26 $isEmbedding = false;
27 $embeddingsDimensions = null;
28 $embedddingsMessage = null;
29 if ( is_array( $this->results ) && count( $this->results ) > 0 ) {
30 $isEmbedding = is_array( $this->results[0] );
31 if ( $isEmbedding ) {
32 $embeddingsDimensions = count( $this->results[0] );
33 $embedddingsMessage = "A $embeddingsDimensions-dimensional embedding was returned.";
34 }
35 }
36 $data = [
37 'result' => $isEmbedding ? $embedddingsMessage : $this->result,
38 'results' => $isEmbedding ? [] : $this->results,
39 'usage' => $this->usage,
40 'system' => [
41 'class' => get_class( $this ),
42 ]
43 ];
44 if ( !empty( $this->needFeedbacks ) ) {
45 $data['needFeedbacks'] = $this->needFeedbacks;
46 }
47 if ( !empty( $this->needClientActions ) ) {
48 $data['needClientActions'] = $this->needClientActions;
49 }
50 return $data;
51 }
52
53 public function set_usage( $usage ) {
54 $this->usage = $usage;
55 }
56
57 public function set_id( $id ) {
58 $this->id = $id;
59 }
60
61 public function set_type( $type ) {
62 $this->type = $type;
63 }
64
65 public function get_total_tokens() {
66 return $this->usage['total_tokens'];
67 }
68
69 public function get_in_tokens( $query = null ) {
70 $in_tokens = $this->usage['prompt_tokens'];
71 if ( empty( $in_tokens ) && $query ) {
72 $in_tokens = $query->get_in_tokens();
73 }
74 return $in_tokens;
75 }
76
77 public function get_out_tokens() {
78 $out_tokens = $this->usage['completion_tokens'];
79 if ( empty( $out_tokens ) ) {
80 $out_tokens = Meow_MWAI_Core::estimate_tokens( $this->result );
81 }
82 return $out_tokens;
83 }
84
85 public function get_price() {
86 // If it's not set return null, but it can be 0
87 if ( !isset( $this->usage['price'] ) ) {
88 return null;
89 }
90 return $this->usage['price'];
91 }
92
93 public function get_units() {
94 if ( isset( $this->usage['total_tokens'] ) ) {
95 return $this->usage['total_tokens'];
96 }
97 else if ( isset( $this->usage['images'] ) ) {
98 return $this->usage['images'];
99 }
100 else if ( isset( $this->usage['seconds'] ) ) {
101 return $this->usage['seconds'];
102 }
103 return null;
104 }
105
106 public function get_type() {
107 return $this->type;
108 }
109
110 public function set_reply( $reply ) {
111 $this->result = $reply;
112 $this->results[] = [ $reply ];
113 }
114
115 public function replace( $search, $replace ) {
116 $this->result = str_replace( $search, $replace, $this->result );
117 $this->results = array_map( function( $result ) use ( $search, $replace ) {
118 return str_replace( $search, $replace, $result );
119 }, $this->results );
120 }
121
122 private function extract_arguments( $funcArgs ) {
123 $finalArgs = [];
124 if ( is_string( $funcArgs ) ) {
125 $arguments = trim( str_replace( "\n", "", $funcArgs ) );
126 if ( substr( $arguments, 0, 1 ) == '{' ) {
127 $arguments = json_decode( $arguments, true );
128 $finalArgs = $arguments;
129 }
130 }
131 else if ( is_array( $funcArgs ) ) {
132 $finalArgs = $funcArgs;
133 }
134 return $finalArgs;
135 }
136
137 /**
138 * Set the choices from OpenAI as the results.
139 * The last (or only) result is set as the result.
140 * @param array $choices ID of the model to use.
141 */
142 public function set_choices( $choices, $rawMessage = null) {
143 $this->results = [];
144 if ( is_array( $choices ) ) {
145 foreach ( $choices as $choice ) {
146
147 // It's chat completion
148 if ( isset( $choice['message'] ) ) {
149
150 // It's text content
151 if ( isset( $choice['message']['content'] ) ) {
152 $content = trim( $choice['message']['content'] );
153 $this->results[] = $content;
154 $this->result = $content;
155 }
156
157 // It's a tool call (OpenAI-style and Anthropic-style)
158 $toolCalls = [];
159 if ( isset( $choice['message']['tool_calls'] ) ) {
160 $tools = $choice['message']['tool_calls'];
161 foreach ( $tools as $tool ) {
162 if ( $tool['type'] === 'function' ) {
163 $toolCalls[] = [
164 'toolId' => $tool['id'],
165 //'mode' => 'interactive',
166 'type' => 'tool_call',
167 'name' => trim( $tool['function']['name'] ),
168 'arguments' => $this->extract_arguments( $tool['function']['arguments'] ),
169 // Represent the original message that triggered the function call
170 'rawMessage' => $rawMessage ? $rawMessage : $choice['message'],
171 ];
172 }
173 }
174 }
175
176 // If it's a function call (Open-AI style; usually for a final execution)
177 if ( isset( $choice['message']['function_call'] ) ) {
178 $content = $choice['message']['function_call'];
179 $toolCalls[] = [
180 'toolId' => null,
181 'mode' => 'static',
182 'type' => 'function_call',
183 'name' => trim( $choice['message']['function_call']['name'] ),
184 'arguments' => $this->extract_arguments( $tool['message']['function_call']['arguments'] ),
185 'rawMessage' => $rawMessage ? $rawMessage : $choice['message'],
186 ];
187 }
188
189 // Resolve the original function from the query
190 if ( !empty( $toolCalls ) ) {
191 foreach ( $toolCalls as &$toolCall ) {
192 if ( $toolCall['type'] !== 'function_call' && $toolCall['type'] !== 'tool_call' ) {
193 continue;
194 }
195 foreach ( $this->query->functions as $function ) {
196 if ( $function->name == $toolCall['name'] ) {
197 $toolCall['function'] = $function;
198 break;
199 }
200 }
201 }
202 }
203
204 // Let's separate the Feedbacks (PHP code) and Client Actions (JS code)
205 $this->needFeedbacks = [];
206 $this->needClientActions = [];
207 foreach ( $toolCalls as $toolCall ) {
208 if ( $toolCall['function']->target !== 'js' ) {
209 $this->needFeedbacks[] = $toolCall;
210 }
211 else if ( $toolCall['function']->target === 'js' ) {
212 $this->needClientActions[] = $toolCall;
213 }
214 }
215 }
216
217 // It's text completion
218 else if ( isset( $choice['text'] ) ) {
219
220 // TODO: Assistants return an array (so actually not really a text completion)
221 // We should probably make this clearer and analyze all the outputs from different endpoints.
222 if ( is_array( $choice['text'] ) ) {
223 $text = trim( $choice['text']['value'] );
224 $this->results[] = $text;
225 $this->result = $text;
226 }
227 else {
228 $text = trim( $choice['text'] );
229 $this->results[] = $text;
230 $this->result = $text;
231 }
232 }
233
234 // It's url/image
235 else if ( isset( $choice['url'] ) ) {
236 $url = trim( $choice['url'] );
237 $this->results[] = $url;
238 $this->result = $url;
239 }
240
241 // It's embedding
242 else if ( isset( $choice['embedding'] ) ) {
243 $content = $choice['embedding'];
244 $this->results[] = $content;
245 $this->result = $content;
246 }
247 }
248 }
249 else {
250 $this->result = $choices;
251 $this->results[] = $choices;
252 }
253 }
254
255 public function toJson() {
256 return json_encode( $this );
257 }
258 }