iT邦幫忙

2021 iThome 鐵人賽

DAY 13
0
永豐金融APIs

試著讀懂與串接永豐金融APIs系列 第 13

Day 0xD - 解開建立訂單回覆的訊息,建立訂單的 Amount 要注意

0x1 前言

昨天訂單總算建立完成了,今天來把回覆的訊息解開並驗證

0x2 處理流程

  • 回覆的結構如下

    {
     "Version": "1.0.0",
     "ShopNo": "商店代碼",
     "APIService": "OrderCreate",
     "Sign": "回覆會提供",
     "Nonce": "回覆會提供",
     "Message": "回覆會提供"
    }
    
  • 解密的需求是 AES key(hash id), IV, Encrypt message,簡單介紹一下流程

    1. 用回覆的 Nonce 計算 IV
    2. 用自己的 4 把 Hash key 算出 hash id
    3. 解密加密訊息
    4. 驗證訊息是否跟 Sign 相符
    5. 判斷回覆的狀態是否為 S0000 – 處理成功 (要注意那個減號不是 \x2D 的那個減號,是全形嗎? 需要大神解釋一下)

程式如下

// app/Http/Controllers/Controller.php
...
public function create_order(Request $request)
{
    $sinopac = $this->initSinopac();
    $data = [
        'ShopNo'        => $sinopac->shop_no,
        'OrderNo'       => 'A' .date('YmdHis'),
        'Amount'        => random_int(4000, 10000) . '00',
        'CurrencyID'    => 'TWD',
        'PrdtName'      => '大河',
        'ReturnURL'     => $request->getBaseUrl() . '/order_reply',
        'BackendURL'    => $request->getBaseUrl() . '/receive_msg',
        'PayType'       => 'A',
        'ATMParam'      => [
            'ExpireDate' => date('Ymd', time() + 604800),
        ],
    ];

    $data = $sinopac->requestDataset('OrderCreate', $data);
    $message = $sinopac->callApi('https://apisbx.sinopac.com/funBIZ/QPay.WebAPI/api/Order', $data);

    $reply_nonce = $message['Nonce'] | '';
    if (!$reply_nonce) {
        $msg = 'Reply message haven\'t Nonce';
        Log::error($msg , $message);
        throw new \HttpResponseException($msg);
    }

    // 1. nonce 計算 iv
    $iv = $sinopac->calculateIv($reply_nonce);
    // 2. 計算 hash_id (AES key)
    $hash_id = $sinopac->calcHashId();
    // 3. message 解密
    $decrypt_message = $sinopac->decryptMessage($message['Message'], $hash_id, $iv);
    // 4. 驗證 sign
    $sign = $sinopac->generateSign($decrypt_message, $reply_nonce, $hash_id);

    if (!($sign === $message['Sign'])) {
        throw new \HttpResponseException('驗證錯誤,內文簽章不同');
    }

    // 這裡的 – 是 \xE2  不是 \x2D
    $description = explode(' – ', $decrypt_message['Description']);
    if ($description[0] !== 'S0000') {
        Log::alert('訂單未建立成功', $decrypt_message['Description']);
        throw new \HttpResponseException("訂單未建立成功");
    }

    return [
        'Reply_Message' => $message,
        'Decrypt_content' => $decrypt_message
    ];
}
...

0x3 補充

建立訂單的 Amount 需要有 00 結尾
https://ithelp.ithome.com.tw/upload/images/20210922/201418057yzKCJeNTs.png

0x4 今日結語

解密的部分是直接複製範例程式,今天解密就比較順利,
明天把建立訂單的紀錄寫進資料庫,就這樣啦,明天見


上一篇
Day 0xC - Debug 地獄第三天,終於逃脫了 (建立訂單)
下一篇
Day 0xE - 建立訂單紀錄到資料庫
系列文
試著讀懂與串接永豐金融APIs30

尚未有邦友留言

立即登入留言