PluginProbe
Bit Form – Contact Form, Payment Forms, Multi Step Forms, Calculator & Custom Form Builder / 2.9.1
Bit Form – Contact Form, Payment Forms, Multi Step Forms, Calculator & Custom Form Builder v2.9.1
V-3.3.0 3.2.2 3.2.1 3.2.0 3.1.4 3.1.3 3.1.2 3.1.1 3.1.0 V3.0.3 V3.0.2 -3.0.1 V_3.0.0 1.1.1 1.1.8 1.2 1.3 1.4 1.4.18 1.5.2 1.9 2.0 2.10.0 2.10.1 2.10.2 All 137 releases
bit-form / includes / Core / Integration / ZohoProjects / ZohoProjectsHandler.php

ZohoProjectsHandler.php in Bit Form – Contact Form, Payment Forms, Multi Step Forms, Calculator & Custom Form Builder 2.9.1, at includes/Core/Integration/ZohoProjects/ZohoProjectsHandler.php

1,168 lines 38.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 /**
4 * ZohoProjects Integration
5 *
6 */
7
8 namespace BitCode\BitForm\Core\Integration\ZohoProjects;
9
10 use BitCode\BitForm\Core\Integration\IntegrationHandler;
11 use BitCode\BitForm\Core\Util\HttpHelper;
12 use BitCode\BitForm\Core\Util\IpTool;
13
14 /**
15 * Provide functionality for ZohoCrm integration
16 */
17 class ZohoProjectsHandler
18 {
19 private $_formID;
20 private $_integrationID;
21
22 public function __construct($integrationID, $formID)
23 {
24 $this->_formID = $formID;
25 $this->_integrationID = $integrationID;
26 }
27
28 /**
29 * Helps to register ajax function's with wp
30 *
31 * @return null
32 */
33 public static function registerAjax()
34 {
35 add_action('wp_ajax_bitforms_zprojects_generate_token', [__CLASS__, 'generateTokens']);
36 add_action('wp_ajax_bitforms_zprojects_refresh_portals', [__CLASS__, 'refreshPortalsAjaxHelper']);
37 add_action('wp_ajax_bitforms_zprojects_refresh_projects', [__CLASS__, 'refreshProjectsAjaxHelper']);
38 add_action('wp_ajax_bitforms_zprojects_refresh_milestones', [__CLASS__, 'refreshMilestonesAjaxHelper']);
39 add_action('wp_ajax_bitforms_zprojects_refresh_tasklists', [__CLASS__, 'refreshTasklistsAjaxHelper']);
40 add_action('wp_ajax_bitforms_zprojects_refresh_tasks', [__CLASS__, 'refreshTasksAjaxHelper']);
41 add_action('wp_ajax_bitforms_zprojects_refresh_fields', [__CLASS__, 'refreshFieldsAjaxHelper']);
42 add_action('wp_ajax_bitforms_zprojects_refresh_users', [__CLASS__, 'refreshUsersAjaxHelper']);
43 add_action('wp_ajax_bitforms_zprojects_refresh_task_layouts', [__CLASS__, 'refreshTaskLaysAjaxHelper']);
44 add_action('wp_ajax_bitforms_zprojects_refresh_groups', [__CLASS__, 'refreshGroupsAjaxHelper']);
45 add_action('wp_ajax_bitforms_zprojects_refresh_tags', [__CLASS__, 'refreshTagsAjaxHelper']);
46 }
47
48 /**
49 * Process ajax request for generate_token
50 *
51 * @return JSON zoho crm api response and status
52 */
53 public static function generateTokens()
54 {
55 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
56 $inputJSON = file_get_contents('php://input');
57 $requestsParams = json_decode($inputJSON);
58 if (
59 empty($requestsParams->{'accounts-server'})
60 || empty($requestsParams->dataCenter)
61 || empty($requestsParams->clientId)
62 || empty($requestsParams->clientSecret)
63 || empty($requestsParams->redirectURI)
64 || empty($requestsParams->code)
65 ) {
66 wp_send_json_error(
67 __(
68 'Requested parameter is empty',
69 'bit-form'
70 ),
71 400
72 );
73 }
74
75 $apiEndpoint = \urldecode($requestsParams->{'accounts-server'}) . '/oauth/v2/token';
76 $requestParams = [
77 'grant_type' => 'authorization_code',
78 'client_id' => $requestsParams->clientId,
79 'client_secret' => $requestsParams->clientSecret,
80 'redirect_uri' => \urldecode($requestsParams->redirectURI),
81 'code' => $requestsParams->code
82 ];
83 $apiResponse = HttpHelper::post($apiEndpoint, $requestParams);
84
85 if (is_wp_error($apiResponse) || !empty($apiResponse->error)) {
86 wp_send_json_error(
87 empty($apiResponse->error) ? 'Unknown' : $apiResponse->error,
88 400
89 );
90 }
91 $apiResponse->generates_on = \time();
92 wp_send_json_success($apiResponse, 200);
93 } else {
94 wp_send_json_error(
95 __(
96 'Token expired',
97 'bit-form'
98 ),
99 401
100 );
101 }
102 }
103
104 public static function refreshPortalsAjaxHelper()
105 {
106 $authorizationHeader = null;
107 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
108 $inputJSON = file_get_contents('php://input');
109 $queryParams = json_decode($inputJSON);
110 if (
111 empty($queryParams->tokenDetails)
112 || empty($queryParams->dataCenter)
113 || empty($queryParams->clientId)
114 || empty($queryParams->clientSecret)
115 ) {
116 wp_send_json_error(
117 __(
118 'Requested parameter is empty',
119 'bit-form'
120 ),
121 400
122 );
123 }
124 $response = [];
125 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
126 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
127 }
128
129 $portalsMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portals/";
130
131 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
132 $portalsMetaResponse = HttpHelper::get($portalsMetaApiEndpoint, null, $authorizationHeader);
133
134 if (!is_wp_error($portalsMetaResponse)) {
135 $allPortals = [];
136 $portals = $portalsMetaResponse->portals;
137
138 if (count($portals) > 0) {
139 foreach ($portals as $portal) {
140 $allPortals[$portal->name] = (object) [
141 'portalId' => $portal->id,
142 'portalName' => $portal->name
143 ];
144 }
145 }
146 uksort($allPortals, 'strnatcasecmp');
147 $response['portals'] = $allPortals;
148 } else {
149 wp_send_json_error(
150 empty($portalsMetaResponse->data) ? 'Unknown' : $portalsMetaResponse->error,
151 400
152 );
153 }
154 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
155 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
156 }
157 wp_send_json_success($response, 200);
158 } else {
159 wp_send_json_error(
160 __(
161 'Token expired',
162 'bit-form'
163 ),
164 401
165 );
166 }
167 }
168
169 public static function refreshProjectsAjaxHelper()
170 {
171 $authorizationHeader = null;
172 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
173 $inputJSON = file_get_contents('php://input');
174 $queryParams = json_decode($inputJSON);
175 if (
176 empty($queryParams->tokenDetails)
177 || empty($queryParams->dataCenter)
178 || empty($queryParams->clientId)
179 || empty($queryParams->clientSecret)
180 || empty($queryParams->portalId)
181 ) {
182 wp_send_json_error(
183 __(
184 'Requested parameter is empty',
185 'bit-form'
186 ),
187 400
188 );
189 }
190 $response = [];
191 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
192 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
193 }
194
195 $projectsMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/projects/?range=1000&status=active";
196
197 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
198 $projectsMetaResponse = HttpHelper::get($projectsMetaApiEndpoint, null, $authorizationHeader);
199
200 // wp_send_json_success($projectsMetaResponse, 200);
201
202 if (!is_wp_error($projectsMetaResponse)) {
203 $allProjects = [];
204 $projects = $projectsMetaResponse->projects;
205
206 if (count($projects) > 0) {
207 foreach ($projects as $project) {
208 $allProjects[$project->name] = (object) [
209 'projectId' => $project->id_string,
210 'projectName' => $project->name
211 ];
212 }
213 }
214 uksort($allProjects, 'strnatcasecmp');
215 $response['projects'] = $allProjects;
216 } else {
217 wp_send_json_error(
218 empty($projectsMetaResponse->data) ? 'Unknown' : $projectsMetaResponse->error,
219 400
220 );
221 }
222 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
223 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
224 }
225 wp_send_json_success($response, 200);
226 } else {
227 wp_send_json_error(
228 __(
229 'Token expired',
230 'bit-form'
231 ),
232 401
233 );
234 }
235 }
236
237 public static function refreshMilestonesAjaxHelper()
238 {
239 $authorizationHeader = null;
240 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
241 $inputJSON = file_get_contents('php://input');
242 $queryParams = json_decode($inputJSON);
243 if (
244 empty($queryParams->tokenDetails)
245 || empty($queryParams->dataCenter)
246 || empty($queryParams->clientId)
247 || empty($queryParams->clientSecret)
248 || empty($queryParams->portalId)
249 || empty($queryParams->projectId)
250 ) {
251 wp_send_json_error(
252 __(
253 'Requested parameter is empty',
254 'bit-form'
255 ),
256 400
257 );
258 }
259 $response = [];
260 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
261 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
262 }
263
264 $milestonesMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/projects/{$queryParams->projectId}/milestones/?range=1000";
265
266 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
267 $milestonesMetaResponse = HttpHelper::get($milestonesMetaApiEndpoint, null, $authorizationHeader);
268
269 if (!is_wp_error($milestonesMetaResponse)) {
270 $allMilestones = [];
271 $milestones = $milestonesMetaResponse->milestones;
272
273 if (count($milestones) > 0) {
274 foreach ($milestones as $milestone) {
275 $allMilestones[$milestone->name] = (object) [
276 'milestoneId' => $milestone->id_string,
277 'milestoneName' => $milestone->name
278 ];
279 }
280 }
281 uksort($allMilestones, 'strnatcasecmp');
282 $response['milestones'] = $allMilestones;
283 } else {
284 wp_send_json_error(
285 empty($milestonesMetaResponse->data) ? 'Unknown' : $milestonesMetaResponse->error,
286 400
287 );
288 }
289 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
290 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
291 }
292 wp_send_json_success($response, 200);
293 } else {
294 wp_send_json_error(
295 __(
296 'Token expired',
297 'bit-form'
298 ),
299 401
300 );
301 }
302 }
303
304 public static function refreshTasklistsAjaxHelper()
305 {
306 $authorizationHeader = null;
307 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
308 $inputJSON = file_get_contents('php://input');
309 $queryParams = json_decode($inputJSON);
310 if (
311 empty($queryParams->tokenDetails)
312 || empty($queryParams->dataCenter)
313 || empty($queryParams->clientId)
314 || empty($queryParams->clientSecret)
315 || empty($queryParams->portalId)
316 || empty($queryParams->projectId)
317 || empty($queryParams->tasklistFlag)
318 ) {
319 wp_send_json_error(
320 __(
321 'Requested parameter is empty',
322 'bit-form'
323 ),
324 400
325 );
326 }
327 $response = [];
328 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
329 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
330 }
331
332 $tasklistsMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/projects/{$queryParams->projectId}/tasklists/?range=1000&flag={$queryParams->tasklistFlag}";
333
334 if ($queryParams->milestoneId) {
335 $tasklistsMetaApiEndpoint .= "&milestone_id={$queryParams->milestoneId}";
336 }
337
338 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
339 $tasklistsMetaResponse = HttpHelper::get($tasklistsMetaApiEndpoint, null, $authorizationHeader);
340
341 if (!is_wp_error($tasklistsMetaResponse)) {
342 $allTasklists = [];
343 $tasklists = $tasklistsMetaResponse->tasklists;
344
345 if (count($tasklists) > 0) {
346 foreach ($tasklists as $tasklist) {
347 $allTasklists[$tasklist->name] = (object) [
348 'tasklistId' => $tasklist->id_string,
349 'tasklistName' => $tasklist->name
350 ];
351 }
352 }
353 uksort($allTasklists, 'strnatcasecmp');
354 $response['tasklists'] = $allTasklists;
355 } else {
356 wp_send_json_error(
357 empty($tasklistsMetaResponse->data) ? 'Unknown' : $tasklistsMetaResponse->error,
358 400
359 );
360 }
361 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
362 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
363 }
364 wp_send_json_success($response, 200);
365 } else {
366 wp_send_json_error(
367 __(
368 'Token expired',
369 'bit-form'
370 ),
371 401
372 );
373 }
374 }
375
376 public static function refreshTasksAjaxHelper()
377 {
378 $authorizationHeader = null;
379 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
380 $inputJSON = file_get_contents('php://input');
381 $queryParams = json_decode($inputJSON);
382 if (
383 empty($queryParams->tokenDetails)
384 || empty($queryParams->dataCenter)
385 || empty($queryParams->clientId)
386 || empty($queryParams->clientSecret)
387 || empty($queryParams->portalId)
388 || empty($queryParams->projectId)
389 ) {
390 wp_send_json_error(
391 __(
392 'Requested parameter is empty',
393 'bit-form'
394 ),
395 400
396 );
397 }
398 $response = [];
399 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
400 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
401 }
402
403 $tasksMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/projects/{$queryParams->projectId}/tasks/?range=1000";
404
405 if ($queryParams->milestoneId) {
406 $tasksMetaApiEndpoint .= "&milestone_id={$queryParams->milestoneId}";
407 }
408 if ($queryParams->tasklistId) {
409 $tasksMetaApiEndpoint .= "&tasklist_id={$queryParams->tasklistId}";
410 }
411
412 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
413 $tasksMetaResponse = HttpHelper::get($tasksMetaApiEndpoint, null, $authorizationHeader);
414
415 if (!is_wp_error($tasksMetaResponse)) {
416 $allTasks = [];
417 $tasks = $tasksMetaResponse->tasks;
418
419 if (count($tasks) > 0) {
420 foreach ($tasks as $task) {
421 $allTasks[$task->name] = (object) [
422 'taskId' => $task->id_string,
423 'taskName' => $task->name
424 ];
425 }
426 }
427 uksort($allTasks, 'strnatcasecmp');
428 $response['tasks'] = $allTasks;
429 } else {
430 wp_send_json_error(
431 empty($tasksMetaResponse->data) ? 'Unknown' : $tasksMetaResponse->error,
432 400
433 );
434 }
435 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
436 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
437 }
438 wp_send_json_success($response, 200);
439 } else {
440 wp_send_json_error(
441 __(
442 'Token expired',
443 'bit-form'
444 ),
445 401
446 );
447 }
448 }
449
450 public static function refreshFieldsAjaxHelper()
451 {
452 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
453 $inputJSON = file_get_contents('php://input');
454 $queryParams = json_decode($inputJSON);
455 if (
456 empty($queryParams->tokenDetails)
457 || empty($queryParams->dataCenter)
458 || empty($queryParams->clientId)
459 || empty($queryParams->clientSecret)
460 || empty($queryParams->portalId)
461 || empty($queryParams->event)
462 ) {
463 wp_send_json_error(
464 __(
465 'Requested parameter is empty',
466 'bit-form'
467 ),
468 400
469 );
470 }
471 $response = [];
472 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
473 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
474 }
475
476 if ('project' === $queryParams->event) {
477 $response = ZohoProjectsHandler::getProjectFields($queryParams->dataCenter, $queryParams->portalId, $queryParams->tokenDetails->access_token);
478 } elseif ('milestone' === $queryParams->event) {
479 $response = ZohoProjectsHandler::getMilestoneFields();
480 } elseif ('tasklist' === $queryParams->event) {
481 $response = ZohoProjectsHandler::getTasklistFields();
482 } elseif ('task' === $queryParams->event || 'subtask' === $queryParams->event) {
483 $response = ZohoProjectsHandler::getTaskFields($queryParams->dataCenter, $queryParams->portalId, $queryParams->tokenDetails->access_token, $queryParams->projectId);
484 } elseif ('issue' === $queryParams->event) {
485 $response = ZohoProjectsHandler::getIssueFields($queryParams->dataCenter, $queryParams->portalId, $queryParams->tokenDetails->access_token, $queryParams->projectId);
486 }
487
488 if (!empty($response['tokenDetails']) && $response['tokenDetails'] && !empty($queryParams->id)) {
489 $response['queryModule'] = $queryParams->module;
490 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response);
491 }
492 wp_send_json_success($response, 200);
493 } else {
494 wp_send_json_error(
495 __(
496 'Token expired',
497 'bit-form'
498 ),
499 401
500 );
501 }
502 }
503
504 protected static function getProjectFields($dataCenter, $portalId, $access_token)
505 {
506 $allFields = [
507 'Project Title' => [
508 'apiName' => 'name',
509 'displayLabel' => 'Project Title',
510 'required' => true
511 ],
512 'Project Overview' => [
513 'apiName' => 'description',
514 'displayLabel' => 'Project Overview'
515 ],
516 'Start Date' => [
517 'apiName' => 'start_date',
518 'displayLabel' => 'Start Date'
519 ],
520 'End Date' => [
521 'apiName' => 'end_date',
522 'displayLabel' => 'End Date'
523 ],
524 'Strict Project' => [
525 'apiName' => 'strict_project',
526 'displayLabel' => 'Strict Project'
527 ],
528 'Project Budget' => [
529 'apiName' => 'budget_type',
530 'displayLabel' => 'Project Budget'
531 ],
532 'Budget Amount' => [
533 'apiName' => 'budget_value',
534 'displayLabel' => 'Budget Amount'
535 ],
536 'Billing Method' => [
537 'apiName' => 'billing_method',
538 'displayLabel' => 'Billing Method'
539 ],
540 'Currency' => [
541 'apiName' => 'currency',
542 'displayLabel' => 'Currency'
543 ],
544 'Threshold Limit' => [
545 'apiName' => 'threshold',
546 'displayLabel' => 'Threshold Limit'
547 ],
548 'Rate Per Hour' => [
549 'apiName' => 'project_rate',
550 'displayLabel' => 'Rate Per Hour'
551 ],
552 'Fixed Cost' => [
553 'apiName' => 'fixed_cost',
554 'displayLabel' => 'Fixed Cost'
555 ],
556 'Bill Status' => [
557 'apiName' => 'bill_status',
558 'displayLabel' => 'Bill Status'
559 ]
560 ];
561
562 $response['required'][] = 'name';
563
564 $customFieldsMetaApiEndpoint = "https://projectsapi.zoho.{$dataCenter}/restapi/portal/{$portalId}/projects/customfields/";
565 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$access_token}";
566 $customFieldsMetaResponse = HttpHelper::get($customFieldsMetaApiEndpoint, null, $authorizationHeader);
567
568 if (!is_wp_error($customFieldsMetaResponse)) {
569 $fields = $customFieldsMetaResponse->project_custom_fields;
570
571 if (count($fields) > 0) {
572 foreach ($fields as $field) {
573 $allFields[$field->field_name] = (object) [
574 'apiName' => $field->field_id,
575 'displayLabel' => $field->field_name
576 ];
577
578 if ($field->is_mandatory) {
579 $response['required'][] = $field->field_id;
580 }
581 }
582 }
583 }
584
585 $response['fields'] = $allFields;
586 uksort($response['fields'], 'strnatcasecmp');
587 usort($response['required'], 'strnatcasecmp');
588
589 return $response;
590 }
591
592 protected static function getMilestoneFields()
593 {
594 $allFields = [
595 'Milestone Title' => [
596 'apiName' => 'name',
597 'displayLabel' => 'Milestone Title',
598 'required' => true
599 ],
600 'Start Date' => [
601 'apiName' => 'start_date',
602 'displayLabel' => 'Start Date',
603 'required' => true
604 ],
605 'End Date' => [
606 'apiName' => 'end_date',
607 'displayLabel' => 'End Date',
608 'required' => true
609 ]
610 ];
611
612 $response['required'] = ['name', 'start_date', 'end_date'];
613
614 $response['fields'] = $allFields;
615 uksort($response['fields'], 'strnatcasecmp');
616 usort($response['required'], 'strnatcasecmp');
617
618 return $response;
619 }
620
621 protected static function getTasklistFields()
622 {
623 $allFields = [
624 'Tasklist Title' => [
625 'apiName' => 'name',
626 'displayLabel' => 'Tasklist Title',
627 'required' => true
628 ]
629 ];
630
631 $response['required'] = ['name'];
632
633 $response['fields'] = $allFields;
634 uksort($response['fields'], 'strnatcasecmp');
635 usort($response['required'], 'strnatcasecmp');
636
637 return $response;
638 }
639
640 protected static function getTaskFields($dataCenter, $portalId, $access_token, $projectId)
641 {
642 $allFields = [
643 'Task Title' => [
644 'apiName' => 'name',
645 'displayLabel' => 'Task Title',
646 'required' => true
647 ],
648 'Task Description' => [
649 'apiName' => 'description',
650 'displayLabel' => 'Task Description'
651 ],
652 'Start Date' => [
653 'apiName' => 'start_date',
654 'displayLabel' => 'Start Date'
655 ],
656 'End Date' => [
657 'apiName' => 'end_date',
658 'displayLabel' => 'End Date'
659 ],
660 'Duration' => [
661 'apiName' => 'duration',
662 'displayLabel' => 'Duration'
663 ],
664 'Duration Type' => [
665 'apiName' => 'duration_type',
666 'displayLabel' => 'Duration Type'
667 ],
668 'Start Time' => [
669 'apiName' => 'start_time',
670 'displayLabel' => 'Start Time'
671 ],
672 'End Time' => [
673 'apiName' => 'end_time',
674 'displayLabel' => 'End Time'
675 ],
676 'Rate Per Hour' => [
677 'apiName' => 'rate_per_hour',
678 'displayLabel' => 'Rate Per Hour'
679 ],
680 'Priority' => [
681 'apiName' => 'priority',
682 'displayLabel' => 'Priority'
683 ]
684 ];
685
686 $response['required'][] = 'name';
687
688 // for associate with project
689 $authorizationHeader = null;
690 if ($projectId) {
691 $customFieldsMetaApiEndpoint = "https://projectsapi.zoho.{$dataCenter}/restapi/portal/{$portalId}/projects/{$projectId}/tasklayouts";
692 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$access_token}";
693 $customFieldsMetaResponse = HttpHelper::get($customFieldsMetaApiEndpoint, null, $authorizationHeader);
694
695 if (!is_wp_error($customFieldsMetaResponse)) {
696 $sections = $customFieldsMetaResponse->section_details;
697
698 if (count($sections) > 0) {
699 foreach ($sections as $section) {
700 $fields = $section->customfield_details;
701 foreach ($fields as $field) {
702 if (!$field->is_default) {
703 $allFields[$field->display_name] = (object) [
704 'apiName' => 'cf_' . $field->column_name,
705 'displayLabel' => $field->display_name
706 ];
707 if ($field->is_mandatory) {
708 $response['required'][] = 'cf_' . $field->column_name;
709 }
710 }
711 }
712 }
713 }
714 }
715 }
716
717 $response['fields'] = $allFields;
718 uksort($response['fields'], 'strnatcasecmp');
719 usort($response['required'], 'strnatcasecmp');
720
721 return $response;
722 }
723
724 protected static function getIssueFields($dataCenter, $portalId, $access_token, $projectId)
725 {
726 $allFields = [
727 'Issue Title' => [
728 'apiName' => 'title',
729 'displayLabel' => 'Issue Title',
730 'required' => true
731 ],
732 'Description' => [
733 'apiName' => 'description',
734 'displayLabel' => 'Description'
735 ],
736 'Due Date' => [
737 'apiName' => 'due_date',
738 'displayLabel' => 'Due Date'
739 ],
740 'Rate Per Hour' => [
741 'apiName' => 'rate_per_hour',
742 'displayLabel' => 'Rate Per Hour'
743 ]
744 ];
745
746 $response['required'] = ['title'];
747
748 // for associate with project
749 $authorizationHeader = null;
750 if ($projectId) {
751 // Custom Fields
752 $customFieldsMetaApiEndpoint = "https://projectsapi.zoho.{$dataCenter}/restapi/portal/{$portalId}/projects/{$projectId}/bugs/customfields/";
753 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$access_token}";
754 $customFieldsMetaResponse = HttpHelper::get($customFieldsMetaApiEndpoint, null, $authorizationHeader);
755
756 if (!is_wp_error($customFieldsMetaResponse)) {
757 $fields = $customFieldsMetaResponse->customfields;
758
759 if (count($fields) > 0) {
760 foreach ($fields as $field) {
761 $allFields[$field->label_name] = (object) [
762 'apiName' => $field->column_name,
763 'displayLabel' => $field->label_name
764 ];
765
766 if ('true' === $field->is_mandatory) {
767 $response['required'][] = $field->column_name;
768 }
769 }
770 }
771 }
772
773 // Default Fields
774 $defaultFieldsMetaApiEndpoint = "https://projectsapi.zoho.{$dataCenter}/restapi/portal/{$portalId}/projects/{$projectId}/bugs/defaultfields/";
775 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$access_token}";
776 $defaultFieldsMetaResponse = HttpHelper::get($defaultFieldsMetaApiEndpoint, null, $authorizationHeader);
777
778 if (!is_wp_error($defaultFieldsMetaResponse)) {
779 $response['defaultfields'] = $defaultFieldsMetaResponse->defaultfields;
780 }
781 }
782
783 $response['fields'] = $allFields;
784 uksort($response['fields'], 'strnatcasecmp');
785 usort($response['required'], 'strnatcasecmp');
786
787 return $response;
788 }
789
790 public static function refreshUsersAjaxHelper()
791 {
792 $authorizationHeader = null;
793 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
794 $inputJSON = file_get_contents('php://input');
795 $queryParams = json_decode($inputJSON);
796 if (
797 empty($queryParams->tokenDetails)
798 || empty($queryParams->dataCenter)
799 || empty($queryParams->clientId)
800 || empty($queryParams->clientSecret)
801 || empty($queryParams->portalId)
802 ) {
803 wp_send_json_error(
804 __(
805 'Requested parameter is empty',
806 'bit-form'
807 ),
808 400
809 );
810 }
811 $response = [];
812 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
813 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
814 }
815
816 $usersMetaApiEndpoint = '';
817
818 if ($queryParams->projectId) {
819 $usersMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/projects/{$queryParams->projectId}/users/";
820 } else {
821 $usersMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/users/";
822 }
823
824 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
825 $usersMetaResponse = HttpHelper::get($usersMetaApiEndpoint, null, $authorizationHeader);
826
827 // wp_send_json_success($usersMetaResponse, 200);
828
829 if (!is_wp_error($usersMetaResponse)) {
830 $users = $usersMetaResponse->users;
831
832 if (count($users) > 0) {
833 foreach ($users as $user) {
834 $response['users'][] = (object) [
835 'userId' => $user->id,
836 'userName' => $user->name,
837 'userEmail' => $user->email,
838 ];
839 }
840 }
841 } else {
842 wp_send_json_error(
843 empty($usersMetaResponse->data) ? 'Unknown' : $usersMetaResponse->error,
844 400
845 );
846 }
847 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
848 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
849 }
850 wp_send_json_success($response, 200);
851 } else {
852 wp_send_json_error(
853 __(
854 'Token expired',
855 'bit-form'
856 ),
857 401
858 );
859 }
860 }
861
862 public static function refreshTaskLaysAjaxHelper()
863 {
864 $authorizationHeader = null;
865 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
866 $inputJSON = file_get_contents('php://input');
867 $queryParams = json_decode($inputJSON);
868 if (
869 empty($queryParams->tokenDetails)
870 || empty($queryParams->dataCenter)
871 || empty($queryParams->clientId)
872 || empty($queryParams->clientSecret)
873 || empty($queryParams->portalId)
874 ) {
875 wp_send_json_error(
876 __(
877 'Requested parameter is empty',
878 'bit-form'
879 ),
880 400
881 );
882 }
883 $response = [];
884 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
885 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
886 }
887
888 $taskLaysMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/tasklayouts";
889
890 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
891 $taskLaysMetaResponse = HttpHelper::get($taskLaysMetaApiEndpoint, null, $authorizationHeader);
892
893 // wp_send_json_success($taskLaysMetaResponse, 200);
894
895 if (!is_wp_error($taskLaysMetaResponse)) {
896 $taskLays = $taskLaysMetaResponse->layouts;
897
898 if (count($taskLays) > 0) {
899 foreach ($taskLays as $taskLay) {
900 $response['taskLays'][] = (object) [
901 'taskLayId' => $taskLay->layout_id,
902 'taskLayName' => $taskLay->layout_name
903 ];
904 }
905 }
906 } else {
907 wp_send_json_error(
908 empty($taskLaysMetaResponse->data) ? 'Unknown' : $taskLaysMetaResponse->error,
909 400
910 );
911 }
912 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
913 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
914 }
915 wp_send_json_success($response, 200);
916 } else {
917 wp_send_json_error(
918 __(
919 'Token expired',
920 'bit-form'
921 ),
922 401
923 );
924 }
925 }
926
927 public static function refreshGroupsAjaxHelper()
928 {
929 $authorizationHeader = null;
930 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
931 $inputJSON = file_get_contents('php://input');
932 $queryParams = json_decode($inputJSON);
933 if (
934 empty($queryParams->tokenDetails)
935 || empty($queryParams->dataCenter)
936 || empty($queryParams->clientId)
937 || empty($queryParams->clientSecret)
938 || empty($queryParams->portalId)
939 ) {
940 wp_send_json_error(
941 __(
942 'Requested parameter is empty',
943 'bit-form'
944 ),
945 400
946 );
947 }
948 $response = [];
949 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
950 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
951 }
952
953 $groupsMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/restapi/portal/{$queryParams->portalId}/projects/groups";
954
955 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
956 $groupsMetaResponse = HttpHelper::get($groupsMetaApiEndpoint, null, $authorizationHeader);
957
958 // wp_send_json_success($groupsMetaResponse, 200);
959
960 if (!is_wp_error($groupsMetaResponse)) {
961 $groups = $groupsMetaResponse->groups;
962
963 if (count($groups) > 0) {
964 foreach ($groups as $group) {
965 $response['groups'][] = (object) [
966 'groupId' => $group->id,
967 'groupName' => $group->name
968 ];
969 }
970 }
971 } else {
972 wp_send_json_error(
973 empty($groupsMetaResponse->data) ? 'Unknown' : $groupsMetaResponse->error,
974 400
975 );
976 }
977 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
978 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
979 }
980 wp_send_json_success($response, 200);
981 } else {
982 wp_send_json_error(
983 __(
984 'Token expired',
985 'bit-form'
986 ),
987 401
988 );
989 }
990 }
991
992 public static function refreshTagsAjaxHelper()
993 {
994 $authorizationHeader = null;
995 if (isset($_REQUEST['_ajax_nonce']) && wp_verify_nonce($_REQUEST['_ajax_nonce'], 'bitforms_save')) {
996 $inputJSON = file_get_contents('php://input');
997 $queryParams = json_decode($inputJSON);
998 if (
999 empty($queryParams->tokenDetails)
1000 || empty($queryParams->dataCenter)
1001 || empty($queryParams->clientId)
1002 || empty($queryParams->clientSecret)
1003 || empty($queryParams->portalId)
1004 ) {
1005 wp_send_json_error(
1006 __(
1007 'Requested parameter is empty',
1008 'bit-form'
1009 ),
1010 400
1011 );
1012 }
1013
1014 $response = [];
1015 if ((intval($queryParams->tokenDetails->generates_on) + (55 * 60)) < time()) {
1016 $response['tokenDetails'] = ZohoProjectsHandler::_refreshAccessToken($queryParams);
1017 }
1018
1019 $tagsMetaApiEndpoint = "https://projectsapi.zoho.{$queryParams->dataCenter}/api/v3/portal/{$queryParams->portalId}/tags";
1020
1021 $authorizationHeader['Authorization'] = "Zoho-oauthtoken {$queryParams->tokenDetails->access_token}";
1022 $tagsMetaResponse = HttpHelper::get($tagsMetaApiEndpoint, null, $authorizationHeader);
1023
1024 // wp_send_json_success($tagsMetaResponse, 200);
1025
1026 if (!is_wp_error($tagsMetaResponse)) {
1027 $tags = $tagsMetaResponse->tags;
1028
1029 if (count($tags) > 0) {
1030 $allTags = [];
1031 foreach ($tags as $tag) {
1032 $allTags[$tag->name] = (object) [
1033 'tagId' => $tag->id,
1034 'tagName' => $tag->name
1035 ];
1036 }
1037 uksort($allTags, 'strnatcasecmp');
1038 $response['tags'] = $allTags;
1039 }
1040 } else {
1041 wp_send_json_error(
1042 empty($tagsMetaResponse->data) ? 'Unknown' : $tagsMetaResponse->error,
1043 400
1044 );
1045 }
1046 if (!empty($response['tokenDetails']) && !empty($queryParams->id)) {
1047 ZohoProjectsHandler::_saveRefreshedToken($queryParams->formID, $queryParams->id, $response['tokenDetails'], $response['lists']);
1048 }
1049 wp_send_json_success($response, 200);
1050 } else {
1051 wp_send_json_error(
1052 __(
1053 'Token expired',
1054 'bit-form'
1055 ),
1056 401
1057 );
1058 }
1059 }
1060
1061 protected static function _refreshAccessToken($apiData)
1062 {
1063 if (
1064 empty($apiData->dataCenter)
1065 || empty($apiData->clientId)
1066 || empty($apiData->clientSecret)
1067 || empty($apiData->tokenDetails)
1068 ) {
1069 return false;
1070 }
1071 $tokenDetails = $apiData->tokenDetails;
1072
1073 $dataCenter = $apiData->dataCenter;
1074 $apiEndpoint = "https://accounts.zoho.{$dataCenter}/oauth/v2/token";
1075 $requestParams = [
1076 'grant_type' => 'refresh_token',
1077 'client_id' => $apiData->clientId,
1078 'client_secret' => $apiData->clientSecret,
1079 'refresh_token' => $tokenDetails->refresh_token,
1080 ];
1081
1082 $apiResponse = HttpHelper::post($apiEndpoint, $requestParams);
1083 if (is_wp_error($apiResponse) || !empty($apiResponse->error)) {
1084 return false;
1085 }
1086 $tokenDetails->generates_on = \time();
1087 $tokenDetails->access_token = $apiResponse->access_token;
1088 return $tokenDetails;
1089 }
1090
1091 /**
1092 * Save updated access_token to avoid unnecessary token generation
1093 *
1094 * @param Integer $formID ID of Integration related form
1095 * @param Integer $integrationID ID of Zoho crm Integration
1096 * @param Obeject $tokenDetails refreshed token info
1097 *
1098 * @return null
1099 */
1100 protected static function _saveRefreshedToken($formID, $integrationID, $tokenDetails, $others = null)
1101 {
1102 if (empty($formID) || empty($integrationID)) {
1103 return;
1104 }
1105
1106 $integrationHandler = new IntegrationHandler($formID, IpTool::getUserDetail());
1107 $zprojectsDetails = $integrationHandler->getAIntegration($integrationID);
1108
1109 if (is_wp_error($zprojectsDetails)) {
1110 return;
1111 }
1112 $newDetails = json_decode($zprojectsDetails[0]->integration_details);
1113
1114 $newDetails->tokenDetails = $tokenDetails;
1115 if (!empty($others['portals'])) {
1116 $newDetails->default->portals = $others['portals'];
1117 }
1118
1119 $integrationHandler->updateIntegration($integrationID, $zprojectsDetails[0]->integration_name, 'Zoho Projects', \json_encode($newDetails), 'form');
1120 }
1121
1122 public function execute(IntegrationHandler $integrationHandler, $integrationData, $fieldValues, $entryID, $logID)
1123 {
1124 $integrationDetails = is_string($integrationData->integration_details) ? json_decode($integrationData->integration_details) : $integrationData->integration_details;
1125
1126 $tokenDetails = $integrationDetails->tokenDetails;
1127 $portalId = $integrationDetails->portalId;
1128 $dataCenter = $integrationDetails->dataCenter;
1129 $fieldMap = $integrationDetails->field_map;
1130 if (
1131 empty($tokenDetails)
1132 || empty($portalId)
1133 || empty($fieldMap)
1134 ) {
1135 return new WP_Error('REQ_FIELD_EMPTY', __('list are required for zoho projects api', 'bit-form'));
1136 }
1137
1138 $requiredParams = null;
1139 if ((intval($tokenDetails->generates_on) + (55 * 60)) < time()) {
1140 $requiredParams['clientId'] = $integrationDetails->clientId;
1141 $requiredParams['clientSecret'] = $integrationDetails->clientSecret;
1142 $requiredParams['dataCenter'] = $integrationDetails->dataCenter;
1143 $requiredParams['tokenDetails'] = $tokenDetails;
1144 $newTokenDetails = ZohoProjectsHandler::_refreshAccessToken((object)$requiredParams);
1145 if ($newTokenDetails) {
1146 ZohoProjectsHandler::_saveRefreshedToken($this->_formID, $this->_integrationID, $newTokenDetails);
1147 $tokenDetails = $newTokenDetails;
1148 }
1149 }
1150
1151 $recordApiHelper = new RecordApiHelper($tokenDetails, $this->_integrationID, $logID);
1152
1153 $zprojectsApiResponse = $recordApiHelper->executeRecordApi(
1154 $this->_formID,
1155 $entryID,
1156 $integrationDetails,
1157 $dataCenter,
1158 $fieldMap,
1159 $fieldValues
1160 );
1161
1162 if (is_wp_error($zprojectsApiResponse)) {
1163 return $zprojectsApiResponse;
1164 }
1165 return $zprojectsApiResponse;
1166 }
1167 }
1168