Skip to main content

ECR integration technical specification

1. POS-KEY

POS-KEY is a secret key used to encrypt and decrypt the data. It is generated by Haojin App.

The default POS-KEY is f46b1f08bec1f39104792cc79ec9aacd


The default encrpytion is ON.

There is an option to switch on/off on merchant portal (MMS) or refresh POS-KEY. And, Haojin App refresh is required to be effective


Steps to refresh POS-KEY Login Haojin App -> My -> Settings -> POS-Key -> generate

Steps to check POS-KEY Login Shop Management Platform-> Settings -> Devices Settings -> POS Key Mgmt tab

2. Encryption

All data is encrypted by AES. The key is POS-KEY and the IV is qfpay202306_hjsh


The data is encoded by Base64 after encryption.

3. Request payload format

AttributeMandatoryTypeDescription
amtYesDoubleAmount e.g. $10.1 => 10.1
func_typeYesStringInstruction code
channelYesStringWallet name, refer to Channel list
out_trade_noNoStringMerchant reference.
if not passed, the out_trade_no won't be passed
camera_idNoIntegercan select using front camera or back camera in QR code payment CPM mode
0: back camera (default),
1: front camera
wait_card_timeoutNoIntegercan set waiting time in credit card payment page, default 120 seconds

3.1 Payment

note

For QR code payment, MPM/CPM mode is automatically selected base on last usage.

Front camera or back camera can be selected to use by parameter camera_id

Time to wait for credit card payment in payment page can be set by parameter wait_card_timeout

{
"content": {"amt": 100, "camera_id":0, "channel": "card_payment","func_type": 1001, "out_trade_no": "456799999999",
"wait_card_timeout":120},
"digest":"76b9186077cdc2bc5d78ae921309811d"
}

For inquiry the transaction result, please use the Inquire API

2.2 Refund / Void

no password input is required in app when initialize refund request

specific parameters

AttributeMandatoryTypeDescription
orderIdYesStringQFPay transaction Id
refund_amountNoStringthe default refund amount is the refundable amount of the order,
support partial refund
allow_modify_flagNoInteger0: Not allow modification of refund amount (default value)
1: allow modification of refund amount
note

for Card payment, Unionpay Card and American Express Card, the amount of same day refund must be full amount

{
"content": {"allow_modify_flag":1, "func_type": 1002,"orderId": "order_id","refund_amount": "0.05"},
"digest": "9C8E9FB05C7C24B6CA04EBFA1263EF41"
}

3.3 Print receipt

{
"content": {"orderId": "12345678","func_type": 3001},
"digest":"79fd145311d54d03e4e685d50f15dd7f"
}

3.4 Print transaction summary

{
"content": {"func_type": 3002},
"digest":"79fd145311d54d03e4e685d50f15dd7f"
}

3.5 Transaction inquiry by order Id

new paramter out_trade_no is supported

{
"content": {"orderId": "1234567890","func_type": 4001},
"digest":"99CE8BF9C7304AC964522D10F51660B4"
}

3.6 Cancel trade/refund request

{
"content": {"func_type": 5001},
"digest": "99CE8BF9C7304AC964522D10F51660B4"
}

content:data request payload digest: signature of data request payload (content), sort the parameters in alphabetical ascending order and concat them in key=value format, use md5 algorithm to get hash value which is signature

Generate signature

sample of generate signature

// original payload
content={"amt":100,"channel": "card_payment","func_type":1001,"out_trade_no":"456799999999"}

// sorted keys in alphabetical ascending order
format_content={amt=100,channel='card_payment',func_type=1001,out_trade_no='456799999999'}

// encryption
// !! if the value is empty, pass '' (empty string) instead
digest=md5(format_content + pos_key)
digest=md5({amt=100,channel='card_payment',func_type=1001,out_trade_no='456799999999'}f46b1f08bec1f39104792cc79ec9aacd)

if encryption is enabled, the above payload will be encrypted by AES at content, and the digest will be calculated based on the encrypted payload.

for example

{
"content": "{func_type: 3002}",
"digest":"79fd145311d54d03e4e685d50f15dd7f"
}

4. Fields explanation

1、 func_type : business type
(1) 1001 Trade
(2) 1002 Refund
(3) 3001 Print receipt
(4) 3002 Print transaction summary
(5) 4001 Transaction inquiry
(6) 5001 Cancel trade/refund request

2、channel: payment method
(1) 、card_payment Card payment
(2) 、wx WeChat Pay
(3) 、alipay Alipay
(4) 、payme PayMe
(5) 、union UnionPay
(6) 、fps FPS
(7) 、octopus Octopus
(8) 、unionpay_card Unionpay Card
(9) `amex_card` American Express Card

3、amt: Transaction amount

4、orderId: Transaction reference number, the same as out_trade_no

5. Response format

{\"respcd\": \"6000\",\"data\": \"{"aaaaaa"}\",\"respmsg\": \"xxxxxxxxxx\",\"resperr\":\"xxxxxxxxxx\"}
1、respcd: response code
(1)、"4003",POS-KEY is invalid
(2)、"5001",Decryption failed
(3)、"4004",Request method is incorrect, may use POST request
(4)、"4005",Other errors
(5)、"4006" Incorrect parameter(s)
(6)、"5001",Decryption failed
(7)、"6000" request succeed
(8)、"6001" request cancel
(9)、"6002" request error

2、respmsg:Response message
3、resperr:Error message
4、data:response data from trade or refund request
(1) data fields in trade response:
respcd;response code
resmsg;response message
reserr;response error message
mchntnm;merchant name
sysdtm;system time
userid;store Id
busicd;business code
txamt;transaction amount
txcurrcd;transaction currency
chnlsn;channel serial number
paydtm;payment time
udid;user id
syssn;system serial number
clisn;client serial number
out_trade_no;merchant order Id
cardscheme;card scheme, e.g. VISA
(2) data field in refund response:
respcd;response code
resmsg;response message
reserr;response error message
sysdtm;system time
paydtm;payment time
txcurrcd;transaction currency
txdtm;trsnaction time
orig_syssn;original system serial number
out_trade_no;merchant order Id
syssn;system serial number
chnlsn;channel serial number
txamt;transaction amount
originTxamt;original transaction amount
(3) data field in transaction inquiry response:
server_time;server time
cancel;cancel status
clisn;client serial number
opuid;operator id
prepay_amt;payment amount
syssn;QF system serial number
tradetp;payment type
sysdtm;QF system time
txcurrcd;transaction currency
origssn;original system serial number
customer_source;customer source
opuser;operator
nickname;user name
allow_refund_amt;refundable amount
desc;description
txamt;transaction amount
busicd;business code
respcd;response code
origbusicd;original business code
chnlsn;channel serial number
cardscheme;card scheme, e.g. VISA

6. USB data transmission method

  1. Connect the POS to the cash register via USB cable.
  2. follow the USB communication protocol to construct the data. See the ninth article for details: "Cash register & Pos communication protocol".
  3. Data response. The received data needs to be parsed according to the communication protocol, and then the data message is obtained, and then decrypted by AES.

7. HTTP protocol

  1. HTTP data transmission method requires POS host IP address and port. The default port of the HTTP method is 9001.
  2. Data message format: (1) Encrypt the data message through AES (2) Initiate the request through the HTTP Post request
  3. Request API (1) Trade: /api/pos/trade (2) Refund: /api/pos/cancel (3) Print receipt: /api/pos/print_receipt (4) Print transaction summary: /api/pos/transaction_info (5) Transaciton inquiry: /api/pos/query_transaction (6) Cancel trade/refund request: /api/pos/cancel_request
  4. The request header needs to be set. The request Content-type format is: application/json
  5. The request result needs to be decrypted by AES to obtain the response message data

8. TCP protocol

  1. The HTTP data transmission method requires POS host and port. The default port of the HTTP method is 9002.
  2. Cash register connects to POS through socket connection
  3. Data is transmitted through socket. The data format is the encrypted data of the data message after AES encryption.
  4. The result of the request needs to be decrypted by AES to obtain the response message data

9. Cash register & Pos communication protocol (USB)

9.1 Use scenario

The cash register and the smart POS device communicate through the serial port or Bluetooth to realize the cash register through the Haojin merchant App on the smart POS to collect and cancel the transaction.

9.2 Communication method

Serial port.

Through the Micro USB interface on the smart POS device or by borrowing the base to convert to USB Host mode, connect to the cash register via USB to serial cable.

USB is more stable than Wifi, secure, and easy to deploy.

9.3 Payload format

Field namecontentDescriptionLength
Start indicator0x2f6estart of payload2 Bytes
version0x01version (static)1 Byte
payload type0x10
0x20
0x30
request
response
response error
1 Byte
response reference number0x01 ~ 0x7fused for request/response, payload splitting / concatenation
incremental for each, in loop
1 Byte
payload lengthtotal bytes from Start indicator to End indicator2 Bytes
payload length (data segment)total bytes of data segment2 Bytes
data segmentdata segment, utf-8 encodingnon static
End indicator0x2f6eindicate end of the payload2 Bytes

9.4 detail explanation

Start indicator and end indicator

In order to avoid the situation that a data packet is split into multiple data blocks due to hardware reasons during communication, resulting in the inability to obtain the contents of the packet normally. The sender adds the start and end characters (0x2f6e) to each packet when sending the packet.

After the receiver receives the packet, it will check whether the first two bytes of the packet are the start character (0x2f6e). If not, an error packet (0x31) will be responded. Otherwise, continue to traverse the subsequent bytes until the end character.

warning

0x2f6e is the hexadecimal representation of /n (string, NOT the carriage return) in ASCII encoding

Payload error type

error typedescription
0x30unknown
0x31format error
0x32validation error
0x33data segment decrypt error
0x34data segment format error
0x35data segment packets error

request and response

When the receiver receives the request packet (packet type is 0x10), it needs to send a response packet to inform the sender of the result of receiving the packet. If the validation is successful, the response packet type is 0x20. If the validation fails, the response packet type is 0x32. The response packet number is the same as the request packet number.

response timeout

Response timeout is 1000ms, if timeout, the request is considered failed, and the device is disconnected.

payload length

  1. total length of the payload, from start indicator to end indicator
  2. payload length of data segment
  3. since the payload length is 2 bytes, the maximum length of the data segment is 65536 bytes
  4. it is recommended to keep the data segment length within 1024 bytes, if the data segment is too long, it should be split into multiple packets
Data pack splitting and concatenation

When sender splits the data segment into multiple packets, the packet number is the same, and the packet length is the total length of the data segment. The receiver needs to wait for the subsequent packets with the same packet number until the packet length is equal to the total length of the data segment, and then send the response packet.

The receiver waits for the timeout of multiple packets to be 500ms. After the timeout, the previously received packets are discarded. If subsequent packets with the same number are received, an error (0x35) response packet is sent.

Data encryption

The sender and receiver need to encrypt the valid data using the AES algorithm. The key is allocated by the service provider.

Key length 16 bytes 128 bits

Key offset ***** Algorithm mode CBC (Cipher Block Chaining) encryption block chain Padding method PKCS5Padding

Serial port settings

Baud rate: 9600 Stop bit: 1 Parity bit: 0 Data bit: 8 Flow control: off

USB to serial port line chip type supported

PL2303 HXD supported CH340 not supported FT232 not supported

The above chip types are the most common USB to serial port chips on the market. The stability and price of the three chips are the same, FT232>CH340>PL2303

Sample data

Sample data is as follows:

{\"content\":\"{\\\"amt\\\":100,\\\"channel\\\":\\\"wx\\\",\\\"funcType\\\":1,\\\"mode\\\":1}\",\"digest\":\"2f0c4683e25a7b9407265033070e9034\"}

complete data request content(Hexadecimal format):

2f6e011001007f00747b22636f6e74656e74223a227b5c22616d745c223a3130302c5c226368616e6e656c5c223a5c2277785c222c5c2266756e63547970655c223a312c5c226d6f64655c223a317d222c22646967657374223a223266306334363833653235613762393430373236353033333037306539303334227d2f6e