PluginProbe
Fluent Support – Helpdesk & Customer Support Ticket System / 2.1.2
Fluent Support – Helpdesk & Customer Support Ticket System v2.1.2
2.3.2 2.3.1 2.3.0 2.2.1 2.2.0 trunk 1.10.0 1.10.1 1.10.2 1.10.3 1.10.4 1.10.5 1.4.0 1.4.1 1.4.2 1.4.5 1.4.6 1.4.7 1.5.0 1.5.1 1.5.2 1.5.3 1.5.4 1.5.5 1.5.6 All 67 releases
fluent-support / app / Http / Controllers / CustomerController.php

CustomerController.php in Fluent Support – Helpdesk & Customer Support Ticket System 2.1.2, at app/Http/Controllers/CustomerController.php

404 lines 13.7 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace FluentSupport\App\Http\Controllers;
4
5 use FluentCrm\App\Models\Subscriber;
6 use FluentSupport\App\Models\Customer;
7 use FluentSupport\Framework\Http\Request\Request;
8 use FluentSupport\App\Services\AvatarUploder;
9 use FluentSupport\App\Services\Helper;
10 use FluentSupport\Framework\Support\Arr;
11
12 /**
13 * CustomerController class for REST API
14 * This class is responsible for getting data for all request related to customer
15 * @package FluentSupport\App\Http\Controllers
16 *
17 * @version 1.0.0
18 */
19 class CustomerController extends Controller
20 {
21 /**
22 * index method will return the list of customers
23 * @param Request $request
24 * @param Customer $customer
25 * @return array
26 */
27 public function index(Request $request, Customer $customer)
28 {
29 return [
30 'customers' => $customer->getCustomers($request->getSafe('search', 'sanitize_text_field'), $request->getSafe('status', 'sanitize_text_field')),
31 ];
32 }
33
34 public function customerField (Request $request,Customer $customer, $customer_id) {
35
36 $userID = $request->getSafe('user_id', 'intval');
37 return[
38 'customerField' => $customer->getCustomerField($customer_id,$userID)
39 ];
40 }
41
42
43 /**
44 * getCustomer method will return individual customer information by customer id
45 * This function will also get information about extra widgets, tickets and Fluent CRM
46 * @param Request $request
47 * @param Customer $customer
48 * @param $customer_id
49 * @return array
50 */
51 public function getCustomer(Request $request, Customer $customer, $customer_id)
52 {
53 $with = $request->get('with', null);
54 $with = is_array($with) ? array_map('sanitize_key', $with) : [];
55
56 return $customer->getCustomer($customer_id, $with);
57 }
58
59 /**
60 * Create method will create new customer
61 * @param Request $request
62 * @param Customer $customer
63 * @return array
64 * @throws \FluentSupport\Framework\Validator\ValidationException
65 */
66 public function create(Request $request, Customer $customer)
67 {
68 // Define expected fields with their sanitizers
69 $fields = [
70 'id' => 'intval',
71 'customer_id' => 'intval',
72 'avatar' => 'esc_url_raw',
73 'person_type' => 'sanitize_text_field',
74 'hash' => 'sanitize_text_field',
75 'description' => 'sanitize_text_field',
76 'photo' => 'esc_url_raw',
77 'email' => 'sanitize_email',
78 'first_name' => 'sanitize_text_field',
79 'last_name' => 'sanitize_text_field',
80 'title' => 'sanitize_text_field',
81 'user_id' => 'intval',
82 'remote_uid' => 'sanitize_text_field',
83 'status' => 'sanitize_text_field',
84 'address_line_1' => 'sanitize_textarea_field',
85 'address_line_2' => 'sanitize_textarea_field',
86 'city' => 'sanitize_text_field',
87 'state' => 'sanitize_text_field',
88 'zip' => 'sanitize_text_field',
89 'country' => 'sanitize_text_field',
90 'note' => 'sanitize_textarea_field',
91 'ip_address' => 'sanitize_text_field',
92 'last_ip_address' => 'sanitize_text_field',
93 ];
94
95 $data = $this->sanitizeRequestData($request, $fields);
96
97 $data = $this->validate($data, [
98 'email' => 'required|email|unique:fs_persons',
99 'first_name' => 'required',
100 'last_name' => 'nullable|string',
101 'title' => 'nullable|string',
102 'user_id' => 'nullable|integer',
103 'remote_uid' => 'nullable|string',
104 'status' => 'nullable|string',
105 'address_line_1' => 'nullable|string',
106 'address_line_2' => 'nullable|string',
107 'city' => 'nullable|string',
108 'state' => 'nullable|string',
109 'zip' => 'nullable|string',
110 'country' => 'nullable|string',
111 'note' => 'nullable|string',
112 'ip_address' => 'nullable|string',
113 'last_ip_address' => 'nullable|string',
114 ]);
115
116 return [
117 'message' => __('Customer has been added', 'fluent-support'),
118 'customer' => $customer->createCustomer($data)
119 ];
120 }
121
122 /**
123 * update method will update existing customer by customer id
124 * @param Request $request
125 * @param Customer $customer
126 * @param $customerId
127 * @return array
128 * @throws \FluentSupport\Framework\Validator\ValidationException
129 */
130 public function update(Request $request, Customer $customer, $customer_id)
131 {
132 // Sanitize only allowed fields and also sanitize any extra fields from hooks
133 $fields = [
134 'id' => 'intval',
135 'customer_id' => 'intval',
136 'avatar' => 'esc_url_raw',
137 'person_type' => 'sanitize_text_field',
138 'hash' => 'sanitize_text_field',
139 'description' => 'sanitize_text_field',
140 'photo' => 'esc_url_raw',
141 'email' => 'sanitize_email',
142 'first_name' => 'sanitize_text_field',
143 'last_name' => 'sanitize_text_field',
144 'title' => 'sanitize_text_field',
145 'user_id' => 'intval',
146 'remote_uid' => 'sanitize_text_field',
147 'status' => 'sanitize_text_field',
148 'address_line_1' => 'sanitize_textarea_field',
149 'address_line_2' => 'sanitize_textarea_field',
150 'city' => 'sanitize_text_field',
151 'state' => 'sanitize_text_field',
152 'zip' => 'sanitize_text_field',
153 'country' => 'sanitize_text_field',
154 'note' => 'sanitize_textarea_field',
155 'ip_address' => 'sanitize_text_field',
156 'last_ip_address' => 'sanitize_text_field',
157 ];
158
159 $data = $this->sanitizeRequestData($request, $fields);
160
161 $data = $this->validate($data, [
162 'email' => 'required|email',
163 'first_name' => 'required',
164 'last_name' => 'nullable|string',
165 'title' => 'nullable|string',
166 'user_id' => 'nullable|integer',
167 'remote_uid' => 'nullable|string',
168 'status' => 'nullable|string',
169 'address_line_1' => 'nullable|string',
170 'address_line_2' => 'nullable|string',
171 'city' => 'nullable|string',
172 'state' => 'nullable|string',
173 'zip' => 'nullable|string',
174 'country' => 'nullable|string',
175 'note' => 'nullable|string',
176 'ip_address' => 'nullable|string',
177 'last_ip_address' => 'nullable|string',
178 ]);
179
180 try {
181 return [
182 'message' => __('Customer has been updated', 'fluent-support'),
183 'customer' => $customer->updateCustomer($customer_id, $data)
184 ];
185 } catch (\Exception $e) {
186 return $this->sendError([
187 'message' => Helper::getSafeErrorMessage($e),
188 'errors' => [
189 'email' => [
190 'unique' => __('Email address has been assigned to other customer', 'fluent-support'),
191 ]
192 ]
193 ], 423);
194 }
195 }
196
197 /**
198 * delete method will delete a customer and all tickets by that customer
199 * @param Request $request
200 * @param Customer $customer
201 * @param int $customerId
202 * @return array
203 */
204 public function delete(Request $request, Customer $customer, $customer_id)
205 {
206 return $customer->deleteCustomer($customer_id);
207 }
208
209 /**
210 * bulkDelete method will delete multiple customers and all their tickets
211 * @param Request $request
212 * @param Customer $customer
213 * @return array
214 */
215 public function bulkDelete(Request $request, Customer $customer)
216 {
217 // Get and sanitize customer_ids before validation
218 $customerIds = $request->get('customer_ids', []);
219 $customerIds = is_array($customerIds) ? array_map('intval', $customerIds) : [];
220
221 // Filter out any zero values (from invalid input)
222 $customerIds = array_filter($customerIds, function ($id) {
223 return $id > 0;
224 });
225
226 $this->validate(['customer_ids' => $customerIds], [
227 'customer_ids' => 'required|array|min:1',
228 'customer_ids.*' => 'required|integer|exists:fs_persons,id'
229 ]);
230
231 return $customer->bulkDeleteCustomers($customerIds);
232 }
233
234 /**
235 * addOrUpdateProfileImage method will update a customer avatar
236 * For a successful upload it's required to send file object, customer id and the user type(customer)
237 * @param Request $request
238 * @return array
239 */
240 public function addOrUpdateProfileImage(Request $request, AvatarUploder $avatarUploder)
241 {
242 try {
243 return $avatarUploder->addOrUpdateProfileImage($request->files(), $request->getSafe('customer_id', 'intval'), 'customer');
244 } catch (\Exception $e) {
245 return $this->sendError([
246 'message' => Helper::getSafeErrorMessage($e),
247 ],
248 $e->getCode()
249 );
250 }
251 }
252
253 /**
254 * resetAvatar method will restore a customer avatar
255 * For a successful upload it's required to send file object, customer id and the user type(customer)
256 * @param Request $request
257 * @param $id
258 * @return array
259 */
260 public function resetAvatar(Customer $customer)
261 {
262 try {
263 $customer->restoreAvatar();
264
265 return [
266 'message' => __('Customer avatar reset to gravatar default', 'fluent-support'),
267 ];
268 } catch (\Exception $e) {
269 return [
270 'message' => Helper::getSafeErrorMessage($e)
271 ];
272 }
273 }
274
275 public function searchContact(Request $request)
276 {
277 $search = $request->getSafe('search', 'sanitize_text_field');
278 if (!$search) {
279 return $this->sendError([
280 'message' => __('Please provide search string', 'fluent-support')
281 ]);
282 }
283
284 $isEmail = is_email($search);
285
286 // search the existing customers first
287 if ($isEmail) {
288 $customers = Customer::select(['first_name', 'last_name', 'email', 'id', 'user_id'])
289 ->where('email', $search)
290 ->get();
291 } else {
292 $customers = Customer::select(['first_name', 'last_name', 'email', 'id', 'user_id'])
293 ->searchBy($search)
294 ->limit(10)
295 ->get();
296 }
297
298 if (!$customers->isEmpty()) {
299 return [
300 'type' => 'search_result',
301 'provider' => 'fluent_support',
302 'data' => $customers,
303 'is_email' => $isEmail,
304 'search' => $search
305 ];
306 }
307
308 // If FluentCRM exist then let's search for
309 if (defined('FLUENTCRM')) {
310
311 if ($isEmail) {
312 $contacts = \FluentCrm\App\Models\Subscriber::where('email', $search)
313 ->select(['first_name', 'last_name', 'email', 'id', 'user_id'])
314 ->get();
315 } else {
316
317 $contacts = \FluentCrm\App\Models\Subscriber::searchBy($search)
318 ->select(['first_name', 'last_name', 'email', 'id', 'user_id'])
319 ->limit(10)
320 ->get();
321 }
322
323 if (!$contacts->isEmpty()) {
324 return [
325 'type' => 'search_result',
326 'provider' => 'fluent_crm',
327 'data' => $contacts,
328 'is_email' => $isEmail
329 ];
330 }
331 }
332
333 // let's search from user's database
334 $user_query = new \WP_User_Query(array('search' => $search, 'number' => 10));
335
336 $users = $user_query->get_results();
337
338 if ($users) {
339 $formattedUsers = [];
340
341 foreach ($users as $user) {
342 $formattedUsers[] = [
343 'id' => $user->ID,
344 'first_name' => $user->first_name,
345 'last_name' => $user->last_name,
346 'user_id' => $user->ID,
347 'email' => $user->user_email
348 ];
349 }
350
351 return [
352 'type' => 'search_result',
353 'provider' => 'wp_users',
354 'data' => $formattedUsers,
355 'is_email' => $isEmail
356 ];
357 }
358
359 return [
360 'type' => 'none',
361 'provider' => 'none',
362 'data' => [],
363 'is_email' => $isEmail
364 ];
365
366 }
367
368 /**
369 * Sanitize request data for given fields. Uses Request::getSafe for known fields
370 * and falls back to sanitize_text_field for any other keys present in the raw request
371 * (useful when hooks inject extra data).
372 *
373 * @param Request $request
374 * @param array $fieldsMap associative array field => sanitizer callable name
375 * @return array
376 */
377 private function sanitizeRequestData(Request $request, array $fieldsMap)
378 {
379 $sanitized = [];
380
381 // Use getSafe for known fields
382 foreach ($fieldsMap as $field => $sanitizer) {
383 $sanitized[$field] = $request->getSafe($field, $sanitizer);
384 }
385
386 // Now sanitize any other incoming keys to avoid unsanitized data
387 $raw = $request->get();
388 foreach ($raw as $key => $value) {
389 if (array_key_exists($key, $sanitized)) {
390 continue;
391 }
392
393 if (is_array($value)) {
394 $sanitized[$key] = array_map('sanitize_text_field', $value);
395 } else {
396 // Fallback sanitizer for unknown fields
397 $sanitized[$key] = is_string($value) ? sanitize_text_field($value) : $value;
398 }
399 }
400
401 return $sanitized;
402 }
403 }
404