1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
declare(strict_types=1); |
4
|
|
|
|
5
|
|
|
/* For licensing terms, see /license.txt */ |
6
|
|
|
|
7
|
|
|
namespace Chamilo\CourseBundle\Repository; |
8
|
|
|
|
9
|
|
|
use Chamilo\CoreBundle\Repository\ResourceRepository; |
10
|
|
|
use Chamilo\CourseBundle\Entity\CDropboxFile; |
11
|
|
|
use Doctrine\Persistence\ManagerRegistry; |
12
|
|
|
|
13
|
|
|
final class CDropboxFileRepository extends ResourceRepository |
14
|
|
|
{ |
15
|
|
|
public function __construct(ManagerRegistry $registry) |
16
|
|
|
{ |
17
|
|
|
parent::__construct($registry, CDropboxFile::class); |
18
|
|
|
} |
19
|
|
|
|
20
|
|
|
/** |
21
|
|
|
* Files I sent (my own uploads), filtered by category: |
22
|
|
|
* - categoryId = 0 → only root |
23
|
|
|
* - categoryId > 0 → only that folder |
24
|
|
|
*/ |
25
|
|
|
public function findSentByContextAndCategory(int $cid, ?int $sid, int $uid, int $categoryId): array |
26
|
|
|
{ |
27
|
|
|
$conn = $this->getEntityManager()->getConnection(); |
28
|
|
|
$sid = (int) ($sid ?? 0); |
29
|
|
|
$sql = <<<SQL |
30
|
|
|
SELECT |
31
|
|
|
f.iid AS id, |
32
|
|
|
f.title AS title, |
33
|
|
|
f.description AS description, |
34
|
|
|
f.filesize AS filesize, |
35
|
|
|
f.last_upload_date AS lastUploadDate, |
36
|
|
|
f.cat_id AS catId, |
37
|
|
|
'' AS recipients |
38
|
|
|
FROM c_dropbox_file f |
39
|
|
|
WHERE f.c_id = :cid |
40
|
|
|
AND f.session_id = :sid |
41
|
|
|
AND f.uploader_id = :uid |
42
|
|
|
AND f.cat_id = :categoryId |
43
|
|
|
ORDER BY f.last_upload_date DESC, f.iid DESC |
44
|
|
|
SQL; |
45
|
|
|
|
46
|
|
|
return $conn->fetchAllAssociative($sql, [ |
47
|
|
|
'cid' => $cid, |
48
|
|
|
'sid' => $sid, |
49
|
|
|
'uid' => $uid, |
50
|
|
|
'categoryId' => $categoryId, |
51
|
|
|
]); |
52
|
|
|
} |
53
|
|
|
|
54
|
|
|
/** |
55
|
|
|
* Files I received (visibility rows), filtered by my category in c_dropbox_person: |
56
|
|
|
* - categoryId = 0 → only root |
57
|
|
|
* - categoryId > 0 → only that folder |
58
|
|
|
*/ |
59
|
|
|
public function findReceivedByContextAndCategory(int $cid, ?int $sid, int $uid, int $categoryId): array |
60
|
|
|
{ |
61
|
|
|
$conn = $this->getEntityManager()->getConnection(); |
62
|
|
|
$sid = $sid ?? 0; |
63
|
|
|
|
64
|
|
|
$sql = <<<SQL |
65
|
|
|
SELECT |
66
|
|
|
f.iid AS id, |
67
|
|
|
f.title AS title, |
68
|
|
|
f.description AS description, |
69
|
|
|
f.filesize AS filesize, |
70
|
|
|
f.last_upload_date AS lastUploadDate, |
71
|
|
|
f.cat_id AS catId, |
72
|
|
|
CONCAT('User #', f.uploader_id) AS uploader |
73
|
|
|
FROM c_dropbox_person p |
74
|
|
|
INNER JOIN c_dropbox_file f |
75
|
|
|
ON f.iid = p.file_id |
76
|
|
|
AND f.c_id = p.c_id |
77
|
|
|
WHERE p.c_id = :cid |
78
|
|
|
AND p.user_id = :uid |
79
|
|
|
AND f.session_id = :sid |
80
|
|
|
AND f.cat_id = :categoryId |
81
|
|
|
ORDER BY f.last_upload_date DESC, f.iid DESC |
82
|
|
|
SQL; |
83
|
|
|
|
84
|
|
|
return $conn->fetchAllAssociative($sql, [ |
85
|
|
|
'cid' => $cid, |
86
|
|
|
'uid' => $uid, |
87
|
|
|
'sid' => $sid, |
88
|
|
|
'categoryId' => $categoryId, |
89
|
|
|
]); |
90
|
|
|
} |
91
|
|
|
|
92
|
|
|
/** |
93
|
|
|
* Move a file to a target category for the given area and user, without creating duplicates. |
94
|
|
|
* |
95
|
|
|
* - area "sent": updates c_dropbox_file.cat_id (uploader's own organization). |
96
|
|
|
* - area "received": updates c_dropbox_person.cat_id (receiver's own organization). |
97
|
|
|
* |
98
|
|
|
* @return int number of affected rows |
99
|
|
|
*/ |
100
|
|
|
public function moveFileForArea( |
101
|
|
|
int $fileId, |
102
|
|
|
int $cid, |
103
|
|
|
?int $sid, |
104
|
|
|
int $uid, |
105
|
|
|
int $targetCatId, |
106
|
|
|
string $area |
107
|
|
|
): int { |
108
|
|
|
$conn = $this->getEntityManager()->getConnection(); |
109
|
|
|
$targetCatId = (int) $targetCatId; |
110
|
|
|
|
111
|
|
|
if ($area === 'sent') { |
112
|
|
|
// Move inside sender's space: update file's category if current user is the uploader. |
113
|
|
|
$sql = <<<SQL |
114
|
|
|
UPDATE c_dropbox_file |
115
|
|
|
SET cat_id = :targetCatId |
116
|
|
|
WHERE iid = :fileId |
117
|
|
|
AND c_id = :cid |
118
|
|
|
AND uploader_id = :uid |
119
|
|
|
SQL; |
120
|
|
|
|
121
|
|
|
return $conn->executeStatement($sql, [ |
122
|
|
|
'targetCatId' => $targetCatId, |
123
|
|
|
'fileId' => $fileId, |
124
|
|
|
'cid' => $cid, |
125
|
|
|
'uid' => $uid, |
126
|
|
|
]); |
127
|
|
|
} |
128
|
|
|
|
129
|
|
|
$conn->beginTransaction(); |
130
|
|
|
try { |
131
|
|
|
// Check recipient visibility exists |
132
|
|
|
$check = <<<SQL |
133
|
|
|
SELECT 1 |
134
|
|
|
FROM c_dropbox_person |
135
|
|
|
WHERE c_id = :cid |
136
|
|
|
AND file_id = :fileId |
137
|
|
|
AND user_id = :uid |
138
|
|
|
LIMIT 1 |
139
|
|
|
SQL; |
140
|
|
|
$exists = (bool) $conn->fetchOne($check, [ |
141
|
|
|
'cid' => $cid, |
142
|
|
|
'fileId' => $fileId, |
143
|
|
|
'uid' => $uid, |
144
|
|
|
]); |
145
|
|
|
|
146
|
|
|
if (!$exists) { |
147
|
|
|
// Not a recipient; nothing to move. |
148
|
|
|
$conn->commit(); |
149
|
|
|
return 0; |
150
|
|
|
} |
151
|
|
|
|
152
|
|
|
// Update the file's category. |
153
|
|
|
$upd = <<<SQL |
154
|
|
|
UPDATE c_dropbox_file |
155
|
|
|
SET cat_id = :targetCatId |
156
|
|
|
WHERE iid = :fileId |
157
|
|
|
AND c_id = :cid |
158
|
|
|
SQL; |
159
|
|
|
$affected = $conn->executeStatement($upd, [ |
160
|
|
|
'targetCatId' => $targetCatId, |
161
|
|
|
'fileId' => $fileId, |
162
|
|
|
'cid' => $cid, |
163
|
|
|
]); |
164
|
|
|
|
165
|
|
|
$conn->commit(); |
166
|
|
|
return $affected; |
167
|
|
|
} catch (\Throwable $e) { |
168
|
|
|
$conn->rollBack(); |
169
|
|
|
throw $e; |
170
|
|
|
} |
171
|
|
|
} |
172
|
|
|
|
173
|
|
|
public function deleteVisibility(array $fileIds, int $cid, ?int $sid, int $uid, string $area): int |
174
|
|
|
{ |
175
|
|
|
if (!$fileIds) { |
|
|
|
|
176
|
|
|
return 0; |
177
|
|
|
} |
178
|
|
|
|
179
|
|
|
$conn = $this->getEntityManager()->getConnection(); |
180
|
|
|
$placeholders = implode(',', array_fill(0, count($fileIds), '?')); |
181
|
|
|
|
182
|
|
|
if ($area === 'sent') { |
183
|
|
|
$sql = "DELETE FROM c_dropbox_file |
184
|
|
|
WHERE iid IN ($placeholders) AND c_id = ? AND session_id = ? AND uploader_id = ?"; |
185
|
|
|
$params = array_merge($fileIds, [$cid, $sid ?? 0, $uid]); |
186
|
|
|
|
187
|
|
|
return $conn->executeStatement($sql, $params); |
188
|
|
|
} |
189
|
|
|
|
190
|
|
|
$sql = "DELETE FROM c_dropbox_person |
191
|
|
|
WHERE file_id IN ($placeholders) AND c_id = ? AND user_id = ?"; |
192
|
|
|
$params = array_merge($fileIds, [$cid, $uid]); |
193
|
|
|
|
194
|
|
|
return $conn->executeStatement($sql, $params); |
195
|
|
|
} |
196
|
|
|
|
197
|
|
|
public function createUploadedFile( |
198
|
|
|
int $cid, |
199
|
|
|
?int $sid, |
200
|
|
|
int $uploaderId, |
201
|
|
|
string $storedFilename, |
202
|
|
|
int $filesize, |
203
|
|
|
string $originalTitle, |
204
|
|
|
?string $description = null |
205
|
|
|
): CDropboxFile { |
206
|
|
|
$now = new \DateTime(); |
207
|
|
|
|
208
|
|
|
$f = new CDropboxFile(); |
209
|
|
|
$f->setCId($cid); |
210
|
|
|
$f->setSessionId($sid ?? 0); |
211
|
|
|
$f->setUploaderId($uploaderId); |
212
|
|
|
$f->setFilename($storedFilename); |
213
|
|
|
$f->setFilesize($filesize); |
214
|
|
|
$f->setTitle($originalTitle); |
215
|
|
|
$f->setDescription($description ?? ''); |
216
|
|
|
$f->setAuthor(null); |
217
|
|
|
$f->setUploadDate($now); |
218
|
|
|
$f->setLastUploadDate($now); |
219
|
|
|
$f->setCatId(0); |
220
|
|
|
|
221
|
|
|
$em = $this->getEntityManager(); |
222
|
|
|
$em->persist($f); |
223
|
|
|
$em->flush(); |
224
|
|
|
|
225
|
|
|
return $f; |
226
|
|
|
} |
227
|
|
|
} |
228
|
|
|
|
This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.
Consider making the comparison explicit by using
empty(..)
or! empty(...)
instead.