1+ <?php
2+ // This file is part of Moodle - https://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+ * Privacy implementation for local_onlinejudge.
19+ *
20+ * @package local_onlinejudge
21+ * @copyright 2024 Online Judge Contributors
22+ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
23+ */
24+
25+ namespace local_onlinejudge \privacy ;
26+
27+ use core_privacy \local \metadata \collection ;
28+ use core_privacy \local \request \approved_contextlist ;
29+ use core_privacy \local \request \approved_userlist ;
30+ use core_privacy \local \request \context ;
31+ use core_privacy \local \request \contextlist ;
32+ use core_privacy \local \request \userlist ;
33+ use core_privacy \local \request \writer ;
34+ use core_privacy \local \request \transform ;
35+
36+ /**
37+ * Privacy provider for local_onlinejudge.
38+ */
39+ class provider implements
40+ \core_privacy \local \metadata \provider,
41+ \core_privacy \local \request \plugin \provider,
42+ \core_privacy \local \request \core_userlist_provider {
43+
44+ /**
45+ * Get the language string identifier with the component's language
46+ * file to explain why this plugin stores no data.
47+ *
48+ * @param collection $collection The initialised collection to add items to.
49+ * @return collection A listing of user data stored through this system.
50+ */
51+ public static function get_metadata (collection $ collection ): collection {
52+ $ collection ->add_database_table ('onlinejudge_tasks ' , [
53+ 'cmid ' => 'privacy:metadata:onlinejudge_tasks:cmid ' ,
54+ 'userid ' => 'privacy:metadata:onlinejudge_tasks:userid ' ,
55+ 'language ' => 'privacy:metadata:onlinejudge_tasks:language ' ,
56+ 'input ' => 'privacy:metadata:onlinejudge_tasks:input ' ,
57+ 'output ' => 'privacy:metadata:onlinejudge_tasks:output ' ,
58+ 'stdout ' => 'privacy:metadata:onlinejudge_tasks:stdout ' ,
59+ 'stderr ' => 'privacy:metadata:onlinejudge_tasks:stderr ' ,
60+ 'compileroutput ' => 'privacy:metadata:onlinejudge_tasks:compileroutput ' ,
61+ 'infoteacher ' => 'privacy:metadata:onlinejudge_tasks:infoteacher ' ,
62+ 'infostudent ' => 'privacy:metadata:onlinejudge_tasks:infostudent ' ,
63+ 'cpuusage ' => 'privacy:metadata:onlinejudge_tasks:cpuusage ' ,
64+ 'memusage ' => 'privacy:metadata:onlinejudge_tasks:memusage ' ,
65+ 'submittime ' => 'privacy:metadata:onlinejudge_tasks:submittime ' ,
66+ 'judgetime ' => 'privacy:metadata:onlinejudge_tasks:judgetime ' ,
67+ 'var1 ' => 'privacy:metadata:onlinejudge_tasks:var1 ' ,
68+ 'var2 ' => 'privacy:metadata:onlinejudge_tasks:var2 ' ,
69+ 'var3 ' => 'privacy:metadata:onlinejudge_tasks:var3 ' ,
70+ 'var4 ' => 'privacy:metadata:onlinejudge_tasks:var4 ' ,
71+ 'status ' => 'privacy:metadata:onlinejudge_tasks:status ' ,
72+ ], 'privacy:metadata:onlinejudge_tasks ' );
73+
74+ return $ collection ;
75+ }
76+
77+ /**
78+ * Get the list of contexts that contain user information for the specified user.
79+ *
80+ * @param int $userid The user to search.
81+ * @return contextlist The contextlist containing the list of contexts used in this plugin.
82+ */
83+ public static function get_contexts_for_userid (int $ userid ): contextlist {
84+ $ contextlist = new contextlist ();
85+
86+ // Find contexts where user has submitted tasks.
87+ $ sql = "SELECT ctx.id
88+ FROM {context} ctx
89+ JOIN {course_modules} cm ON cm.id = ctx.instanceid AND ctx.contextlevel = :contextlevel
90+ JOIN {onlinejudge_tasks} ojt ON ojt.cmid = cm.id
91+ WHERE ojt.userid = :userid " ;
92+
93+ $ contextlist ->add_from_sql ($ sql , [
94+ 'userid ' => $ userid ,
95+ 'contextlevel ' => CONTEXT_MODULE ,
96+ ]);
97+
98+ return $ contextlist ;
99+ }
100+
101+ /**
102+ * Get the list of users who have data within a context.
103+ *
104+ * @param userlist $userlist The userlist containing the list of users who have data in this context/plugin combination.
105+ */
106+ public static function get_users_in_context (userlist $ userlist ) {
107+ $ context = $ userlist ->get_context ();
108+
109+ if (!$ context instanceof \context_module) {
110+ return ;
111+ }
112+
113+ $ sql = "SELECT ojt.userid
114+ FROM {onlinejudge_tasks} ojt
115+ JOIN {course_modules} cm ON cm.id = ojt.cmid
116+ WHERE cm.id = :cmid " ;
117+
118+ $ userlist ->add_from_sql ('userid ' , $ sql , ['cmid ' => $ context ->instanceid ]);
119+ }
120+
121+ /**
122+ * Export all user data for the specified user, in the specified contexts.
123+ *
124+ * @param approved_contextlist $contextlist The approved contexts to export information for.
125+ */
126+ public static function export_user_data (approved_contextlist $ contextlist ) {
127+ global $ DB ;
128+
129+ if (empty ($ contextlist ->count ())) {
130+ return ;
131+ }
132+
133+ $ user = $ contextlist ->get_user ();
134+ $ userid = $ user ->id ;
135+
136+ foreach ($ contextlist ->get_contexts () as $ context ) {
137+ if (!$ context instanceof \context_module) {
138+ continue ;
139+ }
140+
141+ $ cmid = $ context ->instanceid ;
142+
143+ // Get all tasks for this user in this context.
144+ $ tasks = $ DB ->get_records ('onlinejudge_tasks ' , [
145+ 'userid ' => $ userid ,
146+ 'cmid ' => $ cmid ,
147+ ]);
148+
149+ if (!empty ($ tasks )) {
150+ $ taskdata = [];
151+ foreach ($ tasks as $ task ) {
152+ $ taskdata [] = [
153+ 'language ' => $ task ->language ,
154+ 'submittime ' => transform::datetime ($ task ->submittime ),
155+ 'judgetime ' => $ task ->judgetime ? transform::datetime ($ task ->judgetime ) : null ,
156+ 'status ' => $ task ->status ,
157+ 'cpuusage ' => $ task ->cpuusage ,
158+ 'memusage ' => $ task ->memusage ,
159+ 'compileroutput ' => $ task ->compileroutput ,
160+ 'infostudent ' => $ task ->infostudent ,
161+ 'var1 ' => $ task ->var1 ,
162+ 'var2 ' => $ task ->var2 ,
163+ 'var3 ' => $ task ->var3 ,
164+ 'var4 ' => $ task ->var4 ,
165+ ];
166+ }
167+
168+ writer::with_context ($ context )->export_data (
169+ [get_string ('pluginname ' , 'local_onlinejudge ' )],
170+ (object ) ['tasks ' => $ taskdata ]
171+ );
172+ }
173+ }
174+ }
175+
176+ /**
177+ * Delete all data for all users in the specified context.
178+ *
179+ * @param context $context The context to delete in.
180+ */
181+ public static function delete_data_for_all_users_in_context (\context $ context ) {
182+ global $ DB ;
183+
184+ if (!$ context instanceof \context_module) {
185+ return ;
186+ }
187+
188+ $ cmid = $ context ->instanceid ;
189+ $ DB ->delete_records ('onlinejudge_tasks ' , ['cmid ' => $ cmid ]);
190+ }
191+
192+ /**
193+ * Delete all user data for the specified user, in the specified contexts.
194+ *
195+ * @param approved_contextlist $contextlist The approved contexts and user information to delete information for.
196+ */
197+ public static function delete_data_for_user (approved_contextlist $ contextlist ) {
198+ global $ DB ;
199+
200+ if (empty ($ contextlist ->count ())) {
201+ return ;
202+ }
203+
204+ $ userid = $ contextlist ->get_user ()->id ;
205+
206+ foreach ($ contextlist ->get_contexts () as $ context ) {
207+ if (!$ context instanceof \context_module) {
208+ continue ;
209+ }
210+
211+ $ cmid = $ context ->instanceid ;
212+ $ DB ->delete_records ('onlinejudge_tasks ' , [
213+ 'userid ' => $ userid ,
214+ 'cmid ' => $ cmid ,
215+ ]);
216+ }
217+ }
218+
219+ /**
220+ * Delete multiple users within a single context.
221+ *
222+ * @param approved_userlist $userlist The approved context and user information to delete information for.
223+ */
224+ public static function delete_data_for_users (approved_userlist $ userlist ) {
225+ global $ DB ;
226+
227+ $ context = $ userlist ->get_context ();
228+
229+ if (!$ context instanceof \context_module) {
230+ return ;
231+ }
232+
233+ $ userids = $ userlist ->get_userids ();
234+ if (empty ($ userids )) {
235+ return ;
236+ }
237+
238+ $ cmid = $ context ->instanceid ;
239+
240+ list ($ usersql , $ userparams ) = $ DB ->get_in_or_equal ($ userids , SQL_PARAMS_NAMED );
241+ $ params = array_merge (['cmid ' => $ cmid ], $ userparams );
242+
243+ $ DB ->delete_records_select ('onlinejudge_tasks ' , "cmid = :cmid AND userid $ usersql " , $ params );
244+ }
245+ }
0 commit comments