ILIAS  trunk Revision v11.0_alpha-3011-gc6b235a2e85
SuggestedSolutionsDatabaseRepository.php
Go to the documentation of this file.
1<?php
2
19declare(strict_types=1);
20
22
29{
30 public const TABLE_SUGGESTED_SOLUTIONS = 'qpl_sol_sug';
31
32 protected \ilDBInterface $db;
33
34 public function __construct(\ilDBInterface $db)
35 {
36 $this->db = $db;
37 }
38
39 public function create(int $question_id, string $type): SuggestedSolution
40 {
41 $solution = $this->buildSuggestedSolution(
42 -1,
43 $question_id,
44 '',
45 '',
46 0,
47 $type,
48 '',
49 $this->getNow()
50 );
51 return $solution;
52 }
53
57 public function selectFor(int $question_id): array
58 {
59 $ret = [];
60 $query = 'SELECT' . PHP_EOL
61 . 'suggested_solution_id, question_fi, internal_link, import_id, '
62 . 'subquestion_index, type, tstamp, value' . PHP_EOL
63 . 'FROM ' . self::TABLE_SUGGESTED_SOLUTIONS . PHP_EOL
64 . 'WHERE question_fi = ' . $this->db->quote($question_id, 'integer');
65
66 $result = $this->db->query($query);
67
68 while ($row = $this->db->fetchAssoc($result)) {
69 $last_update = \DateTimeImmutable::createFromFormat('U', (string) $row['tstamp']);
70
71 if ($row['type'] === null || $row['type'] === '' || $row['type'] === 'text') {
72 continue;
73 }
74
75 $ret[] = $this->buildSuggestedSolution(
76 (int) $row['suggested_solution_id'],
77 (int) $row['question_fi'],
78 (string) $row['internal_link'],
79 (string) $row['import_id'],
80 (int) $row['subquestion_index'],
81 (string) $row['type'],
82 (string) $row['value'],
83 $last_update
84 );
85 }
86
87 return $ret;
88 }
89
90 public function update(array $suggested_solutions): void
91 {
92 foreach ($suggested_solutions as $solution) {
93 if (!is_a($solution, SuggestedSolution::class)) {
94 throw new \Exception('cannot update other than SuggestedSolution');
95 }
96 };
97
98 foreach ($suggested_solutions as $solution) {
99 $query = 'DELETE FROM ' . self::TABLE_SUGGESTED_SOLUTIONS . PHP_EOL
100 . 'WHERE question_fi = ' . $this->db->quote($solution->getQuestionId(), 'integer') . PHP_EOL
101 . 'AND subquestion_index = ' . $this->db->quote($solution->getSubQuestionIndex(), 'integer');
102 $this->db->manipulate($query);
103
104 $next_id = $this->db->nextId(self::TABLE_SUGGESTED_SOLUTIONS);
105 $internal_link = '';
106 if ($solution->isOfTypeLink()) {
107 $internal_link = $solution->getInternalLink();
108 }
109 $this->db->insert(
110 self::TABLE_SUGGESTED_SOLUTIONS,
111 [
112 'suggested_solution_id' => ['integer', $next_id],
113 'question_fi' => ['integer', $solution->getQuestionId()],
114 'type' => ['text',$solution->getType()],
115 'value' => ['clob', $solution->getStorableValue()],
116 'internal_link' => ['text', $internal_link],
117 'import_id' => ['text', $solution->getImportId()],
118 'subquestion_index' => ['integer', $solution->getSubquestionIndex() ],
119 'tstamp' => ['integer', $this->getNow()->format('U')]
120 ]
121 );
122
123 $this->additionalOnStore($solution);
124 }
125 }
126
127 public function delete(int $suggested_solution_id): void
128 {
129 $query = 'DELETE FROM ' . self::TABLE_SUGGESTED_SOLUTIONS . PHP_EOL
130 . 'WHERE suggested_solution_id = ' . $this->db->quote($suggested_solution_id, 'integer');
131 $this->db->manipulate($query);
132 }
133
134 public function deleteForQuestion(int $question_id): void
135 {
136 $query = 'DELETE FROM ' . self::TABLE_SUGGESTED_SOLUTIONS . PHP_EOL
137 . 'WHERE question_fi = ' . $this->db->quote($question_id, 'integer');
138 $this->db->manipulate($query);
139 $this->additionalOnDelete($question_id);
140 }
141
142 public function clone(int $source_question_id, int $target_question_id): void
143 {
144 if ($source_question_id === $target_question_id) {
145 throw new \LogicException('do not sync with same question');
146 }
147 $this->deleteForQuestion($target_question_id);
148 $suggested_solutions = [];
149 foreach ($this->selectFor($source_question_id) as $solution) {
150 $suggested_solutions[] = $solution->withQuestionId($target_question_id);
151 }
152 $this->update($suggested_solutions);
153 }
154
155 protected function buildSuggestedSolution(
156 int $id,
157 int $question_id,
158 string $internal_link,
159 string $import_id,
160 int $subquestion_index,
161 string $type,
162 string $value,
163 \DateTimeImmutable $last_update
165 switch ($type) {
167 $suggestion_class = SuggestedSolutionFile::class;
168 break;
173 $suggestion_class = SuggestedSolutionLink::class;
174 $value = $internal_link;
175 break;
176 default:
177 throw new \LogicException('invalid suggestion-type in repo.');
178 }
179
180 return new $suggestion_class(
181 $id,
182 $question_id,
183 $subquestion_index,
184 $import_id,
185 $last_update,
186 $type,
187 $value
188 );
189 }
190
191 protected function getNow(): \DateTimeImmutable
192 {
193 return new \DateTimeImmutable();
194 }
195
196
197 protected function additionalOnDelete(int $question_id): void
198 {
199 \ilInternalLink::_deleteAllLinksOfSource("qst", $question_id);
200 }
201
202 protected function additionalOnStore(SuggestedSolution $solution): void
203 {
204 if ($solution->isOfTypeLink()) {
205 if (preg_match("/il_(\d*?)_(\w+)_(\d+)/", $solution->getInternalLink(), $matches)) {
206 \ilInternalLink::_saveLink("qst", $solution->getQuestionId(), $matches[2], (int) $matches[3], (int) $matches[1]);
207 }
208 }
209 }
210}
$id
plugin.php for ilComponentBuildPluginInfoObjectiveTest::testAddPlugins
Definition: plugin.php:23
buildSuggestedSolution(int $id, int $question_id, string $internal_link, string $import_id, int $subquestion_index, string $type, string $value, \DateTimeImmutable $last_update)
Interface ilDBInterface.