Failed Conditions
Push — develop ( ef0a62...79532f )
by Remco
03:16
created

src/Client.php (3 issues)

Labels
Severity
1
<?php
2
/**
3
 * Adyen client
4
 *
5
 * @author    Pronamic <[email protected]>
6
 * @copyright 2005-2019 Pronamic
7
 * @license   GPL-3.0-or-later
8
 * @package   Pronamic\WordPress\Pay\Gateways\Adyen
9
 */
10
11
namespace Pronamic\WordPress\Pay\Gateways\Adyen;
12
13
use Exception;
14
use Pronamic\WordPress\Pay\Core\Gateway as Core_Gateway;
15
use Pronamic\WordPress\Pay\Core\XML\Security;
16
use WP_Error;
17
18
/**
19
 * Adyen client
20
 *
21
 * @author  Remco Tolsma
22
 * @version 1.0.0
23
 * @since   1.0.0
24
 * @link    https://github.com/adyenpayments/php/blob/master/generatepaymentform.php
25
 */
26
class Client {
27
	/**
28
	 * Config.
29
	 *
30
	 * @var Config
31
	 */
32
	private $config;
33
34
	/**
35
	 * Constructs and initializes an Adyen client object.
36
	 *
37
	 * @param Config $config Adyen config.
38
	 */
39 6
	public function __construct( Config $config ) {
40 6
		$this->config = $config;
41 6
	}
42
43
	/**
44
	 * Send request with the specified action and parameters
45
	 *
46
	 * @param string $method Adyen API method.
47
	 * @param object $data   Request data.
48
	 * @return object
49
	 * @throws Exception Throws exception when error occurs.
50
	 */
51 6
	private function send_request( $method, $data ) {
52
		// Request.
53 6
		$url = $this->config->get_api_url( $method );
54
55 6
		$response = wp_remote_request(
56 6
			$url,
57
			array(
58 6
				'method'  => 'POST',
59
				'headers' => array(
60 6
					'X-API-key'    => $this->config->get_api_key(),
61 6
					'Content-Type' => 'application/json',
62
				),
63 6
				'body'    => wp_json_encode( $data ),
64
			)
65
		);
66
67 6
		if ( $response instanceof WP_Error ) {
68 1
			throw new Exception( $response->get_error_message() );
69
		}
70
71
		// Body.
72 5
		$body = wp_remote_retrieve_body( $response );
73
74 5
		$data = json_decode( $body );
75
76
		// JSON error.
77 5
		$json_error = json_last_error();
78
79 5
		if ( JSON_ERROR_NONE !== $json_error ) {
80
			throw new Exception(
81
				json_last_error_msg(),
82
				$json_error
83
			);
84
		}
85
86
		// Object.
87 5
		if ( ! is_object( $data ) ) {
88
			$code = wp_remote_retrieve_response_code( $response );
89
90
			throw new Exception(
91
				sprintf( 'Could not JSON decode Adyen response to an object (HTTP Status Code: %s).', $code ),
92
				intval( $code )
93
			);
94
		}
95
96
		// Error.
97 5
		if ( isset( $data->error ) ) {
98 1
			$error = Error::from_object( $data->error );
99
100 1
			throw $error;
101
		}
102
103
		// Service Exception.
104 4
		if ( isset( $data->status, $data->errorCode, $data->message, $data->errorType ) ) {
105 1
			$service_exception = ServiceException::from_object( $data );
106
107 1
			throw $service_exception;
108
		}
109
110 3
		return $data;
111
	}
112
113
	/**
114
	 * Create payment.
115
	 *
116
	 * @param PaymentRequest $request Payment request.
117
	 * @return PaymentResponse
118
	 */
119 1
	public function create_payment( PaymentRequest $request ) {
120 1
		$data = $this->send_request( 'payments', $request->get_json() );
121
122 1
		return PaymentResponse::from_object( $data );
123
	}
124
125
	/**
126
	 * Create payment session.
127
	 *
128
	 * @param PaymentSessionRequest $request Payment session request.
129
	 * @return PaymentSessionResponse
130
	 */
131 1
	public function create_payment_session( PaymentSessionRequest $request ) {
132 1
		$data = $this->send_request( 'paymentSession', $request->get_json() );
133
134 1
		return PaymentSessionResponse::from_object( $data );
135
	}
136
137
	/**
138
	 * Get payment details.
139
	 *
140
	 * @param string $payload Payload to get payment details for.
141
	 *
142
	 * @return bool|object
143
	 */
144
	public function get_payment_details( $payload ) {
145
		if ( empty( $payload ) ) {
146
			return false;
147
		}
148
149
		$data = array(
150
			'details' => array(
151
				'payload' => $payload,
152
			),
153
		);
154
155
		return $this->send_request( 'payments/details', $data );
0 ignored issues
show
$data of type array<string,array<string,string>> is incompatible with the type object expected by parameter $data of Pronamic\WordPress\Pay\G...\Client::send_request(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

155
		return $this->send_request( 'payments/details', /** @scrutinizer ignore-type */ $data );
Loading history...
156
	}
157
158
	/**
159
	 * Get payment result.
160
	 *
161
	 * @param string $payload Payload to get payment details for.
162
	 *
163
	 * @return bool|object
164
	 */
165
	public function get_payment_result( $payload ) {
166
		if ( empty( $payload ) ) {
167
			return false;
168
		}
169
170
		$data = array(
171
			'payload' => $payload,
172
		);
173
174
		return $this->send_request( 'payments/result', $data );
0 ignored issues
show
$data of type array<string,string> is incompatible with the type object expected by parameter $data of Pronamic\WordPress\Pay\G...\Client::send_request(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

174
		return $this->send_request( 'payments/result', /** @scrutinizer ignore-type */ $data );
Loading history...
175
	}
176
177
	/**
178
	 * Get issuers.
179
	 *
180
	 * @param string $payment_method Payment method.
181
	 *
182
	 * @return array|bool
183
	 */
184
	public function get_issuers( $payment_method = null ) {
185
		// Check payment method.
186
		if ( empty( $payment_method ) ) {
187
			return false;
188
		}
189
190
		// Get issuers.
191
		$methods = $this->get_payment_methods();
192
193
		if ( false === $methods ) {
194
			return false;
195
		}
196
197
		$issuers = array();
198
199
		foreach ( $methods as $method_type => $method ) {
200
			if ( $payment_method !== $method_type ) {
201
				continue;
202
			}
203
204
			if ( ! isset( $method['details']['issuer'] ) ) {
205
				return false;
206
			}
207
208
			foreach ( $method['details']['issuer']->items as $issuer ) {
209
				$id   = Security::filter( $issuer->id );
210
				$name = Security::filter( $issuer->name );
211
212
				$issuers[ $id ] = $name;
213
			}
214
		}
215
216
		return $issuers;
217
	}
218
219
	/**
220
	 * Get payment methods.
221
	 *
222
	 * @return array|bool
223
	 */
224 4
	public function get_payment_methods() {
225
		$data = array(
226 4
			'merchantAccount'       => $this->config->get_merchant_account(),
227
			'allowedPaymentMethods' => array(),
228
		);
229
230 4
		$response = $this->send_request( 'paymentMethods', $data );
0 ignored issues
show
$data of type array<string,array|string> is incompatible with the type object expected by parameter $data of Pronamic\WordPress\Pay\G...\Client::send_request(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

230
		$response = $this->send_request( 'paymentMethods', /** @scrutinizer ignore-type */ $data );
Loading history...
231
232 1
		if ( false === $response ) {
233
			return false;
234
		}
235
236 1
		$payment_methods = array();
237
238 1
		if ( isset( $response->paymentMethods ) ) {
239 1
			foreach ( $response->paymentMethods as $payment_method ) {
240 1
				$type = Security::filter( $payment_method->type );
241 1
				$name = Security::filter( $payment_method->name );
242
243
				$method = array(
244 1
					'name'    => $name,
245
					'details' => array(),
246
				);
247
248 1
				if ( isset( $payment_method->details ) ) {
249 1
					foreach ( $payment_method->details as $detail ) {
250 1
						$key = $detail->key;
251
252 1
						$method['details'][ $key ] = $detail;
253
254 1
						unset( $method['details'][ $key ]->key );
255
					}
256
				}
257
258 1
				$payment_methods[ $type ] = $method;
259
			}
260
		}
261
262 1
		return $payment_methods;
263
	}
264
}
265