Proyectos de Subversion Moodle

Rev

| Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 1
<?php
2
// This file is part of Moodle - http://moodle.org/
3
//
4
// Moodle is free software: you can redistribute it and/or modify
5
// it under the terms of the GNU General Public License as published by
6
// the Free Software Foundation, either version 3 of the License, or
7
// (at your option) any later version.
8
//
9
// Moodle is distributed in the hope that it will be useful,
10
// but WITHOUT ANY WARRANTY; without even the implied warranty of
11
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
// GNU General Public License for more details.
13
//
14
// You should have received a copy of the GNU General Public License
15
// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
16
 
17
/**
18
 * The mod_hvp content user data.
19
 *
20
 * @package    mod_hvp
21
 * @since      Moodle 2.7
22
 * @copyright  2017 Joubel AS
23
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
24
 */
25
 
26
namespace mod_hvp;
27
 
28
defined('MOODLE_INTERNAL') || die();
29
 
30
/**
31
 * Class xapi_result handles xapi results and corresponding db operations.
32
 *
33
 * @package mod_hvp
34
 */
35
class xapi_result {
36
 
37
    /**
38
     * Handle xapi results endpoint
39
     */
40
    public static function handle_ajax() {
41
        // Validate token.
42
        if (!self::validate_token()) {
43
            $core = framework::instance();
44
            \H5PCore::ajaxError($core->h5pF->t('Invalid security token.'),
45
                'INVALID_TOKEN');
46
            return;
47
        }
48
 
49
        $cm = get_coursemodule_from_id('hvp', required_param('contextId', PARAM_INT));
50
        if (!$cm) {
51
            \H5PCore::ajaxError('No such content');
52
            http_response_code(404);
53
            return;
54
        }
55
 
56
        $xapiresult = required_param('xAPIResult', PARAM_RAW);
57
 
58
        // Validate.
59
        $context = \context_module::instance($cm->id);
60
        if (!has_capability('mod/hvp:saveresults', $context)) {
61
            \H5PCore::ajaxError(get_string('nopermissiontosaveresult', 'hvp'));
62
            return;
63
        }
64
 
65
        $xapijson = json_decode($xapiresult);
66
        if (!$xapijson) {
67
            \H5PCore::ajaxError('Invalid json in xAPI data.');
68
            return;
69
        }
70
 
71
        if (!self::validate_xapi_data($xapijson)) {
72
            \H5PCore::ajaxError('Invalid xAPI data.');
73
            return;
74
        }
75
 
76
        // Delete any old results.
77
        self::remove_xapi_data($cm->instance);
78
 
79
        // Store results.
80
        self::store_xapi_data($cm->instance, $xapijson);
81
 
82
        // Successfully inserted xAPI result.
83
        \H5PCore::ajaxSuccess();
84
    }
85
 
86
    /**
87
     * Validate xAPI results token
88
     *
89
     * @return bool True if token was valid
90
     */
91
    private static function validate_token() {
92
        $token = required_param('token', PARAM_ALPHANUM);
93
        return \H5PCore::validToken('xapiresult', $token);
94
 
95
    }
96
 
97
    /**
98
     * Validate xAPI data
99
     *
100
     * @param object $xapidata xAPI data
101
     *
102
     * @return bool True if valid data
103
     */
104
    private static function validate_xapi_data($xapidata) {
105
        $xapidata = new \H5PReportXAPIData($xapidata);
106
        return $xapidata->validateData();
107
    }
108
 
109
    /**
110
     * Store xAPI result(s)
111
     *
112
     * @param int $contentid Content id
113
     * @param object $xapidata xAPI data
114
     * @param int $parentid Parent id
115
     */
116
    private static function store_xapi_data($contentid, $xapidata, $parentid = null) {
117
        global $DB, $USER;
118
 
119
        $xapidata = new \H5PReportXAPIData($xapidata, $parentid);
120
        $insertedid = $DB->insert_record('hvp_xapi_results', (object) array(
121
            'content_id' => $contentid,
122
            'user_id' => $USER->id,
123
            'parent_id' => $xapidata->getParentID(),
124
            'interaction_type' => $xapidata->getInteractionType(),
125
            'description' => $xapidata->getDescription(),
126
            'correct_responses_pattern' => $xapidata->getCorrectResponsesPattern(),
127
            'response' => $xapidata->getResponse(),
128
            'additionals' => $xapidata->getAdditionals(),
129
            'raw_score' => $xapidata->getScoreRaw(),
130
            'max_score' => $xapidata->getScoreMax(),
131
        ));
132
 
133
        // Save sub content statements data.
134
        if ($xapidata->isCompound()) {
135
            foreach ($xapidata->getChildren($contentid) as $child) {
136
                self::store_xapi_data($contentid, $child, $insertedid);
137
            }
138
        }
139
    }
140
 
141
    /**
142
     * Remove xAPI result(s)
143
     *
144
     * @param int $contentid Content id
145
     */
146
    private static function remove_xapi_data($contentid) {
147
        global $DB, $USER;
148
 
149
        $DB->delete_records('hvp_xapi_results', array(
150
            'content_id' => $contentid,
151
            'user_id' => $USER->id
152
        ));
153
    }
154
}