ILIAS  release_5-3 Revision v5.3.23-19-g915713cf615
ResourceLink.php
Go to the documentation of this file.
1<?php
2
4
5use DOMDocument;
6use DOMElement;
11
22{
23
27 const EXT_READ = 1;
31 const EXT_WRITE = 2;
35 const EXT_DELETE = 3;
39 const EXT_CREATE = 4;
43 const EXT_UPDATE = 5;
44
48 const EXT_TYPE_DECIMAL = 'decimal';
52 const EXT_TYPE_PERCENTAGE = 'percentage';
56 const EXT_TYPE_RATIO = 'ratio';
60 const EXT_TYPE_LETTER_AF = 'letteraf';
64 const EXT_TYPE_LETTER_AF_PLUS = 'letterafplus';
68 const EXT_TYPE_PASS_FAIL = 'passfail';
72 const EXT_TYPE_TEXT = 'freetext';
73
79 public $title = null;
85 public $ltiResourceLinkId = null;
91 public $groupSets = null;
97 public $groups = null;
103 public $extRequest = null;
109 public $extRequestHeaders = null;
115 public $extResponse = null;
121 public $extResponseHeaders = null;
133 public $shareApproved = null;
139 public $created = null;
145 public $updated = null;
146
152 private $id = null;
158 private $consumer = null;
164 private $consumerId = null;
170 private $context = null;
176 private $contextId = null;
182 private $settings = null;
188 private $settingsChanged = false;
194 private $extDoc = null;
200 private $extNodes = null;
206 private $dataConnector = null;
207
211 public function __construct()
212 {
213
214 $this->initialize();
215
216 }
217
221 public function initialize()
222 {
223
224 $this->title = '';
225 $this->settings = array();
226 $this->groupSets = null;
227 $this->groups = null;
228 $this->primaryResourceLinkId = null;
229 $this->shareApproved = null;
230 $this->created = null;
231 $this->updated = null;
232
233 }
234
240 public function initialise()
241 {
242
243 $this->initialize();
244
245 }
246
252 public function save()
253 {
254
255 $ok = $this->getDataConnector()->saveResourceLink($this);
256 if ($ok) {
257 $this->settingsChanged = false;
258 }
259
260 return $ok;
261
262 }
263
269 public function delete()
270 {
271
272 return $this->getDataConnector()->deleteResourceLink($this);
273
274 }
275
281 public function getConsumer()
282 {
283
284 if (is_null($this->consumer)) {
285 // begin-patch ilias
286 #if (!is_null($this->context) || !is_null($this->contextId)) {
287 if($this->context || $this->contextId) {
288 $this->consumer = $this->getContext()->getConsumer();
289 } else {
290 $this->consumer = ToolConsumer::fromRecordId($this->consumerId, $this->getDataConnector());
291 }
292 }
293
294 return $this->consumer;
295
296 }
297
303 public function setConsumerId($consumerId)
304 {
305
306 $this->consumer = null;
307 $this->consumerId = $consumerId;
308
309 }
310
316 public function getContext()
317 {
318
319 if (is_null($this->context) && !is_null($this->contextId)) {
320 $this->context = Context::fromRecordId($this->contextId, $this->getDataConnector());
321 }
322
323 return $this->context;
324
325 }
326
332 public function getContextId()
333 {
334
335 return $this->contextId;
336
337 }
338
344 public function setContextId($contextId)
345 {
346
347 $this->context = null;
348 $this->contextId = $contextId;
349
350 }
351
357 public function getKey()
358 {
359
360 return $this->getConsumer()->getKey();
361
362 }
363
369 public function getId()
370 {
371
373
374 }
375
381 public function getRecordId()
382 {
383
384 return $this->id;
385
386 }
387
393 public function setRecordId($id)
394 {
395
396 $this->id = $id;
397
398 }
399
405 public function getDataConnector()
406 {
407
409
410 }
411
420 public function getSetting($name, $default = '')
421 {
422
423 if (array_key_exists($name, $this->settings)) {
424 $value = $this->settings[$name];
425 } else {
426 $value = $default;
427 }
428
429 return $value;
430
431 }
432
439 public function setSetting($name, $value = null)
440 {
441
442 $old_value = $this->getSetting($name);
443 if ($value !== $old_value) {
444 if (!empty($value)) {
445 $this->settings[$name] = $value;
446 } else {
447 unset($this->settings[$name]);
448 }
449 $this->settingsChanged = true;
450 }
451
452 }
453
459 public function getSettings()
460 {
461
462 return $this->settings;
463
464 }
465
471 public function setSettings($settings)
472 {
473
474 $this->settings = $settings;
475
476 }
477
483 public function saveSettings()
484 {
485
486 if ($this->settingsChanged) {
487 $ok = $this->save();
488 } else {
489 $ok = true;
490 }
491
492 return $ok;
493
494 }
495
501 public function hasOutcomesService()
502 {
503
504 $url = $this->getSetting('ext_ims_lis_basic_outcome_url') . $this->getSetting('lis_outcome_service_url');
505
506 return !empty($url);
507
508 }
509
515 public function hasMembershipsService()
516 {
517
518 $url = $this->getSetting('ext_ims_lis_memberships_url');
519
520 return !empty($url);
521
522 }
523
529 public function hasSettingService()
530 {
531
532 $url = $this->getSetting('ext_ims_lti_tool_setting_url');
533
534 return !empty($url);
535
536 }
537
547 public function doOutcomesService($action, $ltiOutcome, $user)
548 {
549
550 $response = false;
551 $this->extResponse = null;
552
553// Lookup service details from the source resource link appropriate to the user (in case the destination is being shared)
554 $sourceResourceLink = $user->getResourceLink();
555 $sourcedId = $user->ltiResultSourcedId;
556
557// Use LTI 1.1 service in preference to extension service if it is available
558 $urlLTI11 = $sourceResourceLink->getSetting('lis_outcome_service_url');
559 $urlExt = $sourceResourceLink->getSetting('ext_ims_lis_basic_outcome_url');
560 if ($urlExt || $urlLTI11) {
561 switch ($action) {
562 case self::EXT_READ:
563 if ($urlLTI11 && ($ltiOutcome->type === self::EXT_TYPE_DECIMAL)) {
564 $do = 'readResult';
565 } else if ($urlExt) {
566 $urlLTI11 = null;
567 $do = 'basic-lis-readresult';
568 }
569 break;
570 case self::EXT_WRITE:
571 if ($urlLTI11 && $this->checkValueType($ltiOutcome, array(self::EXT_TYPE_DECIMAL))) {
572 $do = 'replaceResult';
573 } else if ($this->checkValueType($ltiOutcome)) {
574 $urlLTI11 = null;
575 $do = 'basic-lis-updateresult';
576 }
577 break;
578 case self::EXT_DELETE:
579 if ($urlLTI11 && ($ltiOutcome->type === self::EXT_TYPE_DECIMAL)) {
580 $do = 'deleteResult';
581 } else if ($urlExt) {
582 $urlLTI11 = null;
583 $do = 'basic-lis-deleteresult';
584 }
585 break;
586 }
587 }
588 if (isset($do)) {
589 $value = $ltiOutcome->getValue();
590 if (is_null($value)) {
591 $value = '';
592 }
593 if ($urlLTI11) {
594 $xml = '';
595 if ($action === self::EXT_WRITE) {
596 $xml = <<<EOF
597
598 <result>
599 <resultScore>
600 <language>{$ltiOutcome->language}</language>
601 <textString>{$value}</textString>
602 </resultScore>
603 </result>
604EOF;
605 }
606 $sourcedId = htmlentities($sourcedId);
607 $xml = <<<EOF
608 <resultRecord>
609 <sourcedGUID>
610 <sourcedId>{$sourcedId}</sourcedId>
611 </sourcedGUID>{$xml}
612 </resultRecord>
613EOF;
614 if ($this->doLTI11Service($do, $urlLTI11, $xml)) {
615 switch ($action) {
616 case self::EXT_READ:
617 if (!isset($this->extNodes['imsx_POXBody']["{$do}Response"]['result']['resultScore']['textString'])) {
618 break;
619 } else {
620 $ltiOutcome->setValue($this->extNodes['imsx_POXBody']["{$do}Response"]['result']['resultScore']['textString']);
621 }
622 case self::EXT_WRITE:
623 case self::EXT_DELETE:
624 $response = true;
625 break;
626 }
627 }
628 } else {
629 $params = array();
630 $params['sourcedid'] = $sourcedId;
631 $params['result_resultscore_textstring'] = $value;
632 if (!empty($ltiOutcome->language)) {
633 $params['result_resultscore_language'] = $ltiOutcome->language;
634 }
635 if (!empty($ltiOutcome->status)) {
636 $params['result_statusofresult'] = $ltiOutcome->status;
637 }
638 if (!empty($ltiOutcome->date)) {
639 $params['result_date'] = $ltiOutcome->date;
640 }
641 if (!empty($ltiOutcome->type)) {
642 $params['result_resultvaluesourcedid'] = $ltiOutcome->type;
643 }
644 if (!empty($ltiOutcome->data_source)) {
645 $params['result_datasource'] = $ltiOutcome->data_source;
646 }
647 if ($this->doService($do, $urlExt, $params)) {
648 switch ($action) {
649 case self::EXT_READ:
650 if (isset($this->extNodes['result']['resultscore']['textstring'])) {
651 $response = $this->extNodes['result']['resultscore']['textstring'];
652 }
653 break;
654 case self::EXT_WRITE:
655 case self::EXT_DELETE:
656 $response = true;
657 break;
658 }
659 }
660 }
661 if (is_array($response) && (count($response) <= 0)) {
662 $response = '';
663 }
664 }
665
666 return $response;
667
668 }
669
679 public function doMembershipsService($withGroups = false)
680 {
681
682 $users = array();
684 $this->extResponse = null;
685 $url = $this->getSetting('ext_ims_lis_memberships_url');
686 $params = array();
687 $params['id'] = $this->getSetting('ext_ims_lis_memberships_id');
688 $ok = false;
689 if ($withGroups) {
690 $ok = $this->doService('basic-lis-readmembershipsforcontextwithgroups', $url, $params);
691 }
692 if ($ok) {
693 $this->groupSets = array();
694 $this->groups = array();
695 } else {
696 $ok = $this->doService('basic-lis-readmembershipsforcontext', $url, $params);
697 }
698
699 if ($ok) {
700 if (!isset($this->extNodes['memberships']['member'])) {
701 $members = array();
702 } else if (!isset($this->extNodes['memberships']['member'][0])) {
703 $members = array();
704 $members[0] = $this->extNodes['memberships']['member'];
705 } else {
706 $members = $this->extNodes['memberships']['member'];
707 }
708
709 for ($i = 0; $i < count($members); $i++) {
710
711 $user = User::fromResourceLink($this, $members[$i]['user_id']);
712
713// Set the user name
714 $firstname = (isset($members[$i]['person_name_given'])) ? $members[$i]['person_name_given'] : '';
715 $lastname = (isset($members[$i]['person_name_family'])) ? $members[$i]['person_name_family'] : '';
716 $fullname = (isset($members[$i]['person_name_full'])) ? $members[$i]['person_name_full'] : '';
717 $user->setNames($firstname, $lastname, $fullname);
718
719// Set the user email
720 $email = (isset($members[$i]['person_contact_email_primary'])) ? $members[$i]['person_contact_email_primary'] : '';
721 $user->setEmail($email, $this->getConsumer()->defaultEmail);
722
724 if (isset($members[$i]['roles'])) {
725 $user->roles = ToolProvider::parseRoles($members[$i]['roles']);
726 }
727
728// Set the user groups
729 if (!isset($members[$i]['groups']['group'])) {
730 $groups = array();
731 } else if (!isset($members[$i]['groups']['group'][0])) {
732 $groups = array();
733 $groups[0] = $members[$i]['groups']['group'];
734 } else {
735 $groups = $members[$i]['groups']['group'];
736 }
737 for ($j = 0; $j < count($groups); $j++) {
738 $group = $groups[$j];
739 if (isset($group['set'])) {
740 $set_id = $group['set']['id'];
741 if (!isset($this->groupSets[$set_id])) {
742 $this->groupSets[$set_id] = array('title' => $group['set']['title'], 'groups' => array(),
743 'num_members' => 0, 'num_staff' => 0, 'num_learners' => 0);
744 }
745 $this->groupSets[$set_id]['num_members']++;
746 if ($user->isStaff()) {
747 $this->groupSets[$set_id]['num_staff']++;
748 }
749 if ($user->isLearner()) {
750 $this->groupSets[$set_id]['num_learners']++;
751 }
752 if (!in_array($group['id'], $this->groupSets[$set_id]['groups'])) {
753 $this->groupSets[$set_id]['groups'][] = $group['id'];
754 }
755 $this->groups[$group['id']] = array('title' => $group['title'], 'set' => $set_id);
756 } else {
757 $this->groups[$group['id']] = array('title' => $group['title']);
758 }
759 $user->groups[] = $group['id'];
760 }
761
762// If a result sourcedid is provided save the user
763 if (isset($members[$i]['lis_result_sourcedid'])) {
764 $user->ltiResultSourcedId = $members[$i]['lis_result_sourcedid'];
765 $user->save();
766 }
767 $users[] = $user;
768
769// Remove old user (if it exists)
770 unset($oldUsers[$user->getId(ToolProvider::ID_SCOPE_RESOURCE)]);
771 }
772
773// Delete any old users which were not in the latest list from the tool consumer
774 foreach ($oldUsers as $id => $user) {
775 $user->delete();
776 }
777 } else {
778 $users = false;
779 }
780
781 return $users;
782
783 }
784
793 public function doSettingService($action, $value = null)
794 {
795
796 $response = false;
797 $this->extResponse = null;
798 switch ($action) {
799 case self::EXT_READ:
800 $do = 'basic-lti-loadsetting';
801 break;
802 case self::EXT_WRITE:
803 $do = 'basic-lti-savesetting';
804 break;
805 case self::EXT_DELETE:
806 $do = 'basic-lti-deletesetting';
807 break;
808 }
809 if (isset($do)) {
810
811 $url = $this->getSetting('ext_ims_lti_tool_setting_url');
812 $params = array();
813 $params['id'] = $this->getSetting('ext_ims_lti_tool_setting_id');
814 if (is_null($value)) {
815 $value = '';
816 }
817 $params['setting'] = $value;
818
819 if ($this->doService($do, $url, $params)) {
820 switch ($action) {
821 case self::EXT_READ:
822 if (isset($this->extNodes['setting']['value'])) {
823 $response = $this->extNodes['setting']['value'];
824 if (is_array($response)) {
825 $response = '';
826 }
827 }
828 break;
829 case self::EXT_WRITE:
830 $this->setSetting('ext_ims_lti_tool_setting', $value);
831 $this->saveSettings();
832 $response = true;
833 break;
834 case self::EXT_DELETE:
835 $response = true;
836 break;
837 }
838 }
839 }
840
841 return $response;
842
843 }
844
850 public function hasToolSettingsService()
851 {
852
853 $url = $this->getSetting('custom_link_setting_url');
854
855 return !empty($url);
856
857 }
858
867 public function getToolSettings($mode = Service\ToolSettings::MODE_CURRENT_LEVEL, $simple = true)
868 {
869
870 $url = $this->getSetting('custom_link_setting_url');
871 $service = new Service\ToolSettings($this, $url, $simple);
872 $response = $service->get($mode);
873
874 return $response;
875
876 }
877
885 public function setToolSettings($settings = array())
886 {
887
888 $url = $this->getSetting('custom_link_setting_url');
889 $service = new Service\ToolSettings($this, $url);
891
892 return $response;
893
894 }
895
901 public function hasMembershipService()
902 {
903
904 $has = !empty($this->contextId);
905 if ($has) {
906 $has = !empty($this->getContext()->getSetting('custom_context_memberships_url'));
907 }
908
909 return $has;
910
911 }
912
918 public function getMembership()
919 {
920
921 $response = false;
922 if (!empty($this->contextId)) {
923 $url = $this->getContext()->getSetting('custom_context_memberships_url');
924 if (!empty($url)) {
925 $service = new Service\Membership($this, $url);
926 $response = $service->get();
927 }
928 }
929
930 return $response;
931
932 }
933
945 public function getUserResultSourcedIDs($localOnly = false, $idScope = null)
946 {
947
948 return $this->getDataConnector()->getUserResultSourcedIDsResourceLink($this, $localOnly, $idScope);
949
950 }
951
957 public function getShares()
958 {
959
960 return $this->getDataConnector()->getSharesResourceLink($this);
961
962 }
963
972 public static function fromConsumer($consumer, $ltiResourceLinkId, $tempId = null)
973 {
974
975 $resourceLink = new ResourceLink();
976 $resourceLink->consumer = $consumer;
977 $resourceLink->dataConnector = $consumer->getDataConnector();
978 $resourceLink->ltiResourceLinkId = $ltiResourceLinkId;
979 if (!empty($ltiResourceLinkId)) {
980 $resourceLink->load();
981 if (is_null($resourceLink->id) && !empty($tempId)) {
982 $resourceLink->ltiResourceLinkId = $tempId;
983 $resourceLink->load();
984 $resourceLink->ltiResourceLinkId = $ltiResourceLinkId;
985 }
986 }
987
988 return $resourceLink;
989
990 }
991
1000 public static function fromContext($context, $ltiResourceLinkId, $tempId = null)
1001 {
1002
1003 $resourceLink = new ResourceLink();
1004 $resourceLink->setContextId($context->getRecordId());
1005 $resourceLink->context = $context;
1006 $resourceLink->dataConnector = $context->getDataConnector();
1007 $resourceLink->ltiResourceLinkId = $ltiResourceLinkId;
1008 if (!empty($ltiResourceLinkId)) {
1009 $resourceLink->load();
1010 if (is_null($resourceLink->id) && !empty($tempId)) {
1011 $resourceLink->ltiResourceLinkId = $tempId;
1012 $resourceLink->load();
1013 $resourceLink->ltiResourceLinkId = $ltiResourceLinkId;
1014 }
1015 }
1016
1017 return $resourceLink;
1018
1019 }
1020
1029 public static function fromRecordId($id, $dataConnector)
1030 {
1031 $resourceLink = new ResourceLink();
1032 $resourceLink->dataConnector = $dataConnector;
1033 $resourceLink->load($id);
1034
1035 return $resourceLink;
1036
1037 }
1038
1039###
1040### PRIVATE METHODS
1041###
1042
1050 private function load($id = null)
1051 {
1052
1053 $this->initialize();
1054 $this->id = $id;
1055
1056 return $this->getDataConnector()->loadResourceLink($this);
1057
1058 }
1059
1068 private function checkValueType($ltiOutcome, $supportedTypes = null)
1069 {
1070
1071 if (empty($supportedTypes)) {
1072 $supportedTypes = explode(',', str_replace(' ', '', strtolower($this->getSetting('ext_ims_lis_resultvalue_sourcedids', self::EXT_TYPE_DECIMAL))));
1073 }
1074 $type = $ltiOutcome->type;
1075 $value = $ltiOutcome->getValue();
1076// Check whether the type is supported or there is no value
1077 $ok = in_array($type, $supportedTypes) || (strlen($value) <= 0);
1078 if (!$ok) {
1079// Convert numeric values to decimal
1080 if ($type === self::EXT_TYPE_PERCENTAGE) {
1081 if (substr($value, -1) === '%') {
1082 $value = substr($value, 0, -1);
1083 }
1084 $ok = is_numeric($value) && ($value >= 0) && ($value <= 100);
1085 if ($ok) {
1086 $ltiOutcome->setValue($value / 100);
1087 $ltiOutcome->type = self::EXT_TYPE_DECIMAL;
1088 }
1089 } else if ($type === self::EXT_TYPE_RATIO) {
1090 $parts = explode('/', $value, 2);
1091 $ok = (count($parts) === 2) && is_numeric($parts[0]) && is_numeric($parts[1]) && ($parts[0] >= 0) && ($parts[1] > 0);
1092 if ($ok) {
1093 $ltiOutcome->setValue($parts[0] / $parts[1]);
1094 $ltiOutcome->type = self::EXT_TYPE_DECIMAL;
1095 }
1096// Convert letter_af to letter_af_plus or text
1097 } else if ($type === self::EXT_TYPE_LETTER_AF) {
1098 if (in_array(self::EXT_TYPE_LETTER_AF_PLUS, $supportedTypes)) {
1099 $ok = true;
1100 $ltiOutcome->type = self::EXT_TYPE_LETTER_AF_PLUS;
1101 } else if (in_array(self::EXT_TYPE_TEXT, $supportedTypes)) {
1102 $ok = true;
1103 $ltiOutcome->type = self::EXT_TYPE_TEXT;
1104 }
1105// Convert letter_af_plus to letter_af or text
1106 } else if ($type === self::EXT_TYPE_LETTER_AF_PLUS) {
1107 if (in_array(self::EXT_TYPE_LETTER_AF, $supportedTypes) && (strlen($value) === 1)) {
1108 $ok = true;
1109 $ltiOutcome->type = self::EXT_TYPE_LETTER_AF;
1110 } else if (in_array(self::EXT_TYPE_TEXT, $supportedTypes)) {
1111 $ok = true;
1112 $ltiOutcome->type = self::EXT_TYPE_TEXT;
1113 }
1114// Convert text to decimal
1115 } else if ($type === self::EXT_TYPE_TEXT) {
1116 $ok = is_numeric($value) && ($value >= 0) && ($value <=1);
1117 if ($ok) {
1118 $ltiOutcome->type = self::EXT_TYPE_DECIMAL;
1119 } else if (substr($value, -1) === '%') {
1120 $value = substr($value, 0, -1);
1121 $ok = is_numeric($value) && ($value >= 0) && ($value <=100);
1122 if ($ok) {
1123 if (in_array(self::EXT_TYPE_PERCENTAGE, $supportedTypes)) {
1124 $ltiOutcome->type = self::EXT_TYPE_PERCENTAGE;
1125 } else {
1126 $ltiOutcome->setValue($value / 100);
1127 $ltiOutcome->type = self::EXT_TYPE_DECIMAL;
1128 }
1129 }
1130 }
1131 }
1132 }
1133
1134 return $ok;
1135
1136 }
1137
1147 private function doService($type, $url, $params)
1148 {
1149
1150 $ok = false;
1151 $this->extRequest = null;
1152 $this->extRequestHeaders = '';
1153 $this->extResponse = null;
1154 $this->extResponseHeaders = '';
1155 if (!empty($url)) {
1156 $params = $this->getConsumer()->signParameters($url, $type, $this->getConsumer()->ltiVersion, $params);
1157// Connect to tool consumer
1158 $http = new HTTPMessage($url, 'POST', $params);
1159// Parse XML response
1160 if ($http->send()) {
1161 $this->extResponse = $http->response;
1162 $this->extResponseHeaders = $http->responseHeaders;
1163 try {
1164 $this->extDoc = new DOMDocument();
1165 $this->extDoc->loadXML($http->response);
1166 $this->extNodes = $this->domnodeToArray($this->extDoc->documentElement);
1167 if (isset($this->extNodes['statusinfo']['codemajor']) && ($this->extNodes['statusinfo']['codemajor'] === 'Success')) {
1168 $ok = true;
1169 }
1170 } catch (\Exception $e) {
1171 }
1172 }
1173 $this->extRequest = $http->request;
1174 $this->extRequestHeaders = $http->requestHeaders;
1175 }
1176
1177 return $ok;
1178
1179 }
1180
1190 private function doLTI11Service($type, $url, $xml)
1191 {
1192
1193 $ok = false;
1194 $this->extRequest = null;
1195 $this->extRequestHeaders = '';
1196 $this->extResponse = null;
1197 $this->extResponseHeaders = '';
1198 if (!empty($url)) {
1199 $id = uniqid();
1200 $xmlRequest = <<< EOD
1201<?xml version = "1.0" encoding = "UTF-8"?>
1202<imsx_POXEnvelopeRequest xmlns = "http://www.imsglobal.org/services/ltiv1p1/xsd/imsoms_v1p0">
1203 <imsx_POXHeader>
1204 <imsx_POXRequestHeaderInfo>
1205 <imsx_version>V1.0</imsx_version>
1206 <imsx_messageIdentifier>{$id}</imsx_messageIdentifier>
1207 </imsx_POXRequestHeaderInfo>
1208 </imsx_POXHeader>
1209 <imsx_POXBody>
1210 <{$type}Request>
1211{$xml}
1212 </{$type}Request>
1213 </imsx_POXBody>
1214</imsx_POXEnvelopeRequest>
1215EOD;
1216// Calculate body hash
1217 $hash = base64_encode(sha1($xmlRequest, true));
1218 $params = array('oauth_body_hash' => $hash);
1219
1220// Add OAuth signature
1221 $hmacMethod = new OAuth\OAuthSignatureMethod_HMAC_SHA1();
1222 $consumer = new OAuth\OAuthConsumer($this->getConsumer()->getKey(), $this->getConsumer()->secret, null);
1224 $req->sign_request($hmacMethod, $consumer, null);
1225 $params = $req->get_parameters();
1226 $header = $req->to_header();
1227 $header .= "\nContent-Type: application/xml";
1228// Connect to tool consumer
1229 $http = new HTTPMessage($url, 'POST', $xmlRequest, $header);
1230// Parse XML response
1231 if ($http->send()) {
1232 $this->extResponse = $http->response;
1233 $this->extResponseHeaders = $http->responseHeaders;
1234 try {
1235 $this->extDoc = new DOMDocument();
1236 $this->extDoc->loadXML($http->response);
1237 $this->extNodes = $this->domnodeToArray($this->extDoc->documentElement);
1238 if (isset($this->extNodes['imsx_POXHeader']['imsx_POXResponseHeaderInfo']['imsx_statusInfo']['imsx_codeMajor']) &&
1239 ($this->extNodes['imsx_POXHeader']['imsx_POXResponseHeaderInfo']['imsx_statusInfo']['imsx_codeMajor'] === 'success')) {
1240 $ok = true;
1241 }
1242 } catch (\Exception $e) {
1243 }
1244 }
1245 $this->extRequest = $http->request;
1246 $this->extRequestHeaders = $http->requestHeaders;
1247 }
1248
1249 return $ok;
1250
1251 }
1252
1260 private function domnodeToArray($node)
1261 {
1262
1263 $output = '';
1264 switch ($node->nodeType) {
1265 case XML_CDATA_SECTION_NODE:
1266 case XML_TEXT_NODE:
1267 $output = trim($node->textContent);
1268 break;
1269 case XML_ELEMENT_NODE:
1270 for ($i = 0; $i < $node->childNodes->length; $i++) {
1271 $child = $node->childNodes->item($i);
1272 $v = $this->domnodeToArray($child);
1273 if (isset($child->tagName)) {
1274 $t = $child->tagName;
1275 if (!isset($output[$t])) {
1276 $output[$t] = array();
1277 }
1278 $output[$t][] = $v;
1279 } else {
1280 $s = (string) $v;
1281 if (strlen($s) > 0) {
1282 $output = $s;
1283 }
1284 }
1285 }
1286 if (is_array($output)) {
1287 if ($node->attributes->length) {
1288 $a = array();
1289 foreach ($node->attributes as $attrName => $attrNode) {
1290 $a[$attrName] = (string) $attrNode->value;
1291 }
1292 $output['@attributes'] = $a;
1293 }
1294 foreach ($output as $t => $v) {
1295 if (is_array($v) && count($v)==1 && $t!='@attributes') {
1296 $output[$t] = $v[0];
1297 }
1298 }
1299 }
1300 break;
1301 }
1302
1303 return $output;
1304
1305 }
1306
1307}
const EOF
How fgetc() reports an End Of File.
Definition: JSMin_lib.php:92
$users
Definition: authpage.php:44
An exception for terminatinating execution or to throw for unit testing.
Class to represent an HTTP message.
Definition: HTTPMessage.php:15
Class to represent an OAuth Consumer.
static from_consumer_and_token($consumer, $token, $http_method, $http_url, $parameters=null)
pretty much a helper function to set up the request
Class to represent an OAuth HMAC_SHA1 signature method.
static fromRecordId($id, $dataConnector)
Load the context from the database.
Definition: Context.php:407
Class to provide a connection to a persistent store for LTI objects.
Class to implement the Membership service.
Definition: Membership.php:17
Class to implement a service.
Definition: Service.php:18
Class to implement the Tool Settings service.
const MODE_CURRENT_LEVEL
Settings at current level mode.
static fromRecordId($id, $dataConnector)
Load the tool consumer from the database by its record ID.
static parseRoles($roles)
Get an array of fully qualified user roles.
const ID_SCOPE_RESOURCE
Prefix the ID with the consumer key and resource ID.
static fromResourceLink($resourceLink, $ltiUserId)
Class constructor from resource link.
Definition: User.php:413
$action
$i
Definition: disco.tpl.php:19
if(!is_dir( $entity_dir)) exit("Fatal Error ([A-Za-z0-9]+)\s+" &#(? foreach( $entity_files as $file) $output
$req
Definition: getUserInfo.php:20
$service
Definition: login.php:15
if($format !==null) $name
Definition: metadata.php:146
if( $orgName !==null) if($spconfig->hasValue('contacts')) $email
Definition: metadata.php:193
$xml
Definition: metadata.php:240
$type
$url
$response
$s
Definition: pwgen.php:45
$http
Definition: raiseError.php:7
settings()
Definition: settings.php:2
$params
Definition: disable.php:11