Razorpay for WooCommerce - Version 1.5.0

Version Description

  • Javascript fixes for additional compatibility with other plugins (#47)
  • Adds multi-currency support using WooCommerce Currency Switcher plugin. (#46)
Download this release

Release Info

Developer razorpay
Plugin Icon 128x128 Razorpay for WooCommerce
Version 1.5.0
Comparing to
See all releases

Code changes from version 1.4.5 to 1.5.0

.editorconfig ADDED
@@ -0,0 +1,13 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ; This file is for unifying the coding style for different editors and IDEs.
2
+ ; More information at http://EditorConfig.org
3
+
4
+ root = true
5
+ ; Use 2 spaces for indentation in all files
6
+
7
+ [*.php]
8
+ end_of_line = lf
9
+ charset = utf-8
10
+ trim_trailing_whitespace = true
11
+ indent_style = space
12
+ indent_size = 4
13
+ insert_final_newline = true
ca-bundle.crt CHANGED
File without changes
images/logo.jpg ADDED
Binary file
includes/Errors/ErrorCode.php ADDED
@@ -0,0 +1,20 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+
3
+ namespace Razorpay\Woocommerce\Errors;
4
+
5
+ require_once __DIR__.'/../../razorpay-sdk/Razorpay.php';
6
+
7
+ use Razorpay\Api\Errors as ApiErrors;
8
+
9
+ class ErrorCode extends ApiErrors\ErrorCode
10
+ {
11
+ const INVALID_CURRENCY_ERROR_CODE = 'INVALID_CURRENCY_ERROR';
12
+ const INVALID_CURRENCY_ERROR_MESSAGE = 'The selected currency is invalid.';
13
+
14
+ const WOOCS_MISSING_ERROR_CODE = 'WOOCS_MISSING_ERROR';
15
+ const WOOCS_MISSING_ERROR_MESSAGE = 'The Woocommerce Currency Switcher plugin is missing.';
16
+
17
+ const WOOCS_CURRENCY_MISSING_ERROR_CODE = 'WOOCS_CURRENCY_MISSING_ERROR';
18
+ const WOOCS_CURRENCY_MISSING_ERROR_MESSAGE = 'The current currency and INR needs to be configured in Woocommerce Currency Switcher plugin';
19
+
20
+ }
includes/razorpay-webhook.php CHANGED
@@ -51,7 +51,13 @@ class RZP_Webhook
51
  }
52
  catch (Errors\SignatureVerificationError $e)
53
  {
54
- write_log(['message' => $e->getMessage()]);
 
 
 
 
 
 
55
  return;
56
  }
57
  }
51
  }
52
  catch (Errors\SignatureVerificationError $e)
53
  {
54
+ $log = array(
55
+ 'message' => $e->getMessage(),
56
+ 'data' => $data,
57
+ 'event' => 'razorpay.wc.signature..verify_failed'
58
+ );
59
+
60
+ write_log($log);
61
  return;
62
  }
63
  }
razorpay-payments.php CHANGED
@@ -3,7 +3,7 @@
3
  Plugin Name: WooCommerce Razorpay Payments
4
  Plugin URI: https://razorpay.com
5
  Description: Razorpay Payment Gateway Integration for WooCommerce
6
- Version: 1.4.6
7
  Author: Razorpay
8
  Author URI: https://razorpay.com
9
  */
@@ -14,9 +14,11 @@ if ( ! defined( 'ABSPATH' ) )
14
  }
15
 
16
  require_once __DIR__.'/includes/razorpay-webhook.php';
 
17
 
18
  use Razorpay\Api\Api;
19
  use Razorpay\Api\Errors;
 
20
 
21
  require_once __DIR__.'/razorpay-sdk/Razorpay.php';
22
 
@@ -33,8 +35,14 @@ function woocommerce_razorpay_init()
33
  class WC_Razorpay extends WC_Payment_Gateway
34
  {
35
  // This one stores the WooCommerce Order Id
36
- const SESSION_KEY = 'razorpay_wc_order_id';
37
- const RAZORPAY_PAYMENT_ID = 'razorpay_payment_id';
 
 
 
 
 
 
38
 
39
  public function __construct()
40
  {
@@ -42,6 +50,7 @@ function woocommerce_razorpay_init()
42
  $this->method_title = 'Razorpay';
43
  $this->icon = plugins_url('images/logo.png' , __FILE__);
44
  $this->has_fields = false;
 
45
  $this->init_form_fields();
46
  $this->init_settings();
47
  $this->title = $this->settings['title'];
@@ -128,10 +137,10 @@ function woocommerce_razorpay_init()
128
  'title' => __('Payment Action', 'razorpay'),
129
  'type' => 'select',
130
  'description' => __('Payment action on order compelete', 'razorpay'),
131
- 'default' => 'capture',
132
  'options' => array(
133
- 'authorize' => 'Authorize',
134
- 'capture' => 'Authorize and Capture'
135
  )
136
  ),
137
  'enable_webhook' => array(
@@ -176,7 +185,6 @@ function woocommerce_razorpay_init()
176
  **/
177
  function receipt_page($order)
178
  {
179
- echo '<p>'.__('Thank you for your order, please click the button below to pay with Razorpay.', 'razorpay').'</p>';
180
  echo $this->generate_razorpay_form($order);
181
  }
182
 
@@ -191,7 +199,7 @@ function woocommerce_razorpay_init()
191
  * that is is still correct. If not found
192
  * (or incorrect), create a new Razorpay Order
193
  * @param string $orderId Order Id
194
- * @return mixed Razorpay Order Id or null
195
  */
196
  protected function createOrGetRazorpayOrderId($orderId)
197
  {
@@ -228,13 +236,18 @@ function woocommerce_razorpay_init()
228
  {
229
  try
230
  {
231
- return $this->createRazorpayOrderId(
232
- $orderId, $sessionKey);
233
  }
234
- catch(Exception $e)
 
235
  {
236
- // Order creation failed
237
- return null;
 
 
 
 
 
238
  }
239
  }
240
  }
@@ -251,14 +264,16 @@ function woocommerce_razorpay_init()
251
 
252
  $razorpayOrderId = $this->createOrGetRazorpayOrderId($orderId);
253
 
254
- if ($razorpayOrderId === null)
255
  {
256
- return 'RAZORPAY ERROR: Api could not be reached';
 
257
  }
258
 
259
  $checkoutArgs = $this->getCheckoutArguments($order, $razorpayOrderId);
260
 
261
- $html = $this->generateOrderForm($redirectUrl, $checkoutArgs);
 
262
 
263
  return $html;
264
  }
@@ -275,17 +290,23 @@ function woocommerce_razorpay_init()
275
  $productinfo = "Order $orderId";
276
 
277
  $args = array(
278
- 'key' => $this->key_id,
279
- 'name' => get_bloginfo('name'),
280
- 'currency' => get_woocommerce_currency(),
281
- 'description' => $productinfo,
282
- 'notes' => array(
283
- 'woocommerce_order_id' => $orderId
284
- ),
285
- 'order_id' => $razorpayOrderId,
286
- 'callback_url' => $callbackUrl,
287
  );
288
 
 
 
 
 
 
 
289
  $args['amount'] = $this->getOrderAmountAsInteger($order);
290
 
291
  if (version_compare(WOOCOMMERCE_VERSION, '2.7.0', '>='))
@@ -329,15 +350,56 @@ function woocommerce_razorpay_init()
329
  $api = $this->getRazorpayApiInstance();
330
 
331
  $data = $this->getOrderCreationData($orderId);
332
- $razorpay_order = $api->order->create($data);
333
 
334
- $razorpayOrderId = $razorpay_order['id'];
 
 
335
 
336
  $woocommerce->session->set($sessionKey, $razorpayOrderId);
337
 
338
  return $razorpayOrderId;
339
  }
340
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
341
  protected function verifyOrderAmount($razorpayOrderId, $orderId)
342
  {
343
  $order = new WC_Order($orderId);
@@ -346,10 +408,12 @@ function woocommerce_razorpay_init()
346
 
347
  $razorpayOrder = $api->order->fetch($razorpayOrderId);
348
 
 
 
349
  $razorpayOrderArgs = array(
350
  'id' => $razorpayOrderId,
351
- 'amount' => $this->getOrderAmountAsInteger($order),
352
- 'currency' => get_woocommerce_currency(),
353
  'receipt' => (string) $orderId,
354
  );
355
 
@@ -372,16 +436,35 @@ function woocommerce_razorpay_init()
372
 
373
  if (!isset($this->payment_action))
374
  {
375
- $this->payment_action = 'capture';
376
  }
377
 
378
  $data = array(
379
  'receipt' => $orderId,
380
  'amount' => (int) round($order->get_total() * 100),
381
  'currency' => get_woocommerce_currency(),
382
- 'payment_capture' => ($this->payment_action === 'authorize') ? 0 : 1
 
 
 
383
  );
384
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
385
  return $data;
386
  }
387
 
@@ -601,9 +684,9 @@ EOT;
601
  $sessionKey = $this->getSessionKey($orderId);
602
 
603
  $attributes = array(
604
- 'razorpay_payment_id' => $_POST['razorpay_payment_id'],
605
- 'razorpay_order_id' => $woocommerce->session->get($sessionKey),
606
- 'razorpay_signature' => $_POST['razorpay_signature'],
607
  );
608
 
609
  $api->utility->verifyPaymentSignature($attributes);
@@ -620,11 +703,15 @@ EOT;
620
  {
621
  $error = $_POST['error'];
622
 
623
- $message = 'An error occured. Description : ' . $error['description'] . '. Code : ' . $error['code'];
 
 
 
624
 
625
  if (isset($error['field']) === true)
626
  {
627
- $message .= 'Field : ' . $error['field'];
 
628
  }
629
  }
630
  else
3
  Plugin Name: WooCommerce Razorpay Payments
4
  Plugin URI: https://razorpay.com
5
  Description: Razorpay Payment Gateway Integration for WooCommerce
6
+ Version: 1.5.0
7
  Author: Razorpay
8
  Author URI: https://razorpay.com
9
  */
14
  }
15
 
16
  require_once __DIR__.'/includes/razorpay-webhook.php';
17
+ require_once __DIR__.'/includes/Errors/ErrorCode.php';
18
 
19
  use Razorpay\Api\Api;
20
  use Razorpay\Api\Errors;
21
+ use Razorpay\Woocommerce\Errors as WooErrors;
22
 
23
  require_once __DIR__.'/razorpay-sdk/Razorpay.php';
24
 
35
  class WC_Razorpay extends WC_Payment_Gateway
36
  {
37
  // This one stores the WooCommerce Order Id
38
+ const SESSION_KEY = 'razorpay_wc_order_id';
39
+ const RAZORPAY_PAYMENT_ID = 'razorpay_payment_id';
40
+
41
+ const INR = 'INR';
42
+ const CAPTURE = 'capture';
43
+ const AUTHORIZE = 'authorize';
44
+ const WC_ORDER_ID = 'woocommerce_order_id';
45
+
46
 
47
  public function __construct()
48
  {
50
  $this->method_title = 'Razorpay';
51
  $this->icon = plugins_url('images/logo.png' , __FILE__);
52
  $this->has_fields = false;
53
+
54
  $this->init_form_fields();
55
  $this->init_settings();
56
  $this->title = $this->settings['title'];
137
  'title' => __('Payment Action', 'razorpay'),
138
  'type' => 'select',
139
  'description' => __('Payment action on order compelete', 'razorpay'),
140
+ 'default' => self::CAPTURE,
141
  'options' => array(
142
+ self::AUTHORIZE => 'Authorize',
143
+ self::CAPTURE => 'Authorize and Capture'
144
  )
145
  ),
146
  'enable_webhook' => array(
185
  **/
186
  function receipt_page($order)
187
  {
 
188
  echo $this->generate_razorpay_form($order);
189
  }
190
 
199
  * that is is still correct. If not found
200
  * (or incorrect), create a new Razorpay Order
201
  * @param string $orderId Order Id
202
+ * @return mixed Razorpay Order Id or Exception
203
  */
204
  protected function createOrGetRazorpayOrderId($orderId)
205
  {
236
  {
237
  try
238
  {
239
+ return $this->createRazorpayOrderId($orderId, $sessionKey);
 
240
  }
241
+ // For the bad request errors, it's safe to show the message to the customer.
242
+ catch (Errors\BadRequestError $e)
243
  {
244
+ return $e;
245
+ }
246
+ // For any other exceptions, we make sure that the error message
247
+ // does not propagate to the front-end.
248
+ catch (Exception $e)
249
+ {
250
+ return new Exception("Payment failed");
251
  }
252
  }
253
  }
264
 
265
  $razorpayOrderId = $this->createOrGetRazorpayOrderId($orderId);
266
 
267
+ if(is_a($razorpayOrderId, 'Exception'))
268
  {
269
+ $message = $razorpayOrderId->getMessage();
270
+ return 'RAZORPAY ERROR: Order creation failed with the message \'' . $message . '\'';
271
  }
272
 
273
  $checkoutArgs = $this->getCheckoutArguments($order, $razorpayOrderId);
274
 
275
+ $html = '<p>'.__('Thank you for your order, please click the button below to pay with Razorpay.', 'razorpay').'</p>';
276
+ $html .= $this->generateOrderForm($redirectUrl, $checkoutArgs);
277
 
278
  return $html;
279
  }
290
  $productinfo = "Order $orderId";
291
 
292
  $args = array(
293
+ 'key' => $this->key_id,
294
+ 'name' => get_bloginfo('name'),
295
+ 'currency' => self::INR,
296
+ 'description' => $productinfo,
297
+ 'notes' => array (
298
+ self::WC_ORDER_ID => $orderId
299
+ ),
300
+ 'order_id' => $razorpayOrderId,
301
+ 'callback_url' => $callbackUrl
302
  );
303
 
304
+ if ($order->get_currency() !== self::INR)
305
+ {
306
+ $args['display_currency'] = $order->get_currency();
307
+ $args['display_amount'] = $order->get_total();
308
+ }
309
+
310
  $args['amount'] = $this->getOrderAmountAsInteger($order);
311
 
312
  if (version_compare(WOOCOMMERCE_VERSION, '2.7.0', '>='))
350
  $api = $this->getRazorpayApiInstance();
351
 
352
  $data = $this->getOrderCreationData($orderId);
 
353
 
354
+ $razorpayOrder = $api->order->create($data);
355
+
356
+ $razorpayOrderId = $razorpayOrder['id'];
357
 
358
  $woocommerce->session->set($sessionKey, $razorpayOrderId);
359
 
360
  return $razorpayOrderId;
361
  }
362
 
363
+ /**
364
+ * Convert the currency to INR using rates fetched from Woocommerce Currency Switcher plugin
365
+ *
366
+ * @param Array $data
367
+ *
368
+ * @return Array
369
+ *
370
+ **/
371
+ protected function convertCurrency(& $data)
372
+ {
373
+ global $WOOCS;
374
+
375
+ $currencies = $WOOCS->get_currencies();
376
+
377
+ $currency = $data['currency'];
378
+
379
+ if (array_key_exists(self::INR, $currencies) and array_key_exists($currency, $currencies))
380
+ {
381
+ // If the currenct currency is the same as the default currency set in WooCommerce,
382
+ // Currency Switcher plugin sets the rate of currenct currency as 0, because of which
383
+ // we need to set this to 1 here if it's value is 0
384
+ $currencyConversionRate = ($currencies[$currency]['rate'] == 0 ? 1 : $currencies[$currency]['rate']);
385
+
386
+ // Convert the currency to INR using the rates fetched from the Currency Switcher plugin
387
+ $value = $data['amount'] * $currencies[self::INR]['rate'];
388
+
389
+ $data['amount'] = intval(round($value / $currencyConversionRate));
390
+ $data['currency'] = self::INR;
391
+ }
392
+ else
393
+ {
394
+ throw new Errors\BadRequestError(
395
+ WooErrors\ErrorCode::WOOCS_CURRENCY_MISSING_ERROR_MESSAGE,
396
+ WooErrors\ErrorCode::WOOCS_CURRENCY_MISSING_ERROR_CODE,
397
+ 400
398
+ );
399
+
400
+ }
401
+ }
402
+
403
  protected function verifyOrderAmount($razorpayOrderId, $orderId)
404
  {
405
  $order = new WC_Order($orderId);
408
 
409
  $razorpayOrder = $api->order->fetch($razorpayOrderId);
410
 
411
+ $orderCreationData = $this->getOrderCreationData($orderId);
412
+
413
  $razorpayOrderArgs = array(
414
  'id' => $razorpayOrderId,
415
+ 'amount' => $orderCreationData['amount'],
416
+ 'currency' => $orderCreationData['currency'],
417
  'receipt' => (string) $orderId,
418
  );
419
 
436
 
437
  if (!isset($this->payment_action))
438
  {
439
+ $this->payment_action = self::CAPTURE;
440
  }
441
 
442
  $data = array(
443
  'receipt' => $orderId,
444
  'amount' => (int) round($order->get_total() * 100),
445
  'currency' => get_woocommerce_currency(),
446
+ 'payment_capture' => ($this->payment_action === self::AUTHORIZE) ? 0 : 1,
447
+ 'notes' => array(
448
+ self::WC_ORDER_ID => (string) $orderId,
449
+ ),
450
  );
451
 
452
+ if ($data['currency'] !== self::INR)
453
+ {
454
+ if (class_exists('WOOCS'))
455
+ {
456
+ $this->convertCurrency($data);
457
+ }
458
+ else
459
+ {
460
+ throw new Errors\BadRequestError(
461
+ WooErrors\ErrorCode::WOOCS_MISSING_ERROR_MESSAGE,
462
+ WooErrors\ErrorCode::WOOCS_MISSING_ERROR_CODE,
463
+ 400
464
+ );
465
+ }
466
+ }
467
+
468
  return $data;
469
  }
470
 
684
  $sessionKey = $this->getSessionKey($orderId);
685
 
686
  $attributes = array(
687
+ self::RAZORPAY_PAYMENT_ID => $_POST['razorpay_payment_id'],
688
+ 'razorpay_order_id' => $woocommerce->session->get($sessionKey),
689
+ 'razorpay_signature' => $_POST['razorpay_signature'],
690
  );
691
 
692
  $api->utility->verifyPaymentSignature($attributes);
703
  {
704
  $error = $_POST['error'];
705
 
706
+ $description = htmlentities($error['description']);
707
+ $code = htmlentities($error['code']);
708
+
709
+ $message = 'An error occured. Description : ' . $description . '. Code : ' . $code;
710
 
711
  if (isset($error['field']) === true)
712
  {
713
+ $fieldError = htmlentities($error['field']);
714
+ $message .= 'Field : ' . $fieldError;
715
  }
716
  }
717
  else
razorpay-sdk/src/Errors/ErrorCode.php CHANGED
@@ -14,4 +14,4 @@ class ErrorCode
14
 
15
  return defined(get_class() . '::' . $code);
16
  }
17
- }
14
 
15
  return defined(get_class() . '::' . $code);
16
  }
17
+ }
readme.txt CHANGED
@@ -3,7 +3,7 @@ Contributors: razorpay
3
  Tags: razorpay, payments, india, woocommerce, ecommerce
4
  Requires at least: 3.9.2
5
  Tested up to: 4.7
6
- Stable tag: 1.4.6
7
  License: GPLv2 or later
8
  License URI: http://www.gnu.org/licenses/gpl-2.0.html
9
 
@@ -36,11 +36,15 @@ This is compatible with WooCommerce>=2.4, including the new 3.0 release.
36
 
37
  == Changelog ==
38
 
 
 
 
 
39
  = 1.4.6 =
40
- * Webhooks signature verification bug fix
41
 
42
  = 1.4.4 =
43
- * Added webhooks to the plugin (includes/razorpay-webhook.php)
44
 
45
  = 1.4.2 =
46
  * Added missing classes in the WordPress release (Utility.php was missing)
3
  Tags: razorpay, payments, india, woocommerce, ecommerce
4
  Requires at least: 3.9.2
5
  Tested up to: 4.7
6
+ Stable tag: 1.5.0
7
  License: GPLv2 or later
8
  License URI: http://www.gnu.org/licenses/gpl-2.0.html
9
 
36
 
37
  == Changelog ==
38
 
39
+ = 1.5.0 =
40
+ * Javascript fixes for additional compatibility with other plugins ([#47](https://github.com/razorpay/razorpay-woocommerce/pull/47))
41
+ * Adds multi-currency support using [WooCommerce Currency Switcher](https://wordpress.org/plugins/woocommerce-currency-switcher/) plugin. ([#46](https://github.com/razorpay/razorpay-woocommerce/pull/46))
42
+
43
  = 1.4.6 =
44
+ * Webhooks signature verification fix
45
 
46
  = 1.4.4 =
47
+ * Added webhooks to the plugin (includes/razorpay-webhook.php) ([#18](https://github.com/razorpay/razorpay-woocommerce/pull/18))
48
 
49
  = 1.4.2 =
50
  * Added missing classes in the WordPress release (Utility.php was missing)
script.js CHANGED
@@ -43,9 +43,9 @@
43
  if (element.attachEvent) return element.attachEvent('on' + evnt, funct);
44
  else return element.addEventListener(evnt, funct, false);
45
  }
46
- // Attach event listener
47
- window.onload = function() {
48
  addEvent(document.getElementById('btn-razorpay'), 'click', openCheckout);
49
  openCheckout();
50
- };
51
  })();
43
  if (element.attachEvent) return element.attachEvent('on' + evnt, funct);
44
  else return element.addEventListener(evnt, funct, false);
45
  }
46
+
47
+ addEvent(window, 'DOMContentLoaded', function() {
48
  addEvent(document.getElementById('btn-razorpay'), 'click', openCheckout);
49
  openCheckout();
50
+ });
51
  })();