PluginProbe
WP-Stateless – Google Cloud Storage / trunk
WP-Stateless – Google Cloud Storage vtrunk
4.4.3 2.1.7 2.1.8 2.1.9 2.2.0 2.2.1 2.2.2 2.2.3 2.2.4 2.2.5 2.2.6 2.2.7 2.3.0 2.3.1 2.3.2 3.0 3.0.1 3.0.2 3.0.3 3.0.4 3.1.0 3.1.1 3.2.0 3.2.1 3.2.2 All 62 releases
wp-stateless / lib / classes / class-api.php

class-api.php in WP-Stateless – Google Cloud Storage trunk, at lib/classes/class-api.php

336 lines 11.3 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 /**
4 * API Handler
5 *
6 *
7 *
8 * @since 1.0.0
9 */
10
11 namespace wpCloud\StatelessMedia {
12
13 use wpCloud\StatelessMedia\Sync\FileSync;
14 use wpCloud\StatelessMedia\Sync\ImageSync;
15 use wpCloud\StatelessMedia\Sync\NonLibrarySync;
16
17 if (!class_exists('wpCloud\StatelessMedia\API')) {
18
19 /**
20 * Class API
21 *
22 * @package wpCloud\StatelessMedia
23 */
24 final class API {
25
26 /**
27 * Decoded auth_token data
28 *
29 * @var null|\stdClass
30 */
31 static private $tokenData = null;
32
33 /**
34 * Validate auth token and save data for further processing
35 *
36 * @param \WP_REST_Request $request
37 * @return bool|\WP_Error
38 */
39 static public function authCheck(\WP_REST_Request $request) {
40 $auth_token = $request->get_header('authorization');
41 // Allow using custom `x-wps-auth` header if authorization hedaer is disabled
42 if (!$auth_token) $auth_token = $request->get_header('x-wps-auth');
43
44 if (!$auth_token) return false;
45
46 try {
47 self::$tokenData = Utility::verify_jwt_token($auth_token);
48 } catch (\Exception $e) {
49 self::$tokenData = null;
50 return new \WP_Error('auth_failed', $e->getMessage(), ['status' => 401]);
51 }
52 return true;
53 }
54
55 /**
56 * API Status Endpoint.
57 *
58 * @return \WP_REST_Response
59 */
60 static public function status() {
61 return new \WP_REST_Response(array(
62 "ok" => true,
63 "message" => "API up."
64 ), 200);
65 }
66
67 /**
68 * Get settings
69 *
70 * @todo Implement this if needed
71 * @param \WP_REST_Request $request
72 * @return \WP_REST_Response|\WP_Error
73 */
74 static public function getSettings(\WP_REST_Request $request) {
75 return new \WP_Error('not_implemented', 'Method not implemented', ['status' => 501]);
76 }
77
78 /**
79 * Update settings
80 *
81 * @param \WP_REST_Request $request
82 * @return \WP_REST_Response|\WP_Error
83 */
84 static public function updateSettings(\WP_REST_Request $request) {
85 if (self::$tokenData === null || empty(self::$tokenData->user_id)) {
86 return new \WP_Error('unauthorized', 'Auth token looks incorrect', ['status' => 401]);
87 }
88 $is_gae = apply_filters('wp_stateless_is_app_engine', false);
89 $upload_dir = wp_upload_dir();
90 $is_upload_dir_writable = is_writable($upload_dir['basedir']);
91
92 try {
93 $queryParams = $request->get_json_params();
94 if (empty($queryParams)) throw new \Exception('Query is empty');
95
96 $bucketName = isset($queryParams['bucket_name']) ? $queryParams['bucket_name'] : null;
97 $privateKeyData = isset($queryParams['private_key_data']) ? $queryParams['private_key_data'] : null;
98
99 if (!$bucketName || !$privateKeyData) {
100 throw new \Exception('bucket_name and private_key_data are required');
101 }
102
103 if ($privateKeyData) {
104 $privateKeyData = base64_decode($privateKeyData);
105 }
106
107 switch (self::$tokenData->is_network) {
108 case true:
109 if (!user_can(self::$tokenData->user_id, 'manage_network_options')) {
110 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
111 }
112 /**
113 * If Google App Engine detected - set Stateless mode
114 * and Google App Engine compatibility by default
115 */
116 if ($is_gae || !$is_upload_dir_writable) {
117 update_site_option('sm_mode', 'stateless');
118
119 $modules = get_site_option('stateless-modules', array());
120 if ($is_gae && empty($modules['google-app-engine']) || $modules['google-app-engine'] != 'true') {
121 $modules['google-app-engine'] = 'true';
122 update_site_option('stateless-modules', $modules);
123 }
124 } elseif (get_site_option('sm_mode', 'disabled') == 'disabled') {
125 update_site_option('sm_mode', 'ephemeral');
126 }
127 update_site_option('sm_bucket', $bucketName);
128 update_site_option('sm_key_json', $privateKeyData);
129 break;
130
131 case false:
132 if (!user_can(self::$tokenData->user_id, 'manage_options')) {
133 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
134 }
135 /**
136 * If Google App Engine detected - set Stateless mode
137 * and Google App Engine compatibility by default
138 */
139 if ($is_gae || !$is_upload_dir_writable) {
140 update_option('sm_mode', 'stateless');
141
142 $modules = get_option('stateless-modules', array());
143 if ($is_gae && empty($modules['google-app-engine']) || $modules['google-app-engine'] != 'true') {
144 $modules['google-app-engine'] = 'true';
145 update_option('stateless-modules', $modules);
146 }
147 } elseif (get_option('sm_mode', 'disabled') == 'disabled') {
148 update_option('sm_mode', 'ephemeral');
149 }
150 update_option('sm_bucket', $bucketName);
151 update_option('sm_key_json', $privateKeyData);
152 break;
153 }
154
155 return new \WP_REST_Response(array(
156 'ok' => true,
157 'message' => 'Settings updated successfully'
158 ));
159 } catch (\Throwable $e) {
160 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
161 }
162 }
163
164 /**
165 * Get all available processes with their states
166 *
167 * @return \WP_REST_Response|\WP_Error
168 */
169 static public function syncGetProcesses() {
170 try {
171 if (!user_can(self::$tokenData->user_id, 'manage_options')) {
172 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
173 }
174
175 return new \WP_REST_Response(array(
176 'ok' => true,
177 'data' => Utility::get_available_sync_classes()
178 ));
179 } catch (\Throwable $e) {
180 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
181 }
182 }
183
184 /**
185 * Get a single process by id (base64 encoded class name)
186 *
187 * @param \WP_REST_Request $request
188 * @return \WP_Error|\WP_REST_Response
189 */
190 static public function syncGetProcess(\WP_REST_Request $request) {
191 try {
192 if (!user_can(self::$tokenData->user_id, 'manage_options')) {
193 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
194 }
195
196 $id = base64_decode($request->get_param('id'));
197 if (!class_exists($id)) {
198 throw new \Exception(sprintf('Could not get process by id %s', $id));
199 }
200
201 $syncClasses = Utility::get_available_sync_classes();
202
203 if (!array_key_exists($id, $syncClasses)) {
204 throw new \Exception(sprintf('Could not get process by id %s', $id));
205 }
206
207 return new \WP_REST_Response(array(
208 'ok' => true,
209 'data' => $syncClasses[$id]
210 ));
211 } catch (\Throwable $e) {
212 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
213 }
214 }
215
216 /**
217 * Run sync by processing class id
218 *
219 * @param \WP_REST_Request $request
220 * @return \WP_Error|\WP_REST_Response
221 */
222 static public function syncRun(\WP_REST_Request $request) {
223 try {
224 if (!user_can(self::$tokenData->user_id, 'manage_options')) {
225 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
226 }
227
228 $params = wp_parse_args($request->get_params(), [
229 'id' => null,
230 'limit' => null,
231 'order' => null,
232 ]);
233
234 if (empty($params['id']) || !class_exists($params['id'])) {
235 throw new \Exception(sprintf('Processing class not found: %s', $params['id']));
236 }
237
238 $processingClass = $params['id'];
239
240 return new \WP_REST_Response(array(
241 'ok' => $processingClass::instance()->start($params)
242 ));
243 } catch (\Throwable $e) {
244 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
245 }
246 }
247
248 /**
249 * Stop sync by processing class id
250 *
251 * @param \WP_REST_Request $request
252 * @return \WP_Error|\WP_REST_Response
253 */
254 static public function syncStop(\WP_REST_Request $request) {
255 try {
256 if (!user_can(self::$tokenData->user_id, 'manage_options')) {
257 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
258 }
259
260 $params = wp_parse_args($request->get_params(), [
261 'id' => null
262 ]);
263
264 if (empty($params['id']) || !class_exists($params['id'])) {
265 throw new \Exception(sprintf('Processing class not found: %s', $params['id']));
266 }
267
268 $processingClass = $params['id'];
269
270 return new \WP_REST_Response(array(
271 'ok' => $processingClass::instance()->stop()
272 ));
273 } catch (\Throwable $e) {
274 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
275 }
276 }
277
278 /**
279 * Batch Status Endpoint.
280 *
281 * @param \WP_REST_Request $request
282 * @return \WP_REST_Response
283 */
284 static public function batchState(\WP_REST_Request $request) {
285 try {
286 return new \WP_REST_Response(array(
287 'ok' => true,
288 'data' => apply_filters('wp_stateless_batch_state', [], $request->get_params()),
289 ));
290 } catch (\Throwable $e) {
291 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
292 }
293 }
294
295 /**
296 * Batch action (start/pause/resume)
297 *
298 * @param \WP_REST_Request $request
299 * @return \WP_Error|\WP_REST_Response
300 */
301 static public function batchAction(\WP_REST_Request $request) {
302 try {
303 if (!user_can(self::$tokenData->user_id, 'manage_options')) {
304 return new \WP_Error('not_allowed', 'Sorry, you are not allowed to perform this action', ['status' => 403]);
305 }
306
307 wp_set_current_user(self::$tokenData->user_id);
308
309 $params = wp_parse_args($request->get_params(), [
310 'action' => '',
311 ]);
312
313 if ( empty($params['action']) ) {
314 throw new \Exception('Batch action not set');
315 }
316
317 $action = $params['action'];
318
319 $data = apply_filters("wp_stateless_batch_action_$action", [], $params);
320
321 $data = array_merge(
322 $data,
323 apply_filters("wp_stateless_batch_state", [], ['force_migrations' => true]),
324 );
325
326 return new \WP_REST_Response(array(
327 'data' => $data,
328 ));
329 } catch (\Throwable $e) {
330 return new \WP_Error('internal_server_error', $e->getMessage(), ['status' => 500]);
331 }
332 }
333 }
334 }
335 }
336