only left, pre auth functions for cz host

This commit is contained in:
kizzy 2026-06-24 02:24:40 +07:00
parent 349d1eed2c
commit f42ecdf631
18 changed files with 60 additions and 26 deletions

View File

@ -75,7 +75,10 @@ fun AppNavGraph(
} }
composable(Routes.Dashboard.route) { composable(Routes.Dashboard.route) {
val sharedViewModel: SharedViewModel = hiltViewModel(activity); val sharedViewModel: SharedViewModel = hiltViewModel(activity)
val transProcessViewModel: TransProcessViewModel = hiltViewModel(activity)
transProcessViewModel.resetTransactionStatus()
DashboardScreen2( DashboardScreen2(
onNavigateAmount = { action -> onNavigateAmount = { action ->
if(action == "Sale"){ if(action == "Sale"){

View File

@ -8,6 +8,7 @@ import android.view.View
import android.view.ViewTreeObserver import android.view.ViewTreeObserver
import android.widget.TextView import android.widget.TextView
import androidx.lifecycle.ViewModel import androidx.lifecycle.ViewModel
import com.kizzy.cmhl.utils.ByteUtils
import com.mob.utsmyanmar.config.Constants import com.mob.utsmyanmar.config.Constants
import com.mob.utsmyanmar.config.SunmiPayManager import com.mob.utsmyanmar.config.SunmiPayManager
import com.mob.utsmyanmar.model.PinPadStatus import com.mob.utsmyanmar.model.PinPadStatus
@ -554,10 +555,13 @@ class PinPadViewModel @Inject constructor(
private fun getPanBytes(pan: String): ByteArray { private fun getPanBytes(pan: String): ByteArray {
LogUtil.d(TAG,"pan : $pan")
if (pan.length < 13) { if (pan.length < 13) {
return ByteArray(0) return ByteArray(0)
} }
LogUtil.d(TAG,"pan bytes : ${ByteUtils.byteArrayToHexString(pan
.substring(pan.length - 13, pan.length - 1)
.toByteArray(StandardCharsets.US_ASCII))}")
return pan return pan
.substring(pan.length - 13, pan.length - 1) .substring(pan.length - 13, pan.length - 1)
.toByteArray(StandardCharsets.US_ASCII) .toByteArray(StandardCharsets.US_ASCII)

View File

@ -52,7 +52,7 @@ fun ProcessingRoute(
} }
} else { } else {
LaunchedEffect(Unit) { LaunchedEffect(Unit) {
transProcessViewModel.resetTransactionStatus() // transProcessViewModel.resetTransactionStatus()
transProcessViewModel.startOnlineProcess() transProcessViewModel.startOnlineProcess()
} }

View File

@ -341,6 +341,11 @@ class SettlementViewModel @Inject constructor(
currentPayDetail.settleData = settlementData currentPayDetail.settleData = settlementData
currentPayDetail.amount = totalAmount currentPayDetail.amount = totalAmount
} else { } else {
LogUtil.d(TAG,"sale count :$totalSaleCount")
LogUtil.d(TAG,"sale amount :$totalSaleAmount")
LogUtil.d(TAG,"refund count :$totalRefundCount")
LogUtil.d(TAG,"refund amount :$totalRefundAmount")
currentPayDetail.settleData = currentPayDetail.settleData =
totalSaleCount + totalSaleCount +
totalSaleAmount + totalSaleAmount +

View File

@ -30,6 +30,7 @@ object MockData {
// iccData="9503220100322798=300110100000942" // iccData="9503220100322798=300110100000942"
// ) // )
//debit
private val mockCardData: MockCardData = MockCardData( private val mockCardData: MockCardData = MockCardData(
cardNo="9503032443884321", cardNo="9503032443884321",
expDate="3102", expDate="3102",
@ -38,6 +39,14 @@ object MockData {
iccData="9503032443884321=310220100" iccData="9503032443884321=310220100"
) )
// private val mockCardData: MockCardData = MockCardData(
// cardNo="6244310039574344",
// expDate="3011",
// cardScheme="MPU",
// cardHolderName="Htin Kyaw Win",
// iccData="6244310039574344=30112011558125900000"
// )
fun generateMPUCard(): CardDataX = CardDataX().apply { fun generateMPUCard(): CardDataX = CardDataX().apply {
pan = mockCardData.cardNo pan = mockCardData.cardNo
exp = mockCardData.expDate exp = mockCardData.expDate

View File

@ -29,7 +29,8 @@ public final class TerminalKeyUtil {
SecurityOptV2 mSecurityOptV2 = BaseApplication.getInstance().mSecurityOptV2; SecurityOptV2 mSecurityOptV2 = BaseApplication.getInstance().mSecurityOptV2;
byte[] cvByte = ByteUtil.hexStr2Bytes("B7B520"); byte[] cvByte = ByteUtil.hexStr2Bytes("B7B520");
// byte[] dataByte = ByteUtil.hexStr2Bytes("e121249099a677e8b7d4f6a9d49fe8d1".toUpperCase()); // mpu // byte[] dataByte = ByteUtil.hexStr2Bytes("e121249099a677e8b7d4f6a9d49fe8d1".toUpperCase()); // mpu
byte[] dataByte = ByteUtil.hexStr2Bytes("05FFB893726A5F1E59692D24E72E36AC"); // byte[] dataByte = ByteUtil.hexStr2Bytes("05FFB893726A5F1E59692D24E72E36AC");
byte[] dataByte = ByteUtil.hexStr2Bytes("DB7887664E3A06873342B753171896B1");
byte[] makBytes = ByteUtil.hexStr2Bytes("250738083EC15BD3BA67D66B8A7AA13B"); byte[] makBytes = ByteUtil.hexStr2Bytes("250738083EC15BD3BA67D66B8A7AA13B");
// byte[] makCvBytes = ByteUtil.hexStr2Bytes("204E449B97"); // byte[] makCvBytes = ByteUtil.hexStr2Bytes("204E449B97");
@ -47,11 +48,11 @@ public final class TerminalKeyUtil {
int result = 0; int result = 0;
SystemParamsOperation.getInstance().setTMKIndex("9"); SystemParamsOperation.getInstance().setTMKIndex("9");
// SystemParamsOperation.getInstance().setInjectOnce(false); SystemParamsOperation.getInstance().setInjectOnce(false);
if(!SystemParamsOperation.getInstance().isInjectOnce()) { if(!SystemParamsOperation.getInstance().isInjectOnce()) {
try { try {
// result = mSecurityOptV2.saveKeyDukpt(AidlConstantsV2.Security.KEY_TYPE_DUPKT_IPEK,IPEKByte,IPEKKCVByte,KSNByte,AidlConstantsV2.Security.KEY_ALG_TYPE_3DES,9); // result = mSecurityOptV2.saveKeyDukpt(AidlConstantsV2.Security.KEY_TYPE_DUPKT_IPEK,IPEKByte,IPEKKCVByte,KSNByte,AidlConstantsV2.Security.KEY_ALG_TYPE_3DES,9);
result = mSecurityOptV2.savePlaintextKey(AidlConstantsV2.Security.KEY_TYPE_TMK,dataByte,cvByte,AidlConstantsV2.Security.KEY_ALG_TYPE_3DES,9); result = mSecurityOptV2.savePlaintextKey(AidlConstantsV2.Security.KEY_TYPE_TMK,dataByte,null,AidlConstantsV2.Security.KEY_ALG_TYPE_3DES,9);
LogUtil.d(ContentValues.TAG, "save TMK result:" + result); LogUtil.d(ContentValues.TAG, "save TMK result:" + result);
if (result != 0) { if (result != 0) {
LogUtil.d(TAG, "save TMK fail"); LogUtil.d(TAG, "save TMK fail");

View File

@ -42,7 +42,7 @@ public class BatchUploadProcess {
} }
private BatchUploadProcess() { private BatchUploadProcess() {
isoMsgX = new ISOMsgX.ISOMsgXBuilder(ISOVersion.VERSION_1993, ISOMode.BOTH_HEADER_TPDU,HostName.BPC) isoMsgX = new ISOMsgX.ISOMsgXBuilder(ISOVersion.VERSION_1993, ISOMode.ONLY_HEADER,HostName.CARDZONE)
.build(); .build();
} }
@ -78,7 +78,7 @@ public class BatchUploadProcess {
public void startBatchUpload(BatchListener batchListener) { public void startBatchUpload(BatchListener batchListener) {
HostName hostName = HostName.BPC; HostName hostName = HostName.BPC;
LogUtil.d(TAG, "Starting Batch Upload"); LogUtil.d(TAG, "Starting Batch Upload");
byte[] sendBytes = isoMsgX.buildISOPackets(tradeData, BitmapConfig.BPC_BATCH_UPLOAD, MessageType.BATCH_UPLOAD); byte[] sendBytes = isoMsgX.buildISOPackets(tradeData, BitmapConfig.CZ_BATCH_UPLOAD, MessageType.BATCH_UPLOAD);
ISOSocket.getInstance().enqueue(sendBytes, sendBytes.length,false, new ISOCallback() { ISOSocket.getInstance().enqueue(sendBytes, sendBytes.length,false, new ISOCallback() {
@Override @Override
public void onReceive(byte[] bytes, int length) { public void onReceive(byte[] bytes, int length) {

View File

@ -409,7 +409,8 @@ public class DecodePackage {
if(hostName == HostName.BPC) { if(hostName == HostName.BPC) {
System.arraycopy(body, tmpLen, nextData, 0, datLen); System.arraycopy(body, tmpLen, nextData, 0, datLen);
} else { } else {
System.arraycopy(body, tmpLen, nextData, 0, body.length-tmpLen); // System.arraycopy(body, tmpLen, nextData, 0, body.length-tmpLen);
System.arraycopy(body, tmpLen, nextData, 0, datLen);
} }
// //

View File

@ -280,6 +280,7 @@ public class EncodePackage {
System.arraycopy(fieldBody.getBytes(StandardCharsets.ISO_8859_1), 0, body, index, fieldBody.length()); System.arraycopy(fieldBody.getBytes(StandardCharsets.ISO_8859_1), 0, body, index, fieldBody.length());
index += fieldBody.length(); index += fieldBody.length();
} else { } else {
// MPU
String fieldHead = msgField.getDataStr().substring(0,4); String fieldHead = msgField.getDataStr().substring(0,4);
int bcdLen = (fieldHead.length() / 2) + (fieldHead.length() % 2); int bcdLen = (fieldHead.length() / 2) + (fieldHead.length() % 2);
byte dat[] = new byte[bcdLen]; byte dat[] = new byte[bcdLen];

View File

@ -106,6 +106,9 @@ public class ISOMsgX extends BaseISOMsgX{
MTI = "0400"; MTI = "0400";
// MTI = "0420"; // MTI = "0420";
break; break;
case CZ_REVERSAL:
MTI = "0420";
break;
case NETWORK_MANAGEMENT: case NETWORK_MANAGEMENT:
MTI = "0800"; MTI = "0800";
break; break;

View File

@ -356,11 +356,7 @@ public class ISOSocket {
reversalSwitchFlag = SystemParamsOperation.getInstance().isReversalOn(); reversalSwitchFlag = SystemParamsOperation.getInstance().isReversalOn();
if (reversalSwitchFlag) { if (reversalSwitchFlag) {
if (reversalTrans) { reversalTestCaseFlag = reversalTrans;
reversalTestCaseFlag = true;
} else {
reversalTestCaseFlag = false;
}
} else { } else {
reversalTestCaseFlag = true; reversalTestCaseFlag = true;
} }

View File

@ -58,14 +58,14 @@ public class PrintXImpl extends BaseXPrint implements PrintX {
opts.inJustDecodeBounds = true; opts.inJustDecodeBounds = true;
// Step 1: Only read dimensions first // Step 1: Only read dimensions first
BitmapFactory.decodeResource(resources, R.drawable.print_logo_mpu, opts); BitmapFactory.decodeResource(resources, R.drawable.mob_print_logo, opts);
// Step 2: Calculate sample size so width <= 384px // Step 2: Calculate sample size so width <= 384px
opts.inSampleSize = calculateInSampleSize(opts, 384, 384); opts.inSampleSize = calculateInSampleSize(opts, 384, 384);
opts.inJustDecodeBounds = false; opts.inJustDecodeBounds = false;
// Step 3: Decode scaled-down bitmap // Step 3: Decode scaled-down bitmap
bitmap = BitmapFactory.decodeResource(resources, R.drawable.print_logo_mpu, opts); bitmap = BitmapFactory.decodeResource(resources, R.drawable.mob_print_logo, opts);
} }
@Override @Override

View File

@ -50,14 +50,14 @@ public class ReversalAction {
} }
private ReversalAction() { private ReversalAction() {
isoMsgX = new ISOMsgX.ISOMsgXBuilder(ISOVersion.VERSION_1993, ISOMode.ONLY_HEADER,HostName.FINEXUS) isoMsgX = new ISOMsgX.ISOMsgXBuilder(ISOVersion.VERSION_1993, ISOMode.ONLY_HEADER,HostName.CARDZONE)
.build(); .build();
} }
public ReversalAction setData(TradeData tradeData) { public ReversalAction setData(TradeData tradeData) {
this.tradeData = tradeData; this.tradeData = tradeData;
payDetail = tradeData.getPayDetail(); payDetail = tradeData.getPayDetail();
payDetail.setTransactionType(TransactionType.REVERSAL); payDetail.setTransactionType(TransactionsType.REVERSAL.value);
// payDetail.setTransType(REVERSAL); // payDetail.setTransType(REVERSAL);
if (TextUtils.equals(payDetail.getAccountType(), MPU)) { if (TextUtils.equals(payDetail.getAccountType(), MPU)) {
BITMAP = getBitmapMPU(payDetail); BITMAP = getBitmapMPU(payDetail);
@ -129,7 +129,7 @@ public class ReversalAction {
public void startReversal(ReversalListener reversalListener) { public void startReversal(ReversalListener reversalListener) {
HostName hostName = HostName.BPC; HostName hostName = HostName.BPC;
LogUtil.d(TAG, "Starting Reversal...."); LogUtil.d(TAG, "Starting Reversal....");
byte[] sendBytes = isoMsgX.buildISOPackets(tradeData, BitmapConfig.MPU_NEW_REVERSAL, MessageType.REVERSAL); byte[] sendBytes = isoMsgX.buildISOPackets(tradeData, BitmapConfig.CZ_REVERSAL, MessageType.CZ_REVERSAL);
// byte[] sendBytes = isoMsgX.buildISOPackets(tradeData, BitmapConfig.BPC_AUTOMATIC_REVERSAL, MessageType.REVERSAL); // byte[] sendBytes = isoMsgX.buildISOPackets(tradeData, BitmapConfig.BPC_AUTOMATIC_REVERSAL, MessageType.REVERSAL);
ISOSocket.getInstance().enqueue(sendBytes, sendBytes.length,true, new ISOCallback() { ISOSocket.getInstance().enqueue(sendBytes, sendBytes.length,true, new ISOCallback() {
@Override @Override

View File

@ -5,6 +5,7 @@ public enum MessageType {
AUTHORIZATION, AUTHORIZATION,
AUTHORIZATION_COMPLETE, AUTHORIZATION_COMPLETE,
REVERSAL, REVERSAL,
CZ_REVERSAL,
NETWORK_MANAGEMENT, NETWORK_MANAGEMENT,
TC_ADVICE, TC_ADVICE,
BATCH_UPLOAD, BATCH_UPLOAD,

View File

@ -86,7 +86,7 @@ public class HostUtils {
if (hostName == HostName.MPU) { if (hostName == HostName.MPU) {
bitmap = BitmapConfig.MPU_NEW_REFUND; bitmap = BitmapConfig.MPU_NEW_REFUND;
} else { } else {
bitmap = BitmapConfig.CZ_SALE; bitmap = BitmapConfig.CZ_REFUND;
} }
break; break;
case TIP_ADJUSTMENT: case TIP_ADJUSTMENT:

View File

@ -193,7 +193,10 @@ public class BitmapConfig {
public static final String MPU_NEW_CASH_ADVANCE="7020058020C09000"; public static final String MPU_NEW_CASH_ADVANCE="7020058020C09000";
public static final String CZ_SALE="7020058020C09000"; public static final String CZ_SALE="7020058020C09000";
public static final String CZ_VOID="723805802CC08010"; public static final String CZ_VOID="7038058008C08010";
public static final String CZ_REFUND="703C058008C08000";
public static final String CZ_REVERSAL="7020078000C08000";
public static final String CZ_BATCH_UPLOAD="703805800CC00010";
public static final String UPI_SALE = "7020058020C09200"; public static final String UPI_SALE = "7020058020C09200";

View File

@ -361,7 +361,7 @@ public class FieldUtils {
// } else { // } else {
// iterator.remove(); // iterator.remove();
// } // }
field.setDataStr("001"); field.setDataStr("000");
break; break;
case 24: //Network International Identifier NII case 24: //Network International Identifier NII
@ -379,8 +379,9 @@ public class FieldUtils {
if (payDetail.getTransactionType() == PRE_AUTH_SALE.value) { if (payDetail.getTransactionType() == PRE_AUTH_SALE.value) {
field.setDataStr("06"); field.setDataStr("06");
} }
else if(payDetail.getTransactionType() == REFUND.value) { else if(payDetail.getTransactionType() == REFUND.value || payDetail.getTransactionType() == REVERSAL.value) {
field.setDataStr("00"); // MPU // field.setDataStr("00"); // MPU
field.setDataStr("61"); // CZ
} else if(payDetail.getCardType() == -1) { } else if(payDetail.getCardType() == -1) {
field.setDataStr("08"); field.setDataStr("08");
} }
@ -506,12 +507,16 @@ public class FieldUtils {
break; break;
case 60: //Private(oldMPU) //original Amount Void(new MPU) case 60: //Private(oldMPU) //original Amount Void(new MPU)
//
String field60 = tradeData.getField60(); String field60 = tradeData.getField60();
String lengthValue = String.format(Locale.getDefault(),"%04d", field60.length())+field60; String lengthValue = String.format(Locale.getDefault(),"%04d", field60.length())+field60;
field.setDataStr(lengthValue); field.setDataStr(lengthValue);
// for CardZone
// String field60 = tradeData.getField60();
// String lengthValue = String.format(Locale.getDefault(),"%04d", field60.length())+field60;
// field.setDataStr(field60);
break; break;
case 61: case 61:
// TODO // TODO
@ -538,7 +543,9 @@ public class FieldUtils {
break; break;
case 63: //Private Use case 63: //Private Use
String settleData = payDetail.getSettleData(); String settleData = payDetail.getSettleData();
field.setDataStr(settleData); String settleValue = String.format(Locale.getDefault(),"%04d", settleData.length())+settleData;
field.setDataStr(settleValue);
// field.setDataStr(settleData);
break; break;
case 64: //Message Authentication Code (MAC) Required when the 39 field in the response message is "00" case 64: //Message Authentication Code (MAC) Required when the 39 field in the response message is "00"
field.setDataStr("0000000000000000"); field.setDataStr("0000000000000000");

Binary file not shown.

After

Width:  |  Height:  |  Size: 132 KiB