PluginProbe
User Access Manager / 2.3.14
User Access Manager v2.3.14
2.3.20 2.3.19 2.3.18 2.3.17 2.3.16 2.3.15 2.3.14 2.3.13 trunk 0.6 0.6.1 0.6.2 0.7 0.7 Beta 0.7.0.1 0.8 0.8.0.1 0.8.0.2 0.9 0.9.1 0.9.1.1 0.9.1.2 0.9.1.3 0.9.1.4 1.0 All 136 releases
user-access-manager / src / Controller / Frontend / RedirectController.php

RedirectController.php in User Access Manager 2.3.14, at src/Controller/Frontend/RedirectController.php

305 lines 10.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 declare(strict_types=1);
4
5 namespace UserAccessManager\Controller\Frontend;
6
7 use JetBrains\PhpStorm\NoReturn;
8 use UserAccessManager\Access\AccessHandler;
9 use UserAccessManager\Cache\Cache;
10 use UserAccessManager\Config\MainConfig;
11 use UserAccessManager\Config\WordpressConfig;
12 use UserAccessManager\Controller\Controller;
13 use UserAccessManager\Database\Database;
14 use UserAccessManager\File\FileHandler;
15 use UserAccessManager\File\FileObject;
16 use UserAccessManager\File\FileObjectFactory;
17 use UserAccessManager\Object\ObjectHandler;
18 use UserAccessManager\UserGroup\UserGroupTypeException;
19 use UserAccessManager\Util\Util;
20 use UserAccessManager\Wrapper\Php;
21 use UserAccessManager\Wrapper\Wordpress;
22
23 class RedirectController extends Controller
24 {
25 use LoginControllerTrait;
26
27 public const POST_URL_CACHE_KEY = 'PostUrls';
28
29 public function __construct(
30 Php $php,
31 Wordpress $wordpress,
32 WordpressConfig $wordpressConfig,
33 private MainConfig $mainConfig,
34 private Database $database,
35 private Util $util,
36 private Cache $cache,
37 private ObjectHandler $objectHandler,
38 private AccessHandler $accessHandler,
39 private FileHandler $fileHandler,
40 private FileObjectFactory $fileObjectFactory
41 ) {
42 parent::__construct($php, $wordpress, $wordpressConfig);
43 }
44
45 protected function getWordpress(): Wordpress
46 {
47 return $this->wordpress;
48 }
49
50 public function getPostIdByUrl(string $url): int
51 {
52 $postUrls = (array)$this->cache->getFromRuntimeCache(self::POST_URL_CACHE_KEY);
53
54 if (isset($postUrls[$url]) === true) {
55 return $postUrls[$url];
56 }
57
58 //Filter size
59 $newUrlPieces = preg_split('/-[0-9]+x[0-9]+(_[a-z])?/', $url);
60 $newUrl = (count($newUrlPieces) === 2) ? $newUrlPieces[0] . $newUrlPieces[1] : $newUrlPieces[0];
61 $newUrl = preg_replace('/-pdf\.jpg$/', '.pdf', $newUrl);
62
63 $postId = $this->wordpress->attachmentUrlToPostId($newUrl);
64
65 if ($postId === 0) {
66 $newUrl = preg_replace('/(\\.[^.\\s]{3,4})$/', '-scaled$1', $newUrl);
67 $postId = $this->wordpress->attachmentUrlToPostId($newUrl);
68 }
69
70 $postUrls[$url] = $postId;
71 $this->cache->addToRuntimeCache(self::POST_URL_CACHE_KEY, $postUrls);
72
73 return $postUrls[$url];
74 }
75
76 private function getFileSettingsByType(string $objectType, string $objectUrl): ?FileObject
77 {
78 $fileObject = null;
79
80 if ($objectType === ObjectHandler::ATTACHMENT_OBJECT_TYPE) {
81 $uploadDirs = $this->wordpress->getUploadDir();
82 $uploadDir = str_replace(ABSPATH, '/', $uploadDirs['basedir']);
83 $regex = '/.*' . str_replace('/', '\/', $uploadDir) . '\//i';
84 $cleanObjectUrl = preg_replace($regex, '', $objectUrl);
85 $uploadUrl = str_replace('/files', $uploadDir, $uploadDirs['baseurl']);
86 $objectUrl = rtrim($uploadUrl, '/') . '/' . ltrim($cleanObjectUrl, '/');
87
88 $post = $this->objectHandler->getPost($this->getPostIdByUrl($objectUrl));
89 $postType = $post->post_type ?? '';
90
91 if ($postType === ObjectHandler::ATTACHMENT_OBJECT_TYPE) {
92 $multiPath = str_replace('/files', $uploadDir, $uploadDirs['baseurl']);
93
94 $fileObject = $this->fileObjectFactory->createFileObject(
95 $post->ID,
96 $objectType,
97 $uploadDirs['basedir'] . str_replace($multiPath, '', $objectUrl),
98 $this->wordpress->attachmentIsImage($post->ID)
99 );
100 }
101 } else {
102 $extraParameter = $this->getRequestParameter('uamextra');
103
104 $fileObject = $this->wordpress->applyFilters(
105 'uam_get_file_settings_by_type',
106 $fileObject,
107 $objectType,
108 $objectUrl,
109 $extraParameter
110 );
111 }
112
113 return $fileObject;
114 }
115
116 /**
117 * @throws UserGroupTypeException
118 */
119 public function getFile(string $objectType, string $objectUrl): void
120 {
121 $fileObject = $this->getFileSettingsByType($objectType, $objectUrl);
122
123 if ($fileObject === null) {
124 return;
125 }
126
127 if ($this->accessHandler->checkObjectAccess($fileObject->getType(), $fileObject->getId()) === true) {
128 $file = $fileObject->getFile();
129 } elseif ($fileObject->isImage() === true) {
130 if ($this->mainConfig->getNoAccessImageType() === 'custom') {
131 $file = $this->mainConfig->getCustomNoAccessImage();
132 } else {
133 $realPath = $this->wordpressConfig->getRealPath();
134 $file = $realPath . 'assets' . DIRECTORY_SEPARATOR . 'gfx' . DIRECTORY_SEPARATOR . 'noAccessPic.png';
135 }
136 } else {
137 $this->wordpress->wpDie(TXT_UAM_NO_RIGHTS_MESSAGE, TXT_UAM_NO_RIGHTS_TITLE, ['response' => 403]);
138 return;
139 }
140
141 $this->fileHandler->getFile($file, $fileObject->isImage());
142 }
143
144 private function getRedirectUrlAndPermalink(?string &$permalink): ?string
145 {
146 $permalink = null;
147 $redirect = $this->mainConfig->getRedirect();
148
149 if ($redirect === 'custom_page') {
150 $redirectCustomPage = $this->mainConfig->getRedirectCustomPage();
151 $post = $this->objectHandler->getPost($redirectCustomPage);
152 $url = null;
153
154 if ($post !== false) {
155 $url = $post->guid;
156 $permalink = $this->wordpress->getPageLink($post);
157 }
158 } elseif ($redirect === 'custom_url') {
159 $url = $this->mainConfig->getRedirectCustomUrl();
160 } elseif ($redirect === 'login') {
161 $url = $this->getLoginUrl();
162 } elseif ($redirect === 'origin') {
163 $referer = $this->wordpress->getReferer();
164 $url = $referer !== false ? $referer : $this->wordpress->getHomeUrl('/');
165 } else {
166 $url = $this->wordpress->getHomeUrl('/');
167 }
168
169 return $url;
170 }
171
172 /**
173 * @throws UserGroupTypeException
174 */
175 public function redirectUser(bool $checkPosts = true): void
176 {
177 if ($checkPosts === true) {
178 $posts = $this->wordpress->getWpQuery()->get_posts();
179
180 foreach ($posts as $post) {
181 if ($this->accessHandler->checkObjectAccess($post->post_type, $post->ID)) {
182 return;
183 }
184 }
185 }
186
187 $url = $this->getRedirectUrlAndPermalink($permalink);
188 $currentUrl = $this->util->getCurrentUrl();
189
190 if ($url !== null && $url !== $currentUrl && $permalink !== $currentUrl) {
191 $this->wordpress->wpRedirect($url);
192 $this->php->callExit();
193 }
194 }
195
196 private function getPostIdByName(string $name): int
197 {
198 $postableTypes = implode('\',\'', $this->objectHandler->getPostTypes());
199
200 $query = $this->database->prepare(
201 "SELECT ID
202 FROM {$this->database->getPostsTable()}
203 WHERE post_name = %s
204 AND post_type IN ('$postableTypes')",
205 $name
206 );
207
208 return (int) $this->database->getVariable($query);
209 }
210
211 private function extractObjectTypeAndId(mixed $pageParams, ?string &$objectType, int|string|null &$objectId): void
212 {
213 $objectType = null;
214 $objectId = null;
215
216 $simpleTypes = [
217 'p' => ObjectHandler::GENERAL_POST_OBJECT_TYPE,
218 'page_id' => ObjectHandler::GENERAL_POST_OBJECT_TYPE,
219 'cat_id' => ObjectHandler::GENERAL_TERM_OBJECT_TYPE
220 ];
221
222 foreach ($simpleTypes as $queryVar => $newObjectType) {
223 if (isset($pageParams->query_vars[$queryVar]) === true) {
224 $objectType = $newObjectType;
225 $objectId = $pageParams->query_vars[$queryVar];
226 }
227 }
228
229 if (isset($pageParams->query_vars['name']) === true) {
230 $objectType = ObjectHandler::GENERAL_POST_OBJECT_TYPE;
231 $objectId = $this->getPostIdByName($pageParams->query_vars['name']);
232 } elseif (isset($pageParams->query_vars['pagename']) === true) {
233 $object = $this->wordpress->getPageByPath($pageParams->query_vars['pagename']);
234
235 if ($object !== null) {
236 $objectType = $object->post_type ?? null;
237 $objectId = $object->ID ?? null;
238 }
239 }
240 }
241
242 /**
243 * @throws UserGroupTypeException
244 */
245 public function redirect(?array $headers, mixed $pageParams): ?array
246 {
247 $fileUrl = $this->getRequestParameter('uamgetfile');
248 $fileType = $this->getRequestParameter('uamfiletype');
249
250 if ($fileUrl !== null && $fileType !== null) {
251 $this->getFile($fileType, $fileUrl);
252 } elseif ($this->wordpressConfig->atAdminPanel() === false
253 && $this->mainConfig->getRedirect() !== 'false'
254 ) {
255 $this->extractObjectTypeAndId($pageParams, $objectType, $objectId);
256
257 if ($this->accessHandler->checkObjectAccess($objectType, $objectId) === false) {
258 $this->redirectUser(false);
259 }
260 }
261
262 return $headers;
263 }
264
265 public function getFileUrl(string $url, int|string|null $id): string
266 {
267 // Nginx always supports real urls so we need the new urls only
268 // if we don't use nginx and mod_rewrite is disabled
269 if ($this->mainConfig->lockFile() === true
270 && $this->wordpress->isNginx() === false
271 && $this->wordpress->gotModRewrite() === false
272 ) {
273 $post = $this->objectHandler->getPost($id);
274
275 if ($post !== false) {
276 $type = explode('/', $post->post_mime_type);
277 $type = $type[1] ?? $type[0];
278
279 $lockedFileTypes = $this->mainConfig->getLockedFiles();
280 $fileTypes = explode(',', $lockedFileTypes);
281
282 if ($lockedFileTypes === 'all' || in_array($type, $fileTypes) === true) {
283 $url = $this->wordpress->getHomeUrl('/') . '?uamfiletype=attachment&uamgetfile=' . $url;
284 }
285 }
286 }
287
288 return $url;
289 }
290
291 public function cachePostLinks(string $url, object $post): string
292 {
293 $postUrls = (array) $this->cache->getFromRuntimeCache(self::POST_URL_CACHE_KEY);
294 $postUrls[$url] = $post->ID;
295 $this->cache->addToRuntimeCache(self::POST_URL_CACHE_KEY, $postUrls);
296 return $url;
297 }
298
299 #[NoReturn]
300 public function testXSendFile(): void
301 {
302 $this->fileHandler->deliverXSendFileTestFile();
303 }
304 }
305