diff --git a/enrol/lti/classes/data_connector.php b/enrol/lti/classes/data_connector.php index b02ac8f96ea..d3819c0f5f6 100644 --- a/enrol/lti/classes/data_connector.php +++ b/enrol/lti/classes/data_connector.php @@ -1,5 +1,4 @@ consumertable = $this->dbTableNamePrefix . DataConnector::CONSUMER_TABLE_NAME; + $this->contexttable = $this->dbTableNamePrefix . DataConnector::CONTEXT_TABLE_NAME; + $this->noncetable = $this->dbTableNamePrefix . DataConnector::NONCE_TABLE_NAME; + $this->resourcelinktable = $this->dbTableNamePrefix . DataConnector::RESOURCE_LINK_TABLE_NAME; + $this->sharekeytable = $this->dbTableNamePrefix . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME; + $this->toolproxytable = $this->dbTableNamePrefix . DataConnector::TOOL_PROXY_TABLE_NAME; + $this->userresulttable = $this->dbTableNamePrefix . DataConnector::USER_RESULT_TABLE_NAME; } /** * Load tool consumer object. * * @param ToolConsumer $consumer ToolConsumer object - * * @return boolean True if the tool consumer object was successfully loaded */ public function loadToolConsumer($consumer) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::CONSUMER_TABLE_NAME; - - $ok = false; - $fields = 'id, name, consumer_key256, consumer_key, secret, lti_version, ' . - 'consumer_name, consumer_version, consumer_guid, ' . - 'profile, tool_proxy, settings, protected, enabled, ' . - 'enable_from, enable_until, last_access, created, updated'; $id = $consumer->getRecordId(); - $result = []; if (!empty($id)) { - $result = $DB->get_records($table, ['id' => $id], '', $fields); + $result = $DB->get_record($this->consumertable, ['id' => $id]); } else { $key256 = DataConnector::getConsumerKey($consumer->getKey()); - $result = $DB->get_records($table, ['consumer_key256' => $key256], '', $fields); + $result = $DB->get_record($this->consumertable, ['consumer_key256' => $key256]); } - // TODO Catch exceptions. - foreach ($result as $row) { - if (empty($key256) || empty($row->consumer_key) || ($consumer->getKey() === $row->consumer_key)) { - $consumer->setRecordId(intval($row->id)); - $consumer->name = $row->name; - $consumer->setkey(empty($row->consumer_key) ? $row->consumer_key256 : $row->consumer_key); - $consumer->secret = $row->secret; - $consumer->ltiVersion = $row->lti_version; - $consumer->consumerName = $row->consumer_name; - $consumer->consumerVersion = $row->consumer_version; - $consumer->consumerGuid = $row->consumer_guid; - $consumer->profile = json_decode($row->profile); - $consumer->toolProxy = $row->tool_proxy; - $settings = unserialize($row->settings); - if (!is_array($settings)) { - $settings = array(); - } - $consumer->setSettings($settings); - $consumer->protected = (intval($row->protected) === 1); - $consumer->enabled = (intval($row->enabled) === 1); - $consumer->enableFrom = null; - if (!is_null($row->enable_from)) { - $consumer->enableFrom = strtotime($row->enable_from); - } - $consumer->enableUntil = null; - if (!is_null($row->enable_until)) { - $consumer->enableUntil = strtotime($row->enable_until); - } - $consumer->lastAccess = null; - if (!is_null($row->last_access)) { - $consumer->lastAccess = strtotime($row->last_access); - } - $consumer->created = strtotime($row->created); - $consumer->updated = strtotime($row->updated); - $ok = true; - break; + + if ($result) { + if (empty($key256) || empty($result->consumer_key) || ($consumer->getKey() === $result->consumer_key)) { + $this->build_tool_consumer_object($result, $consumer); + return true; } } - return $ok; - + return false; } /** * Save tool consumer object. * * @param ToolConsumer $consumer Consumer object - * * @return boolean True if the tool consumer object was successfully saved */ public function saveToolConsumer($consumer) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::CONSUMER_TABLE_NAME; - $key = $consumer->getKey(); $key256 = DataConnector::getConsumerKey($key); if ($key === $key256) { $key = null; } $protected = ($consumer->protected) ? 1 : 0; - $enabled = ($consumer->enabled)? 1 : 0; + $enabled = ($consumer->enabled) ? 1 : 0; $profile = (!empty($consumer->profile)) ? json_encode($consumer->profile) : null; - $settingsValue = serialize($consumer->getSettings()); - $time = time(); - $now = date("{$this->dateFormat} {$this->timeFormat}", $time); - $from = null; - if (!is_null($consumer->enableFrom)) { - $from = date("{$this->dateFormat} {$this->timeFormat}", $consumer->enableFrom); - } - $until = null; - if (!is_null($consumer->enableUntil)) { - $until = date("{$this->dateFormat} {$this->timeFormat}", $consumer->enableUntil); - } - $last = null; - if (!is_null($consumer->lastAccess)) { - $last = date($this->dateFormat, $consumer->lastAccess); - } - $data = new \stdClass(); - $data->consumer_key256 = $key256; - $data->consumer_key = $key; - $data->name = $consumer->name; - $data->secret = $consumer->secret; - $data->lti_version = $consumer->ltiVersion; - $data->consumer_name = $consumer->consumerName; - $data->consumer_version = $consumer->consumerVersion; - $data->consumer_guid = $consumer->consumerGuid; - $data->profile = $profile; - $data->tool_proxy = $consumer->toolProxy; - $data->settings = $settingsValue; - $data->protected = $protected; - $data->enabled = $enabled; - $data->enable_from = $from; - $data->enable_until = $until; - $data->last_access = $last; - $data->updated = $now; + $settingsvalue = serialize($consumer->getSettings()); + $now = time(); + $consumer->updated = $now; + $data = [ + 'consumer_key256' => $key256, + 'consumer_key' => $key, + 'name' => $consumer->name, + 'secret' => $consumer->secret, + 'lti_version' => $consumer->ltiVersion, + 'consumer_name' => $consumer->consumerName, + 'consumer_version' => $consumer->consumerVersion, + 'consumer_guid' => $consumer->consumerGuid, + 'profile' => $profile, + 'tool_proxy' => $consumer->toolProxy, + 'settings' => $settingsvalue, + 'protected' => $protected, + 'enabled' => $enabled, + 'enable_from' => $consumer->enableFrom, + 'enable_until' => $consumer->enableUntil, + 'last_access' => $consumer->lastAccess, + 'updated' => $consumer->updated, + ]; $id = $consumer->getRecordId(); + if (empty($id)) { - $data->created = $now; - $id = $DB->insert_record($table, $data); - $consumer->setRecordId($id); - $consumer->created = $time; - // TODO catch error and set $ok to false - $ok = !empty($id); - } else { - $data->id = $id; - $ok = $DB->update_record($table, $data); - } - if ($ok) { - $consumer->updated = $time; - } - - return $ok; - - } - -/** - * Delete tool consumer object. - * - * @param ToolConsumer $consumer Consumer object - * - * @return boolean True if the tool consumer object was successfully deleted - */ - public function deleteToolConsumer($consumer) - { - -// Delete any nonce values for this consumer - $sql = sprintf("DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::NONCE_TABLE_NAME . ' WHERE consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete any outstanding share keys for resource links for this consumer - $sql = sprintf('DELETE sk ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . ' sk ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON sk.resource_link_pk = rl.resource_link_pk ' . - 'WHERE rl.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete any outstanding share keys for resource links for contexts in this consumer - $sql = sprintf('DELETE sk ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . ' sk ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON sk.resource_link_pk = rl.resource_link_pk ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::CONTEXT_TABLE_NAME . ' c ON rl.context_pk = c.context_pk ' . - 'WHERE c.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete any users in resource links for this consumer - $sql = sprintf('DELETE u ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' u ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON u.resource_link_pk = rl.resource_link_pk ' . - 'WHERE rl.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete any users in resource links for contexts in this consumer - $sql = sprintf('DELETE u ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' u ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON u.resource_link_pk = rl.resource_link_pk ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::CONTEXT_TABLE_NAME . ' c ON rl.context_pk = c.context_pk ' . - 'WHERE c.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Update any resource links for which this consumer is acting as a primary resource link - $sql = sprintf("UPDATE {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' prl ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON prl.primary_resource_link_pk = rl.resource_link_pk ' . - 'SET prl.primary_resource_link_pk = NULL, prl.share_approved = NULL ' . - 'WHERE rl.consumer_pk = %d', - $consumer->getRecordId()); - #$ok = mysql_query($sql); - -// Update any resource links for contexts in which this consumer is acting as a primary resource link - $sql = sprintf("UPDATE {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' prl ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON prl.primary_resource_link_pk = rl.resource_link_pk ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::CONTEXT_TABLE_NAME . ' c ON rl.context_pk = c.context_pk ' . - 'SET prl.primary_resource_link_pk = NULL, prl.share_approved = NULL ' . - 'WHERE c.consumer_pk = %d', - $consumer->getRecordId()); - #$ok = mysql_query($sql); - -// Delete any resource links for this consumer - $sql = sprintf('DELETE rl ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ' . - 'WHERE rl.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete any resource links for contexts in this consumer - $sql = sprintf('DELETE rl ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::CONTEXT_TABLE_NAME . ' c ON rl.context_pk = c.context_pk ' . - 'WHERE c.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete any contexts for this consumer - $sql = sprintf('DELETE c ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::CONTEXT_TABLE_NAME . ' c ' . - 'WHERE c.consumer_pk = %d', - $consumer->getRecordId()); - #mysql_query($sql); - -// Delete consumer - $sql = sprintf('DELETE c ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::CONSUMER_TABLE_NAME . ' c ' . - 'WHERE c.consumer_pk = %d', - $consumer->getRecordId()); - #$ok = mysql_query($sql); - - if ($ok) { - $consumer->initialize(); - } - - return $ok; - - } - -### -# Load all tool consumers from the database -### - public function getToolConsumers() - { - - $consumers = array(); - - $sql = 'SELECT consumer_pk, consumer_key, consumer_key, name, secret, lti_version, consumer_name, consumer_version, consumer_guid, ' . - 'profile, tool_proxy, settings, ' . - 'protected, enabled, enable_from, enable_until, last_access, created, updated ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::CONSUMER_TABLE_NAME . ' ' . - 'ORDER BY name'; - #$rsConsumers = mysql_query($sql); - if ($rsConsumers) { - while ($row = mysql_fetch_object($rsConsumers)) { - $consumer = new ToolProvider\ToolConsumer($row->consumer_key, $this); - $consumer->setRecordId(intval($row->consumer_pk)); - $consumer->name = $row->name; - $consumer->secret = $row->secret; - $consumer->ltiVersion = $row->lti_version; - $consumer->consumerName = $row->consumer_name; - $consumer->consumerVersion = $row->consumer_version; - $consumer->consumerGuid = $row->consumer_guid; - $consumer->profile = json_decode($row->profile); - $consumer->toolProxy = $row->tool_proxy; - $settings = unserialize($row->settings); - if (!is_array($settings)) { - $settings = array(); - } - $consumer->setSettings($settings); - $consumer->protected = (intval($row->protected) === 1); - $consumer->enabled = (intval($row->enabled) === 1); - $consumer->enableFrom = null; - if (!is_null($row->enable_from)) { - $consumer->enableFrom = strtotime($row->enable_from); - } - $consumer->enableUntil = null; - if (!is_null($row->enable_until)) { - $consumer->enableUntil = strtotime($row->enable_until); - } - $consumer->lastAccess = null; - if (!is_null($row->last_access)) { - $consumer->lastAccess = strtotime($row->last_access); - } - $consumer->created = strtotime($row->created); - $consumer->updated = strtotime($row->updated); - $consumers[] = $consumer; + $consumer->created = $now; + $data['created'] = $consumer->created; + $id = $DB->insert_record($this->consumertable, (object) $data); + if ($id) { + $consumer->setRecordId($id); + return true; } - mysql_free_result($rsConsumers); + } else { + $data['id'] = $id; + return $DB->update_record($this->consumertable, (object) $data); } + return false; + } + + /** + * Delete tool consumer object and related records. + * + * @param ToolConsumer $consumer Consumer object + * @return boolean True if the tool consumer object was successfully deleted + */ + public function deleteToolConsumer($consumer) { + global $DB; + + $consumerpk = $consumer->getRecordId(); + $deletecondition = ['consumer_pk' => $consumerpk]; + + // Delete any nonce values for this consumer. + $DB->delete_records($this->noncetable, $deletecondition); + + // Delete any outstanding share keys for resource links for this consumer. + $where = "resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + WHERE rl.consumer_pk = :consumer_pk + )"; + $DB->delete_records_select($this->sharekeytable, $where, $deletecondition); + + // Delete any outstanding share keys for resource links for contexts in this consumer. + $where = "resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + INNER JOIN {{$this->contexttable}} c + ON rl.context_pk = c.id + WHERE c.consumer_pk = :consumer_pk + )"; + $DB->delete_records_select($this->sharekeytable, $where, $deletecondition); + + // Delete any users in resource links for this consumer. + $where = "resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + WHERE rl.consumer_pk = :consumer_pk + )"; + $DB->delete_records_select($this->userresulttable, $where, $deletecondition); + + // Delete any users in resource links for contexts in this consumer. + $where = "resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + INNER JOIN {{$this->contexttable}} c + ON rl.context_pk = c.id + WHERE c.consumer_pk = :consumer_pk + )"; + $DB->delete_records_select($this->userresulttable, $where, $deletecondition); + + // Update any resource links for which this consumer is acting as a primary resource link. + $where = "primary_resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + WHERE rl.consumer_pk = :consumer_pk + )"; + $updaterecords = $DB->get_records_select($this->resourcelinktable, $where, $deletecondition); + foreach ($updaterecords as $record) { + $record->primary_resource_link_pk = null; + $record->share_approved = null; + $DB->update_record($this->resourcelinktable, $record); + } + + // Update any resource links for contexts in which this consumer is acting as a primary resource link. + $where = "primary_resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + INNER JOIN {{$this->contexttable}} c + ON rl.context_pk = c.id + WHERE c.consumer_pk = :consumer_pk + )"; + $updaterecords = $DB->get_records_select($this->resourcelinktable, $where, $deletecondition); + foreach ($updaterecords as $record) { + $record->primary_resource_link_pk = null; + $record->share_approved = null; + $DB->update_record($this->resourcelinktable, $record); + } + + // Delete any resource links for contexts in this consumer. + $where = "context_pk IN ( + SELECT c.id + FROM {{$this->contexttable}} c + WHERE c.consumer_pk = :consumer_pk + )"; + $DB->delete_records_select($this->resourcelinktable, $where, $deletecondition); + + // Delete any resource links for this consumer. + $DB->delete_records($this->resourcelinktable, $deletecondition); + + // Delete any contexts for this consumer. + $DB->delete_records($this->contexttable, $deletecondition); + + // Delete consumer. + $DB->delete_records($this->consumertable, ['id' => $consumerpk]); + + $consumer->initialize(); + + return true; + } + + /** + * Load all tool consumers from the database. + * @return array + */ + public function getToolConsumers() { + global $DB; + $consumers = []; + + $rsconsumers = $DB->get_recordset($this->consumertable, null, 'name'); + foreach ($rsconsumers as $row) { + $consumer = new ToolProvider\ToolConsumer($row->consumer_key, $this); + $this->build_tool_consumer_object($row, $consumer); + $consumers[] = $consumer; + } + $rsconsumers->close(); + return $consumers; - } -### -### ToolProxy methods -### - -### -# Load the tool proxy from the database -### - public function loadToolProxy($toolProxy) - { + /* + * ToolProxy methods. + */ + /** + * Load the tool proxy from the database. + * + * @param ToolProxy $toolproxy + * @return bool + */ + public function loadToolProxy($toolproxy) { return false; - } -### -# Save the tool proxy to the database -### - public function saveToolProxy($toolProxy) - { - + /** + * Save the tool proxy to the database. + * + * @param ToolProxy $toolproxy + * @return bool + */ + public function saveToolProxy($toolproxy) { return false; - } -### -# Delete the tool proxy from the database -### - public function deleteToolProxy($toolProxy) - { - + /** + * Delete the tool proxy from the database. + * + * @param ToolProxy $toolproxy + * @return bool + */ + public function deleteToolProxy($toolproxy) { return false; - } -### -### Context methods -### + /* + * Context methods. + */ /** * Load context object. @@ -395,26 +330,26 @@ class data_connector extends DataConnector { */ public function loadContext($context) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::CONTEXT_TABLE_NAME; + if (!empty($context->getRecordId())) { - $params = ['context_pk' => $context->getRecordId()]; + $params = ['id' => $context->getRecordId()]; } else { $params = [ 'consumer_pk' => $context->getConsumer()->getRecordId(), 'lti_context_id' => $context->ltiContextId ]; } - if ($row = $DB->get_record($table, $params)) { - $context->setRecordId(intval($row->context_pk)); - $context->setConsumerId(intval($row->consumer_pk)); + if ($row = $DB->get_record($this->contexttable, $params)) { + $context->setRecordId($row->id); + $context->setConsumerId($row->consumer_pk); $context->ltiContextId = $row->lti_context_id; $settings = unserialize($row->settings); if (!is_array($settings)) { $settings = array(); } $context->setSettings($settings); - $context->created = strtotime($row->created); - $context->updated = strtotime($row->updated); + $context->created = $row->created; + $context->updated = $row->updated; return true; } @@ -429,605 +364,493 @@ class data_connector extends DataConnector { */ public function saveContext($context) { global $DB; - $time = time(); - $now = date("{$this->dateFormat} {$this->timeFormat}", $time); - $settingsValue = serialize($context->getSettings()); + $now = time(); + $context->updated = $now; + $settingsvalue = serialize($context->getSettings()); $id = $context->getRecordId(); - $consumer_pk = $context->getConsumer()->getRecordId(); - $table = $this->dbTableNamePrefix . DataConnector::CONTEXT_TABLE_NAME; + $consumerpk = $context->getConsumer()->getRecordId(); + $isinsert = empty($id); if ($isinsert) { + $context->created = $now; $params = [ - 'consumer_pk' => $consumer_pk, + 'consumer_pk' => $consumerpk, 'lti_context_id' => $context->ltiContextId, - 'settings' => $settingsValue, - 'created' => $now, - 'updated' => $now, + 'settings' => $settingsvalue, + 'created' => $context->created, + 'updated' => $context->updated, ]; - $sql = "INSERT INTO {{$table}} (consumer_pk, lti_context_id, settings, created, updated) - VALUES (:consumer_pk, :lti_context_id, :settings, :created, :updated)"; + $id = $DB->insert_record($this->contexttable, (object) $params); + if ($id) { + $context->setRecordId($id); + return true; + } } else { - $params = [ + $data = (object) [ + 'id' => $id, + 'context_pk' => $consumerpk, 'lti_context_id' => $context->ltiContextId, - 'settings' => $settingsValue, - 'updated' => $now, - 'consumer_pk' => $consumer_pk, - 'context_pk' => $id + 'settings' => $settingsvalue, + 'updated' => $context->updated, ]; - $sql = "UPDATE {{$table}} - SET lti_context_id = :lti_context_id, - settings = :settings, - updated = :updated - WHERE consumer_pk = :consumer_pk - AND context_pk = :context_pk"; + return $DB->update_record($this->contexttable, $data); } - if ($DB->execute($sql, $params)) { - if ($isinsert) { - // consumer_pk, lti_context_id, created and updated should be enough to identify the data we added. - unset($params['settings']); - if ($contextrecord = $DB->get_record($table, $params)) { - $context->setRecordId($contextrecord->context_pk); - $context->created = $time; - } + return false; + } + + /** + * Delete context object. + * + * @param Context $context Context object + * @return boolean True if the Context object was successfully deleted + */ + public function deleteContext($context) { + global $DB; + + $contextid = $context->getRecordId(); + + $params = ['id' => $contextid]; + + // Delete any outstanding share keys for resource links for this context. + $where = "resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + WHERE rl.context_pk = :id + )"; + $DB->delete_records_select($this->sharekeytable, $where, $params); + + // Delete any users in resource links for this context. + $DB->delete_records_select($this->userresulttable, $where, $params); + + // Update any resource links for which this consumer is acting as a primary resource link. + $where = "primary_resource_link_pk IN ( + SELECT rl.id + FROM {{$this->resourcelinktable}} rl + WHERE rl.context_pk = :id + )"; + $updaterecords = $DB->get_records_select($this->resourcelinktable, $where, $params); + foreach ($updaterecords as $record) { + $record->primary_resource_link_pk = null; + $record->share_approved = null; + $DB->update_record($this->resourcelinktable, $record); + } + + // Delete any resource links for this context. + $DB->delete_records($this->resourcelinktable, ['context_pk' => $contextid]); + + // Delete context. + $DB->delete_records($this->contexttable, $params); + + $context->initialize(); + + return true; + } + + /* + * ResourceLink methods + */ + + /** + * Load resource link object. + * + * @param ResourceLink $resourcelink Resource_Link object + * @return boolean True if the resource link object was successfully loaded + */ + public function loadResourceLink($resourcelink) { + global $DB; + + $resourceid = $resourcelink->getRecordId(); + if (!empty($resourceid)) { + $params = ['id' => $resourceid]; + $row = $DB->get_record($this->resourcelinktable, $params); + } else if (!empty($resourcelink->getContext())) { + $params = [ + 'context_pk' => $resourcelink->getContext()->getRecordId(), + 'lti_resource_link_id' => $resourcelink->getId() + ]; + $row = $DB->get_record($this->resourcelinktable, $params); + } else { + $sql = "SELECT r.* + FROM {{$this->resourcelinktable}} r + LEFT OUTER JOIN {{$this->contexttable}} c + ON r.context_pk = c.id + WHERE (r.consumer_pk = ? OR c.consumer_pk = ?) + AND lti_resource_link_id = ?"; + $params = [ + $resourcelink->getConsumer()->getRecordId(), + $resourcelink->getConsumer()->getRecordId(), + $resourcelink->getId() + ]; + $row = $DB->get_record_sql($sql, $params); + } + if ($row) { + $resourcelink->setRecordId($row->id); + if (!is_null($row->context_pk)) { + $resourcelink->setContextId($row->context_pk); + } else { + $resourcelink->setContextId(null); } - $context->updated = $time; + if (!is_null($row->consumer_pk)) { + $resourcelink->setConsumerId($row->consumer_pk); + } else { + $resourcelink->setConsumerId(null); + } + $resourcelink->ltiResourceLinkId = $row->lti_resource_link_id; + $settings = unserialize($row->settings); + if (!is_array($settings)) { + $settings = array(); + } + $resourcelink->setSettings($settings); + if (!is_null($row->primary_resource_link_pk)) { + $resourcelink->primaryResourceLinkId = $row->primary_resource_link_pk; + } else { + $resourcelink->primaryResourceLinkId = null; + } + $resourcelink->shareApproved = (is_null($row->share_approved)) ? null : ($row->share_approved == 1); + $resourcelink->created = $row->created; + $resourcelink->updated = $row->updated; return true; } return false; } -/** - * Delete context object. - * - * @param Context $context Context object - * - * @return boolean True if the Context object was successfully deleted - */ - public function deleteContext($context) - { - -// Delete any outstanding share keys for resource links for this context - $sql = sprintf('DELETE sk ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . ' sk ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON sk.resource_link_pk = rl.resource_link_pk ' . - 'WHERE rl.context_pk = %d', - $context->getRecordId()); - #mysql_query($sql); - -// Delete any users in resource links for this context - $sql = sprintf('DELETE u ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' u ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON u.resource_link_pk = rl.resource_link_pk ' . - 'WHERE rl.context_pk = %d', - $context->getRecordId()); - #mysql_query($sql); - -// Update any resource links for which this consumer is acting as a primary resource link - $sql = sprintf("UPDATE {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' prl ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ON prl.primary_resource_link_pk = rl.resource_link_pk ' . - 'SET prl.primary_resource_link_pk = null, prl.share_approved = null ' . - 'WHERE rl.context_pk = %d', - $context->getRecordId()); - #$ok = mysql_query($sql); - -// Delete any resource links for this consumer - $sql = sprintf('DELETE rl ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' rl ' . - 'WHERE rl.context_pk = %d', - $context->getRecordId()); - #mysql_query($sql); - -// Delete context - $sql = sprintf('DELETE c ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::CONTEXT_TABLE_NAME . ' c ', - 'WHERE c.context_pk = %d', - $context->getRecordId()); - #$ok = mysql_query($sql); - if ($ok) { - $context->initialize(); - } - - return $ok; - - } - -### -### ResourceLink methods -### - - /** - * Load resource link object. - * - * @param ResourceLink $resourceLink Resource_Link object - * - * @return boolean True if the resource link object was successfully loaded - */ - public function loadResourceLink($resourceLink) { - global $DB; - - $table = $this->dbTableNamePrefix . DataConnector::RESOURCE_LINK_TABLE_NAME; - - $ok = false; - $resourceid = $resourceLink->getRecordId(); - $fields = 'id, context_pk, consumer_pk, lti_resource_link_id, settings, primary_resource_link_pk, share_approved, created, updated'; - if (!empty($resourceid)) { - $row = $DB->get_record( - $table, - array('id' => $resourceid), - '', - $fields - ); - } else if (!empty($resourceLink->getContext())) { - $row = $DB->get_record( - $table, - array( - 'context_pk' => $resourceLink->getContext()->getRecordId(), - 'lti_resource_link_id' => $resourceLink->getId() - ), - '', - $fields - ); - } else { - $fields = 'r.id, r.context_pk, r.consumer_pk, r.lti_resource_link_id, r.settings, r.primary_resource_link_pk, r.share_approved, r.created, r.updated '; - $sql = "SELECT $fields " ."FROM {{$table}} r LEFT OUTER JOIN " . - '{' . $this->dbTableNamePrefix . DataConnector::CONTEXT_TABLE_NAME . '} c ' . - 'ON r.context_pk = c.context_pk ' . - ' WHERE ((r.consumer_pk = ?) OR (c.consumer_pk = ?)) AND (lti_resource_link_id = ?)'; - // TODO fix this to use proper xmldb instead of this crazy gross SQL!! - $row = $DB->get_record_sql( - $sql, - array($resourceLink->getConsumer()->getRecordId(), - $resourceLink->getConsumer()->getRecordId(), - $resourceLink->getId()) - ); - } - if ($row) { - $resourceLink->setRecordId(intval($row->id)); - if (!is_null($row->context_pk)) { - $resourceLink->setContextId(intval($row->context_pk)); - } else { - $resourceLink->setContextId(null); - } - if (!is_null($row->consumer_pk)) { - $resourceLink->setConsumerId(intval($row->consumer_pk)); - } else { - $resourceLink->setConsumerId(null); - } - $resourceLink->ltiResourceLinkId = $row->lti_resource_link_id; - $settings = unserialize($row->settings); - if (!is_array($settings)) { - $settings = array(); - } - $resourceLink->setSettings($settings); - if (!is_null($row->primary_resource_link_pk)) { - $resourceLink->primaryResourceLinkId = intval($row->primary_resource_link_pk); - } else { - $resourceLink->primaryResourceLinkId = null; - } - $resourceLink->shareApproved = (is_null($row->share_approved)) ? null : (intval($row->share_approved) === 1); - $resourceLink->created = strtotime($row->created); - $resourceLink->updated = strtotime($row->updated); - $ok = true; - } - - return $ok; - - } - /** * Save resource link object. * - * @param ResourceLink $resourceLink Resource_Link object - * + * @param ResourceLink $resourcelink Resource_Link object * @return boolean True if the resource link object was successfully saved */ - public function saveResourceLink($resourceLink) { + public function saveResourceLink($resourcelink) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::RESOURCE_LINK_TABLE_NAME; - - if (is_null($resourceLink->shareApproved)) { + if (is_null($resourcelink->shareApproved)) { $approved = null; - } else if ($resourceLink->shareApproved) { + } else if ($resourcelink->shareApproved) { $approved = 1; } else { $approved = 0; } - if (empty($resourceLink->primaryResourceLinkId)) { - $primaryResourceLinkId = null; + if (empty($resourcelink->primaryResourceLinkId)) { + $primaryresourcelinkid = null; } else { - $primaryResourceLinkId = strval($resourceLink->primaryResourceLinkId); + $primaryresourcelinkid = $resourcelink->primaryResourceLinkId; } - $time = time(); - $now = date("{$this->dateFormat} {$this->timeFormat}", $time); - $settingsValue = serialize($resourceLink->getSettings()); - if (!empty($resourceLink->getContext())) { - $consumerId = null; - $contextId = strval($resourceLink->getContext()->getRecordId()); - } else if (!empty($resourceLink->getContextId())) { - $consumerId = null; - $contextId = strval($resourceLink->getContextId()); + $now = time(); + $resourcelink->updated = $now; + $settingsvalue = serialize($resourcelink->getSettings()); + if (!empty($resourcelink->getContext())) { + $consumerid = null; + $contextid = $resourcelink->getContext()->getRecordId(); + } else if (!empty($resourcelink->getContextId())) { + $consumerid = null; + $contextid = $resourcelink->getContextId(); } else { - $consumerId = strval($resourceLink->getConsumer()->getRecordId()); - $contextId = null; + $consumerid = $resourcelink->getConsumer()->getRecordId(); + $contextid = null; } - $id = $resourceLink->getRecordId(); + $id = $resourcelink->getRecordId(); - $data = new \stdClass(); - $data->consumer_pk = $consumerId; - $data->lti_resource_link_id = $resourceLink->getId(); - $data->settings = $settingsValue; - $data->primary_resource_link_pk = $primaryResourceLinkId; - $data->share_approved = $approved; - $data->updated = $now; + $data = [ + 'consumer_pk' => $consumerid, + 'context_pk' => $contextid, + 'lti_resource_link_id' => $resourcelink->getId(), + 'settings' => $settingsvalue, + 'primary_resource_link_pk' => $primaryresourcelinkid, + 'share_approved' => $approved, + 'updated' => $resourcelink->updated, + ]; $returnid = null; if (empty($id)) { - $data->created = $now; - $data->context_pk = $contextId; - $returnid = $DB->insert_record($table, $data); - } else if ($contextId !== 'NULL') { - $sql = "UPDATE {{$table}} SET " . - 'consumer_pk = ?, lti_resource_link_id = ?, settings = ?, '. - 'primary_resource_link_pk = ?, share_approved = ?, updated = ? ' . - 'WHERE (context_pk = ?) AND (id = ?)'; - $DB->execute($sql, [ - $consumerId, $resourceLink->getId(), - $settingsValue, $primaryResourceLinkId, $approved, $now, - $contextId, $id - ] - ); - $returnid = $id; - // TODO dml-ify. - } else { - $sql = "UPDATE {{$table}} SET " . - 'context_pk = ?, lti_resource_link_id = ?, settings = ?, '. - 'primary_resource_link_pk = ?, share_approved = ?, updated = ? ' . - 'WHERE (consumer_pk = ?) AND (id = ?)'; - $DB->execute($sql, [ - $contextId, $resourceLink->getId(), - $settingsValue, $primaryResourceLinkId, $approved, $now, - $consumerId, $id - ] - ); - $returnid = $id; - // TODO dml-ify. - } - $ok = !empty($returnid); - if ($ok) { - if (empty($id)) { - $resourceLink->setRecordId($newid); - $resourceLink->created = $time; + $resourcelink->created = $now; + $data['created'] = $resourcelink->created; + $id = $DB->insert_record($this->resourcelinktable, (object) $data); + if ($id) { + $resourcelink->setRecordId($id); + return true; } - $resourceLink->updated = $time; + + } else { + $data['id'] = $id; + return $DB->update_record($this->resourcelinktable, (object) $data); } - return $ok; - + return false; } -/** - * Delete resource link object. - * - * @param ResourceLink $resourceLink Resource_Link object - * - * @return boolean True if the resource link object was successfully deleted - */ - public function deleteResourceLink($resourceLink) - { + /** + * Delete resource link object. + * + * @param ResourceLink $resourcelink Resource_Link object + * @return boolean True if the resource link object and its related records were successfully deleted. + * Otherwise, a DML exception is thrown. + */ + public function deleteResourceLink($resourcelink) { + global $DB; -// Delete any outstanding share keys for resource links for this consumer - $sql = sprintf("DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . ' ' . - 'WHERE (resource_link_pk = %d)', - $resourceLink->getRecordId()); - #$ok = mysql_query($sql); + $resourcelinkid = $resourcelink->getRecordId(); -// Delete users - if ($ok) { - $sql = sprintf("DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' ' . - 'WHERE (resource_link_pk = %d)', - $resourceLink->getRecordId()); - #$ok = mysql_query($sql); + // Delete any outstanding share keys for resource links for this consumer. + $DB->delete_records($this->sharekeytable, ['resource_link_pk' => $resourcelinkid]); + + // Delete users. + $DB->delete_records($this->userresulttable, ['resource_link_pk' => $resourcelinkid]); + + // Update any resource links for which this is the primary resource link. + $records = $DB->get_records($this->resourcelinktable, ['primary_resource_link_pk' => $resourcelinkid]); + foreach ($records as $record) { + $record->primary_resource_link_pk = null; + $DB->update_record($this->resourcelinktable, $record); } -// Update any resource links for which this is the primary resource link - if ($ok) { - $sql = sprintf("UPDATE {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' ' . - 'SET primary_resource_link_pk = NULL ' . - 'WHERE (primary_resource_link_pk = %d)', - $resourceLink->getRecordId()); - #$ok = mysql_query($sql); - } + // Delete resource link. + $DB->delete_records($this->resourcelinktable, ['id' => $resourcelinkid]); -// Delete resource link - if ($ok) { - $sql = sprintf("DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' ' . - 'WHERE (id= %s)', - $resourceLink->getRecordId()); - #$ok = mysql_query($sql); - } - - if ($ok) { - $resourceLink->initialize(); - } - - return $ok; + $resourcelink->initialize(); + return true; } -/** - * Get array of user objects. - * - * Obtain an array of User objects for users with a result sourcedId. The array may include users from other - * resource links which are sharing this resource link. It may also be optionally indexed by the user ID of a specified scope. - * - * @param ResourceLink $resourceLink Resource link object - * @param boolean $localOnly True if only users within the resource link are to be returned (excluding users sharing this resource link) - * @param int $idScope Scope value to use for user IDs - * - * @return array Array of User objects - */ - public function getUserResultSourcedIDsResourceLink($resourceLink, $localOnly, $idScope) - { + /** + * Get array of user objects. + * + * Obtain an array of User objects for users with a result sourcedId. The array may include users from other + * resource links which are sharing this resource link. It may also be optionally indexed by the user ID of a specified scope. + * + * @param ResourceLink $resourcelink Resource link object + * @param boolean $localonly True if only users within the resource link are to be returned + * (excluding users sharing this resource link) + * @param int $idscope Scope value to use for user IDs + * @return array Array of User objects + */ + public function getUserResultSourcedIDsResourceLink($resourcelink, $localonly, $idscope) { + global $DB; - $users = array(); + $users = []; - if ($localOnly) { - $sql = sprintf('SELECT u.user_pk, u.lti_result_sourcedid, u.lti_user_id, u.created, u.updated ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' AS u ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' AS rl ' . - 'ON u.resource_link_pk = rl.resource_link_pk ' . - "WHERE (rl.resource_link_pk = %d) AND (rl.primary_resource_link_pk IS NULL)", - $resourceLink->getRecordId()); - } else { - $sql = sprintf('SELECT u.user_pk, u.lti_result_sourcedid, u.lti_user_id, u.created, u.updated ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' AS u ' . - "INNER JOIN {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' AS rl ' . - 'ON u.resource_link_pk = rl.resource_link_pk ' . - 'WHERE ((rl.resource_link_pk = %d) AND (rl.primary_resource_link_pk IS NULL)) OR ' . - '((rl.primary_resource_link_pk = %d) AND (share_approved = 1))', - $resourceLink->getRecordId(), $resourceLink->getRecordId()); + $params = ['resource_link_pk' => $resourcelink->getRecordId()]; + + // Where clause for the subquery. + $subwhere = "(id = :resource_link_pk AND primary_resource_link_pk IS NULL)"; + if (!$localonly) { + $subwhere .= " OR (primary_resource_link_pk = :resource_link_pk2 AND share_approved = 1)"; + $params['resource_link_pk2'] = $resourcelink->getRecordId(); } - #$rsUser = mysql_query($sql); - if ($rsUser) { - while ($row = mysql_fetch_object($rsUser)) { - $user = ToolProvider\User::fromResourceLink($resourceLink, $row->lti_user_id); - $user->setRecordId(intval($row->user_pk)); - $user->ltiResultSourcedId = $row->lti_result_sourcedid; - $user->created = strtotime($row->created); - $user->updated = strtotime($row->updated); - if (is_null($idScope)) { - $users[] = $user; - } else { - $users[$user->getId($idScope)] = $user; - } + + // The subquery. + $subsql = "SELECT id + FROM {{$this->resourcelinktable}} + WHERE {$subwhere}"; + + // Our main where clause. + $where = "resource_link_pk IN ($subsql)"; + + // Fields to be queried. + $fields = 'id, lti_result_sourcedid, lti_user_id, created, updated'; + + // Fetch records. + $rs = $DB->get_recordset_select($this->userresulttable, $where, $params, '', $fields); + foreach ($rs as $row) { + $user = User::fromResourceLink($resourcelink, $row->lti_user_id); + $user->setRecordId($row->id); + $user->ltiResultSourcedId = $row->lti_result_sourcedid; + $user->created = $row->created; + $user->updated = $row->updated; + if (is_null($idscope)) { + $users[] = $user; + } else { + $users[$user->getId($idscope)] = $user; } } + $rs->close(); return $users; - } -/** - * Get array of shares defined for this resource link. - * - * @param ResourceLink $resourceLink Resource_Link object - * - * @return array Array of ResourceLinkShare objects - */ - public function getSharesResourceLink($resourceLink) - { + /** + * Get array of shares defined for this resource link. + * + * @param ResourceLink $resourcelink Resource_Link object + * @return array Array of ResourceLinkShare objects + */ + public function getSharesResourceLink($resourcelink) { + global $DB; - $shares = array(); + $shares = []; - $sql = sprintf('SELECT consumer_pk, resource_link_pk, share_approved ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_TABLE_NAME . ' ' . - 'WHERE (primary_resource_link_pk = %d) ' . - 'ORDER BY consumer_pk', - $resourceLink->getRecordId()); - #$rsShare = mysql_query($sql); - if ($rsShare) { - while ($row = mysql_fetch_object($rsShare)) { - $share = new ToolProvider\ResourceLinkShare(); - $share->resourceLinkId = intval($row->resource_link_pk); - $share->approved = (intval($row->share_approved) === 1); - $shares[] = $share; - } + $params = ['primary_resource_link_pk' => $resourcelink->getRecordId()]; + $fields = 'id, share_approved, consumer_pk'; + $records = $DB->get_records($this->resourcelinktable, $params, 'consumer_pk', $fields); + foreach ($records as $record) { + $share = new ResourceLinkShare(); + $share->resourceLinkId = $record->id; + $share->approved = $record->share_approved == 1; + $shares[] = $share; } return $shares; - } - -### -### ConsumerNonce methods -### + /* + * ConsumerNonce methods + */ /** * Load nonce object. * * @param ConsumerNonce $nonce Nonce object - * * @return boolean True if the nonce object was successfully loaded */ public function loadConsumerNonce($nonce) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::NONCE_TABLE_NAME; + // Delete any expired nonce values. + $now = time(); + $DB->delete_records_select($this->noncetable, "expires <= ?", [$now]); - $ok = true; - - // Delete any expired nonce values - $now = date("{$this->dateFormat} {$this->timeFormat}", time()); - $DB->delete_records_select($table, "expires <= ?", array($now)); - - // Load the nonce - $result = $DB->get_record($table, array('consumer_pk' => $nonce->getConsumer()->getRecordId(), 'value' => $nonce->getValue()), 'value'); + // Load the nonce. + $params = [ + 'consumer_pk' => $nonce->getConsumer()->getRecordId(), + 'value' => $nonce->getValue() + ]; + $result = $DB->get_field($this->noncetable, 'value', $params); return !empty($result); - } /** * Save nonce object. * * @param ConsumerNonce $nonce Nonce object - * * @return boolean True if the nonce object was successfully saved */ public function saveConsumerNonce($nonce) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::NONCE_TABLE_NAME; - - $expires = date("{$this->dateFormat} {$this->timeFormat}", $nonce->expires); - - $data = new \stdClass(); - $data->consumer_pk = $nonce->getConsumer()->getRecordId(); - $data->value = $nonce->getValue(); - $data->expires = $expires; - - return $DB->insert_record($table, $data, false); + $data = [ + 'consumer_pk' => $nonce->getConsumer()->getRecordId(), + 'value' => $nonce->getValue(), + 'expires' => $nonce->expires + ]; + return $DB->insert_record($this->noncetable, (object) $data, false); } + /* + * ResourceLinkShareKey methods. + */ -### -### ResourceLinkShareKey methods -### + /** + * Load resource link share key object. + * + * @param ResourceLinkShareKey $sharekey Resource_Link share key object + * @return boolean True if the resource link share key object was successfully loaded + */ + public function loadResourceLinkShareKey($sharekey) { + global $DB; -/** - * Load resource link share key object. - * - * @param ResourceLinkShareKey $shareKey Resource_Link share key object - * - * @return boolean True if the resource link share key object was successfully loaded - */ - public function loadResourceLinkShareKey($shareKey) - { + // Clear expired share keys. + $now = time(); + $where = "expires <= :expires"; - $ok = false; + $DB->delete_records_select($this->sharekeytable, $where, ['expires' => $now]); -// Clear expired share keys - $now = date("{$this->dateFormat} {$this->timeFormat}", time()); - $sql = "DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . " WHERE expires <= '{$now}'"; - #mysql_query($sql); - -// Load share key - $id = mysql_real_escape_string($shareKey->getId()); - $sql = 'SELECT resource_link_pk, auto_approve, expires ' . - "FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . ' ' . - "WHERE share_key_id = '{$id}'"; - #$rsShareKey = mysql_query($sql); - if ($rsShareKey) { - $row = mysql_fetch_object($rsShareKey); - if ($row && (intval($row->resource_link_pk) === $shareKey->resourceLinkId)) { - $shareKey->autoApprove = (intval($row->auto_approve) === 1); - $shareKey->expires = strtotime($row->expires); - $ok = true; + // Load share key. + $fields = 'resource_link_pk, auto_approve, expires'; + if ($sharekeyrecord = $DB->get_record($this->sharekeytable, ['share_key_id' => $sharekey->getId()], $fields)) { + if ($sharekeyrecord->resource_link_pk == $sharekey->resourceLinkId) { + $sharekey->autoApprove = $sharekeyrecord->auto_approve == 1; + $sharekey->expires = $sharekeyrecord->expires; + return true; } } - return $ok; - + return false; } -/** - * Save resource link share key object. - * - * @param ResourceLinkShareKey $shareKey Resource link share key object - * - * @return boolean True if the resource link share key object was successfully saved - */ - public function saveResourceLinkShareKey($shareKey) - { + /** + * Save resource link share key object. + * + * @param ResourceLinkShareKey $sharekey Resource link share key object + * @return boolean True if the resource link share key object was successfully saved + */ + public function saveResourceLinkShareKey($sharekey) { + global $DB; - if ($shareKey->autoApprove) { + if ($sharekey->autoApprove) { $approve = 1; } else { $approve = 0; } - $expires = date("{$this->dateFormat} {$this->timeFormat}", $shareKey->expires); - $sql = sprintf("INSERT INTO {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . ' ' . - '(share_key_id, resource_link_pk, auto_approve, expires) ' . - "VALUES (%s, %d, {$approve}, '{$expires}')", - DataConnector::quoted($shareKey->getId()), $shareKey->resourceLinkId); - #$ok = mysql_query($sql); - return $ok; + $expires = $sharekey->expires; + $params = [ + 'share_key_id' => $sharekey->getId(), + 'resource_link_pk' => $sharekey->resourceLinkId, + 'auto_approve' => $approve, + 'expires' => $expires + ]; + + return $DB->insert_record($this->sharekeytable, (object) $params, false); } -/** - * Delete resource link share key object. - * - * @param ResourceLinkShareKey $shareKey Resource link share key object - * - * @return boolean True if the resource link share key object was successfully deleted - */ - public function deleteResourceLinkShareKey($shareKey) - { + /** + * Delete resource link share key object. + * + * @param ResourceLinkShareKey $sharekey Resource link share key object + * @return boolean True if the resource link share key object was successfully deleted + */ + public function deleteResourceLinkShareKey($sharekey) { + global $DB; - $sql = "DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::RESOURCE_LINK_SHARE_KEY_TABLE_NAME . " WHERE share_key_id = '{$shareKey->getId()}'"; - - #$ok = mysql_query($sql); - - if ($ok) { - $shareKey->initialize(); - } - - return $ok; + $DB->delete_records($this->sharekeytable, ['share_key_id' => $sharekey->getId()]); + $sharekey->initialize(); + return true; } + /* + * User methods + */ -### -### User methods -### - -/** - * Load user object. - * - * @param User $user User object - * - * @return boolean True if the user object was successfully loaded - */ + /** + * Load user object. + * + * @param User $user User object + * @return boolean True if the user object was successfully loaded + */ public function loadUser($user) { global $DB; - $table = $this->dbTableNamePrefix . DataConnector::USER_RESULT_TABLE_NAME; - - $ok = false; $userid = $user->getRecordId(); - $fields = 'user_pk, resource_link_pk, lti_user_id, lti_result_sourcedid, created, updated'; + $fields = 'id, resource_link_pk, lti_user_id, lti_result_sourcedid, created, updated'; if (!empty($userid)) { - $row = $DB->get_record($table, array('user_pk' => $userid), $fields); + $row = $DB->get_record($this->userresulttable, ['id' => $userid], $fields); } else { $resourcelinkid = $user->getResourceLink()->getRecordId(); $userid = $user->getId(ToolProvider\ToolProvider::ID_SCOPE_ID_ONLY); $row = $DB->get_record_select( - $table, + $this->userresulttable, "resource_link_pk = ? AND lti_user_id = ?", - array($resourcelinkid, $userid), + [$resourcelinkid, $userid], $fields ); } if ($row) { - $user->setRecordId(intval($row->user_pk)); - $user->setResourceLinkId(intval($row->resource_link_pk)); + $user->setRecordId($row->id); + $user->setResourceLinkId($row->resource_link_pk); $user->ltiUserId = $row->lti_user_id; $user->ltiResultSourcedId = $row->lti_result_sourcedid; - $user->created = strtotime($row->created); - $user->updated = strtotime($row->updated); - $ok = true; + $user->created = $row->created; + $user->updated = $row->updated; + return true; } - return $ok; - + return false; } /** @@ -1039,67 +862,87 @@ class data_connector extends DataConnector { public function saveUser($user) { global $DB; - $time = time(); - $now = date("{$this->dateFormat} {$this->timeFormat}", $time); - $table = $this->dbTableNamePrefix . DataConnector::USER_RESULT_TABLE_NAME; + $now = time(); $isinsert = is_null($user->created); - if ($isinsert) { - $params = [ - 'resource_link_pk' => $user->getResourceLink()->getRecordId(), - 'lti_user_id' => $user->getId(ToolProvider\ToolProvider::ID_SCOPE_ID_ONLY), - 'lti_result_sourcedid' => $user->ltiResultSourcedId, - 'created' => $now, - 'updated' => $now, - ]; - $sql = "INSERT INTO {{$table}} (resource_link_pk, lti_user_id, lti_result_sourcedid, created, updated) - VALUES (:resource_link_pk, :lti_user_id, :lti_result_sourcedid, :created, :updated)"; - } else { - $params = [ - 'lti_result_sourcedid' => $user->ltiResultSourcedId, - 'updated' => $now, - 'user_pk' => $user->getRecordId() - ]; - $sql = "UPDATE {{$table}} - SET lti_result_sourcedid = :lti_result_sourcedid, - updated = :updated - WHERE user_pk = :user_pk"; - } + $user->updated = $now; - if ($DB->execute($sql, $params)) { - if ($isinsert) { - if ($userrecord = $DB->get_record($table, $params)) { - $user->setRecordId($userrecord->user_pk); - $user->created = $time; - } + $params = [ + 'lti_result_sourcedid' => $user->ltiResultSourcedId, + 'updated' => $user->updated + ]; + + if ($isinsert) { + $params['resource_link_pk'] = $user->getResourceLink()->getRecordId(); + $params['lti_user_id'] = $user->getId(ToolProvider\ToolProvider::ID_SCOPE_ID_ONLY); + $user->created = $now; + $params['created'] = $user->created; + $id = $DB->insert_record($this->userresulttable, (object) $params); + if ($id) { + $user->setRecordId($id); + return true; } - $user->updated = $time; - return true; + + } else { + $params['id'] = $user->getRecordId(); + return $DB->update_record($this->userresulttable, (object) $params); } return false; } -/** - * Delete user object. - * - * @param User $user User object - * - * @return boolean True if the user object was successfully deleted - */ - public function deleteUser($user) - { + /** + * Delete user object. + * + * @param User $user User object + * @return boolean True if the user object was successfully deleted + */ + public function deleteUser($user) { + global $DB; - $sql = sprintf("DELETE FROM {$this->dbTableNamePrefix}" . DataConnector::USER_RESULT_TABLE_NAME . ' ' . - 'WHERE (user_pk = %d)', - $user->getRecordId()); - #$ok = mysql_query($sql); - - if ($ok) { - $user->initialize(); - } - - return $ok; + $DB->delete_records($this->userresulttable, ['id' => $user->getRecordId()]); + $user->initialize(); + return true; } + /** + * Builds a ToolConsumer object from a record object from the DB. + * + * @param stdClass $record The DB record object. + * @param ToolConsumer $consumer + */ + protected function build_tool_consumer_object($record, ToolConsumer $consumer) { + $consumer->setRecordId($record->id); + $consumer->name = $record->name; + $key = empty($record->consumer_key) ? $record->consumer_key256 : $record->consumer_key; + $consumer->setKey($key); + $consumer->secret = $record->secret; + $consumer->ltiVersion = $record->lti_version; + $consumer->consumerName = $record->consumer_name; + $consumer->consumerVersion = $record->consumer_version; + $consumer->consumerGuid = $record->consumer_guid; + $consumer->profile = json_decode($record->profile); + $consumer->toolProxy = $record->tool_proxy; + $settings = unserialize($record->settings); + if (!is_array($settings)) { + $settings = array(); + } + $consumer->setSettings($settings); + $consumer->protected = $record->protected == 1; + $consumer->enabled = $record->enabled == 1; + $consumer->enableFrom = null; + if (!is_null($record->enable_from)) { + $consumer->enableFrom = $record->enable_from; + } + $consumer->enableUntil = null; + if (!is_null($record->enable_until)) { + $consumer->enableUntil = $record->enable_until; + } + $consumer->lastAccess = null; + if (!is_null($record->last_access)) { + $consumer->lastAccess = $record->last_access; + } + $consumer->created = $record->created; + $consumer->updated = $record->updated; + } } diff --git a/enrol/lti/classes/tool_provider.php b/enrol/lti/classes/tool_provider.php index 12ce36056b0..a388a780ade 100644 --- a/enrol/lti/classes/tool_provider.php +++ b/enrol/lti/classes/tool_provider.php @@ -71,7 +71,7 @@ class tool_provider extends ToolProvider\ToolProvider { parent::__construct($dataconnector); $this->baseUrl = $CFG->wwwroot; - $toolpath = helper::get_proxy_url($tool); + $toolpath = helper::get_launch_url($toolid); $toolpath = $this->strip_base_url($toolpath); $vendorid = $SITE->shortname; diff --git a/enrol/lti/db/install.xml b/enrol/lti/db/install.xml index 260f1057a0e..31f6622c82a 100644 --- a/enrol/lti/db/install.xml +++ b/enrol/lti/db/install.xml @@ -53,11 +53,11 @@ - +
- + @@ -69,76 +69,61 @@ - - - - - + + + + + - + + +
- +
- + - - + + - +
- +
- - - - - - - - - - - - - - - -
- - - + - - + + - +
- +
+ - + - - + +
- +
@@ -147,54 +132,43 @@ - - + + - + + - - -
- +
+ - + - - + + +
- +
- + - - + + - +
- - - - - - - - - - -
diff --git a/enrol/lti/db/upgrade.php b/enrol/lti/db/upgrade.php index 293bb8051b7..07bd19968ed 100644 --- a/enrol/lti/db/upgrade.php +++ b/enrol/lti/db/upgrade.php @@ -37,7 +37,7 @@ * @return boolean */ function xmldb_enrol_lti_upgrade($oldversion) { - global $CFG, $DB; + global $DB; $dbman = $DB->get_manager(); @@ -49,7 +49,7 @@ function xmldb_enrol_lti_upgrade($oldversion) { // Adding fields to table enrol_lti_lti2_consumer. $table->add_field('id', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); $table->add_field('name', XMLDB_TYPE_CHAR, '50', null, XMLDB_NOTNULL, null, null); - $table->add_field('consumer_key256', XMLDB_TYPE_CHAR, '256', null, XMLDB_NOTNULL, null, null); + $table->add_field('consumer_key256', XMLDB_TYPE_CHAR, '255', null, XMLDB_NOTNULL, null, null); $table->add_field('consumer_key', XMLDB_TYPE_TEXT, null, null, null, null, null); $table->add_field('secret', XMLDB_TYPE_CHAR, '1024', null, XMLDB_NOTNULL, null, null); $table->add_field('lti_version', XMLDB_TYPE_CHAR, '10', null, null, null, null); @@ -61,15 +61,18 @@ function xmldb_enrol_lti_upgrade($oldversion) { $table->add_field('settings', XMLDB_TYPE_TEXT, null, null, null, null, null); $table->add_field('protected', XMLDB_TYPE_INTEGER, '1', null, XMLDB_NOTNULL, null, null); $table->add_field('enabled', XMLDB_TYPE_INTEGER, '1', null, XMLDB_NOTNULL, null, null); - $table->add_field('enable_from', XMLDB_TYPE_DATETIME, null, null, null, null, null); - $table->add_field('enable_until', XMLDB_TYPE_DATETIME, null, null, null, null, null); - $table->add_field('last_access', XMLDB_TYPE_DATETIME, null, null, null, null, null); - $table->add_field('created', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('updated', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('enable_from', XMLDB_TYPE_INTEGER, '10', null, null, null, null); + $table->add_field('enable_until', XMLDB_TYPE_INTEGER, '10', null, null, null, null); + $table->add_field('last_access', XMLDB_TYPE_INTEGER, '10', null, null, null, null); + $table->add_field('created', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); + $table->add_field('updated', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_consumer. $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); + // Adding indexes to table enrol_lti_lti2_consumer. + $table->add_index('consumer_key256_uniq', XMLDB_INDEX_UNIQUE, array('consumer_key256')); + // Conditionally launch create table for enrol_lti_lti2_consumer. if (!$dbman->table_exists($table)) { $dbman->create_table($table); @@ -79,15 +82,15 @@ function xmldb_enrol_lti_upgrade($oldversion) { $table = new xmldb_table('enrol_lti_lti2_tool_proxy'); // Adding fields to table enrol_lti_lti2_tool_proxy. - $table->add_field('tool_proxy_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); + $table->add_field('id', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); $table->add_field('tool_proxy_id', XMLDB_TYPE_CHAR, '32', null, XMLDB_NOTNULL, null, null); $table->add_field('consumer_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); $table->add_field('tool_proxy', XMLDB_TYPE_TEXT, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('created', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('updated', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('created', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); + $table->add_field('updated', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_tool_proxy. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('tool_proxy_pk')); + $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); $table->add_key('tool_proxy_id_uniq', XMLDB_KEY_UNIQUE, array('tool_proxy_id')); $table->add_key('consumer_pk', XMLDB_KEY_FOREIGN, array('consumer_pk'), 'enrol_lti_lti2_consumer', array('id')); @@ -96,49 +99,19 @@ function xmldb_enrol_lti_upgrade($oldversion) { $dbman->create_table($table); } - // Define table enrol_lti_item to be created. - $table = new xmldb_table('enrol_lti_item'); - - // Adding fields to table enrol_lti_item. - $table->add_field('item_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); - $table->add_field('resource_link_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); - $table->add_field('item_title', XMLDB_TYPE_CHAR, '200', null, XMLDB_NOTNULL, null, null); - $table->add_field('item_text', XMLDB_TYPE_TEXT, null, null, null, null, null); - $table->add_field('item_url', XMLDB_TYPE_CHAR, '200', null, null, null, null); - $table->add_field('max_rating', XMLDB_TYPE_INTEGER, '2', null, XMLDB_NOTNULL, null, '5'); - $table->add_field('step', XMLDB_TYPE_INTEGER, '1', null, XMLDB_NOTNULL, null, '1'); - $table->add_field('visible', XMLDB_TYPE_INTEGER, '1', null, XMLDB_NOTNULL, null, '0'); - $table->add_field('created', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('updated', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - - // Adding keys to table enrol_lti_item. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('item_pk')); - $table->add_key( - 'resource_link_pk', - XMLDB_KEY_FOREIGN, - array('resource_link_pk'), - 'enrol_lti_lti2_resource_link', - array('id') - ); - - // Conditionally launch create table for enrol_lti_item. - if (!$dbman->table_exists($table)) { - $dbman->create_table($table); - } - // Define table enrol_lti_lti2_context to be created. $table = new xmldb_table('enrol_lti_lti2_context'); // Adding fields to table enrol_lti_lti2_context. - $table->add_field('context_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); + $table->add_field('id', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); $table->add_field('consumer_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); $table->add_field('lti_context_id', XMLDB_TYPE_CHAR, '255', null, XMLDB_NOTNULL, null, null); $table->add_field('settings', XMLDB_TYPE_TEXT, null, null, null, null, null); - $table->add_field('created', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('updated', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('created', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); + $table->add_field('updated', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_context. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('context_pk')); + $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); $table->add_key('consumer_pk', XMLDB_KEY_FOREIGN, array('consumer_pk'), 'enrol_lti_lti2_consumer', array('id')); // Conditionally launch create table for enrol_lti_lti2_context. @@ -150,13 +123,14 @@ function xmldb_enrol_lti_upgrade($oldversion) { $table = new xmldb_table('enrol_lti_lti2_nonce'); // Adding fields to table enrol_lti_lti2_nonce. + $table->add_field('id', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); $table->add_field('consumer_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); $table->add_field('value', XMLDB_TYPE_CHAR, '32', null, XMLDB_NOTNULL, null, null); - $table->add_field('expires', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('expires', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_nonce. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('consumer_pk', 'value')); - $table->add_key('consumer_pk', XMLDB_KEY_FOREIGN, array('consumer_pk'), 'enrol_lti_lti2_consumer', array('id')); + $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); + $table->add_key('consumer_pk', XMLDB_KEY_FOREIGN_UNIQUE, array('consumer_pk'), 'enrol_lti_lti2_consumer', array('id')); // Conditionally launch create table for enrol_lti_lti2_nonce. if (!$dbman->table_exists($table)) { @@ -174,22 +148,15 @@ function xmldb_enrol_lti_upgrade($oldversion) { $table->add_field('settings', XMLDB_TYPE_TEXT, null, null, null, null, null); $table->add_field('primary_resource_link_pk', XMLDB_TYPE_INTEGER, '11', null, null, null, null); $table->add_field('share_approved', XMLDB_TYPE_INTEGER, '1', null, null, null, null); - $table->add_field('created', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('updated', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('created', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); + $table->add_field('updated', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_resource_link. $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); - $table->add_key('context_pk', XMLDB_KEY_FOREIGN, array('context_pk'), 'enrol_lti_lti2_context', array('context_pk')); - $table->add_key( - 'primary_resource_link_pk', - XMLDB_KEY_FOREIGN, - array('primary_resource_link_pk'), - 'enrol_lti_lti2_resource_link', - array('id') - ); - - // Adding indexes to table enrol_lti_lti2_resource_link. - $table->add_index('consumer_pk', XMLDB_INDEX_NOTUNIQUE, array('consumer_pk')); + $table->add_key('context_pk', XMLDB_KEY_FOREIGN, array('context_pk'), 'enrol_lti_lti2_context', array('id')); + $table->add_key('primary_resource_link_pk', XMLDB_KEY_FOREIGN, array('primary_resource_link_pk'), + 'enrol_lti_lti2_resource_link', array('id')); + $table->add_key('consumer_pk', XMLDB_KEY_FOREIGN, array('consumer_pk'), 'enrol_lti_lti2_consumer', array('id')); // Conditionally launch create table for enrol_lti_lti2_resource_link. if (!$dbman->table_exists($table)) { @@ -200,20 +167,16 @@ function xmldb_enrol_lti_upgrade($oldversion) { $table = new xmldb_table('enrol_lti_lti2_share_key'); // Adding fields to table enrol_lti_lti2_share_key. + $table->add_field('id', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); $table->add_field('share_key_id', XMLDB_TYPE_CHAR, '32', null, XMLDB_NOTNULL, null, null); $table->add_field('resource_link_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); $table->add_field('auto_approve', XMLDB_TYPE_INTEGER, '1', null, XMLDB_NOTNULL, null, null); - $table->add_field('expires', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('expires', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_share_key. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('share_key_id')); - $table->add_key( - 'resource_link_pk', - XMLDB_KEY_FOREIGN, - array('resource_link_pk'), - 'enrol_lti_lti2_resource_link', - array('id') - ); + $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); + $table->add_key('share_key_id', XMLDB_KEY_UNIQUE, array('share_key_id')); + $table->add_key('resource_link_pk', XMLDB_KEY_FOREIGN_UNIQUE, array('resource_link_pk'), 'enrol_lti_lti2_resource_link', array('id')); // Conditionally launch create table for enrol_lti_lti2_share_key. if (!$dbman->table_exists($table)) { @@ -224,45 +187,23 @@ function xmldb_enrol_lti_upgrade($oldversion) { $table = new xmldb_table('enrol_lti_lti2_user_result'); // Adding fields to table enrol_lti_lti2_user_result. - $table->add_field('user_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); + $table->add_field('id', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null); $table->add_field('resource_link_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); $table->add_field('lti_user_id', XMLDB_TYPE_CHAR, '255', null, XMLDB_NOTNULL, null, null); $table->add_field('lti_result_sourcedid', XMLDB_TYPE_CHAR, '1024', null, XMLDB_NOTNULL, null, null); - $table->add_field('created', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); - $table->add_field('updated', XMLDB_TYPE_DATETIME, null, null, XMLDB_NOTNULL, null, null); + $table->add_field('created', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); + $table->add_field('updated', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, null, null); // Adding keys to table enrol_lti_lti2_user_result. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('user_pk')); - $table->add_key( - 'resource_link_pk', - XMLDB_KEY_FOREIGN, - array('resource_link_pk'), - 'enrol_lti_lti2_resource_link', - array('id') - ); + $table->add_key('primary', XMLDB_KEY_PRIMARY, array('id')); + $table->add_key('resource_link_pk', XMLDB_KEY_FOREIGN, array('resource_link_pk'), + 'enrol_lti_lti2_resource_link', array('id')); // Conditionally launch create table for enrol_lti_lti2_user_result. if (!$dbman->table_exists($table)) { $dbman->create_table($table); } - // Define table enrol_lti_rating to be created. - $table = new xmldb_table('enrol_lti_rating'); - - // Adding fields to table enrol_lti_rating. - $table->add_field('item_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); - $table->add_field('user_pk', XMLDB_TYPE_INTEGER, '11', null, XMLDB_NOTNULL, null, null); - $table->add_field('rating', XMLDB_TYPE_NUMBER, '10, 2', null, XMLDB_NOTNULL, null, null); - - // Adding keys to table enrol_lti_rating. - $table->add_key('primary', XMLDB_KEY_PRIMARY, array('item_pk', 'user_pk')); - $table->add_key('item_pk', XMLDB_KEY_FOREIGN, array('item_pk'), 'enrol_lti_item', array('item_pk')); - - // Conditionally launch create table for enrol_lti_rating. - if (!$dbman->table_exists($table)) { - $dbman->create_table($table); - } - // Lti savepoint reached. upgrade_plugin_savepoint(true, 2016052303, 'enrol', 'lti'); } diff --git a/enrol/lti/proxy.php b/enrol/lti/proxy.php index 3c7cd825f2c..0819536a7f4 100644 --- a/enrol/lti/proxy.php +++ b/enrol/lti/proxy.php @@ -45,7 +45,7 @@ $PAGE->set_title(get_string('registration', 'enrol_lti')); // If we do not compare with a shared secret, someone could very easily // guess an id for the enrolment. if (!\enrol_lti\helper::verify_proxy_token($toolid, $token)) { - throw new \moodle_exception('incorrecttoken', 'enrol_lti'); // TODO can we do an LTI error? Not really important as this bug will only occur if the url is wrong. + throw new \moodle_exception('incorrecttoken', 'enrol_lti'); } $tool = \enrol_lti\helper::get_lti_tool($toolid); @@ -66,6 +66,14 @@ if ($tool->status != ENROL_INSTANCE_ENABLED) { exit(); } +$messagetype = required_param('lti_message_type', PARAM_TEXT); + +// Only accept proxy registration requests from this endpoint. +if ($messagetype != "ToolProxyRegistrationRequest") { + print_error('invalidrequest', 'enrol_lti'); + exit(); +} + $toolprovider = new \enrol_lti\tool_provider($toolid); $toolprovider->handleRequest(); echo $OUTPUT->header(); diff --git a/enrol/lti/tests/data_connector_test.php b/enrol/lti/tests/data_connector_test.php index 0c588d30753..cd9887ade20 100644 --- a/enrol/lti/tests/data_connector_test.php +++ b/enrol/lti/tests/data_connector_test.php @@ -400,7 +400,7 @@ class enrol_lti_data_connector_testcase extends advanced_testcase { } /** - * Test for data_connector::loadContext(). + * Test for data_connector::saveContext(). */ public function test_save_context() { $dc = new data_connector(); @@ -876,11 +876,6 @@ class enrol_lti_data_connector_testcase extends advanced_testcase { // Save the nonce. $this->assertTrue($dc->saveConsumerNonce($nonce)); - - // We should only be doing inserts and a consumer can only have one nonce record. - // So saving again the nonce without it getting cleaned up (by data_connector::loadConsumerNonce()) will throw an exception. - $this->expectException('dml_write_exception'); - $this->assertTrue($dc->saveConsumerNonce($nonce)); } /** diff --git a/enrol/lti/tool.php b/enrol/lti/tool.php index c67fb93749a..6c212f2863e 100644 --- a/enrol/lti/tool.php +++ b/enrol/lti/tool.php @@ -57,11 +57,12 @@ $consumerkey = required_param('oauth_consumer_key', PARAM_TEXT); $ltiversion = optional_param('lti_version', null, PARAM_TEXT); $messagetype = required_param('lti_message_type', PARAM_TEXT); -// Only accept launch requests from this old LTI endpoint. +// Only accept launch requests from this endpoint. if ($messagetype != "basic-lti-launch-request") { print_error('invalidrequest', 'enrol_lti'); exit(); } + // Special handling for LTIv1 launch requests. if ($ltiversion === \IMSGlobal\LTI\ToolProvider\ToolProvider::LTI_VERSION1) { $dataconnector = new \enrol_lti\data_connector(); @@ -79,9 +80,9 @@ if ($ltiversion === \IMSGlobal\LTI\ToolProvider\ToolProvider::LTI_VERSION1) { $consumer->protected = true; $consumer->save(); } - - $toolprovider = new \enrol_lti\tool_provider($toolid); - $toolprovider->handleRequest(); } + +$toolprovider = new \enrol_lti\tool_provider($toolid); +$toolprovider->handleRequest(); echo $OUTPUT->header(); echo $OUTPUT->footer();