3 declare(strict_types=1);
    35         $this->
id = 
'Score.collection';
    36         $this->
template = 
'/{context_id}/lineitems/{item_id}/lineitem/scores';
    37         $this->variables[] = 
'Scores.url';
    38         $this->formats[] = 
'application/vnd.ims.lis.v1.scorecontainer+json';
    39         $this->formats[] = 
'application/vnd.ims.lis.v1.score+json';
    40         $this->methods[] = 
'POST';
    49         $contextId = 
$params[
'context_id'];
    75             $response->
setCode($returnCode); 
    77             $response->
setCode($e->getCode());
    85         $score = json_decode($requestData);
    87         $userId = self::getUsrIdForObjectAndUsrIdent($objId, $score->userId);
    88         if ($userId == null) {
    90             throw new Exception(
'User not available', 404);
    95             !isset($score->userId) ||
    96             !isset($score->gradingProgress) ||
    97             !isset($score->activityProgress) ||
    98             !isset($score->timestamp) ||
    99             isset($score->timestamp) && !self::validate_iso8601_date($score->timestamp) ||
   100             (isset($score->scoreGiven) && !is_numeric($score->scoreGiven)) ||
   101             (isset($score->scoreGiven) && !isset($score->scoreMaximum)) ||
   102             (isset($score->scoreMaximum) && !is_numeric($score->scoreMaximum))
   106             throw new Exception(
'Incorrect score received', 400);
   110         if (!isset($score->scoreMaximum)) {
   111             $score->scoreMaximum = 1;
   113         if (isset($score->scoreGiven)) {
   114             if ($score->gradingProgress != 
'FullyGraded') {
   115                 $score->scoreGiven = null;
   118         $result = (float) $score->scoreGiven / (
float) $score->scoreMaximum;
   123         $ltiObjRes->readProperties($objId);
   125         if (!$ltiObjRes->isAvailable()) {
   126             throw new Exception(
'Tool for Object not available', 404);
   130         if ($result >= $ltiObjRes->getMasteryScore()) {
   135         $lp_percentage = (
int) round(100 * $result);
   138         if (empty($consRes)) {
   143         if (!isset($consRes->id)) {
   144             $consRes->id = $DIC->database()->nextId(
'lti_consumer_results');
   146         $DIC->database()->replace(
   147             'lti_consumer_results',
   149                 'id' => array(
'integer', $consRes->id)
   152                 'obj_id' => array(
'integer', $objId),
   153                 'usr_id' => array(
'integer', $userId),
   154                 'result' => array(
'float', $result)
   160         $ltiTimestamp = DateTimeImmutable::createFromFormat(DateTimeInterface::RFC3339_EXTENDED, $score->timestamp);
   161         if (!$ltiTimestamp) { 
   162             $ltiTimestamp = DateTimeImmutable::createFromFormat(DateTimeInterface::ISO8601, $score->timestamp);
   164         if (!$ltiTimestamp) { 
   165             $ltiTimestamp = 
new DateTime(
'now');
   168             'id' => array(
'integer', $DIC->database()->nextId(
'lti_consumer_grades')),
   169             'obj_id' => array(
'integer', $objId),
   170             'usr_id' => array(
'integer', $userId),
   171             'score_given' => array(
'float', $score->scoreGiven),
   172             'score_maximum' => array(
'float', $score->scoreMaximum),
   173             'activity_progress' => array(
'text', $score->activityProgress),
   174             'grading_progress' => array(
'text', $score->gradingProgress),
   175             'lti_timestamp' => array(
'timestamp',$ltiTimestamp->format(
"Y-m-d H:i:s")),
   176             'stored' => array(
'timestamp', date(
"Y-m-d H:i:s"))
   178         $DIC->database()->insert(
'lti_consumer_grades', $gradeValues);
   187         if (preg_match(
'/^([\+-]?\d{4}(?!\d{2}\b))((-?)((0[1-9]|1[0-2])' .
   188                 '(\3([12]\d|0[1-9]|3[01]))?|W([0-4]\d|5[0-2])(-?[1-7])?|(00[1-9]|0[1-9]\d|[12]\d{2}|3([0-5]\d|6[1-6])))' .
   189                 '([T\s]((([01]\d|2[0-3])((:?)[0-5]\d)?|24\:?00)([\.,]\d+(?!:))?)?(\17[0-5]\d([\.,]\d+)?)' .
   190                 '?([zZ]|([\+-])([01]\d|2[0-3]):?([0-5]\d)?)?)?)?$/', $date) > 0) {
   199         $atExist = strpos($userIdent, 
'@');
   201         $query = 
"SELECT usr_id FROM cmix_users WHERE obj_id = " . $DIC->database()->quote($objId, 
'integer');
   204             $query .= 
" AND usr_ident = " . $DIC->database()->quote($userIdent, 
'text');
   206             $query .= 
" AND" . $DIC->database()->like(
'usr_ident', 
'text', $userIdent . 
'@%');
   208         $res = $DIC->database()->query($query);
   211         while ($row = $DIC->database()->fetchAssoc(
$res)) {
   212             $usrId = (
int) $row[
'usr_id'];
 const LP_STATUS_COMPLETED_NUM
 
array $params
Template variables parsed from the resource template. 
 
execute(ilLTIConsumerServiceResponse $response)
Execute the request for this resource. 
 
static validate_iso8601_date(string $date)
 
parseTemplate()
Parse the template for variables. 
 
ilLTIConsumerServiceBase $service
Service associated with this resource. 
 
const LP_STATUS_IN_PROGRESS_NUM
 
getRequestData()
Get the request body. 
 
__construct(ilLTIConsumerServiceBase $service)
 
const SCOPE_GRADESERVICE_SCORE
Scope for access to Score service. 
 
static getUsrIdForObjectAndUsrIdent(int $objId, string $userIdent)
 
setCode(int $code)
Set the response code. 
 
checkScore(string $requestData, int $objId)
 
static getByKeys(int $a_obj_id, int $a_usr_id, ?bool $a_create=false)
Get a result by object and user key. 
 
setReason(string $reason)
Set the response reason. 
 
static writeStatus(int $a_obj_id, int $a_user_id, int $a_status, int $a_percentage=0, bool $a_force_per=false, ?int &$a_old_status=self::LP_STATUS_NOT_ATTEMPTED_NUM)
Write status for user and object.