Николай

Николай

С нами с 27 июня 2016; Место в рейтинге пользователей: #380
Alexey
14 февраля 2021, 22:31
1
+2
Привет! В файле core/components/minishop2/custom/payment/robokassa.class.php заменить метод getPaymentLink на следующий код:

public function getPaymentLink(msOrder $order)
    {
        $id = $order->get('id');
        $sum = number_format($order->get('cost'), 2, '.', '');
	//список товаров в заказе
	$order_goods = $this->modx->getCollection('msOrderProduct', ['order_id' => $id]);
	$tmp = [];
	foreach($order_goods as $key => $good) {
	    $tmp[$key]['name'] = $good->name;
	    $tmp[$key]['quantity'] = $good->count;
	    $tmp[$key]['sum'] = $good->cost;
	    $tmp[$key]['tax'] = 'none';
	}
		
        //номенклатура заказа
        $receipt = ['items' => array_values($tmp)];
	$receipt_json = json_encode($receipt, JSON_UNESCAPED_UNICODE);
	$SignatureValue = md5($this->config['login'] . ':' . $sum . ':' . $id. ':' . $receipt_json . ':' . $this->config['pass1']);
        $request = array(
            'url' => $this->config['checkoutUrl'],
            'MrchLogin' => $this->config['login'],
            'OutSum' => $sum,
            'InvId' => $id,
            'Desc' => 'Payment #' . $id,
            'IncCurrLabel' => $this->config['currency'],
            'Culture' => $this->config['culture'],
            'Receipt' => $receipt_json,
            'SignatureValue' => $SignatureValue,
        );
        
        if (!empty($this->config['test_mode'])) {
            $request['isTest'] = 1;
        }
        $link = $this->config['checkoutUrl'] . '?' . http_build_query($request);
        return $link;
    }

Компонент давно не обновляется, нужна была оперативность, поэтому правил исходники компонента. Нужно иметь в виду, что если выйдет апдейт, то эти правки будут затерты. Про расширение классов, думаю, можно немало информации найти, хотя бы здесь.

Делал под конкретный сайта, поэтому передавал только необходимые параметры. Советую почитать тут ( skrinshoter.ru/s/140221/5d2fQ6PK?a ), возможно, нужно передать другую систему налогообложения, налоговую ставку и т.д…
Dmitry P.
04 августа 2020, 10:39
2
0
У меня возникла похожая проблема, только в тестовом режиме компонент ругался при каждой оплате. Методом тыка выяснил, что сигнатура в компоненте не совпадает с сигнатурой от робокассы, и связано это вроде как с наличием копеек.
Помогло поправить метод receive в классе оплаты Robokassa (core/components/minishop2/custom/payment/robokassa.class.php)
Добавил вычисление сигнатуры без копеек
$sum3 = number_format($order->get('cost'), 0, '.', '');
$crc3 = strtoupper(md5($sum3 . ':' . $id . ':' . $this->config['pass2']));
И в последующем ифе проверку
if ($crc == $crc1 || $crc == $crc2 || $crc == $crc3) {...}
Полный код метода:
public function receive(msOrder $order, $params = array())
    {
        $id = $order->get('id');
        $crc = strtoupper($_REQUEST['SignatureValue']);
        // Production
        $sum1 = number_format($order->get('cost'), 6, '.', '');
        $crc1 = strtoupper(md5($sum1 . ':' . $id . ':' . $this->config['pass2']));
        // Test
        $sum2 = number_format($order->get('cost'), 2, '.', '');
        $crc2 = strtoupper(md5($sum2 . ':' . $id . ':' . $this->config['pass2']));
        
        /** вот эти две строки добавил*/
        $sum3 = number_format($order->get('cost'), 0, '.', '');
        $crc3 = strtoupper(md5($sum3 . ':' . $id . ':' . $this->config['pass2']));

        if ($crc == $crc1 || $crc == $crc2 || $crc == $crc3) { //и здесь одно условие
            /** @var miniShop2 $miniShop2 */
            $miniShop2 = $this->modx->getService('miniShop2');
            @$this->modx->context->key = 'mgr';
            $miniShop2->changeOrderStatus($order->get('id'), 2);
            exit('OK');
        } else {
            $this->paymentError('Err: wrong signature.', $params);
        }
    }