PluginProbe
Fluent Support – Helpdesk & Customer Support Ticket System / 1.10.0
Fluent Support – Helpdesk & Customer Support Ticket System v1.10.0
2.4.0 2.3.2 2.3.1 2.3.0 2.2.1 2.2.0 trunk 1.10.0 1.10.1 1.10.2 1.10.3 1.10.4 1.10.5 1.4.0 1.4.1 1.4.2 1.4.5 1.4.6 1.4.7 1.5.0 1.5.1 1.5.2 1.5.3 1.5.4 1.5.5 All 68 releases
fluent-support / app / Hooks / Handlers / ExternalPages.php

ExternalPages.php in Fluent Support – Helpdesk & Customer Support Ticket System 1.10.0, at app/Hooks/Handlers/ExternalPages.php

158 lines 4.6 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace FluentSupport\App\Hooks\Handlers;
4
5
6 use FluentSupport\App\Models\Attachment;
7 use FluentSupport\App\Models\Ticket;
8 use FluentSupport\App\Services\Helper;
9 use FluentSupport\Framework\Support\Arr;
10
11 class ExternalPages
12 {
13 public function route()
14 {
15 $route = sanitize_text_field($_REQUEST['fs_view']);
16
17 $methodMaps = [
18 'ticket' => 'handleTicketView'
19 ];
20
21 if (isset($methodMaps[$route])) {
22 $this->{$methodMaps[$route]}();
23 }
24
25 }
26
27 public function handleTicketView()
28 {
29 if (!Helper::isPublicSignedTicketEnabled()) {
30 $this->handleInvalidTicket();
31 } else {
32 $this->handleValidTicket();
33 }
34 }
35
36 /**
37 * Display the attachment.
38 *
39 * Uses the new rewrite endpoint to get an attachment ID
40 * and display the attachment if the currently logged in user
41 * has the authorization to.
42 *
43 * @return void
44 * @since 3.2.0
45 */
46 public function view_attachment()
47 {
48 $attachmentHash = sanitize_text_field($_REQUEST['fst_file']);
49
50 if (empty($attachmentHash)) {
51 die('Invalid Attachment Hash');
52 }
53
54 $attachment = $this->getAttachmentByHash($attachmentHash);
55
56 if (!$attachment) {
57 die('Invalid Attachment Hash');
58 }
59
60 // check signature hash
61 if (!$this->validateAttachmentSignature($attachment)) {
62 $dieMessage = esc_html__('Sorry, Your secure sign is invalid, Please reload the previous page and get new signed url', 'fluent-support');
63 die(esc_html($dieMessage)); // Escaping the die message again for safety
64 }
65
66 //If external file
67 if ('local' !== $attachment->driver) {
68 if(!empty($attachment->full_url)){
69 $this->redirectToExternalAttachment($attachment->full_url);
70 }else{
71 die('File could not be found');
72 }
73 }
74
75 //Handle Local file
76 if (!file_exists($attachment->file_path)) {
77 die('File could not be found');
78 }
79 $this->serveLocalAttachment($attachment);
80 }
81
82 private function getAttachmentByHash($attachmentHash)
83 {
84 return Attachment::where('file_hash', $attachmentHash)->first();
85 }
86
87 private function validateAttachmentSignature($attachment)
88 {
89 $sign = md5($attachment->id . date('YmdH'));
90 return $sign === $_REQUEST['secure_sign'];
91 }
92
93 private function handleInvalidTicket()
94 {
95 $ticketId = absint(Arr::get($_REQUEST, 'ticket_id'));
96 $ticket = Ticket::where('id', $ticketId)->first();
97
98 if (!$ticket) {
99 $this->showInvalidPortalMessage();
100 } else {
101 $this->redirectToTicketView($ticket);
102 }
103 }
104
105 private function handleValidTicket()
106 {
107 $ticketHash = sanitize_text_field(Arr::get($_REQUEST, 'support_hash'));
108 $ticketId = absint(Arr::get($_REQUEST, 'ticket_id'));
109 $ticket = Ticket::where('hash', $ticketHash)->where('id', $ticketId)->first();
110
111 if (!$ticket) {
112 $this->showInvalidPortalMessage();
113 } elseif (get_current_user_id()) {
114 $this->redirectToTicketView($ticket);
115 }
116 }
117
118 private function showInvalidPortalMessage()
119 {
120 echo '<h3 style="text-align: center; margin: 50px 0;">' . esc_html__('Invalid Support Portal URL', 'fluent-support') . '</h3>';
121 die();
122 }
123
124 private function redirectToTicketView($ticket)
125 {
126 $redirectUrl = Helper::getTicketViewUrl($ticket);
127 $this->redirectToExternalAttachment($redirectUrl);
128 }
129
130 private function redirectToExternalAttachment($redirectUrl)
131 {
132 wp_redirect($redirectUrl, 307);
133 exit();
134 }
135
136 // Helper method to serve an attachment
137 private function serveLocalAttachment($attachment)
138 {
139 $file_path = realpath($attachment->file_path);
140 $uploads = wp_upload_dir();
141 $uploads_dir = realpath($uploads['basedir']); // Ensures both paths are absolute
142
143 if (!$file_path || !$uploads_dir || strpos($file_path, $uploads_dir) !== 0 || !file_exists($file_path)) {
144 wp_die(esc_html__('File not found or access denied', 'fluent-support'), 403);
145 return;
146 }
147
148 ob_get_clean();
149 ini_set('user_agent', 'Fluent Support/' . FLUENT_SUPPORT_VERSION . '; ' . esc_url(get_bloginfo('url')));
150
151 header("Content-Type: " . esc_attr($attachment->file_type));
152 header("Content-Disposition: inline; filename=\"" . esc_attr($attachment->title) . "\"");
153 readfile($file_path);
154 die();
155 }
156
157 }
158