| @@ -1,219 +1,217 @@ | ||
| 1 | -<?php | |
| 2 | - /** | |
| 3 | - * Copyright 2014 Freemius, Inc. | |
| 4 | - * | |
| 5 | - * Licensed under the GPL v2 (the "License"); you may | |
| 6 | - * not use this file except in compliance with the License. You may obtain | |
| 7 | - * a copy of the License at | |
| 8 | - * | |
| 9 | - * http://choosealicense.com/licenses/gpl-v2/ | |
| 10 | - * | |
| 11 | - * Unless required by applicable law or agreed to in writing, software | |
| 12 | - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT | |
| 13 | - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the | |
| 14 | - * License for the specific language governing permissions and limitations | |
| 15 | - * under the License. | |
| 16 | - */ | |
| 17 | - | |
| 18 | - if ( ! defined( 'ABSPATH' ) ) { | |
| 19 | - exit; | |
| 20 | - } | |
| 21 | - | |
| 22 | - if ( ! defined( 'FS_API__VERSION' ) ) { | |
| 23 | - define( 'FS_API__VERSION', '1' ); | |
| 24 | - } | |
| 25 | - if ( ! defined( 'FS_SDK__PATH' ) ) { | |
| 26 | - define( 'FS_SDK__PATH', dirname( __FILE__ ) ); | |
| 27 | - } | |
| 28 | - if ( ! defined( 'FS_SDK__EXCEPTIONS_PATH' ) ) { | |
| 29 | - define( 'FS_SDK__EXCEPTIONS_PATH', FS_SDK__PATH . '/Exceptions/' ); | |
| 30 | - } | |
| 31 | - | |
| 32 | - if ( ! function_exists( 'json_decode' ) ) { | |
| 33 | - throw new Exception( 'Freemius needs the JSON PHP extension.' ); | |
| 34 | - } | |
| 35 | - | |
| 36 | - // Include all exception files. | |
| 37 | - $exceptions = array( | |
| 38 | - 'Exception', | |
| 39 | - 'InvalidArgumentException', | |
| 40 | - 'ArgumentNotExistException', | |
| 41 | - 'EmptyArgumentException', | |
| 42 | - 'OAuthException' | |
| 43 | - ); | |
| 44 | - | |
| 45 | - foreach ( $exceptions as $e ) { | |
| 46 | - require_once FS_SDK__EXCEPTIONS_PATH . $e . '.php'; | |
| 47 | - } | |
| 48 | - | |
| 49 | - if ( class_exists( 'Freemius_Api_Base' ) ) { | |
| 50 | - return; | |
| 51 | - } | |
| 52 | - | |
| 53 | - abstract class Freemius_Api_Base { | |
| 54 | - const VERSION = '1.0.4'; | |
| 55 | - const FORMAT = 'json'; | |
| 56 | - | |
| 57 | - protected $_id; | |
| 58 | - protected $_public; | |
| 59 | - protected $_secret; | |
| 60 | - protected $_scope; | |
| 61 | - protected $_isSandbox; | |
| 62 | - | |
| 63 | - /** | |
| 64 | - * @param string $pScope 'app', 'developer', 'plugin', 'user' or 'install'. | |
| 65 | - * @param number $pID Element's id. | |
| 66 | - * @param string $pPublic Public key. | |
| 67 | - * @param string $pSecret Element's secret key. | |
| 68 | - * @param bool $pIsSandbox Whether or not to run API in sandbox mode. | |
| 69 | - */ | |
| 70 | - public function Init( $pScope, $pID, $pPublic, $pSecret, $pIsSandbox = false ) { | |
| 71 | - $this->_id = $pID; | |
| 72 | - $this->_public = $pPublic; | |
| 73 | - $this->_secret = $pSecret; | |
| 74 | - $this->_scope = $pScope; | |
| 75 | - $this->_isSandbox = $pIsSandbox; | |
| 76 | - } | |
| 77 | - | |
| 78 | - public function IsSandbox() { | |
| 79 | - return $this->_isSandbox; | |
| 80 | - } | |
| 81 | - | |
| 82 | - function CanonizePath( $pPath ) { | |
| 83 | - $pPath = trim( $pPath, '/' ); | |
| 84 | - $query_pos = strpos( $pPath, '?' ); | |
| 85 | - $query = ''; | |
| 86 | - | |
| 87 | - if ( false !== $query_pos ) { | |
| 88 | - $query = substr( $pPath, $query_pos ); | |
| 89 | - $pPath = substr( $pPath, 0, $query_pos ); | |
| 90 | - } | |
| 91 | - | |
| 92 | - // Trim '.json' suffix. | |
| 93 | - $format_length = strlen( '.' . self::FORMAT ); | |
| 94 | - $start = $format_length * ( - 1 ); //negative | |
| 95 | - if ( substr( strtolower( $pPath ), $start ) === ( '.' . self::FORMAT ) ) { | |
| 96 | - $pPath = substr( $pPath, 0, strlen( $pPath ) - $format_length ); | |
| 97 | - } | |
| 98 | - | |
| 99 | - switch ( $this->_scope ) { | |
| 100 | - case 'app': | |
| 101 | - $base = '/apps/' . $this->_id; | |
| 102 | - break; | |
| 103 | - case 'developer': | |
| 104 | - $base = '/developers/' . $this->_id; | |
| 105 | - break; | |
| 106 | - case 'user': | |
| 107 | - $base = '/users/' . $this->_id; | |
| 108 | - break; | |
| 109 | - case 'plugin': | |
| 110 | - $base = '/plugins/' . $this->_id; | |
| 111 | - break; | |
| 112 | - case 'install': | |
| 113 | - $base = '/installs/' . $this->_id; | |
| 114 | - break; | |
| 115 | - default: | |
| 116 | - throw new Freemius_Exception( 'Scope not implemented.' ); | |
| 117 | - } | |
| 118 | - | |
| 119 | - return '/v' . FS_API__VERSION . $base . | |
| 120 | - ( ! empty( $pPath ) ? '/' : '' ) . $pPath . | |
| 121 | - ( ( false === strpos( $pPath, '.' ) ) ? '.' . self::FORMAT : '' ) . $query; | |
| 122 | - } | |
| 123 | - | |
| 124 | - abstract function MakeRequest( $pCanonizedPath, $pMethod = 'GET', $pParams = array() ); | |
| 125 | - | |
| 126 | - /** | |
| 127 | - * @param string $pPath | |
| 128 | - * @param string $pMethod | |
| 129 | - * @param array $pParams | |
| 130 | - * | |
| 131 | - * @return object[]|object|null | |
| 132 | - */ | |
| 133 | - private function _Api( $pPath, $pMethod = 'GET', $pParams = array() ) { | |
| 134 | - $pMethod = strtoupper( $pMethod ); | |
| 135 | - | |
| 136 | - try { | |
| 137 | - $result = $this->MakeRequest( $pPath, $pMethod, $pParams ); | |
| 138 | - } catch ( Freemius_Exception $e ) { | |
| 139 | - // Map to error object. | |
| 140 | - $result = (object) $e->getResult(); | |
| 141 | - } catch ( Exception $e ) { | |
| 142 | - // Map to error object. | |
| 143 | - $result = (object) array( | |
| 144 | - 'error' => (object) array( | |
| 145 | - 'type' => 'Unknown', | |
| 146 | - 'message' => $e->getMessage() . ' (' . $e->getFile() . ': ' . $e->getLine() . ')', | |
| 147 | - 'code' => 'unknown', | |
| 148 | - 'http' => 402 | |
| 149 | - ) | |
| 150 | - ); | |
| 151 | - } | |
| 152 | - | |
| 153 | - return $result; | |
| 154 | - } | |
| 155 | - | |
| 156 | - public function Api( $pPath, $pMethod = 'GET', $pParams = array() ) { | |
| 157 | - return $this->_Api( $this->CanonizePath( $pPath ), $pMethod, $pParams ); | |
| 158 | - } | |
| 159 | - | |
| 160 | - /** | |
| 161 | - * Base64 decoding that does not need to be urldecode()-ed. | |
| 162 | - * | |
| 163 | - * Exactly the same as PHP base64 encode except it uses | |
| 164 | - * `-` instead of `+` | |
| 165 | - * `_` instead of `/` | |
| 166 | - * No padded = | |
| 167 | - * | |
| 168 | - * @param string $input Base64UrlEncoded() string | |
| 169 | - * | |
| 170 | - * @return string | |
| 171 | - */ | |
| 172 | - protected static function Base64UrlDecode( $input ) { | |
| 173 | - /** | |
| 174 | - * IMPORTANT NOTE: | |
| 175 | - * This is a hack suggested by @otto42 and @greenshady from | |
| 176 | - * the theme's review team. The usage of base64 for API | |
| 177 | - * signature encoding was approved in a Slack meeting | |
| 178 | - * held on Tue (10/25 2016). | |
| 179 | - * | |
| 180 | - * @todo Remove this hack once the base64 error is removed from the Theme Check. | |
| 181 | - * | |
| 182 | - * @since 1.2.2 | |
| 183 | - * @author Vova Feldman (@svovaf) | |
| 184 | - */ | |
| 185 | - $fn = 'base64' . '_decode'; | |
| 186 | - return $fn( strtr( $input, '-_', '+/' ) ); | |
| 187 | - } | |
| 188 | - | |
| 189 | - /** | |
| 190 | - * Base64 encoding that does not need to be urlencode()ed. | |
| 191 | - * | |
| 192 | - * Exactly the same as base64 encode except it uses | |
| 193 | - * `-` instead of `+ | |
| 194 | - * `_` instead of `/` | |
| 195 | - * | |
| 196 | - * @param string $input string | |
| 197 | - * | |
| 198 | - * @return string Base64 encoded string | |
| 199 | - */ | |
| 200 | - protected static function Base64UrlEncode( $input ) { | |
| 201 | - /** | |
| 202 | - * IMPORTANT NOTE: | |
| 203 | - * This is a hack suggested by @otto42 and @greenshady from | |
| 204 | - * the theme's review team. The usage of base64 for API | |
| 205 | - * signature encoding was approved in a Slack meeting | |
| 206 | - * held on Tue (10/25 2016). | |
| 207 | - * | |
| 208 | - * @todo Remove this hack once the base64 error is removed from the Theme Check. | |
| 209 | - * | |
| 210 | - * @since 1.2.2 | |
| 211 | - * @author Vova Feldman (@svovaf) | |
| 212 | - */ | |
| 213 | - $fn = 'base64' . '_encode'; | |
| 214 | - $str = strtr( $fn( $input ), '+/', '-_' ); | |
| 215 | - $str = str_replace( '=', '', $str ); | |
| 216 | - | |
| 217 | - return $str; | |
| 218 | - } | |
| 219 | - } | |
| 1 | +<?php | |
| 2 | + /** | |
| 3 | + * Copyright 2014 Freemius, Inc. | |
| 4 | + * | |
| 5 | + * Licensed under the GPL v2 (the "License"); you may | |
| 6 | + * not use this file except in compliance with the License. You may obtain | |
| 7 | + * a copy of the License at | |
| 8 | + * | |
| 9 | + * http://choosealicense.com/licenses/gpl-v2/ | |
| 10 | + * | |
| 11 | + * Unless required by applicable law or agreed to in writing, software | |
| 12 | + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT | |
| 13 | + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the | |
| 14 | + * License for the specific language governing permissions and limitations | |
| 15 | + * under the License. | |
| 16 | + */ | |
| 17 | + | |
| 18 | + if ( ! defined( 'ABSPATH' ) ) { | |
| 19 | + exit; | |
| 20 | + } | |
| 21 | + | |
| 22 | + if ( ! defined( 'FS_API__VERSION' ) ) { | |
| 23 | + define( 'FS_API__VERSION', '1' ); | |
| 24 | + } | |
| 25 | + if ( ! defined( 'FS_SDK__PATH' ) ) { | |
| 26 | + define( 'FS_SDK__PATH', dirname( __FILE__ ) ); | |
| 27 | + } | |
| 28 | + if ( ! defined( 'FS_SDK__EXCEPTIONS_PATH' ) ) { | |
| 29 | + define( 'FS_SDK__EXCEPTIONS_PATH', FS_SDK__PATH . '/Exceptions/' ); | |
| 30 | + } | |
| 31 | + | |
| 32 | + if ( ! function_exists( 'json_decode' ) ) { | |
| 33 | + throw new Exception( 'Freemius needs the JSON PHP extension.' ); | |
| 34 | + } | |
| 35 | + | |
| 36 | + // Include all exception files. | |
| 37 | + $exceptions = array( | |
| 38 | + 'Exception', | |
| 39 | + 'InvalidArgumentException', | |
| 40 | + 'ArgumentNotExistException', | |
| 41 | + 'EmptyArgumentException', | |
| 42 | + 'OAuthException' | |
| 43 | + ); | |
| 44 | + | |
| 45 | + foreach ( $exceptions as $e ) { | |
| 46 | + require_once FS_SDK__EXCEPTIONS_PATH . $e . '.php'; | |
| 47 | + } | |
| 48 | + | |
| 49 | + if ( ! class_exists( 'Freemius_Api_Base' ) ) { | |
| 50 | + abstract class Freemius_Api_Base { | |
| 51 | + const VERSION = '1.0.4'; | |
| 52 | + const FORMAT = 'json'; | |
| 53 | + | |
| 54 | + protected $_id; | |
| 55 | + protected $_public; | |
| 56 | + protected $_secret; | |
| 57 | + protected $_scope; | |
| 58 | + protected $_isSandbox; | |
| 59 | + | |
| 60 | + /** | |
| 61 | + * @param string $pScope 'app', 'developer', 'plugin', 'user' or 'install'. | |
| 62 | + * @param number $pID Element's id. | |
| 63 | + * @param string $pPublic Public key. | |
| 64 | + * @param string $pSecret Element's secret key. | |
| 65 | + * @param bool $pIsSandbox Whether or not to run API in sandbox mode. | |
| 66 | + */ | |
| 67 | + public function Init( $pScope, $pID, $pPublic, $pSecret, $pIsSandbox = false ) { | |
| 68 | + $this->_id = $pID; | |
| 69 | + $this->_public = $pPublic; | |
| 70 | + $this->_secret = $pSecret; | |
| 71 | + $this->_scope = $pScope; | |
| 72 | + $this->_isSandbox = $pIsSandbox; | |
| 73 | + } | |
| 74 | + | |
| 75 | + public function IsSandbox() { | |
| 76 | + return $this->_isSandbox; | |
| 77 | + } | |
| 78 | + | |
| 79 | + function CanonizePath( $pPath ) { | |
| 80 | + $pPath = trim( $pPath, '/' ); | |
| 81 | + $query_pos = strpos( $pPath, '?' ); | |
| 82 | + $query = ''; | |
| 83 | + | |
| 84 | + if ( false !== $query_pos ) { | |
| 85 | + $query = substr( $pPath, $query_pos ); | |
| 86 | + $pPath = substr( $pPath, 0, $query_pos ); | |
| 87 | + } | |
| 88 | + | |
| 89 | + // Trim '.json' suffix. | |
| 90 | + $format_length = strlen( '.' . self::FORMAT ); | |
| 91 | + $start = $format_length * ( - 1 ); //negative | |
| 92 | + if ( substr( strtolower( $pPath ), $start ) === ( '.' . self::FORMAT ) ) { | |
| 93 | + $pPath = substr( $pPath, 0, strlen( $pPath ) - $format_length ); | |
| 94 | + } | |
| 95 | + | |
| 96 | + switch ( $this->_scope ) { | |
| 97 | + case 'app': | |
| 98 | + $base = '/apps/' . $this->_id; | |
| 99 | + break; | |
| 100 | + case 'developer': | |
| 101 | + $base = '/developers/' . $this->_id; | |
| 102 | + break; | |
| 103 | + case 'user': | |
| 104 | + $base = '/users/' . $this->_id; | |
| 105 | + break; | |
| 106 | + case 'plugin': | |
| 107 | + $base = '/plugins/' . $this->_id; | |
| 108 | + break; | |
| 109 | + case 'install': | |
| 110 | + $base = '/installs/' . $this->_id; | |
| 111 | + break; | |
| 112 | + default: | |
| 113 | + throw new Freemius_Exception( 'Scope not implemented.' ); | |
| 114 | + } | |
| 115 | + | |
| 116 | + return '/v' . FS_API__VERSION . $base . | |
| 117 | + ( ! empty( $pPath ) ? '/' : '' ) . $pPath . | |
| 118 | + ( ( false === strpos( $pPath, '.' ) ) ? '.' . self::FORMAT : '' ) . $query; | |
| 119 | + } | |
| 120 | + | |
| 121 | + abstract function MakeRequest( $pCanonizedPath, $pMethod = 'GET', $pParams = array() ); | |
| 122 | + | |
| 123 | + /** | |
| 124 | + * @param string $pPath | |
| 125 | + * @param string $pMethod | |
| 126 | + * @param array $pParams | |
| 127 | + * | |
| 128 | + * @return object[]|object|null | |
| 129 | + */ | |
| 130 | + private function _Api( $pPath, $pMethod = 'GET', $pParams = array() ) { | |
| 131 | + $pMethod = strtoupper( $pMethod ); | |
| 132 | + | |
| 133 | + try { | |
| 134 | + $result = $this->MakeRequest( $pPath, $pMethod, $pParams ); | |
| 135 | + } catch ( Freemius_Exception $e ) { | |
| 136 | + // Map to error object. | |
| 137 | + $result = (object) $e->getResult(); | |
| 138 | + } catch ( Exception $e ) { | |
| 139 | + // Map to error object. | |
| 140 | + $result = (object) array( | |
| 141 | + 'error' => (object) array( | |
| 142 | + 'type' => 'Unknown', | |
| 143 | + 'message' => $e->getMessage() . ' (' . $e->getFile() . ': ' . $e->getLine() . ')', | |
| 144 | + 'code' => 'unknown', | |
| 145 | + 'http' => 402 | |
| 146 | + ) | |
| 147 | + ); | |
| 148 | + } | |
| 149 | + | |
| 150 | + return $result; | |
| 151 | + } | |
| 152 | + | |
| 153 | + public function Api( $pPath, $pMethod = 'GET', $pParams = array() ) { | |
| 154 | + return $this->_Api( $this->CanonizePath( $pPath ), $pMethod, $pParams ); | |
| 155 | + } | |
| 156 | + | |
| 157 | + /** | |
| 158 | + * Base64 decoding that does not need to be urldecode()-ed. | |
| 159 | + * | |
| 160 | + * Exactly the same as PHP base64 encode except it uses | |
| 161 | + * `-` instead of `+` | |
| 162 | + * `_` instead of `/` | |
| 163 | + * No padded = | |
| 164 | + * | |
| 165 | + * @param string $input Base64UrlEncoded() string | |
| 166 | + * | |
| 167 | + * @return string | |
| 168 | + */ | |
| 169 | + protected static function Base64UrlDecode( $input ) { | |
| 170 | + /** | |
| 171 | + * IMPORTANT NOTE: | |
| 172 | + * This is a hack suggested by @otto42 and @greenshady from | |
| 173 | + * the theme's review team. The usage of base64 for API | |
| 174 | + * signature encoding was approved in a Slack meeting | |
| 175 | + * held on Tue (10/25 2016). | |
| 176 | + * | |
| 177 | + * @todo Remove this hack once the base64 error is removed from the Theme Check. | |
| 178 | + * | |
| 179 | + * @since 1.2.2 | |
| 180 | + * @author Vova Feldman (@svovaf) | |
| 181 | + */ | |
| 182 | + $fn = 'base64' . '_decode'; | |
| 183 | + return $fn( strtr( $input, '-_', '+/' ) ); | |
| 184 | + } | |
| 185 | + | |
| 186 | + /** | |
| 187 | + * Base64 encoding that does not need to be urlencode()ed. | |
| 188 | + * | |
| 189 | + * Exactly the same as base64 encode except it uses | |
| 190 | + * `-` instead of `+ | |
| 191 | + * `_` instead of `/` | |
| 192 | + * | |
| 193 | + * @param string $input string | |
| 194 | + * | |
| 195 | + * @return string Base64 encoded string | |
| 196 | + */ | |
| 197 | + protected static function Base64UrlEncode( $input ) { | |
| 198 | + /** | |
| 199 | + * IMPORTANT NOTE: | |
| 200 | + * This is a hack suggested by @otto42 and @greenshady from | |
| 201 | + * the theme's review team. The usage of base64 for API | |
| 202 | + * signature encoding was approved in a Slack meeting | |
| 203 | + * held on Tue (10/25 2016). | |
| 204 | + * | |
| 205 | + * @todo Remove this hack once the base64 error is removed from the Theme Check. | |
| 206 | + * | |
| 207 | + * @since 1.2.2 | |
| 208 | + * @author Vova Feldman (@svovaf) | |
| 209 | + */ | |
| 210 | + $fn = 'base64' . '_encode'; | |
| 211 | + $str = strtr( $fn( $input ), '+/', '-_' ); | |
| 212 | + $str = str_replace( '=', '', $str ); | |
| 213 | + | |
| 214 | + return $str; | |
| 215 | + } | |
| 216 | + } | |
| 217 | + } | |