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
 * Search area for course custom fields.
19
 *
20
 * @package core_course
21
 * @copyright Toni Barbera <toni@moodle.com>
22
 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
23
 */
24
 
25
namespace core_course\search;
26
 
27
use core_course\customfield\course_handler;
28
use core_customfield\data_controller;
29
use core_customfield\field_controller;
30
 
31
defined('MOODLE_INTERNAL') || die();
32
 
33
/**
34
 * Search area for course custom fields.
35
 *
36
 * @package core_course
37
 * @copyright Toni Barbera <toni@moodle.com>
38
 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
39
 */
40
class customfield extends \core_search\base {
41
 
42
    /**
43
     * Custom fields are indexed at course context.
44
     *
45
     * @var array
46
     */
47
    protected static $levels = [CONTEXT_COURSE];
48
 
49
    /**
50
     * Returns recordset containing required data for indexing
51
     * course custom fields.
52
     *
53
     * @param int $modifiedfrom timestamp
54
     * @param \context|null $context Restriction context
55
     * @return \moodle_recordset|null Recordset or null if no change possible
56
     */
57
    public function get_document_recordset($modifiedfrom = 0, \context $context = null) {
58
        global $DB;
59
 
60
        list ($contextjoin, $contextparams) = $this->get_course_level_context_restriction_sql($context, 'c', SQL_PARAMS_NAMED);
61
        if ($contextjoin === null) {
62
            return null;
63
        }
64
 
65
        $fields = course_handler::create()->get_fields();
66
        if (!$fields) {
67
            $fields = array();
68
        }
69
        list($fieldsql, $fieldparam) = $DB->get_in_or_equal(array_keys($fields), SQL_PARAMS_NAMED, 'fld', true, 0);
70
 
71
        // Restrict recordset to CONTEXT_COURSE (since we are implementing it to core_course\search).
72
        $sql = "SELECT d.*
73
                  FROM {customfield_data} d
74
                  JOIN {course} c ON c.id = d.instanceid
75
                  JOIN {context} cnt ON cnt.instanceid = c.id
76
           $contextjoin
77
                 WHERE d.timemodified >= :modifiedfrom
78
                   AND cnt.contextlevel = :contextlevel
79
                   AND d.fieldid $fieldsql
80
              ORDER BY d.timemodified ASC";
81
        return $DB->get_recordset_sql($sql , array_merge($contextparams,
82
            ['modifiedfrom' => $modifiedfrom, 'contextlevel' => CONTEXT_COURSE], $fieldparam));
83
    }
84
 
85
    /**
86
     * Returns the document associated with this section.
87
     *
88
     * @param \stdClass $record
89
     * @param array $options
90
     * @return \core_search\document|bool
91
     */
92
    public function get_document($record, $options = array()) {
93
        global $PAGE;
94
 
95
        try {
96
            $context = \context_course::instance($record->instanceid);
97
        } catch (\moodle_exception $ex) {
98
            // Notify it as we run here as admin, we should see everything.
99
            debugging('Error retrieving ' . $this->areaid . ' ' . $record->id . ' document, not all required data is available: ' .
100
                $ex->getMessage(), DEBUG_DEVELOPER);
101
            return false;
102
        }
103
 
104
        $handler = course_handler::create();
105
        $field = $handler->get_fields()[$record->fieldid];
106
        $data = data_controller::create(0, $record, $field);
107
 
108
        // Prepare associative array with data from DB.
109
        $doc = \core_search\document_factory::instance($record->id, $this->componentname, $this->areaname);
110
        $doc->set('title', content_to_text($field->get('name'), false));
111
        $doc->set('content', content_to_text($data->export_value(), FORMAT_HTML));
112
        $doc->set('contextid', $context->id);
113
        $doc->set('courseid', $context->instanceid);
114
        $doc->set('owneruserid', \core_search\manager::NO_OWNER_ID);
115
        $doc->set('modified', $record->timemodified);
116
 
117
        // Check if this document should be considered new.
118
        if (isset($options['lastindexedtime']) && ($options['lastindexedtime'] < $record->timecreated)) {
119
            // If the document was created after the last index time, it must be new.
120
            $doc->set_is_new(true);
121
        }
122
 
123
        return $doc;
124
    }
125
 
126
    /**
127
     * Whether the user can access the document or not.
128
     *
129
     * @param int $id The custom field data ID
130
     * @return int
131
     */
132
    public function check_access($id) {
133
        global $DB;
134
 
135
        $coursesql = '
136
            SELECT c.*
137
              FROM {course} c
138
              JOIN {customfield_data} d ON d.instanceid = c.id
139
             WHERE d.id = :dataid';
140
 
141
        // Verify both the course and data record still exist.
142
        $course = $DB->get_record_sql($coursesql, ['dataid' => $id]);
143
        if (!$course) {
144
            return \core_search\manager::ACCESS_DELETED;
145
        }
146
 
147
        // Check whether user is enrolled and the course is visible, or user can view it while hidden.
148
        $context = \context_course::instance($course->id);
149
        $userenrolled = is_enrolled($context) &&
150
            ($course->visible || has_capability('moodle/course:viewhiddencourses', $context));
151
 
152
        // Grant access if user is considered enrolled, or they can otherwise see the course info.
153
        if ($userenrolled || \core_course_category::can_view_course_info($course)) {
154
            return \core_search\manager::ACCESS_GRANTED;
155
        }
156
 
157
        return \core_search\manager::ACCESS_DENIED;
158
    }
159
 
160
    /**
161
     * Link to the course.
162
     *
163
     * @param \core_search\document $doc
164
     * @return \moodle_url
165
     */
166
    public function get_doc_url(\core_search\document $doc) {
167
        return $this->get_context_url($doc);
168
    }
169
 
170
    /**
171
     * Link to the course.
172
     *
173
     * @param \core_search\document $doc
174
     * @return \moodle_url
175
     */
176
    public function get_context_url(\core_search\document $doc) {
177
        return new \moodle_url('/course/view.php', array('id' => $doc->get('courseid')));
178
    }
179
 
180
    /**
181
     * Returns the moodle component name.
182
     *
183
     * It might be the plugin name (whole frankenstyle name) or the core subsystem name.
184
     *
185
     * @return string
186
     */
187
    public function get_component_name() {
188
        return 'course';
189
    }
190
 
191
    /**
192
     * Returns an icon instance for the document.
193
     *
194
     * @param \core_search\document $doc
195
     * @return \core_search\document_icon
196
     */
197
    public function get_doc_icon(\core_search\document $doc): \core_search\document_icon {
198
        return new \core_search\document_icon('i/customfield');
199
    }
200
 
201
    /**
202
     * Returns a list of category names associated with the area.
203
     *
204
     * @return array
205
     */
206
    public function get_category_names() {
207
        return [
208
            \core_search\manager::SEARCH_AREA_CATEGORY_COURSE_CONTENT,
209
            \core_search\manager::SEARCH_AREA_CATEGORY_COURSES
210
        ];
211
    }
212
}