*/ if ( ! defined( 'ABSPATH' ) ) { exit; } class Group107_AccessibleDocs_API_Handler { /** * Send a POST request to an external API using wp_remote_post. * * @param string $url The API endpoint URL. * @param array $data The data to send in the request body. * @param array $headers The HTTP headers for the request. * @param string $data_type Determins if need to json_encode $data. * @return array Response with success flag and data or error message. */ public static function accessible_docs_api_request($url, $data, $method, $headers, $data_type = 'json') { // Add source identifier to all requests $headers['X-AccessibleDocs-Source'] = 'wordpress-plugin'; // Prepare arguments for the HTTP request $args = array( 'method' => $method, 'headers' => $headers, 'timeout' => 180, 'sslverify' => false, ); if (!empty($data)) { $args['body'] = ('json' === $data_type) ? json_encode($data) : $data; } // Make the HTTP request $response = wp_remote_request($url, $args); // Check for WP_Error if (is_wp_error($response)) { return array( 'success' => false, 'error' => $response->get_error_message(), ); } // Check HTTP status code $http_code = wp_remote_retrieve_response_code($response); if ($http_code < 200 || $http_code > 299) { return array( 'success' => false, 'error' => "Server returned HTTP code {$http_code}", ); } // Retrieve the response body $body = wp_remote_retrieve_body($response); // If expecting JSON, decode it and check for errors if ('json' === $data_type) { $responseData = json_decode($body, true); if (json_last_error() !== JSON_ERROR_NONE) { error_log("JSON decode error: " . json_last_error_msg()); $responseData = null; } } else { $responseData = $body; } return array( 'success' => true, 'data' => $responseData, ); } /** * Perform a login request to get the API access token. * * @return array Response with access token or error message. */ public static function accessible_docs_login_request() { // Get email and password from options $settings = get_option('accessible_docs_settings'); $email = $settings['email'] ?? ''; $password = $settings['password'] ?? ''; // Check if email or password is empty if (empty($email) || empty($password)) { return [ 'success' => false, 'error' => __('Email or password is not set in the plugin settings.', 'accessible-docs'), ]; } // Define the API endpoint URL $url = ACCESSIBLE_DOCS_API_URL . "/v1/login"; $data = [ "email" => $email, "password" => $password ]; $headers = [ "Content-Type" => "application/json", ]; // Perform the API request and return the response return self::accessible_docs_api_request($url, $data, 'POST', $headers, 'json'); } /** * Check the processing status of an accessible document file via API. * * This function retrieves the file status from the external API and updates * the database status accordingly. * * @param int $accessible_docs_file_id The ID of the document in the external system. * @return string The file status ('completed' or 'in-process'). */ public static function accessible_docs_check_file_status($accessible_docs_file_id) { // Retrieve API access token $tokenData = self::accessible_docs_login_request(); // Ensure the token retrieval was successful if (!isset($tokenData['data']['accessToken'])) { return [ 'status' => false, 'error' => __('Unable to retrieve access token', 'accessible-docs')]; } $accessToken = $tokenData['data']['accessToken']; $url = ACCESSIBLE_DOCS_API_URL . "/v1/user/files/" . $accessible_docs_file_id; // Set request headers $headers = [ "Authorization" => "Bearer " . $accessToken, "Content-Type" => "application/json", ]; // Make API request to get file data $response_data = self::accessible_docs_api_request($url, [], 'GET', $headers, 'json'); // Check if the request was successful if (!isset($response_data['data']['state'])) { return [ 'status' => 'error', 'error' => __('Failed to check status in the system', 'accessible-docs')]; } // Determine the file processing status $status = ($response_data['data']['state'] === 'completed') ? 'completed' : 'in-process'; return [ 'status' => $status ]; } /** * Upload a file to the accessible docs API. * * @param string $email The email address for notifications. * @param int $file_id The WordPress attachment file ID. * @return mixed The API response data if successful, 'error' on failure. */ public static function accessible_docs_upload_file($email, $file_id) { // Retrieve API access token $tokenData = self::accessible_docs_login_request(); // Ensure the token retrieval was successful if (empty($tokenData['data']['accessToken'])) { return [ 'status' => false, 'error' => __('Unable to retrieve access token', 'accessible-docs')]; } $accessToken = $tokenData['data']['accessToken']; $url = ACCESSIBLE_DOCS_API_URL . "/v1/user/files/"; // Get file details $file_path = get_attached_file($file_id); if (!file_exists($file_path)) { return [ 'status' => false, 'error' => __('The file you are trying to send was not found.', 'accessible-docs')]; } $file_name = basename($file_path); $file_size = filesize($file_path); $mime_type = get_post_mime_type($file_id); $data = [ 'name' => $file_name, 'externalNotification' => ['email' => $email], 'mime' => $mime_type, 'processing' => 'auto', 'size' => $file_size, 'tags' => [], ]; // Set request headers $headers = [ "Authorization" => "Bearer " . $accessToken, "Content-Type" => "application/json", ]; // Make API request to create a file entry $response_data = self::accessible_docs_api_request($url, $data, 'POST', $headers, 'json'); // Check for the upload URL and upload the file to the server if ( isset($response_data['data']['uploadUrl']) && !empty($response_data['data']['uploadUrl']) ) { $upload_response = self::accessible_docs_upload_file_to_server($file_id, $response_data['data']['uploadUrl']); if (!$upload_response) { $response_data['success'] = false; } } return $response_data['success'] ? ['status' => 'success', 'data' => $response_data['data']] : ['status' => 'error', 'error' => __('File failed to upload', 'accessible-docs')]; } /** * Upload the file to the accessible docs server using the provided upload URL. * * @param int $file_id The WordPress attachment file ID. * @param string $url The URL to upload the file to. * @return bool True if the upload was successful, false otherwise. */ public static function accessible_docs_upload_file_to_server($file_id, $url) { // Ensure required function is available if (!function_exists('download_url')) { require_once ABSPATH . 'wp-admin/includes/file.php'; } //Temporary fix, will be deleted add_filter('http_request_args', function($r, $url) { $r['sslverify'] = false; return $r; }, 10, 2); // Get the file URL $file_url = wp_get_attachment_url($file_id); if (!$file_url) { return false; // Return false if the file URL is not found } // Temporarily download the file $temp_file = download_url($file_url); if (is_wp_error($temp_file)) { return false; // Return false if the file could not be downloaded } // Read file content $file_data = file_get_contents($temp_file); if ($file_data === false) { wp_delete_file($temp_file); return false; } // Get MIME type $mime_type = get_post_mime_type($file_id); // Set request headers $headers = [ "Content-Type" => $mime_type, ]; // Upload the file using PUT request $response = self::accessible_docs_api_request($url, $file_data, 'PUT', $headers, 'not-json'); if( !$response ['success'] ) { return false; } // Delete the temporary file wp_delete_file($temp_file); return true; } }