Merge branch 'production_2.2' into test
This commit is contained in:
commit
c3246b907a
@ -13,7 +13,6 @@
|
||||
<option value="$PROJECT_DIR$/app" />
|
||||
<option value="$PROJECT_DIR$/baselib" />
|
||||
<option value="$PROJECT_DIR$/ecr" />
|
||||
<option value="$PROJECT_DIR$/ecr-service" />
|
||||
<option value="$PROJECT_DIR$/ecr-service-lib" />
|
||||
<option value="$PROJECT_DIR$/link-service-lib" />
|
||||
<option value="$PROJECT_DIR$/mpulib" />
|
||||
|
||||
11
CHANGELOG.md
Normal file
11
CHANGELOG.md
Normal file
@ -0,0 +1,11 @@
|
||||
# Change log UAT
|
||||
|
||||
## [2.12] - 2026-05-06
|
||||
|
||||
- **Pinpad Sound Toggle**
|
||||
- Beep is ON by default
|
||||
- Can Toggle PinPad sound on Side Navigation ( Under SystemManagement Tab)
|
||||
|
||||
- **Transaction Search**
|
||||
- Search now matches by both Trace No and RRN instead of Trace No only
|
||||
- Trace No uses partial match (`contains`), RRN uses exact match (`equals`)
|
||||
@ -14,8 +14,8 @@ android {
|
||||
applicationId "com.utsmm.kbz"
|
||||
minSdk 24
|
||||
targetSdk 33
|
||||
versionCode 21
|
||||
versionName "2.1"
|
||||
versionCode 2
|
||||
versionName "2.0"
|
||||
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
|
||||
}
|
||||
|
||||
@ -50,7 +50,7 @@ android {
|
||||
buildTypes {
|
||||
release {
|
||||
minifyEnabled true
|
||||
shrinkResources false
|
||||
shrinkResources true
|
||||
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
|
||||
}
|
||||
debug {
|
||||
@ -204,7 +204,7 @@ dependencies {
|
||||
|
||||
// ECR Dependencies - Modern ECR Client Library
|
||||
// implementation project(path: ':ecr-client-lib')
|
||||
implementation project(path: ':ecr-service-lib')
|
||||
// implementation project(path: ':ecr-service-lib')
|
||||
|
||||
// Core Libraries
|
||||
implementation project(path: ':paylibs')
|
||||
|
||||
1
app/proguard-rules.pro
vendored
1
app/proguard-rules.pro
vendored
@ -266,3 +266,4 @@
|
||||
|
||||
-dontwarn com.xgd.smartpos.manager.app.UsageInfo
|
||||
-dontwarn com.xgd.smartpos.manager.app.UsageStats
|
||||
-dontwarn javax.lang.model.element.Modifier
|
||||
@ -35,6 +35,10 @@
|
||||
<uses-permission android:name="android.permission.WAKE_LOCK" />
|
||||
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
|
||||
<uses-permission android:name="android.permission.REQUEST_IGNORE_BATTERY_OPTIMIZATIONS" />
|
||||
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
|
||||
<uses-permission android:name="android.permission.ACCESS_BACKGROUND_LOCATION"/>
|
||||
|
||||
|
||||
<!-- android:noHistory="true"-->
|
||||
<!-- android:excludeFromRecents="true"-->
|
||||
|
||||
@ -4,6 +4,7 @@ import androidx.appcompat.app.ActionBarDrawerToggle;
|
||||
import androidx.appcompat.app.AppCompatActivity;
|
||||
import androidx.databinding.DataBindingUtil;
|
||||
import androidx.drawerlayout.widget.DrawerLayout;
|
||||
import androidx.lifecycle.Observer;
|
||||
import androidx.lifecycle.ViewModelProvider;
|
||||
import androidx.navigation.NavController;
|
||||
import androidx.navigation.NavDestination;
|
||||
@ -32,6 +33,7 @@ import com.nexgo.downloadkey.downloadflow.DownloadFlowResultEntity;
|
||||
import com.nexgo.downloadkey.downloadflow.DownloadResult;
|
||||
import com.nexgo.oaf.apiv3.device.pinpad.PinPad;
|
||||
import com.nexgo.oaf.apiv3.device.pinpad.WorkKeyTypeEnum;
|
||||
import com.utsmm.kbz.util.LocationUtil;
|
||||
import com.utsmyanmar.baselib.BaseApplication;
|
||||
import com.utsmyanmar.baselib.repo.Repository;
|
||||
import com.utsmyanmar.baselib.ui.AnimationDialog;
|
||||
@ -115,6 +117,7 @@ public class MainActivity extends AppCompatActivity implements
|
||||
super.onCreate(savedInstanceState);
|
||||
|
||||
BaseApplication.getInstance().deviceEngine.getPlatform().hideNavigationBar();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().showNavigationBar();
|
||||
|
||||
// Keep screen on
|
||||
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
|
||||
@ -157,10 +160,8 @@ public class MainActivity extends AppCompatActivity implements
|
||||
}
|
||||
|
||||
private void initKey(){
|
||||
SystemParamsOperation.getInstance().setTmsAddress("https://api-tms-uat.kbzbank.com:8443/sirius");
|
||||
// SystemParamsOperation.getInstance().setTmsAddress("https://sirius-nest.utsmyanmar.com");
|
||||
SystemParamsOperation.getInstance().setEReceiptAddress("https://api-tms-uat.kbzbank.com:8443/receipt");
|
||||
// SystemParamsOperation.getInstance().setEReceiptAddress("http://receipt-nest.utsmyanmar.com");
|
||||
SystemParamsOperation.getInstance().setTmsAddress("https://api-tms.kbzbank.com/sirius");
|
||||
SystemParamsOperation.getInstance().setEReceiptAddress("https://api-tms.kbzbank.com/receipt");
|
||||
|
||||
PinPad pinPad = MyApplication.getInstance().deviceEngine.getPinPad();
|
||||
byte[] encryptedPIK = SystemParamsOperation.getInstance().getPIK();
|
||||
@ -176,6 +177,7 @@ public class MainActivity extends AppCompatActivity implements
|
||||
|
||||
private void initViewModels() {
|
||||
sharedViewModel = new ViewModelProvider(this).get(SharedViewModel.class);
|
||||
sharedViewModel.getToastMsg().observe(this, this::showToast);
|
||||
}
|
||||
|
||||
private void setupUI() {
|
||||
@ -427,20 +429,19 @@ public class MainActivity extends AppCompatActivity implements
|
||||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
getLocation();
|
||||
SystemParamsOperation.getInstance().setSetupEcr(false);
|
||||
SystemParamsOperation.getInstance().setDownloadedParams(false);
|
||||
|
||||
handleAutoSettlementIntent(getIntent());
|
||||
BaseApplication.getInstance().deviceEngine.getPlatform().hideNavigationBar();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().showNavigationBar();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onStop(){
|
||||
super.onStop();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().showNavigationBar();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().enableHomeButton();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().enableTaskButton();
|
||||
BaseApplication.getInstance().deviceEngine.getPlatform().showNavigationBar();
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -450,30 +451,81 @@ public class MainActivity extends AppCompatActivity implements
|
||||
handleAutoSettlementIntent(intent);
|
||||
}
|
||||
|
||||
public void getLocation() {
|
||||
LocationUtil.getCurrentLocation(MainActivity.this, new LocationUtil.LocationCallback() {
|
||||
@Override
|
||||
public void onSuccess(double lat, double lng) {
|
||||
LogUtil.d("Location", "Current Location: " + lat + ", " + lng);
|
||||
LocationUtil.setLat(lat);
|
||||
LocationUtil.setLng(lng);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onError(String reason) {
|
||||
LogUtil.e("Location", "get Location error: " + reason);
|
||||
LocationUtil.setLat(0.00);
|
||||
LocationUtil.setLng(0.00);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void handleAutoSettlementIntent(Intent intent) {
|
||||
if (intent == null) return;
|
||||
|
||||
// Handle regular auto settlement
|
||||
boolean auto = intent.getBooleanExtra("AUTO_SETTLEMENT", false);
|
||||
if (auto) {
|
||||
boolean hasPOS = intent.getBooleanExtra("AUTO_SETTLEMENT", false);
|
||||
boolean hasQR = intent.getBooleanExtra("AUTO_QR_SETTLEMENT", false);
|
||||
|
||||
if (hasPOS) {
|
||||
PayDetail payDetail = (PayDetail) intent.getSerializableExtra("EXTRA_PAY_DETAIL");
|
||||
if (payDetail != null) {
|
||||
|
||||
sharedViewModel.payDetail.setValue(payDetail);
|
||||
sharedViewModel.transactionsType.setValue(TransactionsType.SETTLEMENT);
|
||||
sharedViewModel.setAmount(POSUtil.getInstance().getDecimalAmountSeparatorFormat(payDetail.getAmount()));
|
||||
|
||||
try {
|
||||
navController.navigate(R.id.transactionResultFragment);
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Navigation error: " + e.getMessage());
|
||||
}
|
||||
|
||||
// If QR also exists, trigger it AFTER POS result is done
|
||||
if (hasQR) {
|
||||
navigateToQRSettlementAfterPOS(intent);
|
||||
}
|
||||
} else {
|
||||
|
||||
// POS had no data, go straight to QR if available
|
||||
if (hasQR) {
|
||||
handleQRSettlement(intent);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// Handle QR auto settlement
|
||||
boolean autoQR = intent.getBooleanExtra("AUTO_QR_SETTLEMENT", false);
|
||||
if (autoQR) {
|
||||
} else if (hasQR) {
|
||||
// Only QR settlement, no POS
|
||||
handleQRSettlement(intent);
|
||||
}
|
||||
}
|
||||
|
||||
private void navigateToQRSettlementAfterPOS(Intent intent) {
|
||||
// Observe transactionResultFragment's completion via ViewModel
|
||||
// When POS result screen signals "done" (print complete / user dismissed),
|
||||
// then navigate to QR result
|
||||
sharedViewModel.onSettlementResultDone.observe(this, new Observer<Boolean>() {
|
||||
@Override
|
||||
public void onChanged(Boolean done) {
|
||||
if (done != null && done) {
|
||||
// Remove observer so it only fires once
|
||||
sharedViewModel.onSettlementResultDone.removeObserver(this);
|
||||
// Reset flag
|
||||
sharedViewModel.onSettlementResultDone.postValue(false);
|
||||
// Now navigate to QR
|
||||
handleQRSettlement(intent);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void handleQRSettlement(Intent intent) {
|
||||
int qrSaleCount = intent.getIntExtra("QR_SALE_COUNT", 0);
|
||||
long qrSaleAmount = intent.getLongExtra("QR_SALE_AMOUNT", 0L);
|
||||
int qrRefundCount = intent.getIntExtra("QR_REFUND_COUNT", 0);
|
||||
@ -481,7 +533,6 @@ public class MainActivity extends AppCompatActivity implements
|
||||
long totalAmount = intent.getLongExtra("QR_TOTAL_AMOUNT", 0L);
|
||||
List<PayDetail> qrTransList = (List<PayDetail>) intent.getSerializableExtra("QR_TRANS_LIST");
|
||||
|
||||
// Create QR settlement PayDetail
|
||||
SettleData settleData = new SettleData(
|
||||
qrSaleCount, qrSaleAmount, 0, 0L, qrRefundCount, qrRefundAmount, 0, 0L);
|
||||
|
||||
@ -493,7 +544,6 @@ public class MainActivity extends AppCompatActivity implements
|
||||
payDetail.setAmount(totalAmount);
|
||||
payDetail.setTradeAnswerCode("000");
|
||||
|
||||
|
||||
sharedViewModel.setAmount(POSUtil.getInstance().getDecimalAmountSeparatorFormat(totalAmount));
|
||||
sharedViewModel.payDetails.setValue(qrTransList);
|
||||
sharedViewModel.payDetail.setValue(payDetail);
|
||||
@ -505,14 +555,10 @@ public class MainActivity extends AppCompatActivity implements
|
||||
LogUtil.e(TAG, "QR Auto Settlement navigation error: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().showNavigationBar();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().enableHomeButton();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().enableTaskButton();
|
||||
// Clean up RxJava disposables
|
||||
compositeDisposable.clear();
|
||||
// Reset screen mode
|
||||
|
||||
@ -29,9 +29,11 @@ import com.denzcoskun.imageslider.constants.ScaleTypes;
|
||||
import com.denzcoskun.imageslider.models.SlideModel;
|
||||
import com.nexgo.oaf.apiv3.emv.AidEntity;
|
||||
import com.nexgo.oaf.apiv3.emv.CapkEntity;
|
||||
import com.pos.connection.bridge.binder.ECRConstant;
|
||||
//import com.pos.connection.bridge.binder.ECRConstant;
|
||||
|
||||
import com.utsmm.kbz.util.MockData;
|
||||
//import com.utsmm.kbz.util.ecr.ModernECRFactory;
|
||||
//import com.utsmm.kbz.util.ecr.ModernECRManager;
|
||||
import com.utsmyanmar.baselib.BaseApplication;
|
||||
import com.utsmyanmar.baselib.emv.EmvParamOperation;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
@ -63,6 +65,7 @@ import com.utsmm.kbz.ui.core_viewmodel.TMSProcessViewModel;
|
||||
import com.utsmm.kbz.util.Connectivity;
|
||||
|
||||
|
||||
import com.utsmm.kbz.util.CurrencySelectionHelper;
|
||||
import com.utsmm.kbz.util.dialog.AlertXDialog;
|
||||
import com.utsmm.kbz.util.enums.SettlementType;
|
||||
import com.utsmm.kbz.util.ecr.CoreUtils;
|
||||
@ -112,6 +115,7 @@ public class MainFragment extends DataBindingFragment {
|
||||
private String cardPrimaryIp = "";
|
||||
private String cardPrimarySecIp = "";
|
||||
private CurrencyType cardPrimaryCurrency = CurrencyType.MMK;
|
||||
private CurrencySelectionHelper currencySelectionHelper;
|
||||
|
||||
@Inject
|
||||
EmvParamOperation emvParamOperation;
|
||||
@ -136,6 +140,7 @@ public class MainFragment extends DataBindingFragment {
|
||||
sharedViewModel = getFragmentScopeViewModel(SharedViewModel.class);
|
||||
mainViewModel = getFragmentScopeViewModel(MainViewModel.class);
|
||||
tmsProcessViewModel = getFragmentScopeViewModel(TMSProcessViewModel.class);
|
||||
currencySelectionHelper = new CurrencySelectionHelper(this, sharedViewModel);
|
||||
|
||||
// Initialize ModernECRManager
|
||||
// ModernECRFactory factory = new ModernECRFactory(requireContext(), sharedViewModel);
|
||||
@ -170,9 +175,7 @@ public class MainFragment extends DataBindingFragment {
|
||||
NexGoSDK.getInstance().cancelCheckCard();
|
||||
NexGoSDK.getInstance().closeReader();
|
||||
enableHomeButton();
|
||||
// disableTaskButton();
|
||||
// BaseApplication.getInstance().deviceEngine.getPlatform().hideNavigationBar();
|
||||
BaseApplication.getInstance().deviceEngine.getPlatform().showNavigationBar();
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
@ -262,7 +265,7 @@ public class MainFragment extends DataBindingFragment {
|
||||
sharedViewModel.setManualEntryStatus(SystemParamsOperation.getInstance().getManualEntryStatus());
|
||||
|
||||
// queryAidCAPKList();
|
||||
queryAidCAPKList();
|
||||
// queryAidCAPKList();
|
||||
// generateMockQR();
|
||||
}
|
||||
|
||||
@ -281,16 +284,21 @@ public class MainFragment extends DataBindingFragment {
|
||||
LogUtil.d(TAG, "Total CAPK :" + noCAPK);
|
||||
for (CapkEntity capkEntity : capkList) {
|
||||
LogUtil.d(TAG, "CAPK Entity :" + capkEntity.getRid());
|
||||
if(capkEntity.getRid().equals("A000000003")) {
|
||||
if(capkEntity.getRid().equals("A000000004")) {
|
||||
LogUtil.d(TAG, "CAPK Entity check sum:" + capkEntity.getCheckSum());
|
||||
LogUtil.d(TAG, "CAPK Entity modulus:" + capkEntity.getModulus());
|
||||
LogUtil.d(TAG, "CAPK Entity index:" + capkEntity.getCapkIdx());
|
||||
}
|
||||
|
||||
}
|
||||
// for (AidEntity aidEntity : aidList) {
|
||||
// LogUtil.d(TAG, "AID Entity :" + aidEntity.getAid());
|
||||
for (AidEntity aidEntity : aidList) {
|
||||
LogUtil.d(TAG, "AID Entity :" + aidEntity.getAid());
|
||||
// if(aidEntity.getAid().startsWith("A000000003")) {
|
||||
LogUtil.d(TAG, "AID Entity AID:" + aidEntity.getAid());
|
||||
LogUtil.d(TAG, "AID Entity ASI:" + aidEntity.getAsi());
|
||||
LogUtil.d(TAG, "AID Entity Version:" + aidEntity.getAppVerNum());
|
||||
// }
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@ -316,8 +324,8 @@ public class MainFragment extends DataBindingFragment {
|
||||
if (checkECRServiceAppExistOrNot()) {
|
||||
// Initialize Modern ECR Manager
|
||||
// modernECRManager.init();
|
||||
//
|
||||
// // Observe navigation requests
|
||||
////
|
||||
//// // Observe navigation requests
|
||||
// modernECRManager.getNavigationRequest().observe(getViewLifecycleOwner(), destinationId -> {
|
||||
// if (destinationId != null) {
|
||||
// delayFunctionCall(() -> isRouteValidAndNavigateToRoute(destinationId));
|
||||
@ -627,6 +635,16 @@ public class MainFragment extends DataBindingFragment {
|
||||
default:
|
||||
return value;
|
||||
}
|
||||
// currencySelectionHelper.showCardCurrencyChooser(this::startCardSaleFlow);
|
||||
}
|
||||
|
||||
private void showCurrencyChooserForSignOn() {
|
||||
currencySelectionHelper.showCardCurrencyChooser(this::navigateToSignOn);
|
||||
}
|
||||
|
||||
private void navigateToSignOn() {
|
||||
routeId = R.id.action_nav_main_to_nav_sign_on;
|
||||
safeNavigateToRouteId();
|
||||
}
|
||||
|
||||
private void processBatch() {
|
||||
@ -1017,12 +1035,10 @@ public class MainFragment extends DataBindingFragment {
|
||||
showSingleInfoDialog(getResourceString(R.string.txt_please_enable_internet));
|
||||
} else if (SystemParamsOperation.getInstance().isNeedSettlement()) {
|
||||
AlertXDialog.getInstance().showDialog(requireContext(), getResourceString(R.string.title_need_settle), getResourceString(R.string.txt_do_you_want_to_continue), () -> {
|
||||
routeId = R.id.action_nav_main_to_nav_sign_on;
|
||||
safeNavigateToRouteId();
|
||||
showCurrencyChooserForSignOn();
|
||||
});
|
||||
} else {
|
||||
routeId = R.id.action_nav_main_to_nav_sign_on;
|
||||
safeNavigateToRouteId();
|
||||
showCurrencyChooserForSignOn();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -20,6 +20,7 @@ import com.google.gson.Gson;
|
||||
import com.utsmm.kbz.MainActivity;
|
||||
|
||||
import com.utsmm.kbz.util.EReceiptUtil;
|
||||
import com.utsmm.kbz.util.enums.TransactionStatus;
|
||||
import com.utsmyanmar.baselib.network.model.e_receipt.EReceiptRequest;
|
||||
import com.utsmyanmar.baselib.repo.Repository;
|
||||
import com.utsmm.kbz.BuildConfig;
|
||||
@ -34,6 +35,8 @@ import io.reactivex.rxjava3.schedulers.Schedulers;
|
||||
import retrofit2.HttpException;
|
||||
|
||||
import com.utsmyanmar.paylibs.Constant;
|
||||
import com.utsmyanmar.paylibs.batch_upload.BatchListener;
|
||||
import com.utsmyanmar.paylibs.batch_upload.BatchUploadProcess;
|
||||
import com.utsmyanmar.paylibs.isobuilder.ISOMode;
|
||||
import com.utsmyanmar.paylibs.isobuilder.builderx.ISOMsgX;
|
||||
import com.utsmyanmar.paylibs.isobuilder.builderx.ISOVersion;
|
||||
@ -44,6 +47,8 @@ import com.utsmyanmar.paylibs.model.SettleData;
|
||||
import com.utsmyanmar.paylibs.model.TradeData;
|
||||
import com.utsmyanmar.paylibs.network.ISOCallback;
|
||||
import com.utsmyanmar.paylibs.network.ISOSocket;
|
||||
import com.utsmyanmar.paylibs.sign_on.EchoTestProcess;
|
||||
import com.utsmyanmar.paylibs.sign_on.SignOnListener;
|
||||
import com.utsmyanmar.paylibs.utils.LogUtil;
|
||||
import com.utsmyanmar.paylibs.utils.MessageType;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
@ -74,14 +79,25 @@ public class AutoSettleService extends Service {
|
||||
private boolean regularSettlementCompleted = false;
|
||||
private boolean qrSettlementCompleted = false;
|
||||
|
||||
// Observers to keep reference for cleanup
|
||||
private Observer<java.util.List<com.utsmyanmar.paylibs.model.PayDetail>> regularSettlementObserver;
|
||||
private Observer<java.util.List<com.utsmyanmar.paylibs.model.PayDetail>> qrSettlementObserver;
|
||||
private boolean posHasData = false; // true = POS actually ran and has result
|
||||
private boolean qrHasData = false; // true = QR actually ran and has result
|
||||
|
||||
// Observers to keep reference for cleanup
|
||||
private Observer<List<PayDetail>> regularSettlementObserver;
|
||||
private Observer<List<PayDetail>> qrSettlementObserver;
|
||||
|
||||
private int i = 0;
|
||||
|
||||
private boolean flag = false;
|
||||
@Inject
|
||||
Repository repository;
|
||||
|
||||
private PayDetail pendingPayDetail = null;
|
||||
private Bundle pendingQrData = null;
|
||||
|
||||
private boolean posSettlementReady = false;
|
||||
private boolean qrSettlementReady = false;
|
||||
ArrayList<PayDetail> payDetails = new ArrayList<>();
|
||||
|
||||
public static final String NOTIFICATION_CHANNEL_ID = "10001";
|
||||
private final static String default_notification_channel_id = "default";
|
||||
@ -188,6 +204,10 @@ public class AutoSettleService extends Service {
|
||||
if (regularSettlementCompleted) {
|
||||
return;
|
||||
}
|
||||
|
||||
payDetails.clear();
|
||||
payDetails.addAll(list);
|
||||
|
||||
regularSettlementCompleted = true;
|
||||
|
||||
repository.getSettlementPOS().removeObserver(this);
|
||||
@ -225,7 +245,13 @@ public class AutoSettleService extends Service {
|
||||
String bitmap = BitmapConfig.BPC_SETTLEMENT;
|
||||
payDetail.setTransType(TransactionsType.SETTLEMENT.name);
|
||||
payDetail.setTransactionType(TransactionType.SETTLEMENT);
|
||||
if(!flag) {
|
||||
payDetail.setProcessCode(TransactionsType.SETTLEMENT.processCode);
|
||||
} else {
|
||||
bitmap = BitmapConfig.BPC_SETTLEMENT_TRAILER;
|
||||
payDetail.setProcessCode("910000");
|
||||
}
|
||||
|
||||
payDetail.setBatchNo(SystemParamsOperation.getInstance().getCurrentBatchNum());
|
||||
|
||||
SettleData settleData = new SettleData(
|
||||
@ -245,6 +271,14 @@ public class AutoSettleService extends Service {
|
||||
} else {
|
||||
settlementData = "C" + String.format(Locale.getDefault(), "%012d", totalAmount);
|
||||
}
|
||||
|
||||
if(totalAmount == 0 && (saleCount == 0 || preCount == 0 || refundCount == 0 || caCount == 0)) {
|
||||
posSettlementReady = true;
|
||||
posHasData = false;
|
||||
checkAndLaunch();
|
||||
checkIfBothSettlementsComplete();
|
||||
return;
|
||||
}
|
||||
payDetail.setSettleData(settlementData);
|
||||
payDetail.setAmount(totalAmount);
|
||||
|
||||
@ -269,7 +303,7 @@ public class AutoSettleService extends Service {
|
||||
if (TextUtils.equals(resultStr, Constant.ANSWER_CODE_ACCEPT) || TextUtils.equals(resultStr, Constant.ANSWER_CODE_APPROVED)) {
|
||||
payDetail.setIsNeedReversal(false);
|
||||
} else if (TextUtils.equals(resultStr, "95") || TextUtils.equals(resultStr, "095")) {
|
||||
payDetail.setIsNeedReversal(true);
|
||||
payDetail.setIsNeedReversal(!flag);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -284,34 +318,25 @@ public class AutoSettleService extends Service {
|
||||
public void onComplete() {
|
||||
LogUtil.d(TAG, "Auto settlement transaction completed successfully");
|
||||
|
||||
if (list != null && !list.isEmpty()) {
|
||||
if(payDetail.getIsNeedReversal()) {
|
||||
flag = true;
|
||||
batchUploadProcess();
|
||||
} else {
|
||||
|
||||
flag = false;
|
||||
|
||||
if (!list.isEmpty()) {
|
||||
for (PayDetail p : list) {
|
||||
repository.deletePayDetail(p);
|
||||
}
|
||||
}
|
||||
repository.insertPayDetail(payDetail);
|
||||
|
||||
try {
|
||||
PayDetail cleanPayDetail = new PayDetail();
|
||||
cleanPayDetail.setTransType(payDetail.getTransType());
|
||||
cleanPayDetail.setTransactionType(payDetail.getTransactionType());
|
||||
cleanPayDetail.setProcessCode(payDetail.getProcessCode());
|
||||
cleanPayDetail.setBatchNo(payDetail.getBatchNo());
|
||||
cleanPayDetail.setSettleData(payDetail.getSettleData());
|
||||
cleanPayDetail.setAmount(payDetail.getAmount());
|
||||
cleanPayDetail.setTradeAnswerCode(payDetail.getTradeAnswerCode());
|
||||
cleanPayDetail.setIsNeedReversal(payDetail.getIsNeedReversal());
|
||||
networkCutOver(payDetail);
|
||||
|
||||
// Use notification-based approach to reliably launch the app
|
||||
launchAppWithSettlementResult("AUTO_SETTLEMENT", cleanPayDetail, null);
|
||||
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Error launching app with settlement result: " + e.getMessage());
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
checkIfBothSettlementsComplete();
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
@ -319,6 +344,41 @@ public class AutoSettleService extends Service {
|
||||
repository.getSettlementPOS().observeForever(regularSettlementObserver);
|
||||
}
|
||||
|
||||
private void batchUploadProcess() {
|
||||
|
||||
if(payDetails == null || payDetails.isEmpty()){
|
||||
regularSettlementCompleted = false;
|
||||
performSettlement();
|
||||
return;
|
||||
}
|
||||
|
||||
PayDetail payDetail = payDetails.get(i);
|
||||
TradeData tradeData = new TradeData();
|
||||
tradeData.setPayDetail(payDetail);
|
||||
BatchUploadProcess.getInstance().enqueue(tradeData).startBatchUpload(new BatchListener() {
|
||||
@Override
|
||||
public void onSuccessBatch() {
|
||||
|
||||
if (i < payDetails.size() - 1) {
|
||||
LogUtil.d(TAG, "Pay detail Size:" + payDetails.size());
|
||||
LogUtil.d(TAG, "Count value:" + i);
|
||||
i++;
|
||||
batchUploadProcess();
|
||||
} else {
|
||||
regularSettlementCompleted = false;
|
||||
performSettlement();
|
||||
}
|
||||
|
||||
LogUtil.e(TAG, "Batch Upload Success");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailBatch() {
|
||||
LogUtil.e(TAG, "Batch Upload Fail");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void performQRSettlement() {
|
||||
if (qrSettlementCompleted) {
|
||||
return;
|
||||
@ -365,6 +425,9 @@ public class AutoSettleService extends Service {
|
||||
}
|
||||
} catch (IllegalStateException e) {
|
||||
LogUtil.e(TAG, "QR Auto Settlement: Database cursor error - likely due to large data size: " + e);
|
||||
qrSettlementReady = true;
|
||||
qrHasData = false;
|
||||
checkAndLaunch();
|
||||
checkIfBothSettlementsComplete();
|
||||
return;
|
||||
}
|
||||
@ -422,19 +485,24 @@ public class AutoSettleService extends Service {
|
||||
qrData.putLong("QR_TOTAL_AMOUNT", totalAmount);
|
||||
qrData.putSerializable("QR_TRANS_LIST", qrTransactionsList);
|
||||
// Use notification-based approach to reliably launch the app
|
||||
launchAppWithSettlementResult("AUTO_QR_SETTLEMENT", null, qrData);
|
||||
pendingQrData = qrData;
|
||||
qrHasData = true;
|
||||
// launchAppWithSettlementResult("AUTO_QR_SETTLEMENT", null, qrData,false);
|
||||
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Error launching app for QR settlement: " + e.getMessage());
|
||||
qrHasData = false;
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
LogUtil.d(TAG, "QR Auto Settlement completed successfully");
|
||||
} else {
|
||||
LogUtil.d(TAG, "No QR transactions found for auto settlement");
|
||||
qrHasData = false;
|
||||
}
|
||||
}
|
||||
|
||||
qrSettlementReady = true;
|
||||
checkAndLaunch();
|
||||
checkIfBothSettlementsComplete();
|
||||
}
|
||||
};
|
||||
@ -480,19 +548,75 @@ public class AutoSettleService extends Service {
|
||||
|
||||
}
|
||||
|
||||
private void launchAppWithSettlementResult(String settlementType,
|
||||
PayDetail payDetail,
|
||||
Bundle qrData) {
|
||||
private void networkCutOver(PayDetail payDetail) {
|
||||
EchoTestProcess.getInstance().enqueueCutOver().startSignOn(new SignOnListener() {
|
||||
@Override
|
||||
public void onSuccessSignOn() {
|
||||
|
||||
pendingPayDetail = payDetail;
|
||||
posHasData = true;
|
||||
posSettlementReady = true;
|
||||
checkAndLaunch();
|
||||
checkIfBothSettlementsComplete();
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailureSignOn(Integer resultCode) {
|
||||
LogUtil.d(TAG,"Failure Cut Over message: "+resultCode);
|
||||
// POS done but cutover failed — still mark ready
|
||||
posSettlementReady = true;
|
||||
posHasData = false;
|
||||
checkAndLaunch();
|
||||
checkIfBothSettlementsComplete();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNetworkFailSignOn(String message) {
|
||||
LogUtil.d(TAG,"Network Fail Cut Over message: "+message);
|
||||
posSettlementReady = true;
|
||||
posHasData = false;
|
||||
checkAndLaunch();
|
||||
checkIfBothSettlementsComplete();
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void checkAndLaunch() {
|
||||
// !!!! need to add flag, if don't want both at once
|
||||
if (!posSettlementReady || !qrSettlementReady) {
|
||||
LogUtil.d(TAG, "Waiting for both settlements... POS=" + posSettlementReady + " QR=" + qrSettlementReady);
|
||||
return;
|
||||
}
|
||||
|
||||
LogUtil.d(TAG, "Both settlements ready. POS has data=" + posHasData + ", QR has data=" + qrHasData);
|
||||
|
||||
if (!posHasData && !qrHasData) {
|
||||
LogUtil.d(TAG, "No settlement data to display");
|
||||
return;
|
||||
}
|
||||
|
||||
launchMainActivity();
|
||||
}
|
||||
|
||||
private void launchMainActivity() {
|
||||
try {
|
||||
Intent launchIntent = new Intent(this, MainActivity.class);
|
||||
launchIntent.putExtra(settlementType, true);
|
||||
launchIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
|
||||
Intent.FLAG_ACTIVITY_CLEAR_TOP |
|
||||
Intent.FLAG_ACTIVITY_SINGLE_TOP);
|
||||
|
||||
if ("AUTO_SETTLEMENT".equals(settlementType) && payDetail != null) {
|
||||
if (posHasData && pendingPayDetail != null) {
|
||||
launchIntent.putExtra("AUTO_SETTLEMENT", true);
|
||||
launchIntent.putExtra("EXTRA_TRANSACTION_TYPE", TransactionsType.SETTLEMENT.value);
|
||||
launchIntent.putExtra("EXTRA_PAY_DETAIL", payDetail);
|
||||
} else if ("AUTO_QR_SETTLEMENT".equals(settlementType) && qrData != null) {
|
||||
launchIntent.putExtra("EXTRA_TRANSACTION_TYPE", TransactionsType.MMQR_SETTLEMENT.value);
|
||||
launchIntent.putExtras(qrData);
|
||||
launchIntent.putExtra("EXTRA_PAY_DETAIL", pendingPayDetail);
|
||||
}
|
||||
|
||||
if (qrHasData && pendingQrData != null) {
|
||||
launchIntent.putExtra("AUTO_QR_SETTLEMENT", true);
|
||||
launchIntent.putExtra("EXTRA_QR_TRANSACTION_TYPE", TransactionsType.MMQR_SETTLEMENT.value);
|
||||
launchIntent.putExtras(pendingQrData);
|
||||
}
|
||||
|
||||
PendingIntent pendingIntent = PendingIntent.getActivity(
|
||||
@ -503,13 +627,9 @@ public class AutoSettleService extends Service {
|
||||
);
|
||||
|
||||
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
|
||||
|
||||
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
|
||||
NotificationChannel channel = new NotificationChannel(
|
||||
"SETTLEMENT_COMPLETE",
|
||||
"Settlement Complete",
|
||||
NotificationManager.IMPORTANCE_HIGH
|
||||
);
|
||||
"SETTLEMENT_COMPLETE", "Settlement Complete", NotificationManager.IMPORTANCE_HIGH);
|
||||
channel.setDescription("Auto settlement completion notifications");
|
||||
notificationManager.createNotificationChannel(channel);
|
||||
}
|
||||
@ -524,25 +644,24 @@ public class AutoSettleService extends Service {
|
||||
.setFullScreenIntent(pendingIntent, true);
|
||||
notificationManager.notify(2001, builder.build());
|
||||
|
||||
LogUtil.d(TAG, " Settlement complete notification created - will launch app when tapped");
|
||||
// Reset state
|
||||
pendingPayDetail = null;
|
||||
pendingQrData = null;
|
||||
posSettlementReady = false;
|
||||
qrSettlementReady = false;
|
||||
posHasData = false;
|
||||
qrHasData = false;
|
||||
|
||||
try {
|
||||
launchIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
|
||||
Intent.FLAG_ACTIVITY_CLEAR_TOP |
|
||||
Intent.FLAG_ACTIVITY_SINGLE_TOP |
|
||||
Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT |
|
||||
Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
|
||||
startActivity(launchIntent);
|
||||
} catch (Exception directException) {
|
||||
LogUtil.d(TAG, "Direct launch failed (expected on modern Android), notification approach will handle it");
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Error creating settlement notification: " + e.getMessage());
|
||||
LogUtil.e(TAG, "Error launching MainActivity: " + e.getMessage());
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
private void sendEReceipt(EReceiptRequest request) {
|
||||
try {
|
||||
LogUtil.d(TAG, "Sending e-receipt: " + new Gson().toJson(request));
|
||||
|
||||
@ -13,6 +13,7 @@ import androidx.navigation.Navigation;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.stream.MalformedJsonException;
|
||||
import com.utsmm.kbz.MainActivity;
|
||||
import com.utsmm.kbz.config.Constants;
|
||||
import com.nexgo.downloadkey.downloadflow.DownloadFEntity;
|
||||
import com.nexgo.downloadkey.downloadflow.DownloadFlow;
|
||||
@ -162,6 +163,10 @@ public class SettingsFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
private void updateReversalSettings() {
|
||||
boolean isVisible = SystemParamsOperation.getInstance().getAutoReversalEnable();
|
||||
LogUtil.d("SettingsFragment", "isVisible " + isVisible);
|
||||
binding.reversalCard.setVisibility(isVisible ? View.VISIBLE : View.GONE);
|
||||
|
||||
boolean isEnabled = SystemParamsOperation.getInstance().isReversalOn();
|
||||
binding.reversalSwitch.setChecked(isEnabled);
|
||||
binding.reversalSummary.setText(isEnabled ?
|
||||
@ -327,6 +332,17 @@ public class SettingsFragment extends DataBindingFragment {
|
||||
}
|
||||
}
|
||||
|
||||
public void onClearReversalClick() {
|
||||
try {
|
||||
sharedViewModel.transactionsType.postValue(TransactionsType.CLEAR_REVERSAL);
|
||||
sharedViewModel.setTransMenu(TransMenu.CLEAR_REVERSAL);
|
||||
Navigation.findNavController(requireActivity(), R.id.nav_host_fragment)
|
||||
.navigate(R.id.inputPasswordFragment);
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Error in clear reversal click: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
public void onTmsConfigClick() {
|
||||
try {
|
||||
LogUtil.d(TAG, "TMS Config clicked");
|
||||
@ -393,6 +409,9 @@ public class SettingsFragment extends DataBindingFragment {
|
||||
private void downloadParams(String lastTransName, String lastTransTime) {
|
||||
try {
|
||||
LogUtil.d(TAG, "Downloading params for transaction: " + lastTransName);
|
||||
|
||||
((MainActivity) requireActivity()).getLocation();
|
||||
|
||||
SiriusRequest siriusReq = TMSUtil.getInstance().generateRequestParams(getContext(), lastTransName, lastTransTime);
|
||||
|
||||
mainViewModel.getParams(siriusReq)
|
||||
|
||||
@ -151,6 +151,12 @@ public class CardWaitingFragment extends DataBindingFragment implements DataBind
|
||||
}else if(sharedViewModel.getIsSeePhone().getValue() != null && sharedViewModel.getIsSeePhone().getValue()) {
|
||||
cardReadViewModel.setCheckCardAlertMsg("Please Tap!",false);
|
||||
setupCardReadProcess(true);
|
||||
} else if(sharedViewModel.getIsCardAppBlock().getValue() != null && sharedViewModel.getIsCardAppBlock().getValue()) {
|
||||
cardReadViewModel.setCheckCardAlertMsg("Magstripe not allowed!",false);
|
||||
setupCardReadProcess(true);
|
||||
} else if(sharedViewModel.getIsContactlessRestricted().getValue() != null && sharedViewModel.getIsContactlessRestricted().getValue()) {
|
||||
cardReadViewModel.setCheckCardAlertMsg("Tap not allowed!",false);
|
||||
setupCardReadProcess(true);
|
||||
} else {
|
||||
setupCardReadProcess(false);
|
||||
}
|
||||
@ -163,6 +169,7 @@ public class CardWaitingFragment extends DataBindingFragment implements DataBind
|
||||
|
||||
sharedViewModel.setIsFallback(false);
|
||||
sharedViewModel.setIsSeePhone(false);
|
||||
sharedViewModel.setIsContactlessRestricted(false);
|
||||
|
||||
// cardReadViewModel.cancelCheckCard();
|
||||
|
||||
@ -256,9 +263,20 @@ public class CardWaitingFragment extends DataBindingFragment implements DataBind
|
||||
if(sharedViewModel.getIsSeePhone().getValue() != null && sharedViewModel.getIsSeePhone().getValue()) {
|
||||
allType.add(CardSlotTypeEnum.RF);
|
||||
waitTimeout = 20;
|
||||
} else if(!SystemParamsOperation.getInstance().isNfcEnabled()) {
|
||||
allType.add(CardSlotTypeEnum.ICC1);
|
||||
allType.add(CardSlotTypeEnum.SWIPE);
|
||||
} else if(sharedViewModel.getIsContactlessRestricted().getValue() != null && sharedViewModel.getIsContactlessRestricted().getValue()) {
|
||||
allType.add(CardSlotTypeEnum.ICC1);
|
||||
// allType.add(CardSlotTypeEnum.SWIPE);
|
||||
} else {
|
||||
allType.add(CardSlotTypeEnum.ICC1);
|
||||
allType.add(CardSlotTypeEnum.RF);
|
||||
|
||||
if(SystemParamsOperation.getInstance().isMagStripeEnabled()) {
|
||||
allType.add(CardSlotTypeEnum.SWIPE);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// int allType = AidlConstants.CardType.IC.getValue() | AidlConstants.CardType.MAGNETIC.getValue();
|
||||
@ -286,7 +304,7 @@ public class CardWaitingFragment extends DataBindingFragment implements DataBind
|
||||
|
||||
} else if (isFallback && cardType == CardTypeX.MAG) {
|
||||
/* do fallback transactions */
|
||||
sharedViewModel.isEmv.setValue(false);
|
||||
sharedViewModel.isEmv.postValue(false);
|
||||
cardReadViewModel.setCardTransactionType(CardTransactionType.FALLBACK);
|
||||
|
||||
} else if (cardType == CardTypeX.IC || cardType == CardTypeX.NFC) {
|
||||
|
||||
@ -246,7 +246,6 @@ public class ConfirmTransactionFragment extends DataBindingFragment implements D
|
||||
public void onConfirm(){
|
||||
|
||||
if (sharedViewModel.transactionsType.getValue() == TransactionsType.TIP_ADJUSTMENT) {
|
||||
|
||||
routeId = R.id.action_confirmTransactionFragment_to_inputTipAmountFragment;
|
||||
safeNavigateToRouteId();
|
||||
|
||||
|
||||
@ -3,6 +3,7 @@ package com.utsmm.kbz.ui.core_ui;
|
||||
import android.os.Bundle;
|
||||
import android.text.TextUtils;
|
||||
import android.view.View;
|
||||
import android.widget.Toast;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
@ -158,6 +159,7 @@ public class EmvTransactionFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
observeEmvResultStatus();
|
||||
observePinWarning();
|
||||
}
|
||||
|
||||
private boolean isNotManualTransaction() {
|
||||
@ -230,7 +232,19 @@ public class EmvTransactionFragment extends DataBindingFragment {
|
||||
case ON_NEXT_SCREEN:
|
||||
navigateToRRNScreen();
|
||||
break;
|
||||
case INSERT_OR_MANUAL:
|
||||
if(cardReadViewModel.cardTypeData.getValue() != null && cardReadViewModel.cardTypeData.getValue() == CardTypeX.NFC.value) {
|
||||
isCardTaped("Please insert or type card",new CardDetectCallback() {
|
||||
@Override
|
||||
public void onComplete() {
|
||||
sharedViewModel.setIsContactlessRestricted(true);
|
||||
navigateToCheckCard();
|
||||
}
|
||||
});
|
||||
}
|
||||
break;
|
||||
case READ_CARD_RETRY:
|
||||
LogUtil.d(TAG,"Card type :"+cardReadViewModel.cardTypeData.getValue());
|
||||
if(cardReadViewModel.cardTypeData.getValue()!= null && cardReadViewModel.cardTypeData.getValue() == CardTypeX.IC.value) {
|
||||
isCardInserted(new CardDetectCallback() {
|
||||
@Override
|
||||
@ -243,12 +257,30 @@ public class EmvTransactionFragment extends DataBindingFragment {
|
||||
isCardTaped("Please try again",new CardDetectCallback() {
|
||||
@Override
|
||||
public void onComplete() {
|
||||
sharedViewModel.setIsSeePhone(true);
|
||||
sharedViewModel.setIsSeePhone(false);
|
||||
navigateToCheckCard();
|
||||
}
|
||||
});
|
||||
}
|
||||
break;
|
||||
case CARD_APP_BLOCKED:
|
||||
if(cardReadViewModel.cardTypeData.getValue()!= null && cardReadViewModel.cardTypeData.getValue() == CardTypeX.IC.value) {
|
||||
isCardInserted(new CardDetectCallback() {
|
||||
@Override
|
||||
public void onComplete() {
|
||||
sharedViewModel.setIsCardAppBlock(true);
|
||||
navigateToCheckCard();
|
||||
}
|
||||
});
|
||||
} else if(cardReadViewModel.cardTypeData.getValue() != null && cardReadViewModel.cardTypeData.getValue() == CardTypeX.NFC.value) {
|
||||
isCardTaped("Please try again",new CardDetectCallback() {
|
||||
@Override
|
||||
public void onComplete() {
|
||||
sharedViewModel.setIsCardAppBlock(true);
|
||||
navigateToCheckCard();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// sharedViewModel.set_errorFragmentMsg("Interface not found!");
|
||||
// navigateToError();
|
||||
break;
|
||||
@ -330,6 +362,15 @@ public class EmvTransactionFragment extends DataBindingFragment {
|
||||
});
|
||||
}
|
||||
|
||||
private void observePinWarning() {
|
||||
emvTransactionViewModel.pinRemainingCount.observe(getViewLifecycleOwner(), msg -> {
|
||||
if (!TextUtils.isEmpty(msg)) {
|
||||
Toast.makeText(requireContext(), msg, Toast.LENGTH_SHORT).show();
|
||||
emvTransactionViewModel.pinRemainingCount.setValue("");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void observeEmvErrorCode() {
|
||||
dismissLoadingDialog();
|
||||
emvTransactionViewModel.errorCodeMsg.observe(getViewLifecycleOwner(), pair -> {
|
||||
|
||||
@ -201,7 +201,7 @@ public class InputRRNFragment extends DataBindingFragment {
|
||||
|
||||
private void checkRRNPreAuthVoid(boolean isECR) {
|
||||
|
||||
rrnViewModel.searchPayDetail(cardNo,rrnNo).observe(getViewLifecycleOwner(), new Observer<PayDetail>() {
|
||||
rrnViewModel.searchPayDetailPreCancel(cardNo,rrnNo).observe(getViewLifecycleOwner(), new Observer<PayDetail>() {
|
||||
@Override
|
||||
public void onChanged(PayDetail payDetail) {
|
||||
if(payDetail != null) {
|
||||
@ -245,6 +245,8 @@ public class InputRRNFragment extends DataBindingFragment {
|
||||
|
||||
} else {
|
||||
|
||||
LogUtil.d(TAG,"PreAuth Cancel RRN not found!");
|
||||
|
||||
terminateProcess(isECR);
|
||||
|
||||
}
|
||||
@ -551,16 +553,16 @@ public class InputRRNFragment extends DataBindingFragment {
|
||||
// }
|
||||
|
||||
} else {
|
||||
terminatedTransRefund(isECR);
|
||||
// terminatedTransRefund(isECR);
|
||||
|
||||
// PayDetail newPay = transProcessViewModel.getPayDetail();
|
||||
// newPay.setReferNo(rrnNo);
|
||||
//
|
||||
// transProcessViewModel.setPayDetail(newPay);
|
||||
//
|
||||
// sharedViewModel.rrNNo.setValue(rrnNo);
|
||||
//
|
||||
// callNextScreen();
|
||||
PayDetail newPay = transProcessViewModel.getPayDetail();
|
||||
newPay.setReferNo(rrnNo);
|
||||
|
||||
transProcessViewModel.setPayDetail(newPay);
|
||||
|
||||
sharedViewModel.rrNNo.setValue(rrnNo);
|
||||
|
||||
callNextScreen();
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@ -173,6 +173,7 @@ public class InputTraceNoFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
sharedViewModel.payDetail.setValue(payDetail);
|
||||
sharedViewModel.setAmount(POSUtil.getInstance().getDecimalAmountSeparatorFormat(payDetail.getAmount()));
|
||||
|
||||
if(sharedViewModel.hostType.getValue() == HostType.MPU) {
|
||||
boolean isMpu = "MPU".equals(payDetail.getAccountType());
|
||||
|
||||
@ -131,6 +131,7 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
}
|
||||
private void mockMPUCard() {
|
||||
LogUtil.d(TAG,"initialize mock card data...");
|
||||
sharedViewModel.isEmv.setValue(false);
|
||||
routeId = R.id.action_processingCardFragment_to_pinPadFragment;
|
||||
transProcessViewModel.transType.setValue(sharedViewModel.transactionsType.getValue());
|
||||
pinPadViewModel.transType.setValue(sharedViewModel.transactionsType.getValue());
|
||||
@ -159,6 +160,7 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
return;
|
||||
}
|
||||
}
|
||||
sharedViewModel.isEmv.setValue(false);
|
||||
|
||||
routeId = R.id.action_processingCardFragment_to_pinPadFragment;
|
||||
transProcessViewModel.transType.setValue(sharedViewModel.transactionsType.getValue());
|
||||
@ -168,12 +170,29 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
transProcessViewModel.setTradeData(tradeData);
|
||||
pinPadViewModel.setTradeData(tradeData);
|
||||
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_VOID ) {
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_VOID && SystemParamsOperation.getInstance().getPreAuthVoidManualEnabled() ) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
safeNavigateToRouteId();
|
||||
return;
|
||||
|
||||
}
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_SALE && SystemParamsOperation.getInstance().getPreAuthManualEnabled()) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
safeNavigateToRouteId();
|
||||
return;
|
||||
|
||||
}
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_COMPLETE && SystemParamsOperation.getInstance().getPreAuthCompleteManualEnabled()) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
safeNavigateToRouteId();
|
||||
return;
|
||||
|
||||
}
|
||||
// else if(sharedViewModel.transactionsType.getValue() == TransactionsType.REFUND) {
|
||||
// sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_card_not_supported));
|
||||
@ -183,7 +202,9 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
|
||||
sharedViewModel.setCardDataExist(true);
|
||||
|
||||
if(sharedViewModel.getAmountExist().getValue() != null && !sharedViewModel.getAmountExist().getValue()) {
|
||||
if(sharedViewModel.getTransMenu().getValue() != TransMenu.PRE_AUTH_FULL_VOID
|
||||
&& sharedViewModel.getAmountExist().getValue() != null
|
||||
&& !sharedViewModel.getAmountExist().getValue()) {
|
||||
routeId = R.id.action_processingCardFragment_to_inputAmountFragment;
|
||||
}
|
||||
|
||||
@ -238,13 +259,28 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
transProcessViewModel.setTradeData(tradeData);
|
||||
}
|
||||
|
||||
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_VOID ) {
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_VOID && SystemParamsOperation.getInstance().getPreAuthVoidManualEnabled() ) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
|
||||
}
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_SALE && SystemParamsOperation.getInstance().getPreAuthManualEnabled()) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
|
||||
|
||||
}
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_COMPLETE && SystemParamsOperation.getInstance().getPreAuthCompleteManualEnabled()) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
// else if(sharedViewModel.transactionsType.getValue() == TransactionsType.REFUND) {
|
||||
// routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
// }
|
||||
@ -274,8 +310,39 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
emvTransactionViewModel.transType.setValue(sharedViewModel.transactionsType.getValue());
|
||||
|
||||
if (SystemParamsOperation.getInstance().isEmvEnabled()) {
|
||||
|
||||
prepareEmvTransaction();
|
||||
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_VOID && SystemParamsOperation.getInstance().getPreAuthVoidManualEnabled() ) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
safeNavigateToRouteId();
|
||||
return;
|
||||
|
||||
}
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_SALE && SystemParamsOperation.getInstance().getPreAuthManualEnabled()) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
safeNavigateToRouteId();
|
||||
return;
|
||||
|
||||
|
||||
}
|
||||
if(sharedViewModel.getTransactionsType().getValue() == TransactionsType.PRE_AUTH_COMPLETE && SystemParamsOperation.getInstance().getPreAuthCompleteManualEnabled()) {
|
||||
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_alert_pre_auth_cancel));
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
safeNavigateToRouteId();
|
||||
return;
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
routeId = R.id.action_processingCardFragment_to_emvTransactionFragment;
|
||||
|
||||
} else {
|
||||
routeId = R.id.action_processingCardFragment_to_errorFragment;
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_please_enable_emv));
|
||||
@ -307,9 +374,7 @@ public class ProcessingCardFragment extends DataBindingFragment {
|
||||
LogUtil.d(TAG,"card type:"+cardType);
|
||||
LogUtil.d(TAG,"is MPU:"+isMPU);
|
||||
|
||||
// delayFunctionCall(()->{
|
||||
//
|
||||
// });
|
||||
|
||||
handlePreEmvProcess();
|
||||
|
||||
}
|
||||
|
||||
@ -6,6 +6,8 @@ import android.view.View;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.lifecycle.LiveData;
|
||||
import androidx.lifecycle.Observer;
|
||||
import androidx.navigation.NavController;
|
||||
import androidx.navigation.NavDestination;
|
||||
|
||||
@ -17,6 +19,11 @@ import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.network.model.e_receipt.EReceiptRequest;
|
||||
import com.utsmyanmar.baselib.util.DataBindingConfig;
|
||||
import com.utsmyanmar.baselib.util.TimeoutCallback;
|
||||
import com.utsmyanmar.paylibs.model.TradeData;
|
||||
import com.utsmyanmar.paylibs.print.PrintUtils;
|
||||
import com.utsmyanmar.paylibs.reversal.ReversalAction;
|
||||
import com.utsmyanmar.paylibs.reversal.ReversalListener;
|
||||
import com.utsmyanmar.paylibs.system.BaseErrorCode;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
import com.utsmm.kbz.BR;
|
||||
import com.utsmm.kbz.R;
|
||||
@ -104,6 +111,17 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
setToolBarTitleWithoutBackIcon(getResourceString(R.string.title_processing));
|
||||
|
||||
|
||||
checkReversal();
|
||||
|
||||
|
||||
|
||||
// disableNavigationBar();
|
||||
|
||||
getNavController(Constants.NAV_HOST_ID).addOnDestinationChangedListener(listener);
|
||||
|
||||
}
|
||||
|
||||
private void startTransactionProcess() {
|
||||
if(isEmvTrans()) {
|
||||
startTransactionProcess(emvTransactionProcessViewModel);
|
||||
} else {
|
||||
@ -111,13 +129,55 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
sharedViewModel.loadingMsg(getResourceString(R.string.txt_sending));
|
||||
|
||||
// disableNavigationBar();
|
||||
|
||||
getNavController(Constants.NAV_HOST_ID).addOnDestinationChangedListener(listener);
|
||||
|
||||
}
|
||||
|
||||
private void checkReversal() {
|
||||
observeOnce(sharedViewModel.getLastReversalTransaction(), payDetail -> {
|
||||
if (payDetail != null) {
|
||||
TradeData tradeData = new TradeData();
|
||||
tradeData.setPayDetail(payDetail);
|
||||
LogUtil.d(TAG, "Sending Reversal!");
|
||||
sharedViewModel.loadingMsg(getResourceString(R.string.txt_sending_reversal));
|
||||
|
||||
ReversalAction.getInstance().setData(tradeData).enqueue().startReversal(new ReversalListener() {
|
||||
@Override
|
||||
public void onSuccessReversal() {
|
||||
LogUtil.d(TAG, "Reversal Success!");
|
||||
payDetail.setIsNeedReversal(false);
|
||||
sharedViewModel.updatePayDetail(payDetail);
|
||||
delayFunctionCall(()->startTransactionProcess());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onNetworkFail(String msg) {
|
||||
LogUtil.d(TAG, "Reversal Network Fail!" + msg);
|
||||
startTransactionProcess();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailReversal(String msg) {
|
||||
LogUtil.d(TAG, "Reversal Fail!" + msg);
|
||||
startTransactionProcess();
|
||||
}
|
||||
});
|
||||
} else {
|
||||
LogUtil.d(TAG,"No reversal found!");
|
||||
startTransactionProcess();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private <T> void observeOnce(LiveData<T> liveData, Observer<T> observer) {
|
||||
liveData.observe(getViewLifecycleOwner(), new Observer<T>() {
|
||||
@Override
|
||||
public void onChanged(T t) {
|
||||
liveData.removeObserver(this);
|
||||
observer.onChanged(t);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
private boolean isEmvTrans() {
|
||||
return sharedViewModel.isEmv.getValue() != null && sharedViewModel.isEmv.getValue();
|
||||
}
|
||||
@ -258,6 +318,18 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
safeNavigateToRouteId();
|
||||
}
|
||||
|
||||
private void handleAfterTransaction() {
|
||||
if (SystemParamsOperation.getInstance().getDemoStatus()) {
|
||||
delayFunctionCall(() -> {
|
||||
sharedViewModel.dismissLoadingMsg();
|
||||
callNextScreen();
|
||||
}, 1500);
|
||||
} else {
|
||||
sharedViewModel.dismissLoadingMsg();
|
||||
callNextScreen();
|
||||
}
|
||||
}
|
||||
|
||||
private void observeData(ProcessingTransaction processingTransaction) {
|
||||
|
||||
processingTransaction.getTransStatus().observe(getViewLifecycleOwner(), transResultStatus -> {
|
||||
@ -269,9 +341,13 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
|
||||
switch (transResultStatus) {
|
||||
case FAIL:
|
||||
sharedViewModel.pushReceipt(buildEReceiptCardReceipt(payDetail, false, "FAILED"));
|
||||
sharedViewModel.pushReceipt(buildEReceiptCardReceipt(payDetail, false, BaseErrorCode.getCode(payDetail.getTradeAnswerCode())));
|
||||
handleAfterTransaction();
|
||||
break;
|
||||
case SUCCESS:
|
||||
sharedViewModel.pushReceipt(buildEReceiptCardReceipt(payDetail, true, "SUCCESS"));
|
||||
sharedViewModel.pushReceipt(buildEReceiptCardReceipt(payDetail, true, BaseErrorCode.getCode(payDetail.getTradeAnswerCode())));
|
||||
handleAfterTransaction();
|
||||
break;
|
||||
case OFFLINE_SUCCESS:
|
||||
if(SystemParamsOperation.getInstance().getDemoStatus()) {
|
||||
delayFunctionCall(()->{
|
||||
@ -288,6 +364,7 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
|
||||
break;
|
||||
case OFFLINE_FAILURE:
|
||||
sharedViewModel.pushReceipt(buildEReceiptCardReceipt(payDetail, false, BaseErrorCode.getCode(payDetail.getTradeAnswerCode())));
|
||||
sharedViewModel.dismissLoadingMsg();
|
||||
sharedViewModel.set_errorFragmentMsg(getResourceString(R.string.txt_offline_failure));
|
||||
navigateToError();
|
||||
@ -385,20 +462,6 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
private String mapDE3ToShortCode(String de3) {
|
||||
if (de3 == null) return "UNK";
|
||||
|
||||
switch (de3) {
|
||||
case "000000": return "S"; // Sale
|
||||
case "020000": return "V"; // Void
|
||||
case "200000": return "R"; // Refund
|
||||
case "030000": return "P"; // Preauth
|
||||
case "310000": return "PC"; // Preauth Complete
|
||||
}
|
||||
return "UNK"; // Unknown
|
||||
}
|
||||
|
||||
public static String mapTransactionType(int type) {
|
||||
switch (type) {
|
||||
case 1: // SALE
|
||||
@ -450,6 +513,16 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
default: return currency; // Already alphabetic? return as-is
|
||||
}
|
||||
}
|
||||
|
||||
private String formatDE43(String value) {
|
||||
if (value == null) value = "";
|
||||
|
||||
if (value.length() > 40) {
|
||||
return value.substring(0, 40);
|
||||
}
|
||||
|
||||
return String.format("%-40s", value); // right pad with space
|
||||
}
|
||||
private EReceiptCardRequest buildEReceiptCardReceipt(PayDetail payDetail, boolean isSuccess, String reason){
|
||||
//current timestamp
|
||||
String currentTimestamp = new java.text.SimpleDateFormat(
|
||||
@ -468,15 +541,29 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
DecimalFormat df = new DecimalFormat("0.00");
|
||||
String amount = df.format(realAmount);
|
||||
|
||||
String rawName = PrintUtils.getInstance()
|
||||
.getCardHolderName(payDetail.getCardHolderName());
|
||||
|
||||
String secondLine = PrintUtils.getInstance()
|
||||
.processNameSpaceSecondLine(rawName);
|
||||
|
||||
String firstLine = PrintUtils.getInstance()
|
||||
.processNameSpaceFirstLine(rawName, secondLine);
|
||||
|
||||
|
||||
String cardHolderName = firstLine +
|
||||
(secondLine.isEmpty() ? "" : " " + secondLine);
|
||||
|
||||
EReceiptCardRequest request = new EReceiptCardRequest();
|
||||
request.setDE2(payDetail.getCardNo());
|
||||
request.setDE3(mapDE3ToShortCode(payDetail.getProcessCode()));
|
||||
request.setDE2(PrintUtils.getInstance().maskCardNumberPciDss(payDetail.getCardNo()));
|
||||
request.setDE3(mapTransactionType(payDetail.getTransactionType()));
|
||||
request.setDE4(amount);
|
||||
request.setDE7(currentTimestamp);
|
||||
request.setDE11(payDetail.getVoucherNo());
|
||||
request.setDE22(mapTransactionType(payDetail.getTransactionType()));
|
||||
// request.setDE22(mapTransactionType(payDetail.getTransactionType()));
|
||||
request.setDE22(PrintUtils.getInstance().getEntryType(payDetail.getCardType()));
|
||||
request.setDE37(payDetail.getReferNo());
|
||||
request.setDE38(payDetail.getAuthNo());
|
||||
request.setDE38(payDetail.getApprovalCode());
|
||||
request.setDE39(isSuccess ? "A" : "E");
|
||||
request.setDE41(terminalId);
|
||||
request.setDE42(merchantId);
|
||||
@ -485,6 +572,12 @@ public class ProcessingFragment extends DataBindingFragment {
|
||||
request.setInvoiceNumber(payDetail.getInvoiceNo());
|
||||
request.setAppId(appId);
|
||||
request.setDescription(reason);
|
||||
request.setBatchNumber(payDetail.batchNo);
|
||||
request.setDE55(payDetail.getAppLabel());
|
||||
request.setCardLabel(payDetail.getAccountType());
|
||||
request.setDE14(PrintUtils.getInstance().getFormatExpDate(payDetail.getEXPDate()));
|
||||
request.setDE43(formatDE43(cardHolderName));
|
||||
request.setDE48(payDetail.getAID());
|
||||
|
||||
return request;
|
||||
}
|
||||
|
||||
@ -10,6 +10,8 @@ import androidx.appcompat.app.AppCompatActivity;
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.JsonSyntaxException;
|
||||
import com.google.gson.stream.MalformedJsonException;
|
||||
import com.utsmm.kbz.MainActivity;
|
||||
import com.utsmm.kbz.util.LocationUtil;
|
||||
import com.utsmyanmar.baselib.emv.EmvParamOperation;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusError;
|
||||
@ -156,6 +158,8 @@ public class TransactionResultFragment extends DataBindingFragment implements Da
|
||||
return;
|
||||
}
|
||||
|
||||
((MainActivity) requireActivity()).getLocation();
|
||||
|
||||
SiriusRequest siriusReq = TMSUtil.getInstance().generateRequestParams(
|
||||
getContext(),
|
||||
payDetail.getTransType(),
|
||||
@ -331,6 +335,7 @@ public class TransactionResultFragment extends DataBindingFragment implements Da
|
||||
sharedViewModel.startPrintSettlement(new PrintXStatus() {
|
||||
@Override
|
||||
public void onSuccess() {
|
||||
sharedViewModel.onSettlementResultDone.postValue(true);
|
||||
isCardInside();
|
||||
}
|
||||
|
||||
|
||||
@ -78,13 +78,21 @@ public class EmvTransactionProcessViewModel extends EmvBaseViewModel implements
|
||||
break;
|
||||
}
|
||||
try {
|
||||
if (mPayDetail.PINCipher != null && !mPayDetail.PINCipher.isEmpty()) {
|
||||
LogUtil.d("EmvTransactionProcessViewModel", "mPayDetail" + mPayDetail.PINCipher);
|
||||
LogUtil.d("EmvTransactionProcessViewModel", "is offline pin entered " + isOfflinePinEntered);
|
||||
|
||||
if ((mPayDetail.PINCipher != null && !mPayDetail.PINCipher.isEmpty())) {
|
||||
LogUtil.d("EmvTransactionProcessViewModel", "condition 1");
|
||||
emvHandler.onSetPinInputResponse(true, false);
|
||||
} else if (isOfflinePinEntered) {
|
||||
emvHandler.onSetPinInputResponse(true, false);
|
||||
} else {
|
||||
} else if(isOfflinePinEntered){
|
||||
LogUtil.d("EmvTransactionProcessViewModel", "condition 2");
|
||||
emvHandler.onSetPinInputResponse(true, false);
|
||||
}else {
|
||||
LogUtil.d("EmvTransactionProcessViewModel", "condition 3");
|
||||
|
||||
emvHandler.onSetPinInputResponse(true, true);
|
||||
}
|
||||
|
||||
if (transType.getValue() == TransactionsType.PRE_AUTH_COMPLETE || transType.getValue() == TransactionsType.PRE_AUTH_VOID || transType.getValue() == TransactionsType.REFUND) {
|
||||
emvResultStatus.postValue(EmvResultStatus.ON_NEXT_SCREEN);
|
||||
}
|
||||
@ -162,7 +170,13 @@ public class EmvTransactionProcessViewModel extends EmvBaseViewModel implements
|
||||
handleTransactionFail(msg.arg1, msg.obj.toString());
|
||||
break;
|
||||
case EMV_TRY_AGAIN:
|
||||
emvResultStatus.postValue(EmvResultStatus.READ_CARD);
|
||||
emvResultStatus.postValue(EmvResultStatus.READ_CARD_RETRY);
|
||||
break;
|
||||
case EMV_INSERT_OR_MANUAL:
|
||||
emvResultStatus.postValue(EmvResultStatus.INSERT_OR_MANUAL);
|
||||
break;
|
||||
case EMV_CARD_APP_BLOCK:
|
||||
emvResultStatus.postValue(EmvResultStatus.CARD_APP_BLOCKED);
|
||||
break;
|
||||
case EMV_CONFIRM_CODE_VERIFY:
|
||||
emvResultStatus.postValue(EmvResultStatus.CONFIRM_CODE_VERIFY);
|
||||
@ -443,8 +457,8 @@ public class EmvTransactionProcessViewModel extends EmvBaseViewModel implements
|
||||
|
||||
@Override
|
||||
public void processPreVoidDb(PayDetail payResult) {
|
||||
mPayDetail.setIsCanceled(true);
|
||||
updatePayDetail(mPayDetail);
|
||||
oldTransPayDetail.setIsCanceled(true);
|
||||
updatePayDetail(oldTransPayDetail);
|
||||
repository.insertPayDetail(updateCurrentDateAndTime(payResult));
|
||||
}
|
||||
|
||||
@ -458,9 +472,11 @@ public class EmvTransactionProcessViewModel extends EmvBaseViewModel implements
|
||||
if(oldTransPayDetail.getAmount() == payResult.getAmount()) {
|
||||
|
||||
oldTransPayDetail.setIsCanceled(true);
|
||||
oldTransPayDetail.setAdjust(true);
|
||||
updatePayDetail(oldTransPayDetail);
|
||||
} else {
|
||||
oldTransPayDetail.setIsCanceled(false);
|
||||
oldTransPayDetail.setAdjust(true);
|
||||
updatePayDetail(oldTransPayDetail);
|
||||
}
|
||||
repository.insertPayDetail(updateCurrentDateAndTime(payResult));
|
||||
|
||||
@ -13,112 +13,109 @@ import java.util.Objects;
|
||||
|
||||
public class InputAmountViewModel extends ViewModel {
|
||||
|
||||
private static final String TAG = InputAmountViewModel.class.getSimpleName();
|
||||
|
||||
public MutableLiveData<String> inputAmountView = new MutableLiveData<>();
|
||||
|
||||
public SingleLiveEvent<String> invalidAmountMsg = new SingleLiveEvent<>();
|
||||
|
||||
public SingleLiveEvent<String> availableAmount = new SingleLiveEvent<>();
|
||||
|
||||
private static final int MAX_INT_DIGITS = 10;
|
||||
private static final int MAX_DECIMAL_DIGITS = 2;
|
||||
|
||||
public InputAmountViewModel() {
|
||||
inputAmountView.setValue("0");
|
||||
}
|
||||
|
||||
private int countDecimalDigits(double number) {
|
||||
String numberStr = Double.toString(number);
|
||||
int decimalIndex = numberStr.indexOf('.');
|
||||
return decimalIndex >= 0 ? numberStr.length() - decimalIndex - 1 : 0;
|
||||
private String formatInteger(String value) {
|
||||
if (TextUtils.isEmpty(value)) return "0";
|
||||
double amt = Double.parseDouble(value);
|
||||
DecimalFormat formatter = new DecimalFormat("#,###");
|
||||
return formatter.format(amt);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
public NumberKeyboard.KeyClickCallback onKeyClick() {
|
||||
return new NumberKeyboard.KeyClickCallback() {
|
||||
|
||||
@Override
|
||||
public void onNumClick(int keyNum) {
|
||||
|
||||
if (inputAmountView.getValue().length() == 15) {
|
||||
String current = inputAmountView.getValue();
|
||||
if (current == null) return;
|
||||
|
||||
String raw = current.replace(",", "");
|
||||
|
||||
if (raw.contains(".")) {
|
||||
|
||||
String[] parts = raw.split("\\.");
|
||||
String intPart = parts[0];
|
||||
String decimalPart = parts.length > 1 ? parts[1] : "";
|
||||
|
||||
if (decimalPart.length() >= MAX_DECIMAL_DIGITS) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (TextUtils.equals(inputAmountView.getValue(), "0")) {
|
||||
inputAmountView.setValue(keyNum + "");
|
||||
} else if (inputAmountView.getValue().contains(".")) {
|
||||
StringBuilder inputAmount = new StringBuilder();
|
||||
inputAmount.append(inputAmountView.getValue());
|
||||
|
||||
int dotIndex = inputAmount.indexOf(".");
|
||||
|
||||
if(inputAmount.substring(dotIndex).length() > 0 && inputAmount.substring(dotIndex+1).length() == 2) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (inputAmountView.getValue().contains(",")) {
|
||||
inputAmountView.setValue(inputAmountView.getValue().replace(",", ""));
|
||||
}
|
||||
double amt = Double.parseDouble(inputAmountView.getValue());
|
||||
if (countDecimalDigits(amt) < 2) {
|
||||
inputAmountView.setValue(inputAmountView.getValue() + keyNum);
|
||||
}
|
||||
raw = raw + keyNum;
|
||||
|
||||
} else {
|
||||
if (inputAmountView.getValue().contains(",")) {
|
||||
inputAmountView.setValue(inputAmountView.getValue().replace(",", ""));
|
||||
|
||||
if (raw.length() >= MAX_INT_DIGITS) {
|
||||
return;
|
||||
}
|
||||
inputAmountView.setValue(inputAmountView.getValue() + keyNum);
|
||||
double amt = Double.parseDouble(inputAmountView.getValue());
|
||||
DecimalFormat formatter = new DecimalFormat("#,###");
|
||||
inputAmountView.setValue(formatter.format(amt));
|
||||
|
||||
if (TextUtils.equals(raw, "0")) {
|
||||
raw = String.valueOf(keyNum);
|
||||
} else {
|
||||
raw = raw + keyNum;
|
||||
}
|
||||
}
|
||||
|
||||
if (raw.contains(".")) {
|
||||
String[] parts = raw.split("\\.");
|
||||
String formattedInt = formatInteger(parts[0]);
|
||||
String decimal = parts.length > 1 ? parts[1] : "";
|
||||
inputAmountView.setValue(formattedInt + "." + decimal);
|
||||
} else {
|
||||
inputAmountView.setValue(formatInteger(raw));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDelClick() {
|
||||
if (Objects.requireNonNull(inputAmountView.getValue()).contains(".")) {
|
||||
return;
|
||||
}
|
||||
if (inputAmountView.getValue().length() == 15) {
|
||||
return;
|
||||
}
|
||||
if (TextUtils.equals(inputAmountView.getValue(), "0")) {
|
||||
|
||||
String current = inputAmountView.getValue();
|
||||
if (current == null) return;
|
||||
|
||||
if (current.contains(".")) return;
|
||||
|
||||
if (TextUtils.equals(current, "0")) {
|
||||
inputAmountView.setValue("0.");
|
||||
} else {
|
||||
|
||||
inputAmountView.setValue(inputAmountView.getValue() + ".");
|
||||
inputAmountView.setValue(current + ".");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCleanClick() {
|
||||
if (inputAmountView.getValue() != null) {
|
||||
if (inputAmountView.getValue().contains(".")) {
|
||||
StringBuilder inputAmount = new StringBuilder();
|
||||
inputAmount.append(inputAmountView.getValue());
|
||||
inputAmount.deleteCharAt(inputAmount.length() - 1);
|
||||
inputAmountView.setValue(inputAmount.toString());
|
||||
} else if (!inputAmountView.getValue().equals("0")) {
|
||||
String currentValue = inputAmountView.getValue();
|
||||
|
||||
String rawNumber = currentValue.replace(",", "");
|
||||
String current = inputAmountView.getValue();
|
||||
if (current == null) return;
|
||||
|
||||
if (rawNumber.length() > 1) {
|
||||
rawNumber = rawNumber.substring(0, rawNumber.length() - 1);
|
||||
String raw = current.replace(",", "");
|
||||
|
||||
double amt = Double.parseDouble(rawNumber);
|
||||
DecimalFormat formatter = new DecimalFormat("#,###");
|
||||
inputAmountView.setValue(formatter.format(amt));
|
||||
} else {
|
||||
if (raw.length() <= 1) {
|
||||
inputAmountView.setValue("0");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
raw = raw.substring(0, raw.length() - 1);
|
||||
|
||||
if (raw.contains(".")) {
|
||||
String[] parts = raw.split("\\.");
|
||||
String formattedInt = formatInteger(parts[0]);
|
||||
String decimal = parts.length > 1 ? parts[1] : "";
|
||||
inputAmountView.setValue(formattedInt + "." + decimal);
|
||||
} else {
|
||||
inputAmountView.setValue(formatInteger(raw));
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@ -41,6 +41,12 @@ public class InputRRNViewModel extends ViewModel {
|
||||
return repository.searchPayDetail(cardNo,rrn);
|
||||
}
|
||||
|
||||
public LiveData<PayDetail> searchPayDetailPreCancel(String cardNo,String rrn) {
|
||||
return repository.searchPayDetailPreCancel(cardNo,rrn);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
public NumberKeyboard.KeyClickCallback onKeyClick(){
|
||||
return new NumberKeyboard.KeyClickCallback() {
|
||||
|
||||
@ -1,7 +1,9 @@
|
||||
package com.utsmm.kbz.ui.core_viewmodel;
|
||||
|
||||
import android.annotation.SuppressLint;
|
||||
import android.graphics.Bitmap;
|
||||
import android.util.Log;
|
||||
import android.widget.ListView;
|
||||
|
||||
import dagger.hilt.android.lifecycle.HiltViewModel;
|
||||
import androidx.lifecycle.LiveData;
|
||||
@ -73,7 +75,8 @@ public class SharedViewModel extends ViewModel {
|
||||
|
||||
public SingleLiveEvent<String> transactionName = new SingleLiveEvent<>();
|
||||
|
||||
|
||||
// In SharedViewModel
|
||||
public MutableLiveData<Boolean> onSettlementResultDone = new MutableLiveData<>(false);
|
||||
/*May 16 2022*/
|
||||
public SingleLiveEvent<Boolean> isEcr = new SingleLiveEvent<>();
|
||||
|
||||
@ -161,10 +164,14 @@ public class SharedViewModel extends ViewModel {
|
||||
|
||||
public MutableLiveData<Integer> loadingView = new MutableLiveData<>(8);
|
||||
public SingleLiveEvent<String> loadingMsg = new SingleLiveEvent<>();
|
||||
private final SingleLiveEvent<String> toastMsg = new SingleLiveEvent<>();
|
||||
|
||||
private SingleLiveEvent<Boolean> isFallback = new SingleLiveEvent<>();
|
||||
private SingleLiveEvent<Boolean> isSeePhone = new SingleLiveEvent<>();
|
||||
|
||||
private SingleLiveEvent<Boolean> isContactlessRestricted = new SingleLiveEvent<>();
|
||||
private SingleLiveEvent<Boolean> isCardAppBlock = new SingleLiveEvent<>();
|
||||
|
||||
private SingleLiveEvent<Boolean> _isCardDataExist = new SingleLiveEvent<>();
|
||||
|
||||
private SingleLiveEvent<Boolean> _isAmountExist = new SingleLiveEvent<>();
|
||||
@ -233,10 +240,18 @@ public class SharedViewModel extends ViewModel {
|
||||
|
||||
public SingleLiveEvent<Boolean> getIsFallback() { return isFallback;}
|
||||
|
||||
public void setIsCardAppBlock(boolean status) { isCardAppBlock.setValue(status);}
|
||||
|
||||
public SingleLiveEvent<Boolean> getIsCardAppBlock() {return isCardAppBlock;}
|
||||
|
||||
public void setIsSeePhone(boolean status) { isSeePhone.setValue(status);}
|
||||
|
||||
public SingleLiveEvent<Boolean> getIsSeePhone() { return isSeePhone;}
|
||||
|
||||
public void setIsContactlessRestricted(boolean status) { isContactlessRestricted.setValue(status);}
|
||||
|
||||
public SingleLiveEvent<Boolean> getIsContactlessRestricted() {return isContactlessRestricted;}
|
||||
|
||||
public void setCardDataExist(boolean exist) { _isCardDataExist.setValue(exist);}
|
||||
|
||||
public SingleLiveEvent<Boolean> getCardDataExist() { return _isCardDataExist; }
|
||||
@ -288,6 +303,14 @@ public class SharedViewModel extends ViewModel {
|
||||
loadingMsg.setValue("");
|
||||
}
|
||||
|
||||
public SingleLiveEvent<String> getToastMsg() {
|
||||
return toastMsg;
|
||||
}
|
||||
|
||||
public void postToastMsg(String msg) {
|
||||
toastMsg.postValue(msg);
|
||||
}
|
||||
|
||||
public Observable<SiriusResponse> getParams(SiriusRequest siriusRequest) {
|
||||
return repository.getParams(siriusRequest);
|
||||
}
|
||||
@ -441,6 +464,14 @@ public class SharedViewModel extends ViewModel {
|
||||
return repository.getReversalTransaction(voucherNo);
|
||||
}
|
||||
|
||||
public LiveData<PayDetail> getLastReversalTransaction() {
|
||||
return repository.getLastReversalTransaction();
|
||||
}
|
||||
|
||||
public LiveData<List<PayDetail>> getAllReversalTransaction() {
|
||||
return repository.getAllReversalTransactions();
|
||||
}
|
||||
|
||||
public void updatePayDetail(PayDetail payDetail){
|
||||
repository.updatePayDetail(payDetail);
|
||||
}
|
||||
@ -456,13 +487,17 @@ public class SharedViewModel extends ViewModel {
|
||||
}
|
||||
|
||||
|
||||
@SuppressLint("CheckResult")
|
||||
public void pushReceipt(Object body){
|
||||
Log.d("push receipt", new Gson().toJson(body));
|
||||
repository.sendReceipt(body)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.subscribe(
|
||||
response -> Log.d("E-Receipt", "Success =>"+ response.getMessage()),
|
||||
response -> {
|
||||
Log.d("E-Receipt", "Success =>"+ response.getMessage());
|
||||
postToastMsg("E-Receipt saved successfully");
|
||||
},
|
||||
error -> {
|
||||
if (error instanceof HttpException) {
|
||||
HttpException httpEx = (HttpException) error;
|
||||
@ -474,11 +509,14 @@ public class SharedViewModel extends ViewModel {
|
||||
// Parse JSON to model
|
||||
EReceiptResponse res = new Gson().fromJson(errorJson, EReceiptResponse.class);
|
||||
Log.e("E-Receipt", "Parsed Error => " + res.getMessage());
|
||||
postToastMsg("E-Receipt could not save!");
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
postToastMsg("E-Receipt could not save!");
|
||||
}
|
||||
} else {
|
||||
Log.e("E-Receipt", "Unexpected error => " + error.getMessage());
|
||||
postToastMsg("E-Receipt could not save!");
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
@ -304,13 +304,16 @@ public class TransProcessViewModel extends ViewModel implements ProcessingTransa
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
public void processPreCompDb(PayDetail payResult) {
|
||||
if(oldTransPayDetail.getAmount() == payResult.getAmount()) {
|
||||
|
||||
oldTransPayDetail.setIsCanceled(true);
|
||||
oldTransPayDetail.setAdjust(true);
|
||||
updatePayDetail(oldTransPayDetail);
|
||||
} else {
|
||||
oldTransPayDetail.setIsCanceled(false);
|
||||
oldTransPayDetail.setAdjust(true);
|
||||
updatePayDetail(oldTransPayDetail);
|
||||
}
|
||||
repository.insertPayDetail(updateCurrentDateAndTime(payResult));
|
||||
|
||||
@ -9,12 +9,14 @@ import com.utsmm.kbz.MainViewModel;
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.config.Constants;
|
||||
import com.utsmm.kbz.ui.core_viewmodel.SharedViewModel;
|
||||
import com.utsmm.kbz.util.CurrencySelectionHelper;
|
||||
|
||||
public class DashboardPreAuthBottomSheet extends DataBindingBottomSheetFragment {
|
||||
|
||||
|
||||
private MainViewModel mainViewModel;
|
||||
private SharedViewModel sharedViewModel;
|
||||
private CurrencySelectionHelper currencySelectionHelper;
|
||||
|
||||
private static final int hostId = Constants.NAV_HOST_ID;
|
||||
private int routeId;
|
||||
@ -24,6 +26,7 @@ public class DashboardPreAuthBottomSheet extends DataBindingBottomSheetFragment
|
||||
protected void initViewModel() {
|
||||
mainViewModel = getFragmentScopeViewModel(MainViewModel.class);
|
||||
sharedViewModel = getFragmentScopeViewModel(SharedViewModel.class);
|
||||
currencySelectionHelper = new CurrencySelectionHelper(this, sharedViewModel);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -52,10 +55,11 @@ public class DashboardPreAuthBottomSheet extends DataBindingBottomSheetFragment
|
||||
} else if (checkTid()) {
|
||||
showDeclineDialog("Please Download Config!");
|
||||
} else {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.transactionsType.setValue(TransactionsType.PRE_AUTH_SALE);
|
||||
|
||||
routeId = R.id.action_dashboardPreAuthBottomSheet_to_inputAmountFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@ -65,10 +69,11 @@ public class DashboardPreAuthBottomSheet extends DataBindingBottomSheetFragment
|
||||
} else if (checkTid()) {
|
||||
showDeclineDialog("Please Download Config!");
|
||||
} else {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.transactionsType.setValue(TransactionsType.PRE_AUTH_COMPLETE);
|
||||
|
||||
routeId = R.id.action_dashboardPreAuthBottomSheet_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
@ -86,4 +91,8 @@ public class DashboardPreAuthBottomSheet extends DataBindingBottomSheetFragment
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void showCurrencyChooserForCardFlow(Runnable onSelected) {
|
||||
currencySelectionHelper.showCardCurrencyChooser(onSelected);
|
||||
}
|
||||
}
|
||||
|
||||
@ -10,6 +10,7 @@ import com.utsmm.kbz.MainViewModel;
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.config.Constants;
|
||||
import com.utsmm.kbz.ui.core_viewmodel.SharedViewModel;
|
||||
import com.utsmm.kbz.util.CurrencySelectionHelper;
|
||||
|
||||
public class DashboardPreAuthCancelBottomSheet extends DataBindingBottomSheetFragment {
|
||||
|
||||
@ -17,6 +18,7 @@ public class DashboardPreAuthCancelBottomSheet extends DataBindingBottomSheetFra
|
||||
|
||||
private MainViewModel mainViewModel;
|
||||
private SharedViewModel sharedViewModel;
|
||||
private CurrencySelectionHelper currencySelectionHelper;
|
||||
|
||||
private int currentId = R.id.dashboardPreAuthCancelBottomSheet;
|
||||
private int routeId;
|
||||
@ -26,6 +28,7 @@ public class DashboardPreAuthCancelBottomSheet extends DataBindingBottomSheetFra
|
||||
protected void initViewModel() {
|
||||
mainViewModel = getFragmentScopeViewModel(MainViewModel.class);
|
||||
sharedViewModel = getFragmentScopeViewModel(SharedViewModel.class);
|
||||
currencySelectionHelper = new CurrencySelectionHelper(this, sharedViewModel);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -61,12 +64,13 @@ public class DashboardPreAuthCancelBottomSheet extends DataBindingBottomSheetFra
|
||||
} else if (checkTid()) {
|
||||
showDeclineDialog("Please Download Config!");
|
||||
} else {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.transactionsType.setValue(TransactionsType.PRE_AUTH_VOID);
|
||||
sharedViewModel.setTransMenu(TransMenu.PRE_AUTH_FULL_VOID);
|
||||
sharedViewModel.amount.postValue(null);
|
||||
|
||||
routeId = R.id.action_dashboardPreAuthCancelBottomSheet_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
@ -82,14 +86,19 @@ public class DashboardPreAuthCancelBottomSheet extends DataBindingBottomSheetFra
|
||||
} else if (checkTid()) {
|
||||
showDeclineDialog("Please Download Config!");
|
||||
} else {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.transactionsType.setValue(TransactionsType.PRE_AUTH_VOID);
|
||||
sharedViewModel.setTransMenu(TransMenu.PRE_AUTH_PARTIAL_VOID);
|
||||
sharedViewModel.amount.postValue(null);
|
||||
|
||||
routeId = R.id.action_dashboardPreAuthCancelBottomSheet_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void showCurrencyChooserForCardFlow(Runnable onSelected) {
|
||||
currencySelectionHelper.showCardCurrencyChooser(onSelected);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -30,6 +30,7 @@ import com.utsmm.kbz.config.Constants;
|
||||
import com.utsmm.kbz.config.data.model.Features;
|
||||
import com.utsmm.kbz.ui.adapters.MainAdapter;
|
||||
import com.utsmm.kbz.ui.core_viewmodel.SharedViewModel;
|
||||
import com.utsmm.kbz.util.CurrencySelectionHelper;
|
||||
import com.utsmm.kbz.util.tms.TMSUtil;
|
||||
|
||||
import java.util.ArrayList;
|
||||
@ -41,6 +42,7 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
|
||||
private MainViewModel mainViewModel;
|
||||
private SharedViewModel sharedViewModel;
|
||||
private CurrencySelectionHelper currencySelectionHelper;
|
||||
|
||||
private ArrayList<Features> featuresList = new ArrayList<>();
|
||||
|
||||
@ -76,6 +78,7 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
protected void initViewModel() {
|
||||
mainViewModel = getFragmentScopeViewModel(MainViewModel.class);
|
||||
sharedViewModel = getFragmentScopeViewModel(SharedViewModel.class);
|
||||
currencySelectionHelper = new CurrencySelectionHelper(this, sharedViewModel);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -175,6 +178,9 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
case CASH_ADVANCE:
|
||||
new DashboardTransFragment.ClickEvent().onClickCashAdvance();
|
||||
break;
|
||||
case CLEAR_REVERSAL:
|
||||
new DashboardTransFragment.ClickEvent().onClickClearReversal();
|
||||
break;
|
||||
case DEVICE_CONFIG:
|
||||
new DashboardTransFragment.ClickEvent().onClickDeviceConfig();
|
||||
break;
|
||||
@ -227,9 +233,11 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
public void onClickRefund() {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.setTransactionsType(TransactionsType.REFUND);
|
||||
routeId = R.id.action_dashboardTransFragment_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
}
|
||||
|
||||
public void onClickPreAuth () {
|
||||
@ -248,19 +256,23 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
public void onClickPreAuthCancel () {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.setTransactionsType(TransactionsType.PRE_AUTH_VOID);
|
||||
sharedViewModel.setTransMenu(TransMenu.PRE_AUTH_FULL_VOID);
|
||||
sharedViewModel.amount.postValue("0"); // null to 0
|
||||
// sharedViewModel.amount.postValue(null);
|
||||
routeId = R.id.action_dashboardTransFragment_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
public void onClickPreAuthComp () {
|
||||
showCurrencyChooserForCardFlow(() -> {
|
||||
sharedViewModel.setTransactionsType(TransactionsType.PRE_AUTH_COMPLETE);
|
||||
routeId = R.id.action_dashboardTransFragment_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId,routeId,hostId);
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
@ -281,6 +293,14 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
public void onClickClearReversal() {
|
||||
sharedViewModel.transactionsType.postValue(TransactionsType.CLEAR_REVERSAL);
|
||||
sharedViewModel.setTransMenu(TransMenu.CLEAR_REVERSAL);
|
||||
routeId = R.id.action_dashboardTransFragment_to_inputPasswordFragment;
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
}
|
||||
|
||||
public void onClickDeviceConfig(){
|
||||
routeId = R.id.action_dashboardTransFragment_to_deviceConfig;
|
||||
safeRouteTo(currentId, routeId, hostId);
|
||||
@ -471,6 +491,7 @@ public class DashboardTransFragment extends DataBindingFragment {
|
||||
|
||||
private interface CurrencySelectCallback {
|
||||
void onSelected(String currency);
|
||||
// currencySelectionHelper.showCardCurrencyChooser(onSelected);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -4,6 +4,7 @@ import androidx.databinding.library.baseAdapters.BR;
|
||||
import androidx.lifecycle.Observer;
|
||||
|
||||
import com.google.gson.stream.MalformedJsonException;
|
||||
import com.utsmm.kbz.MainActivity;
|
||||
import com.utsmyanmar.baselib.emv.EmvParamOperation;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusRequest;
|
||||
@ -104,6 +105,7 @@ public class DisabledTerminalFragment extends DataBindingFragment {
|
||||
|
||||
private void downloadParams(String lastTransName,String lastTransTime) {
|
||||
showLoadingDialog("Downloading...");
|
||||
((MainActivity) requireActivity()).getLocation();
|
||||
SiriusRequest siriusReq = TMSUtil.getInstance().generateRequestParams(getContext(),lastTransName,lastTransTime);
|
||||
mainViewModel.getParams(siriusReq).subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
|
||||
@ -53,6 +53,7 @@ public class ManagementFunctionFragment extends DataBindingFragment {
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
sharedViewModel.printerDisabled.setValue(!SystemParamsOperation.getInstance().getPrinterEnabled());
|
||||
setToolBarTitleWithBackIcon(getString(R.string.title_select_function));
|
||||
}
|
||||
|
||||
|
||||
@ -145,6 +145,18 @@ public class ReprintAnyTransactionFragment extends DataBindingFragment {
|
||||
cardViewAdapter.updateList(searchedLists);
|
||||
}
|
||||
|
||||
private void searchByTraceAndRRN(String input) {
|
||||
for (PayDetail s : lists) {
|
||||
boolean matchTrace = s.getVoucherNo() != null && s.getVoucherNo().contains(input);
|
||||
boolean matchRRN = s.getReferNo() != null && s.getReferNo().contains(input);
|
||||
|
||||
if (matchTrace || matchRRN) {
|
||||
searchedLists.add(s);
|
||||
}
|
||||
}
|
||||
cardViewAdapter.updateList(searchedLists);
|
||||
}
|
||||
|
||||
public class ClickEvent {
|
||||
|
||||
public void onClickSearch() {
|
||||
@ -152,7 +164,7 @@ public class ReprintAnyTransactionFragment extends DataBindingFragment {
|
||||
String input = managementViewModel.txtRRNTrace.getValue();
|
||||
|
||||
if(input != null && !input.isEmpty()) {
|
||||
searchByTrace(input);
|
||||
searchByTraceAndRRN(input);
|
||||
} else {
|
||||
searchedLists.addAll(lists);
|
||||
}
|
||||
|
||||
@ -210,13 +210,35 @@ public class SelectHostFragment extends DataBindingFragment implements DataBindi
|
||||
|
||||
private void clearReversal() {
|
||||
checkPointReversal = false;
|
||||
sharedViewModel.getReversalTransaction(SystemParamsOperation.getInstance().getCurrentSerialNum()).observe(getViewLifecycleOwner(), payDetail -> {
|
||||
if (payDetail != null) {
|
||||
if (!checkPointReversal) {
|
||||
// sharedViewModel.getReversalTransaction(SystemParamsOperation.getInstance().getCurrentSerialNum()).observe(getViewLifecycleOwner(), payDetail -> {
|
||||
// if (payDetail != null) {
|
||||
// if (!checkPointReversal) {
|
||||
// payDetail.setIsNeedReversal(false);
|
||||
// sharedViewModel.updatePayDetail(payDetail);
|
||||
// checkPointReversal = true;
|
||||
//
|
||||
// showSuccessDialog("Clear reversal success!");
|
||||
// }
|
||||
// } else {
|
||||
// if (!checkPointReversal) {
|
||||
// showInfoDialog("Clear reversal", "No reversal found!");
|
||||
// checkPointReversal = true;
|
||||
// }
|
||||
//
|
||||
// }
|
||||
// });
|
||||
|
||||
sharedViewModel.getAllReversalTransaction().observe(getViewLifecycleOwner(), new Observer<List<PayDetail>>() {
|
||||
@Override
|
||||
public void onChanged(List<PayDetail> payDetails) {
|
||||
if(payDetails != null && !payDetails.isEmpty()) {
|
||||
if(!checkPointReversal) {
|
||||
for (PayDetail payDetail : payDetails) {
|
||||
payDetail.setIsNeedReversal(false);
|
||||
sharedViewModel.updatePayDetail(payDetail);
|
||||
checkPointReversal = true;
|
||||
|
||||
}
|
||||
checkPointReversal = true;
|
||||
showSuccessDialog("Clear reversal success!");
|
||||
}
|
||||
} else {
|
||||
@ -224,7 +246,7 @@ public class SelectHostFragment extends DataBindingFragment implements DataBindi
|
||||
showInfoDialog("Clear reversal", "No reversal found!");
|
||||
checkPointReversal = true;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@ -51,6 +51,8 @@ public class TransactionSummaryFragment extends DataBindingFragment {
|
||||
final Calendar myCalendar = Calendar.getInstance();
|
||||
final Calendar myCalendar2 = Calendar.getInstance();
|
||||
|
||||
ArrayList<PayDetail> filteredLists = new ArrayList<>();
|
||||
|
||||
@Override
|
||||
protected void initViewModel() {
|
||||
managementViewModel = getFragmentScopeViewModel(ManagementViewModel.class);
|
||||
@ -224,10 +226,15 @@ public class TransactionSummaryFragment extends DataBindingFragment {
|
||||
}
|
||||
}
|
||||
|
||||
private SettleData processTransactionData(List<PayDetail> payDetailList, SimpleDateFormat formatter,
|
||||
Date yesterday, Date start, Date end) {
|
||||
private SettleData processTransactionData(List<PayDetail> payDetailList,
|
||||
SimpleDateFormat formatter,
|
||||
Date yesterday,
|
||||
Date start,
|
||||
Date end) {
|
||||
try {
|
||||
// Create a local helper class for readable mutability
|
||||
// ✅ IMPORTANT: clear old data
|
||||
filteredLists.clear();
|
||||
|
||||
class Counter {
|
||||
int count = 0;
|
||||
long amount = 0L;
|
||||
@ -250,38 +257,32 @@ public class TransactionSummaryFragment extends DataBindingFragment {
|
||||
Counter preAuthCompVoid = new Counter();
|
||||
Counter refund = new Counter();
|
||||
|
||||
// ✅ Use ONE consistent format
|
||||
SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yy HH:mm", Locale.getDefault());
|
||||
ArrayList<PayDetail> filteredLists = new ArrayList<>();
|
||||
|
||||
// Filter transactions by date
|
||||
for (PayDetail pay : payDetailList) {
|
||||
try {
|
||||
Date transDate = formatter.parse(pay.getTransDate());
|
||||
if (yesterday.compareTo(transDate) <= 0) {
|
||||
filteredLists.add(pay);
|
||||
}
|
||||
} catch (ParseException e) {
|
||||
LogUtil.e(TAG, "Error parsing transaction date: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
LogUtil.d(TAG, "Filtered transactions count: " + filteredLists.size());
|
||||
|
||||
// Process filtered transactions
|
||||
for (PayDetail pay : filteredLists) {
|
||||
try {
|
||||
// ✅ Combine date + time correctly
|
||||
Date currentDate = sdf.parse(pay.transDate + " " + pay.transTime);
|
||||
|
||||
if ((currentDate.after(start) || currentDate.equals(start)) &&
|
||||
(currentDate.before(end) || currentDate.equals(end))) {
|
||||
if (currentDate == null) continue;
|
||||
|
||||
// ✅ Correct inclusive range check
|
||||
if (!currentDate.before(start) && !currentDate.after(end)) {
|
||||
|
||||
// ✅ Keep filtered list for printing
|
||||
filteredLists.add(pay);
|
||||
|
||||
if (sharedViewModel.hostType.getValue() == HostType.QR) {
|
||||
|
||||
if (pay.getTransactionType() == TransactionsType.MMQR.value && pay.getQrTransStatus() == 1) {
|
||||
wave.inc(pay.amount);
|
||||
} else if (pay.getTransactionType() == TransactionsType.MMQR_REFUND.value && pay.getQrTransStatus() == 1) {
|
||||
waveRefund.inc(pay.amount);
|
||||
}
|
||||
|
||||
} else if (sharedViewModel.hostType.getValue() == HostType.MPU) {
|
||||
|
||||
if (pay.getTransactionType() == TransactionsType.VOID.value) {
|
||||
voidTran.inc(pay.amount);
|
||||
} else if (pay.getTransactionType() == TransactionsType.SALE.value) {
|
||||
@ -301,11 +302,14 @@ public class TransactionSummaryFragment extends DataBindingFragment {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} catch (ParseException e) {
|
||||
LogUtil.e(TAG, "Error parsing transaction datetime: " + e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
LogUtil.d(TAG, "Filtered transactions count: " + filteredLists.size());
|
||||
|
||||
return new SettleData(
|
||||
sale.count, sale.amount,
|
||||
wave.count, wave.amount,
|
||||
@ -318,6 +322,7 @@ public class TransactionSummaryFragment extends DataBindingFragment {
|
||||
refund.count, refund.amount,
|
||||
waveRefund.count, waveRefund.amount
|
||||
);
|
||||
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Error processing transaction data: " + e.getMessage());
|
||||
return null;
|
||||
@ -366,7 +371,7 @@ public class TransactionSummaryFragment extends DataBindingFragment {
|
||||
private void printReceipt(PayDetail payDetail) {
|
||||
try {
|
||||
LogUtil.d(TAG, "Starting receipt print");
|
||||
PrintXReceipt.getInstance().printSmileSummaryReport(payDetail, sharedViewModel.hostType.getValue(), new PrintXStatus() {
|
||||
PrintXReceipt.getInstance().printSmileSummaryReport(payDetail, filteredLists, sharedViewModel.hostType.getValue(), new PrintXStatus() {
|
||||
@Override
|
||||
public void onSuccess() {
|
||||
LogUtil.d(TAG, "Receipt printed successfully");
|
||||
|
||||
@ -77,7 +77,7 @@ public class ManualEntryFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
private void processEmvCard() {
|
||||
if(sharedViewModel.transactionsType.getValue() == TransactionsType.REFUND || sharedViewModel.transactionsType.getValue() == TransactionsType.PRE_AUTH_VOID) {
|
||||
if(sharedViewModel.transactionsType.getValue() == TransactionsType.REFUND || sharedViewModel.transactionsType.getValue() == TransactionsType.PRE_AUTH_VOID || sharedViewModel.transactionsType.getValue() == TransactionsType.PRE_AUTH_COMPLETE) {
|
||||
routeId = R.id.action_manualEntryFragment_to_inputRRNFragment;
|
||||
} else {
|
||||
routeId = R.id.action_manualEntryFragment_to_emvTransactionFragment;
|
||||
@ -106,7 +106,7 @@ public class ManualEntryFragment extends DataBindingFragment {
|
||||
payDetail.setICC55("");
|
||||
// payDetail.setAuthNo(manualEntryViewModel.cvv.getValue());
|
||||
|
||||
|
||||
emvTransactionProcessViewModel.cardNum.setValue(cardNo);
|
||||
emvTransactionProcessViewModel.setTradeData(tradeData);
|
||||
|
||||
safeNavigateToRouteId();
|
||||
|
||||
@ -4,6 +4,8 @@ import android.content.Context;
|
||||
import android.text.TextUtils;
|
||||
import android.util.Log;
|
||||
|
||||
import androidx.databinding.ObservableBoolean;
|
||||
|
||||
import com.nexgo.oaf.apiv3.APIProxy;
|
||||
import com.nexgo.oaf.apiv3.DeviceEngine;
|
||||
import com.nexgo.oaf.apiv3.DeviceInfo;
|
||||
@ -12,6 +14,7 @@ import com.nexgo.oaf.apiv3.device.printer.AlignEnum;
|
||||
import com.nexgo.oaf.apiv3.device.printer.GrayLevelEnum;
|
||||
import com.nexgo.oaf.apiv3.device.printer.LineOptionEntity;
|
||||
import com.nexgo.oaf.apiv3.device.printer.Printer;
|
||||
import com.utsmyanmar.baselib.BaseApplication;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusHost;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusMerchant;
|
||||
@ -20,12 +23,14 @@ import com.utsmyanmar.baselib.util.DataBindingConfig;
|
||||
import com.utsmyanmar.paylibs.Constant;
|
||||
import com.utsmyanmar.paylibs.sign_on.EchoTestProcess;
|
||||
import com.utsmyanmar.paylibs.sign_on.SignOnListener;
|
||||
import com.utsmyanmar.paylibs.utils.LogUtil;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
import com.utsmm.kbz.BR;
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.ui.core_viewmodel.SharedViewModel;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Observable;
|
||||
|
||||
public class NaviMainFragment extends DataBindingFragment {
|
||||
|
||||
@ -115,6 +120,36 @@ public class NaviMainFragment extends DataBindingFragment {
|
||||
|
||||
public class ClickEvent {
|
||||
|
||||
private static final String PREF_NAME = "pinpad_prefs";
|
||||
private static final String KEY_PINPAD_SOUND = "pinpad_sound_enabled";
|
||||
|
||||
public final ObservableBoolean pinpadSoundEnabled;
|
||||
|
||||
public ClickEvent() {
|
||||
boolean savedValue = loadPinpadSoundState();
|
||||
this.pinpadSoundEnabled = new ObservableBoolean(savedValue);
|
||||
|
||||
BaseApplication.getInstance().deviceEngine.getPlatform().enablePinpadBeep(savedValue);
|
||||
}
|
||||
|
||||
public boolean loadPinpadSoundState(){
|
||||
return BaseApplication.getInstance().getSharedPreferences(PREF_NAME, Context.MODE_PRIVATE).getBoolean(KEY_PINPAD_SOUND, true);
|
||||
}
|
||||
|
||||
public void savePinpadSoundState(boolean enabled){
|
||||
BaseApplication.getInstance().getSharedPreferences(PREF_NAME, Context.MODE_PRIVATE).edit().putBoolean(KEY_PINPAD_SOUND, enabled).apply();
|
||||
}
|
||||
|
||||
public void onClickPinpadSound(){
|
||||
boolean newState = !pinpadSoundEnabled.get();
|
||||
int result = BaseApplication.getInstance().deviceEngine.getPlatform().enablePinpadBeep(newState);
|
||||
if(result == SdkResult.Success){
|
||||
pinpadSoundEnabled.set(newState);
|
||||
savePinpadSoundState(newState);
|
||||
// LogUtil.d("NaviMainFragment", "pinpad enabled");
|
||||
}
|
||||
}
|
||||
|
||||
public void onClickEcho() {
|
||||
showLoadingDialog("Sending Echo!");
|
||||
processEchoTest(false);
|
||||
|
||||
@ -359,7 +359,10 @@ public class PinPadViewModel extends ViewModel {
|
||||
handler.obtainMessage(ON_ERROR_PIN_PAD,retCode).sendToTarget();
|
||||
}
|
||||
LogUtil.d(TAG,"RetCode:"+retCode);
|
||||
if(retCode != SdkResult.PinPad_No_Pin_Input) {
|
||||
payDetail.setPINCipher(ByteUtil.bytes2HexStr(data));
|
||||
}
|
||||
|
||||
LogUtil.d(TAG,"data bytes:"+ByteUtil.bytes2HexStr(data));
|
||||
}
|
||||
|
||||
|
||||
@ -5,6 +5,7 @@ import androidx.lifecycle.ViewModelProvider;
|
||||
import androidx.navigation.fragment.NavHostFragment;
|
||||
|
||||
import com.utsmm.kbz.BR;
|
||||
import com.utsmm.kbz.MainActivity;
|
||||
import com.utsmm.kbz.MainViewModel;
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.config.Constants;
|
||||
|
||||
@ -42,8 +42,7 @@ public class RefundCertificateManager {
|
||||
return;
|
||||
};
|
||||
|
||||
// String downloadBase = tmsAddress.trim() + "/api/v1/file/download?filePath="; //local
|
||||
String downloadBase = tmsAddress.trim() + "/file/download?filePath="; // uat and prod
|
||||
String downloadBase = tmsAddress.trim() + "/file/download?filePath=";
|
||||
|
||||
String certUrl = SystemParamsOperation.getInstance().getCertificateUrl();
|
||||
String clientCertUrl = SystemParamsOperation.getInstance().getCertificateClientUrl();
|
||||
|
||||
@ -44,6 +44,8 @@ public class HostConfigViewModel extends ViewModel {
|
||||
|
||||
// Third Host
|
||||
public MutableLiveData<String> thirdHostName = new MutableLiveData<>();
|
||||
public MutableLiveData<String> thirdHostTid = new MutableLiveData<>();
|
||||
public MutableLiveData<String> thirdHostMid = new MutableLiveData<>();
|
||||
public MutableLiveData<String> thirdHostShortCode = new MutableLiveData<>();
|
||||
public MutableLiveData<String> thirdHostPrimaryIp = new MutableLiveData<>();
|
||||
public MutableLiveData<String> thirdHostPrimaryPort = new MutableLiveData<>();
|
||||
@ -96,6 +98,8 @@ public class HostConfigViewModel extends ViewModel {
|
||||
|
||||
if (sp.getThirdHostName() != null && !sp.getThirdHostName().isEmpty()) {
|
||||
thirdHostName.setValue(sp.getThirdHostName());
|
||||
thirdHostTid.setValue(sp.getThirdHostTerminalId());
|
||||
thirdHostMid.setValue(sp.getThirdHostMerchantId());
|
||||
thirdHostShortCode.setValue(sp.getThirdHostShortCode());
|
||||
|
||||
String[] thp = split(sp.getThirdHostIpAddress());
|
||||
|
||||
@ -15,7 +15,6 @@ import com.nexgo.downloadkey.downloadflow.DownloadFlowResultEntity;
|
||||
import com.nexgo.downloadkey.downloadflow.DownloadResult;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.util.DataBindingConfig;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
import com.utsmm.kbz.BR;
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.databinding.FragmentInjectKeyBinding;
|
||||
@ -84,22 +83,11 @@ public class InjectKeyFragment extends DataBindingFragment {
|
||||
}
|
||||
|
||||
private void updateConfigurationInfo() {
|
||||
binding.serialNumberValue.setText(getDisplayValue(TMSUtil.getInstance().getSerialNumber()));
|
||||
}
|
||||
|
||||
String terminalId = SystemParamsOperation.getInstance().getTerminalId();
|
||||
binding.terminalIdValue.setText(terminalId != null && !terminalId.isEmpty() ?
|
||||
terminalId : "Not configured");
|
||||
|
||||
// Update Merchant ID
|
||||
String merchantId = SystemParamsOperation.getInstance().getMerchantId();
|
||||
binding.merchantIdValue.setText(merchantId != null && !merchantId.isEmpty() ?
|
||||
merchantId : "Not configured");
|
||||
|
||||
// Update Serial Number
|
||||
String serialNo = TMSUtil.getInstance().getSerialNumber();
|
||||
binding.serialNumberValue.setText(serialNo != null && !serialNo.isEmpty() ?
|
||||
serialNo : "Not configured");
|
||||
|
||||
|
||||
private String getDisplayValue(String value) {
|
||||
return !TextUtils.isEmpty(value) ? value : "Not configured";
|
||||
}
|
||||
|
||||
private void loadKeyFromKeyPOS() {
|
||||
@ -122,21 +110,18 @@ public class InjectKeyFragment extends DataBindingFragment {
|
||||
|
||||
mDownloadFlow = DownloadFlow.getInstance();
|
||||
|
||||
String terminalId = SystemParamsOperation.getInstance().getTerminalId();
|
||||
String merchantId = SystemParamsOperation.getInstance().getMerchantId();
|
||||
String serialNo = TMSUtil.getInstance().getSerialNumber();
|
||||
|
||||
// Validate configuration
|
||||
if (TextUtils.isEmpty(terminalId) || TextUtils.isEmpty(merchantId) || TextUtils.isEmpty(serialNo)) {
|
||||
if (TextUtils.isEmpty(serialNo)) {
|
||||
dismissLoadingDialog();
|
||||
showDeclineDialog("Please configure Terminal ID, Merchant ID first in TMS Configuration");
|
||||
showDeclineDialog("Serial number is not configured");
|
||||
return;
|
||||
}
|
||||
|
||||
final DownloadFEntity downloadFEntity = new DownloadFEntity();
|
||||
downloadFEntity.setSn(serialNo.getBytes());
|
||||
downloadFEntity.setMid(merchantId.getBytes());
|
||||
downloadFEntity.setTid(terminalId.getBytes());
|
||||
downloadFEntity.setMid(null);
|
||||
downloadFEntity.setTid(null);
|
||||
downloadFEntity.setTmkIndex(keyIndexTmp);
|
||||
downloadFEntity.setPort(0);
|
||||
downloadFEntity.setTimeOut(10);
|
||||
|
||||
@ -86,6 +86,7 @@ public class QRSettlementTransactionFragment extends DataBindingFragment impleme
|
||||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
sharedViewModel.printerDisabled.setValue(!SystemParamsOperation.getInstance().getPrinterEnabled());
|
||||
setToolBarTitleWithBackIcon(getString(R.string.title_qr_settlement));
|
||||
|
||||
String merchantName = SystemParamsOperation.getInstance().getMerchantName();
|
||||
@ -134,7 +135,7 @@ public class QRSettlementTransactionFragment extends DataBindingFragment impleme
|
||||
managementViewModel.detailReportLayoutLoadingVisibility.setValue(8);
|
||||
managementViewModel.detailReportLayoutVisibility.setValue(8);
|
||||
managementViewModel.detailReportLayoutViewVisibility.setValue(0);
|
||||
managementViewModel.detailReportBottomLayoutVisibility.setValue(0);
|
||||
managementViewModel.detailReportBottomLayoutVisibility.setValue(isLastSettlementPrinterDisabled() ? 8 : 0);
|
||||
}
|
||||
|
||||
private void showEmptyDataView() {
|
||||
@ -149,6 +150,13 @@ public class QRSettlementTransactionFragment extends DataBindingFragment impleme
|
||||
managementViewModel.cardTypeDR.setValue("QR PAY");
|
||||
}
|
||||
|
||||
private boolean isLastSettlementPrinterDisabled() {
|
||||
Boolean printerDisabled = sharedViewModel.printerDisabled.getValue();
|
||||
return sharedViewModel.getTransMenu().getValue() == TransMenu.LAST_SETTLEMENT
|
||||
&& printerDisabled != null
|
||||
&& printerDisabled;
|
||||
}
|
||||
|
||||
private void observeQRTransactions() {
|
||||
managementViewModel.getTransactionHistory().observe(getViewLifecycleOwner(), payDetailList -> {
|
||||
if (payDetailList != null) {
|
||||
|
||||
@ -9,10 +9,14 @@ import androidx.annotation.Nullable;
|
||||
import androidx.lifecycle.Observer;
|
||||
|
||||
import com.utsmm.kbz.ui.management.ManagementViewModel;
|
||||
import com.utsmm.kbz.ui.settlement.model.CurrencyBucket;
|
||||
import com.utsmm.kbz.util.CurrencySelectionHelper;
|
||||
import com.utsmm.kbz.util.EReceiptUtil;
|
||||
import com.utsmm.kbz.util.enums.TransactionStatus;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.network.model.e_receipt.EReceiptRequest;
|
||||
import com.utsmyanmar.baselib.util.DataBindingConfig;
|
||||
import com.utsmyanmar.paylibs.model.CardSettleData;
|
||||
import com.utsmyanmar.paylibs.model.PayDetail;
|
||||
import com.utsmyanmar.paylibs.model.TradeData;
|
||||
import com.utsmyanmar.paylibs.print.printx.PrintXStatus;
|
||||
@ -32,6 +36,7 @@ import com.utsmm.kbz.ui.core_viewmodel.SharedViewModel;
|
||||
import com.utsmm.kbz.util.ecr.CoreUtils;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
|
||||
|
||||
public class SettlementTransactionFragment extends DataBindingFragment implements DataBindingFragment.BackPressCallback{
|
||||
@ -42,7 +47,7 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
private SharedViewModel sharedViewModel;
|
||||
|
||||
private ManagementViewModel managementViewModel;
|
||||
|
||||
private CurrencySelectionHelper currencySelectionHelper;
|
||||
private int routeId;
|
||||
|
||||
int saleCount = 0;
|
||||
@ -54,11 +59,16 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
long refundAmount = 0;
|
||||
long caAmount = 0;
|
||||
|
||||
private final CurrencyBucket mmkBucket = new CurrencyBucket();
|
||||
private final CurrencyBucket usdBucket = new CurrencyBucket();
|
||||
|
||||
@Override
|
||||
protected void initViewModel() {
|
||||
settlementViewModel = getFragmentScopeViewModel(SettlementViewModel.class);
|
||||
sharedViewModel = getFragmentScopeViewModel(SharedViewModel.class);
|
||||
managementViewModel = getFragmentScopeViewModel(ManagementViewModel.class);
|
||||
|
||||
currencySelectionHelper = new CurrencySelectionHelper(this, sharedViewModel);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -88,6 +98,8 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
boolean printerDisabled = !SystemParamsOperation.getInstance().getPrinterEnabled();
|
||||
sharedViewModel.printerDisabled.setValue(printerDisabled);
|
||||
|
||||
if(sharedViewModel.getTransMenu().getValue() == TransMenu.LAST_SETTLEMENT) {
|
||||
setToolBarTitleWithBackIcon(getString(R.string.txt_subtitle_reprint_last_settle_report));
|
||||
@ -103,6 +115,8 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
|
||||
if(sharedViewModel.getTransMenu().getValue() == TransMenu.REVIEW_BATCH){
|
||||
settlementViewModel.btmLayout.setValue(8);
|
||||
} else if(sharedViewModel.getTransMenu().getValue() == TransMenu.LAST_SETTLEMENT && printerDisabled) {
|
||||
settlementViewModel.btmLayout.setValue(8);
|
||||
} else {
|
||||
settlementViewModel.btmLayout.setValue(0);
|
||||
}
|
||||
@ -170,6 +184,7 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
caCount = payDetail.getSettleDataObj().getCashAdvanceCount();
|
||||
caAmount = payDetail.getSettleDataObj().getCashAdvanceAmount();
|
||||
|
||||
applyStoredCurrencyBreakdown(payDetail);
|
||||
|
||||
settlementViewModel.isNoData.setValue(false);
|
||||
|
||||
@ -222,20 +237,24 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
if((transType == TransactionType.SALE || "SALE".equalsIgnoreCase(transName)) && !payDetail.isCanceled){
|
||||
saleCount ++;
|
||||
saleAmount += payDetail.getAmount();
|
||||
addToCurrencyBucket(payDetail, BucketType.SALE);
|
||||
} else if((transType == TransactionType.PRE_SALE_COMPLETE
|
||||
|| "PREAUTH COMPLETION".equalsIgnoreCase(transName)
|
||||
|| "PRE_AUTH_COMPLETE".equalsIgnoreCase(transName)) && !payDetail.isCanceled){
|
||||
preCount ++;
|
||||
preAmount += payDetail.getAmount();
|
||||
addToCurrencyBucket(payDetail, BucketType.PRE_AUTH_COMPLETE);
|
||||
}
|
||||
else if(transType == TransactionType.REFUND || "REFUND".equalsIgnoreCase(transName)){
|
||||
refundCount ++;
|
||||
refundAmount += payDetail.getAmount();
|
||||
addToCurrencyBucket(payDetail, BucketType.REFUND);
|
||||
}else if(transType == TransactionType.CASH_ADVANCE
|
||||
|| "CASH_OUT".equalsIgnoreCase(transName)
|
||||
|| "CASH_ADVANCE".equalsIgnoreCase(transName)){
|
||||
caCount ++;
|
||||
caAmount += payDetail.getAmount();
|
||||
addToCurrencyBucket(payDetail, BucketType.CASH_ADVANCE);
|
||||
}
|
||||
}
|
||||
long totalAmount = saleAmount + preAmount + caAmount;
|
||||
@ -276,6 +295,8 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
preAmount = 0L;
|
||||
refundAmount = 0L;
|
||||
caAmount = 0L;
|
||||
resetCurrencyBucket(mmkBucket);
|
||||
resetCurrencyBucket(usdBucket);
|
||||
}
|
||||
|
||||
private void setSettlementViewModelData(int saleCount,long saleAmount,int preCount,long preAmount,int refundCount,long refundAmount,int caCount,long caAmount) {
|
||||
@ -287,6 +308,10 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
settlementViewModel.refund_amount.setValue(refundAmount);
|
||||
settlementViewModel.ca_count.setValue(caCount);
|
||||
settlementViewModel.ca_amount.setValue(caAmount);
|
||||
settlementViewModel.sale_breakdown.setValue(buildBreakdownText(mmkBucket.saleCount, mmkBucket.saleAmount, usdBucket.saleCount, usdBucket.saleAmount));
|
||||
settlementViewModel.pre_breakdown.setValue(buildBreakdownText(mmkBucket.preCount, mmkBucket.preAmount, usdBucket.preCount, usdBucket.preAmount));
|
||||
settlementViewModel.refund_breakdown.setValue(buildBreakdownText(mmkBucket.refundCount, mmkBucket.refundAmount, usdBucket.refundCount, usdBucket.refundAmount));
|
||||
settlementViewModel.ca_breakdown.setValue(buildBreakdownText(mmkBucket.caCount, mmkBucket.caAmount, usdBucket.caCount, usdBucket.caAmount));
|
||||
|
||||
if(sharedViewModel.getTransMenu().getValue() == TransMenu.REVIEW_BATCH) {
|
||||
SettleData settleData = new SettleData(saleCount,saleAmount,preCount,preAmount,refundCount,refundAmount,caCount,caAmount);
|
||||
@ -300,6 +325,118 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
|
||||
}
|
||||
|
||||
private enum BucketType {
|
||||
SALE,
|
||||
PRE_AUTH_COMPLETE,
|
||||
REFUND,
|
||||
CASH_ADVANCE
|
||||
}
|
||||
|
||||
|
||||
|
||||
private void resetCurrencyBucket(CurrencyBucket bucket) {
|
||||
bucket.saleCount = 0;
|
||||
bucket.saleAmount = 0L;
|
||||
bucket.preCount = 0;
|
||||
bucket.preAmount = 0L;
|
||||
bucket.refundCount = 0;
|
||||
bucket.refundAmount = 0L;
|
||||
bucket.caCount = 0;
|
||||
bucket.caAmount = 0L;
|
||||
}
|
||||
|
||||
private void addToCurrencyBucket(PayDetail payDetail, BucketType bucketType) {
|
||||
CurrencyBucket bucket = getCurrencyBucket(payDetail.getCurrencyCode());
|
||||
long amount = payDetail.getAmount();
|
||||
switch (bucketType) {
|
||||
case SALE:
|
||||
bucket.saleCount++;
|
||||
bucket.saleAmount += amount;
|
||||
break;
|
||||
case PRE_AUTH_COMPLETE:
|
||||
bucket.preCount++;
|
||||
bucket.preAmount += amount;
|
||||
break;
|
||||
case REFUND:
|
||||
bucket.refundCount++;
|
||||
bucket.refundAmount += amount;
|
||||
break;
|
||||
case CASH_ADVANCE:
|
||||
bucket.caCount++;
|
||||
bucket.caAmount += amount;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private CurrencyBucket getCurrencyBucket(String currencyCode) {
|
||||
return "USD".equals(normalizeCurrency(currencyCode)) ? usdBucket : mmkBucket;
|
||||
}
|
||||
|
||||
private void applyStoredCurrencyBreakdown(PayDetail payDetail) {
|
||||
resetCurrencyBucket(mmkBucket);
|
||||
resetCurrencyBucket(usdBucket);
|
||||
|
||||
List<CardSettleData> cardSettleDataList = payDetail.getCardSettleData();
|
||||
if (cardSettleDataList != null && !cardSettleDataList.isEmpty()) {
|
||||
for (CardSettleData item : cardSettleDataList) {
|
||||
applyStoredCardSettle(item);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
String normalizedCurrency = normalizeCurrency(payDetail.getCurrencyCode());
|
||||
CurrencyBucket bucket = "USD".equals(normalizedCurrency) ? usdBucket : mmkBucket;
|
||||
bucket.saleCount = saleCount;
|
||||
bucket.saleAmount = saleAmount;
|
||||
bucket.preCount = preCount;
|
||||
bucket.preAmount = preAmount;
|
||||
bucket.refundCount = refundCount;
|
||||
bucket.refundAmount = refundAmount;
|
||||
bucket.caCount = caCount;
|
||||
bucket.caAmount = caAmount;
|
||||
}
|
||||
|
||||
private void applyStoredCardSettle(CardSettleData item) {
|
||||
CurrencyBucket bucket = getCurrencyBucket(item.getCurrencyCode());
|
||||
String transType = item.getTransType() == null ? "" : item.getTransType().trim().toUpperCase(Locale.getDefault());
|
||||
|
||||
if ("SALE".equals(transType)) {
|
||||
bucket.saleCount++;
|
||||
bucket.saleAmount += item.getAmount();
|
||||
} else if ("PREAUTH COMPLETION".equals(transType) || "PRE_AUTH_COMPLETE".equals(transType)) {
|
||||
bucket.preCount++;
|
||||
bucket.preAmount += item.getAmount();
|
||||
} else if ("REFUND".equals(transType)) {
|
||||
bucket.refundCount++;
|
||||
bucket.refundAmount += item.getAmount();
|
||||
} else if ("CASH_OUT".equals(transType) || "CASH_ADVANCE".equals(transType)) {
|
||||
bucket.caCount++;
|
||||
bucket.caAmount += item.getAmount();
|
||||
}
|
||||
}
|
||||
|
||||
private String buildBreakdownText(int mmkCount, long mmkAmount, int usdCount, long usdAmount) {
|
||||
return "MMK " + mmkCount + " / " + POSUtil.getInstance().getDecimalAmountSeparatorFormat(mmkAmount)
|
||||
+ " USD " + usdCount + " / " + POSUtil.getInstance().getDecimalAmountSeparatorFormat(usdAmount);
|
||||
}
|
||||
|
||||
private String normalizeCurrency(String currencyCode) {
|
||||
if (currencyCode == null) {
|
||||
return "MMK";
|
||||
}
|
||||
|
||||
String value = currencyCode.trim().toUpperCase(Locale.getDefault());
|
||||
switch (value) {
|
||||
case "840":
|
||||
case "USD":
|
||||
return "USD";
|
||||
case "104":
|
||||
case "MMK":
|
||||
default:
|
||||
return "MMK";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private void navigateMainScreen(){
|
||||
routeId = R.id.action_settlementTransactionFragment_to_nav_main;
|
||||
@ -311,15 +448,24 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
safeNavigateToRouteId();
|
||||
}
|
||||
|
||||
private boolean isUSDSettleNeeded() {
|
||||
return (usdBucket.saleCount != 0 || usdBucket.preCount != 0 || usdBucket.refundCount != 0 || usdBucket.caCount != 0);
|
||||
}
|
||||
private void networkCutOver() {
|
||||
EchoTestProcess.getInstance().enqueueCutOver().startSignOn(new SignOnListener() {
|
||||
@Override
|
||||
public void onSuccessSignOn() {
|
||||
|
||||
// showSuccessDialog("Approved!");
|
||||
if(settlementViewModel.resultString.getValue() != TransactionStatus.ON_FINAL_SUCCESS) {
|
||||
currencySelectionHelper.applyCardCurrencyAndHost("MMK");
|
||||
settlementViewModel.startSettlementProcess(mmkBucket,true);
|
||||
} else {
|
||||
navigateToNext();
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailureSignOn(Integer resultCode) {
|
||||
showDeclineDialog("Failure:"+resultCode);
|
||||
@ -345,12 +491,15 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
showLoadingDialog("Sending Batch Upload...");
|
||||
break;
|
||||
case ON_SUCCESS:
|
||||
updateData();
|
||||
dismissLoadingDialog();
|
||||
networkCutOver();
|
||||
break;
|
||||
case ON_FINAL_SUCCESS:
|
||||
dismissLoadingDialog();
|
||||
updateData();
|
||||
if (!SystemParamsOperation.getInstance().getDemoStatus()) {
|
||||
|
||||
networkCutOver(); // bpc
|
||||
navigateToNext();
|
||||
} else {
|
||||
navigateToNext();
|
||||
}
|
||||
@ -415,11 +564,22 @@ public class SettlementTransactionFragment extends DataBindingFragment implement
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
public void onConfirm(){
|
||||
|
||||
if(sharedViewModel.getTransMenu().getValue() == TransMenu.SETTLEMENT) {
|
||||
/* April 10 , 2024 Smile requested not to send to host even settlement button was clicked */
|
||||
settlementViewModel.startSettlementProcess();
|
||||
|
||||
if(isUSDSettleNeeded()) {
|
||||
currencySelectionHelper.applyCardCurrencyAndHost("USD");
|
||||
settlementViewModel.startSettlementProcess(usdBucket,false);
|
||||
} else {
|
||||
currencySelectionHelper.applyCardCurrencyAndHost("MMK");
|
||||
settlementViewModel.startSettlementProcess(mmkBucket,true);
|
||||
}
|
||||
|
||||
|
||||
showLoadingDialog("Sending ...");
|
||||
} else if(sharedViewModel.getTransMenu().getValue() == TransMenu.REVIEW_BATCH) {
|
||||
sharedViewModel.startPrintSettlement(new PrintXStatus() {
|
||||
|
||||
@ -7,6 +7,7 @@ import androidx.lifecycle.LiveData;
|
||||
import androidx.lifecycle.MutableLiveData;
|
||||
import androidx.lifecycle.ViewModel;
|
||||
|
||||
import com.utsmm.kbz.ui.settlement.model.CurrencyBucket;
|
||||
import com.utsmm.kbz.util.EReceiptUtil;
|
||||
import com.utsmyanmar.baselib.network.model.e_receipt.EReceiptRequest;
|
||||
import com.utsmyanmar.baselib.repo.Repository;
|
||||
@ -75,15 +76,19 @@ public class SettlementViewModel extends ViewModel {
|
||||
|
||||
public SingleLiveEvent<Integer> sale_count = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<Long> sale_amount = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<String> sale_breakdown = new SingleLiveEvent<>();
|
||||
|
||||
public SingleLiveEvent<Integer> pre_count = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<Long> pre_amount = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<String> pre_breakdown = new SingleLiveEvent<>();
|
||||
|
||||
public SingleLiveEvent<Integer> refund_count = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<Long> refund_amount = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<String> refund_breakdown = new SingleLiveEvent<>();
|
||||
|
||||
public SingleLiveEvent<Integer> ca_count = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<Long> ca_amount = new SingleLiveEvent<>();
|
||||
public SingleLiveEvent<String> ca_breakdown = new SingleLiveEvent<>();
|
||||
|
||||
public SingleLiveEvent<SettlementType> settlementType = new SingleLiveEvent<>();
|
||||
|
||||
@ -111,18 +116,26 @@ public class SettlementViewModel extends ViewModel {
|
||||
private ISOMsgX isoMsgX;
|
||||
|
||||
|
||||
public CurrencyBucket currentBucket= new CurrencyBucket();
|
||||
|
||||
private boolean isLast = true;
|
||||
|
||||
@Inject
|
||||
public SettlementViewModel(Repository repository) {
|
||||
this.repository = repository;
|
||||
|
||||
sale_count.setValue(0);
|
||||
sale_amount.setValue(0L);
|
||||
sale_breakdown.setValue("");
|
||||
pre_count.setValue(0);
|
||||
pre_amount.setValue(0L);
|
||||
pre_breakdown.setValue("");
|
||||
refund_count.setValue(0);
|
||||
refund_amount.setValue(0L);
|
||||
refund_breakdown.setValue("");
|
||||
ca_count.setValue(0);
|
||||
ca_amount.setValue(0L);
|
||||
ca_breakdown.setValue("");
|
||||
|
||||
isoMsgX = new ISOMsgX.ISOMsgXBuilder(ISOVersion.VERSION_1993, ISOMode.BOTH_HEADER_TPDU,HostName.BPC)
|
||||
.build();
|
||||
@ -221,14 +234,7 @@ public class SettlementViewModel extends ViewModel {
|
||||
if(payDetails != null && payDetails.size() > 0) {
|
||||
for (PayDetail pay:payDetails) {
|
||||
|
||||
// if(paydetail.getTransactionType() == TransactionsType.SALE.value) {
|
||||
// paydetail.setIsSettle(true);
|
||||
// updatePayDetail(paydetail);
|
||||
// } else {
|
||||
deletePayDetail(pay);
|
||||
// repository.deletePayDetail(paydetail);
|
||||
// }
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
@ -257,22 +263,14 @@ public class SettlementViewModel extends ViewModel {
|
||||
|
||||
|
||||
@SuppressWarnings("ConstantConditions")
|
||||
public void startSettlementProcess() {
|
||||
saleCount = sale_count.getValue();
|
||||
saleAmount = sale_amount.getValue();
|
||||
preAuthCount = pre_count.getValue();
|
||||
preAuthAmount = pre_amount.getValue();
|
||||
refundCount = refund_count.getValue();
|
||||
refundAmount = refund_amount.getValue();
|
||||
caCount = ca_count.getValue();
|
||||
caAmount = ca_amount.getValue();
|
||||
|
||||
public void startSettlementProcess(CurrencyBucket currencyBucket,boolean isLast) {
|
||||
this.isLast = isLast;
|
||||
SystemParamsOperation.getInstance().getIncrementBatchNo();
|
||||
|
||||
if(SystemParamsOperation.getInstance().getDemoStatus()) {
|
||||
requestDemoProcessSettlement();
|
||||
requestDemoProcessSettlement(currencyBucket);
|
||||
} else {
|
||||
requestOnlineProcessSettlement();
|
||||
requestOnlineProcessSettlement(currencyBucket);
|
||||
}
|
||||
|
||||
}
|
||||
@ -291,7 +289,7 @@ public class SettlementViewModel extends ViewModel {
|
||||
|
||||
|
||||
|
||||
private void requestDemoProcessSettlement() {
|
||||
private void requestDemoProcessSettlement(CurrencyBucket currencyBucket) {
|
||||
|
||||
|
||||
TradeData tradeData = Params.newTrade(true);
|
||||
@ -313,18 +311,18 @@ public class SettlementViewModel extends ViewModel {
|
||||
payDetail.setBatchNo(SystemParamsOperation.getInstance().getCurrentBatchNum()); //for print receipt
|
||||
|
||||
/*POS*/
|
||||
payDetail.setSettleList(sale_count.getValue() + ":" + sale_amount.getValue() + "-" + ca_count.getValue() + ":" + ca_amount.getValue() + "-" + refund_count.getValue() + ":" + refund_amount.getValue() + "-" + pre_count.getValue() + ":" + pre_amount.getValue()); // for print receipt
|
||||
payDetail.setSettleList(currencyBucket.saleCount+ ":" + currencyBucket.saleAmount + "-" + currencyBucket.caCount + ":" + currencyBucket.caAmount + "-" + currencyBucket.refundCount + ":" + currencyBucket.refundAmount + "-" + currencyBucket.preCount + ":" + currencyBucket.preAmount); // for print receipt
|
||||
/*POS*/
|
||||
SettleData settleData = new SettleData(saleCount,saleAmount,preAuthCount,preAuthAmount,refundCount,refundAmount,caCount,caAmount);
|
||||
SettleData settleData = new SettleData(currencyBucket.saleCount, currencyBucket.saleAmount, currencyBucket.preCount, currencyBucket.preAmount, currencyBucket.refundCount, currencyBucket.refundAmount, currencyBucket.caCount, currencyBucket.caAmount);
|
||||
payDetail.setSettleDataObj(settleData);
|
||||
|
||||
long totalAmount = saleAmount + preAuthAmount + refundAmount + caAmount;
|
||||
long totalAmount = currencyBucket.saleAmount + currencyBucket.preAmount + currencyBucket.refundAmount + currencyBucket.caAmount;
|
||||
|
||||
String settlementData = "";
|
||||
if(refundAmount != 0L) {
|
||||
if(currencyBucket.refundAmount != 0L) {
|
||||
|
||||
long creditTotal = saleAmount + preAuthAmount + caAmount;
|
||||
long subTotal = creditTotal - refundAmount;
|
||||
long creditTotal = currencyBucket.saleAmount + currencyBucket.preAmount + currencyBucket.caAmount;
|
||||
long subTotal = creditTotal - currencyBucket.refundAmount;
|
||||
|
||||
if(subTotal < 0L) {
|
||||
settlementData = "D"+ String.format(Locale.getDefault(), "%012d", Math.abs(subTotal));
|
||||
@ -343,27 +341,27 @@ public class SettlementViewModel extends ViewModel {
|
||||
updateDB();
|
||||
insertPayDetail(payDetail);
|
||||
|
||||
resultString.postValue(TransactionStatus.ON_SUCCESS);
|
||||
resultString.postValue(TransactionStatus.ON_FINAL_SUCCESS);
|
||||
}
|
||||
|
||||
private void requestOnlineProcessSettlement() {
|
||||
|
||||
private void requestOnlineProcessSettlement(CurrencyBucket currencyBucket) {
|
||||
|
||||
currentBucket = currencyBucket;
|
||||
|
||||
HostName hostName = HostName.BPC;
|
||||
|
||||
|
||||
String field60 = SystemParamsOperation.getInstance().getCurrentBatchNum();
|
||||
|
||||
int sale2Count = saleCount + preAuthCount;
|
||||
long sale2Amount = saleAmount + preAuthAmount;
|
||||
int sale2Count = currencyBucket.saleCount + currencyBucket.preCount;
|
||||
long sale2Amount = currencyBucket.saleAmount + currencyBucket.preAmount;
|
||||
|
||||
String totalSaleCount = String.format(Locale.getDefault(), "%03d", sale2Count);
|
||||
String totalSaleAmount = String.format(Locale.getDefault(), "%010d00", sale2Amount);
|
||||
String totalRefundCount = String.format(Locale.getDefault(), "%03d", refundCount);
|
||||
String totalRefundAmount = String.format(Locale.getDefault(), "%010d00", refundAmount == 0L ? 0 : refundAmount);
|
||||
String totalDebitSaleCount = String.format(Locale.getDefault(), "%03d", caCount);
|
||||
String totalDebitSaleAmount = String.format(Locale.getDefault(), "%010d00", caAmount == 0L ? 0 : caAmount);
|
||||
String totalRefundCount = String.format(Locale.getDefault(), "%03d", currencyBucket.refundCount);
|
||||
String totalRefundAmount = String.format(Locale.getDefault(), "%010d00", currencyBucket.refundAmount == 0L ? 0 : currencyBucket.refundAmount);
|
||||
String totalDebitSaleCount = String.format(Locale.getDefault(), "%03d", currencyBucket.caCount);
|
||||
String totalDebitSaleAmount = String.format(Locale.getDefault(), "%010d00", currencyBucket.caAmount == 0L ? 0 : currencyBucket.caAmount);
|
||||
String totalERefundCount = String.format(Locale.getDefault(), "%03d", 0);
|
||||
String totalERefundAmount = String.format(Locale.getDefault(), "%010d00", 0);
|
||||
|
||||
@ -394,26 +392,32 @@ public class SettlementViewModel extends ViewModel {
|
||||
|
||||
}
|
||||
|
||||
if(isLast) {
|
||||
payDetail.setCurrencyCode("104");
|
||||
} else {
|
||||
payDetail.setCurrencyCode("840");
|
||||
}
|
||||
|
||||
// CA:CA - CD - FT
|
||||
payDetail.setBatchNo(SystemParamsOperation.getInstance().getCurrentBatchNum()); //for print receipt
|
||||
|
||||
/*POS*/
|
||||
payDetail.setSettleList(sale_count.getValue() + ":" + sale_amount.getValue() + "-" + ca_count.getValue() + ":" + ca_amount.getValue() + "-" + refund_count.getValue() + ":" + refund_amount.getValue() + "-" + pre_count.getValue() + ":" + pre_amount.getValue()); // for print receipt
|
||||
payDetail.setSettleList(currencyBucket.saleCount+ ":" + currencyBucket.saleAmount + "-" + currencyBucket.caCount + ":" + currencyBucket.caAmount + "-" + currencyBucket.refundCount + ":" + currencyBucket.refundAmount + "-" + currencyBucket.preCount + ":" + currencyBucket.preAmount); // for print receipt
|
||||
/*POS*/
|
||||
SettleData settleData = new SettleData(saleCount,saleAmount,preAuthCount,preAuthAmount,refundCount,refundAmount,caCount,caAmount);
|
||||
SettleData settleData = new SettleData(currencyBucket.saleCount, currencyBucket.saleAmount, currencyBucket.preCount, currencyBucket.preAmount, currencyBucket.refundCount, currencyBucket.refundAmount, currencyBucket.caCount, currencyBucket.caAmount);
|
||||
payDetail.setSettleDataObj(settleData);
|
||||
|
||||
if(payDetails != null)
|
||||
payDetail.setCardSettleData(CardSettleData.convertFromPayDetail(payDetails));
|
||||
|
||||
if(hostName == HostName.BPC) {
|
||||
long totalAmount = saleAmount + preAuthAmount + refundAmount + caAmount;
|
||||
long totalAmount = currencyBucket.saleAmount + currencyBucket.preAmount + currencyBucket.refundAmount + currencyBucket.caAmount;
|
||||
|
||||
String settlementData = "";
|
||||
if(refundAmount != 0L) {
|
||||
if(currencyBucket.refundAmount != 0L) {
|
||||
|
||||
long creditTotal = saleAmount + preAuthAmount + caAmount;
|
||||
long subTotal = creditTotal - refundAmount;
|
||||
long creditTotal = currencyBucket.saleAmount + currencyBucket.preAmount + currencyBucket.caAmount;
|
||||
long subTotal = creditTotal - currencyBucket.refundAmount;
|
||||
|
||||
if(subTotal < 0L) {
|
||||
settlementData = "D"+ String.format(Locale.getDefault(), "%012d", Math.abs(subTotal));
|
||||
@ -462,11 +466,7 @@ public class SettlementViewModel extends ViewModel {
|
||||
} else if (TextUtils.equals(resultStr, "95") || TextUtils.equals(resultStr, "095")) {
|
||||
//reversal
|
||||
// if (!flag && isNoData.getValue()) {
|
||||
if (!flag ) {
|
||||
payDetail.setIsNeedReversal(true);
|
||||
} else {
|
||||
payDetail.setIsNeedReversal(false);
|
||||
}
|
||||
payDetail.setIsNeedReversal(!flag);
|
||||
|
||||
}
|
||||
} else {
|
||||
@ -480,7 +480,7 @@ public class SettlementViewModel extends ViewModel {
|
||||
if (!isSecondCall) {
|
||||
ISOSocket.getInstance().switchIp();
|
||||
resultString.postValue(TransactionStatus.ON_SECONDARY);
|
||||
requestOnlineProcessSettlement();
|
||||
requestOnlineProcessSettlement(currencyBucket);
|
||||
isSecondCall = true;
|
||||
} else {
|
||||
resultString.postValue(TransactionStatus.ON_ERROR);
|
||||
@ -501,7 +501,7 @@ public class SettlementViewModel extends ViewModel {
|
||||
/* Batch Upload Start Here*/
|
||||
|
||||
flag = true;
|
||||
batchUploadProcess();
|
||||
batchUploadProcess(isLast);
|
||||
} else {
|
||||
|
||||
/* this flag is to send batch upload again when host response 95 next time */
|
||||
@ -512,52 +512,79 @@ public class SettlementViewModel extends ViewModel {
|
||||
|
||||
// to leave data for testing
|
||||
// if (settlementType.getValue() == SettlementType.NORMAL) {
|
||||
if(isLast) {
|
||||
updateDB();
|
||||
|
||||
|
||||
// }
|
||||
|
||||
|
||||
}
|
||||
|
||||
insertPayDetail(payDetail);
|
||||
|
||||
if (errorFlag) {
|
||||
resultString.postValue(TransactionStatus.ON_ERROR);
|
||||
} else {
|
||||
if(isLast) {
|
||||
resultString.postValue(TransactionStatus.ON_FINAL_SUCCESS);
|
||||
} else {
|
||||
resultString.postValue(TransactionStatus.ON_SUCCESS);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void batchUploadProcess() {
|
||||
private void batchUploadProcess(boolean isLast) {
|
||||
resultString.postValue(TransactionStatus.ON_BATCH_UPLOAD);
|
||||
|
||||
if(payDetails == null || payDetails.size() == 0){
|
||||
requestOnlineProcessSettlement();
|
||||
if (payDetails == null || payDetails.isEmpty()) {
|
||||
requestOnlineProcessSettlement(currentBucket);
|
||||
return;
|
||||
}
|
||||
|
||||
// Advance index, skipping entries that don't belong to this pass
|
||||
while (i < payDetails.size()) {
|
||||
PayDetail payDetail = payDetails.get(i);
|
||||
boolean isMMK = payDetail.getCurrencyCode().equals("104");
|
||||
|
||||
if (isLast && !isMMK) {
|
||||
// isLast = true → MMK pass, skip USD
|
||||
LogUtil.d(TAG, "Skipping USD transaction at index: " + i);
|
||||
i++;
|
||||
continue;
|
||||
} else if (!isLast && isMMK) {
|
||||
// isLast = false → USD pass, skip MMK
|
||||
LogUtil.d(TAG, "Skipping MMK transaction at index: " + i);
|
||||
i++;
|
||||
continue;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
if (i >= payDetails.size()) {
|
||||
requestOnlineProcessSettlement(currentBucket);
|
||||
return;
|
||||
}
|
||||
|
||||
PayDetail payDetail = payDetails.get(i);
|
||||
|
||||
TradeData tradeData = new TradeData();
|
||||
tradeData.setPayDetail(payDetail);
|
||||
BatchUploadProcess.getInstance().enqueue(tradeData).startBatchUpload(new BatchListener() {
|
||||
@Override
|
||||
public void onSuccessBatch() {
|
||||
LogUtil.e(TAG, "Batch Upload Success");
|
||||
LogUtil.d(TAG, "Pay detail Size: " + payDetails.size());
|
||||
LogUtil.d(TAG, "Count value: " + i);
|
||||
|
||||
if (i < payDetails.size() - 1) {
|
||||
LogUtil.d(TAG, "Pay detail Size:" + payDetails.size());
|
||||
LogUtil.d(TAG, "Count value:" + i);
|
||||
i++;
|
||||
batchUploadProcess();
|
||||
batchUploadProcess(isLast);
|
||||
} else {
|
||||
requestOnlineProcessSettlement();
|
||||
requestOnlineProcessSettlement(currentBucket);
|
||||
}
|
||||
|
||||
LogUtil.e(TAG, "Batch Upload Success");
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@ -0,0 +1,89 @@
|
||||
package com.utsmm.kbz.ui.settlement.model;
|
||||
|
||||
public class CurrencyBucket {
|
||||
public int saleCount;
|
||||
public long saleAmount;
|
||||
public int preCount;
|
||||
public long preAmount;
|
||||
public int refundCount;
|
||||
public long refundAmount;
|
||||
public int caCount;
|
||||
public long caAmount;
|
||||
|
||||
public CurrencyBucket(){}
|
||||
|
||||
public CurrencyBucket(int saleCount, long saleAmount, int preCount, long preAmount, int refundCount, long refundAmount, int caCount, long caAmount) {
|
||||
this.saleCount = saleCount;
|
||||
this.saleAmount = saleAmount;
|
||||
this.preCount = preCount;
|
||||
this.preAmount = preAmount;
|
||||
this.refundCount = refundCount;
|
||||
this.refundAmount = refundAmount;
|
||||
this.caCount = caCount;
|
||||
this.caAmount = caAmount;
|
||||
}
|
||||
|
||||
public void setSaleCount(int saleCount) {
|
||||
this.saleCount = saleCount;
|
||||
}
|
||||
|
||||
public void setSaleAmount(long saleAmount) {
|
||||
this.saleAmount = saleAmount;
|
||||
}
|
||||
|
||||
public void setPreCount(int preCount) {
|
||||
this.preCount = preCount;
|
||||
}
|
||||
|
||||
public void setPreAmount(long preAmount) {
|
||||
this.preAmount = preAmount;
|
||||
}
|
||||
|
||||
public void setRefundCount(int refundCount) {
|
||||
this.refundCount = refundCount;
|
||||
}
|
||||
|
||||
public void setRefundAmount(long refundAmount) {
|
||||
this.refundAmount = refundAmount;
|
||||
}
|
||||
|
||||
public void setCaCount(int caCount) {
|
||||
this.caCount = caCount;
|
||||
}
|
||||
|
||||
public void setCaAmount(long caAmount) {
|
||||
this.caAmount = caAmount;
|
||||
}
|
||||
|
||||
public int getSaleCount() {
|
||||
return saleCount;
|
||||
}
|
||||
|
||||
public long getSaleAmount() {
|
||||
return saleAmount;
|
||||
}
|
||||
|
||||
public int getPreCount() {
|
||||
return preCount;
|
||||
}
|
||||
|
||||
public long getPreAmount() {
|
||||
return preAmount;
|
||||
}
|
||||
|
||||
public int getRefundCount() {
|
||||
return refundCount;
|
||||
}
|
||||
|
||||
public long getRefundAmount() {
|
||||
return refundAmount;
|
||||
}
|
||||
|
||||
public int getCaCount() {
|
||||
return caCount;
|
||||
}
|
||||
|
||||
public long getCaAmount() {
|
||||
return caAmount;
|
||||
}
|
||||
}
|
||||
@ -13,7 +13,6 @@ import com.utsmm.kbz.BR;
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.config.Constants;
|
||||
import com.utsmm.kbz.util.enums.ResponseStatus;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
|
||||
/*
|
||||
* This file is not using in this project cuz IPEK is used instead of TMK.
|
||||
@ -56,7 +55,6 @@ public class SignOnFragment extends DataBindingFragment {
|
||||
super.onViewCreated(view, savedInstanceState);
|
||||
|
||||
signOnViewModel.startSignOnProcess();
|
||||
|
||||
observeData();
|
||||
}
|
||||
|
||||
|
||||
@ -15,6 +15,7 @@ import androidx.annotation.Nullable;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.stream.MalformedJsonException;
|
||||
import com.utsmm.kbz.MainActivity;
|
||||
import com.utsmm.kbz.service.AutoAlarmReceiver;
|
||||
import com.utsmyanmar.baselib.fragment.DataBindingFragment;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusError;
|
||||
@ -139,6 +140,8 @@ public class TMSProcessFragment extends DataBindingFragment {
|
||||
|
||||
private void downloadParams(String lastTransName,String lastTransTime,TMSUpdate tmsUpdate) {
|
||||
|
||||
((MainActivity) requireActivity()).getLocation();
|
||||
|
||||
tmsProcessViewModel.setTmsDownloadStatus(TMSDownloadStatus.DOWNLOADING);
|
||||
tmsProcessViewModel.setTmsDownloadMsg("Downloading...");
|
||||
|
||||
|
||||
@ -0,0 +1,269 @@
|
||||
package com.utsmm.kbz.util;
|
||||
|
||||
import android.text.TextUtils;
|
||||
import android.util.TypedValue;
|
||||
import android.view.Gravity;
|
||||
import android.widget.LinearLayout;
|
||||
import android.widget.TextView;
|
||||
|
||||
import androidx.appcompat.app.AlertDialog;
|
||||
import androidx.appcompat.widget.AppCompatButton;
|
||||
import androidx.core.content.ContextCompat;
|
||||
import androidx.fragment.app.Fragment;
|
||||
|
||||
import com.utsmm.kbz.R;
|
||||
import com.utsmm.kbz.ui.core_viewmodel.SharedViewModel;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
import com.utsmyanmar.paylibs.utils.enums.CurrencyType;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
|
||||
public class CurrencySelectionHelper {
|
||||
|
||||
private static boolean globalPrimaryHostCached = false;
|
||||
private static String globalPrimaryHostName = "";
|
||||
private static String globalPrimaryTid = "";
|
||||
private static String globalPrimaryMid = "";
|
||||
private static String globalPrimaryIp = "";
|
||||
private static String globalPrimarySecIp = "";
|
||||
private static CurrencyType globalPrimaryCurrency = CurrencyType.MMK;
|
||||
|
||||
private final Fragment fragment;
|
||||
private final SharedViewModel sharedViewModel;
|
||||
private String primaryHostName = "";
|
||||
private String primaryTid = "";
|
||||
private String primaryMid = "";
|
||||
private String primaryIp = "";
|
||||
private String primarySecIp = "";
|
||||
private CurrencyType primaryCurrency = CurrencyType.MMK;
|
||||
|
||||
public CurrencySelectionHelper(Fragment fragment, SharedViewModel sharedViewModel) {
|
||||
this.fragment = fragment;
|
||||
this.sharedViewModel = sharedViewModel;
|
||||
}
|
||||
|
||||
public void showCardCurrencyChooser(Runnable onSelected) {
|
||||
showCardCurrencyChooser(onSelected, null);
|
||||
}
|
||||
|
||||
public void showCardCurrencyChooser(Runnable onSelected, Runnable onCancelled) {
|
||||
List<String> currencies = getAvailableCardCurrencies();
|
||||
if (currencies.isEmpty()) {
|
||||
applyCardCurrencyAndHost("MMK");
|
||||
onSelected.run();
|
||||
return;
|
||||
}
|
||||
|
||||
if (currencies.size() == 1) {
|
||||
applyCardCurrencyAndHost(currencies.get(0));
|
||||
onSelected.run();
|
||||
return;
|
||||
}
|
||||
|
||||
showCurrencyPickerDialog("Choose Currency", currencies, currency -> {
|
||||
applyCardCurrencyAndHost(currency);
|
||||
onSelected.run();
|
||||
}, onCancelled);
|
||||
}
|
||||
|
||||
private List<String> getAvailableCardCurrencies() {
|
||||
cachePrimaryCardHostIfNeeded();
|
||||
LinkedHashSet<String> values = new LinkedHashSet<>();
|
||||
|
||||
if (primaryCurrency != null && !TextUtils.isEmpty(primaryCurrency.name)) {
|
||||
values.add(normalizeCurrency(primaryCurrency.name));
|
||||
}
|
||||
|
||||
if (!SystemParamsOperation.getInstance().getDuelCurrencyStatus()) {
|
||||
return new ArrayList<>(values);
|
||||
}
|
||||
|
||||
String secondaryCurrency = normalizeCurrency(SystemParamsOperation.getInstance().getThirdHostCurrency());
|
||||
if (!TextUtils.isEmpty(SystemParamsOperation.getInstance().getThirdHostName()) && !TextUtils.isEmpty(secondaryCurrency)) {
|
||||
values.add(secondaryCurrency);
|
||||
}
|
||||
|
||||
return new ArrayList<>(values);
|
||||
}
|
||||
|
||||
public void applyCardCurrencyAndHost(String selectedCurrency) {
|
||||
cachePrimaryCardHostIfNeeded();
|
||||
|
||||
String selected = normalizeCurrency(selectedCurrency);
|
||||
String secondaryCurrency = normalizeCurrency(SystemParamsOperation.getInstance().getThirdHostCurrency());
|
||||
boolean dualCurrencyEnabled = SystemParamsOperation.getInstance().getDuelCurrencyStatus();
|
||||
|
||||
boolean useSecondaryCardHost = dualCurrencyEnabled
|
||||
&& !TextUtils.isEmpty(SystemParamsOperation.getInstance().getThirdHostName())
|
||||
&& !TextUtils.isEmpty(secondaryCurrency)
|
||||
&& secondaryCurrency.equals(selected);
|
||||
|
||||
if (useSecondaryCardHost) {
|
||||
SystemParamsOperation.getInstance().setHostName(SystemParamsOperation.getInstance().getThirdHostName());
|
||||
SystemParamsOperation.getInstance().setTerminalId(SystemParamsOperation.getInstance().getThirdHostTerminalId());
|
||||
SystemParamsOperation.getInstance().setMerchantId(SystemParamsOperation.getInstance().getThirdHostMerchantId());
|
||||
SystemParamsOperation.getInstance().setIpAddress(SystemParamsOperation.getInstance().getThirdHostIpAddress());
|
||||
SystemParamsOperation.getInstance().setSecIpAddress(SystemParamsOperation.getInstance().getThirdHostSecIpAddress());
|
||||
} else {
|
||||
SystemParamsOperation.getInstance().setHostName(primaryHostName);
|
||||
SystemParamsOperation.getInstance().setTerminalId(primaryTid);
|
||||
SystemParamsOperation.getInstance().setMerchantId(primaryMid);
|
||||
SystemParamsOperation.getInstance().setIpAddress(primaryIp);
|
||||
SystemParamsOperation.getInstance().setSecIpAddress(primarySecIp);
|
||||
}
|
||||
|
||||
CurrencyType currencyType = useSecondaryCardHost ? toCurrencyType(selected) : primaryCurrency;
|
||||
SystemParamsOperation.getInstance().setCurrencyType(currencyType);
|
||||
if (sharedViewModel != null) {
|
||||
sharedViewModel.set_currencyText(currencyType.name);
|
||||
}
|
||||
}
|
||||
|
||||
private void cachePrimaryCardHostIfNeeded() {
|
||||
SystemParamsOperation sp = SystemParamsOperation.getInstance();
|
||||
String currentHostName = sp.getHostName();
|
||||
String secondaryHostName = sp.getThirdHostName();
|
||||
boolean currentIsSecondary = !TextUtils.isEmpty(secondaryHostName)
|
||||
&& secondaryHostName.equals(currentHostName);
|
||||
|
||||
if (!currentIsSecondary) {
|
||||
globalPrimaryHostName = currentHostName;
|
||||
globalPrimaryTid = sp.getTerminalId();
|
||||
globalPrimaryMid = sp.getMerchantId();
|
||||
globalPrimaryIp = sp.getIpAddress();
|
||||
globalPrimarySecIp = sp.getSecIpAddress();
|
||||
CurrencyType activeCurrency = sp.getCurrencyType();
|
||||
globalPrimaryCurrency = activeCurrency == null ? CurrencyType.MMK : activeCurrency;
|
||||
globalPrimaryHostCached = true;
|
||||
}
|
||||
|
||||
if (!globalPrimaryHostCached) {
|
||||
CurrencyType activeCurrency = sp.getCurrencyType();
|
||||
globalPrimaryCurrency = activeCurrency == null ? CurrencyType.MMK : activeCurrency;
|
||||
globalPrimaryHostCached = true;
|
||||
}
|
||||
|
||||
primaryHostName = globalPrimaryHostName;
|
||||
primaryTid = globalPrimaryTid;
|
||||
primaryMid = globalPrimaryMid;
|
||||
primaryIp = globalPrimaryIp;
|
||||
primarySecIp = globalPrimarySecIp;
|
||||
primaryCurrency = globalPrimaryCurrency;
|
||||
}
|
||||
|
||||
private CurrencyType toCurrencyType(String value) {
|
||||
String normalized = normalizeCurrency(value);
|
||||
try {
|
||||
return CurrencyType.valueOf(normalized);
|
||||
} catch (Exception ignored) {
|
||||
return CurrencyType.MMK;
|
||||
}
|
||||
}
|
||||
|
||||
private String normalizeCurrency(String raw) {
|
||||
if (TextUtils.isEmpty(raw)) {
|
||||
return "";
|
||||
}
|
||||
|
||||
String value = raw.trim().toUpperCase();
|
||||
switch (value) {
|
||||
case "104":
|
||||
case "MMK":
|
||||
return "MMK";
|
||||
case "840":
|
||||
case "USD":
|
||||
return "USD";
|
||||
case "156":
|
||||
case "CNY":
|
||||
case "RMB":
|
||||
return "CNY";
|
||||
case "764":
|
||||
case "THB":
|
||||
return "THB";
|
||||
case "643":
|
||||
case "RUB":
|
||||
return "RUB";
|
||||
default:
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
private void showCurrencyPickerDialog(
|
||||
String title,
|
||||
List<String> currencies,
|
||||
CurrencySelectCallback callback,
|
||||
Runnable onCancelled
|
||||
) {
|
||||
LinearLayout root = new LinearLayout(fragment.requireContext());
|
||||
root.setOrientation(LinearLayout.VERTICAL);
|
||||
root.setPadding(dp(20), dp(20), dp(20), dp(12));
|
||||
|
||||
TextView tvTitle = new TextView(fragment.requireContext());
|
||||
tvTitle.setText(title);
|
||||
tvTitle.setTextSize(TypedValue.COMPLEX_UNIT_SP, 20);
|
||||
tvTitle.setTextColor(ContextCompat.getColor(fragment.requireContext(), R.color.colorTextTitle));
|
||||
tvTitle.setPadding(0, 0, 0, dp(16));
|
||||
root.addView(tvTitle);
|
||||
|
||||
final AlertDialog[] dialogHolder = new AlertDialog[1];
|
||||
for (String currency : currencies) {
|
||||
AppCompatButton button = new AppCompatButton(fragment.requireContext());
|
||||
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(
|
||||
LinearLayout.LayoutParams.MATCH_PARENT,
|
||||
dp(56)
|
||||
);
|
||||
lp.bottomMargin = dp(10);
|
||||
button.setLayoutParams(lp);
|
||||
button.setAllCaps(false);
|
||||
button.setText(currency);
|
||||
button.setTextSize(TypedValue.COMPLEX_UNIT_SP, 18);
|
||||
button.setGravity(Gravity.CENTER);
|
||||
button.setBackgroundResource(R.drawable.bg_rounded_btn_cv);
|
||||
button.setTextColor(ContextCompat.getColor(fragment.requireContext(), R.color.white));
|
||||
button.setOnClickListener(v -> {
|
||||
if (dialogHolder[0] != null) {
|
||||
dialogHolder[0].dismiss();
|
||||
}
|
||||
callback.onSelected(currency);
|
||||
});
|
||||
root.addView(button);
|
||||
}
|
||||
|
||||
AppCompatButton cancel = new AppCompatButton(fragment.requireContext());
|
||||
LinearLayout.LayoutParams cancelLp = new LinearLayout.LayoutParams(
|
||||
LinearLayout.LayoutParams.MATCH_PARENT,
|
||||
dp(52)
|
||||
);
|
||||
cancel.setLayoutParams(cancelLp);
|
||||
cancel.setAllCaps(false);
|
||||
cancel.setText("Cancel");
|
||||
cancel.setTextSize(TypedValue.COMPLEX_UNIT_SP, 16);
|
||||
cancel.setBackgroundResource(R.drawable.bg_rounded_btn_cancel_cv);
|
||||
cancel.setTextColor(ContextCompat.getColor(fragment.requireContext(), R.color.colorPrimary));
|
||||
cancel.setOnClickListener(v -> {
|
||||
if (dialogHolder[0] != null) {
|
||||
dialogHolder[0].dismiss();
|
||||
}
|
||||
if (onCancelled != null) {
|
||||
onCancelled.run();
|
||||
}
|
||||
});
|
||||
root.addView(cancel);
|
||||
|
||||
AlertDialog dialog = new AlertDialog.Builder(fragment.requireContext())
|
||||
.setView(root)
|
||||
.create();
|
||||
dialogHolder[0] = dialog;
|
||||
dialog.show();
|
||||
}
|
||||
|
||||
private int dp(int value) {
|
||||
return Math.round(value * fragment.requireContext().getResources().getDisplayMetrics().density);
|
||||
}
|
||||
|
||||
private interface CurrencySelectCallback {
|
||||
void onSelected(String currency);
|
||||
}
|
||||
}
|
||||
@ -160,11 +160,16 @@ public class EReceiptUtil {
|
||||
return request;
|
||||
}
|
||||
|
||||
private String getDecimalAmount(long amount) {
|
||||
double realAmount = amount / 100.0;
|
||||
DecimalFormat df = new DecimalFormat("0.00");
|
||||
return df.format(realAmount);
|
||||
}
|
||||
|
||||
public EReceiptRequest generateMPUReceipt(PayDetail payDetail) {
|
||||
|
||||
double realAmount = payDetail.getAmount() / 100.0;
|
||||
DecimalFormat df = new DecimalFormat("0.00");
|
||||
String amount = df.format(realAmount);
|
||||
|
||||
String amount = getDecimalAmount(payDetail.getAmount());
|
||||
|
||||
String currentTimeStamp = new java.text.SimpleDateFormat("MMddHHmmss", java.util.Locale.getDefault())
|
||||
.format(new java.util.Date());
|
||||
@ -178,26 +183,27 @@ public class EReceiptUtil {
|
||||
SettleData settleData = payDetail.getSettleDataObj();
|
||||
|
||||
long totalAmt = settleData.getSaleAmount() + settleData.getRefundAmount() + settleData.getPreAuthCompAmount() + settleData.getCashAdvanceAmount();
|
||||
double realTotalAmount = totalAmt / 100.0;
|
||||
String totalAmount = df.format(realTotalAmount);
|
||||
request.setDE4(totalAmount);
|
||||
|
||||
request.setDE4(getDecimalAmount(totalAmt));
|
||||
|
||||
|
||||
request.setDE63_01(settleData.getSaleCount() + "");
|
||||
request.setDE63_02(settleData.getSaleAmount() + "");
|
||||
request.setDE63_02(getDecimalAmount(settleData.getSaleAmount()));
|
||||
request.setDE63_03(settleData.getRefundCount() + "");
|
||||
request.setDE63_04(settleData.getRefundAmount() + "");
|
||||
request.setDE63_04(getDecimalAmount(settleData.getRefundAmount()));
|
||||
request.setDE63_05(settleData.getPreAuthCompCount() + "");
|
||||
request.setDE63_06(settleData.getPreAuthCompAmount() + "");
|
||||
request.setDE63_06(getDecimalAmount(settleData.getPreAuthCompAmount()));
|
||||
request.setDE63_07(settleData.getCashAdvanceCount() + "");
|
||||
request.setDE63_08(settleData.getCashAdvanceAmount() + "");
|
||||
request.setDE63_08(getDecimalAmount(settleData.getCashAdvanceAmount()));
|
||||
invoiceNo = SystemParamsOperation.getInstance().getIncrementInvoiceNum();
|
||||
request.setBatchNumber(batchNumber);
|
||||
request.setInvoiceNumber(invoiceNo);
|
||||
request.setDescription("success");
|
||||
request.setDE39("A");
|
||||
request.setDE37("0000");
|
||||
request.setDE49("MMK");
|
||||
request.setDE49(currencyCodeToText(payDetail.getCurrencyCode()));
|
||||
|
||||
|
||||
} else {
|
||||
request.setDE2(POSUtil.getInstance().getCardNumMasking(payDetail.getCardNo()));
|
||||
|
||||
@ -207,9 +213,9 @@ public class EReceiptUtil {
|
||||
request.setDE37(payDetail.getReferNo());
|
||||
request.setDE38(payDetail.getApprovalCode());
|
||||
// will check it later for currency code
|
||||
request.setDE49("MMK");
|
||||
request.setDE49(currencyCodeToText(payDetail.getCurrencyCode()));
|
||||
request.setInvoiceNumber(payDetail.getInvoiceNo());
|
||||
request.setCardLabel("MPU");
|
||||
request.setCardLabel(payDetail.getAccountType());
|
||||
|
||||
if (payDetail.getTradeAnswerCode().equals("000") || payDetail.getTradeAnswerCode().equals("00")) {
|
||||
|
||||
@ -279,6 +285,28 @@ public class EReceiptUtil {
|
||||
return request;
|
||||
}
|
||||
|
||||
private String currencyCodeToText(String currencyCode) {
|
||||
String currencyText = "MMK";
|
||||
switch (currencyCode) {
|
||||
case "840":
|
||||
currencyCode = "USD";
|
||||
break;
|
||||
case "156":
|
||||
currencyCode = "RMB";
|
||||
break;
|
||||
case "764":
|
||||
currencyCode = "THB";
|
||||
break;
|
||||
case "643":
|
||||
currencyCode = "RUB";
|
||||
break;
|
||||
default:
|
||||
currencyCode = "MMK";
|
||||
break;
|
||||
}
|
||||
return currencyCode;
|
||||
}
|
||||
|
||||
private static List<Transaction> buildTransactions(List<QRSettleData> qrSettleData) {
|
||||
List<Transaction> list = new ArrayList<>();
|
||||
|
||||
|
||||
111
app/src/main/java/com/utsmm/kbz/util/LocationUtil.java
Normal file
111
app/src/main/java/com/utsmm/kbz/util/LocationUtil.java
Normal file
@ -0,0 +1,111 @@
|
||||
package com.utsmm.kbz.util;
|
||||
|
||||
import android.Manifest;
|
||||
import android.app.Activity;
|
||||
import android.app.AlertDialog;
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.location.Location;
|
||||
import android.location.LocationListener;
|
||||
import android.location.LocationManager;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.core.app.ActivityCompat;
|
||||
|
||||
public class LocationUtil {
|
||||
public interface LocationCallback {
|
||||
void onSuccess(double lat, double lng);
|
||||
void onError(String reason);
|
||||
}
|
||||
|
||||
private static LocationListener listener;
|
||||
private static double lat = 0.00;
|
||||
private static double lng = 0.00;
|
||||
|
||||
public static void getCurrentLocation(
|
||||
@NonNull Activity activity,
|
||||
@NonNull LocationCallback callback) {
|
||||
|
||||
LocationManager lm =
|
||||
(LocationManager) activity.getSystemService(Context.LOCATION_SERVICE);
|
||||
|
||||
if (lm == null) {
|
||||
callback.onError("LocationManager is null");
|
||||
return;
|
||||
}
|
||||
|
||||
if (ActivityCompat.checkSelfPermission(activity,
|
||||
Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
|
||||
|
||||
ActivityCompat.requestPermissions(
|
||||
activity,
|
||||
new String[]{Manifest.permission.ACCESS_FINE_LOCATION},
|
||||
201
|
||||
);
|
||||
callback.onError("Permission not granted");
|
||||
return;
|
||||
}
|
||||
|
||||
boolean gpsEnabled = lm.isProviderEnabled(LocationManager.GPS_PROVIDER);
|
||||
boolean netEnabled = lm.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
|
||||
|
||||
if (!gpsEnabled && !netEnabled) {
|
||||
callback.onError("No location provider enabled");
|
||||
return;
|
||||
}
|
||||
|
||||
Location location = lm.getLastKnownLocation(LocationManager.GPS_PROVIDER);
|
||||
if (location == null) {
|
||||
location = lm.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
|
||||
}
|
||||
|
||||
if (location != null) {
|
||||
callback.onSuccess(location.getLatitude(), location.getLongitude());
|
||||
return;
|
||||
}
|
||||
|
||||
listener = new LocationListener() {
|
||||
@Override
|
||||
public void onLocationChanged(@NonNull Location location) {
|
||||
callback.onSuccess(
|
||||
location.getLatitude(),
|
||||
location.getLongitude()
|
||||
);
|
||||
lm.removeUpdates(this); // 🔥 stop GPS
|
||||
}
|
||||
};
|
||||
|
||||
lm.requestLocationUpdates(
|
||||
LocationManager.GPS_PROVIDER,
|
||||
2000,
|
||||
1,
|
||||
listener
|
||||
);
|
||||
}
|
||||
|
||||
public static void stop(Context context) {
|
||||
if (listener != null) {
|
||||
LocationManager lm =
|
||||
(LocationManager) context.getSystemService(Context.LOCATION_SERVICE);
|
||||
if (lm != null) lm.removeUpdates(listener);
|
||||
listener = null;
|
||||
}
|
||||
}
|
||||
|
||||
public static double getLat() {
|
||||
return lat;
|
||||
}
|
||||
|
||||
public static double getLng() {
|
||||
return lng;
|
||||
}
|
||||
|
||||
public static void setLat(double lat) {
|
||||
LocationUtil.lat = lat;
|
||||
}
|
||||
|
||||
public static void setLng(double lng) {
|
||||
LocationUtil.lng = lng;
|
||||
}
|
||||
|
||||
}
|
||||
@ -6,6 +6,7 @@ import com.utsmyanmar.paylibs.model.CardInfo;
|
||||
import com.utsmyanmar.paylibs.model.MAGCardInfo;
|
||||
import com.utsmyanmar.paylibs.model.PayDetail;
|
||||
import com.utsmyanmar.paylibs.model.TradeData;
|
||||
import com.utsmyanmar.paylibs.model.enums.TransCVM;
|
||||
import com.utsmyanmar.paylibs.utils.core_utils.SystemParamsOperation;
|
||||
import com.utsmyanmar.paylibs.utils.iso_utils.TransactionsType;
|
||||
import com.utsmyanmar.paylibs.utils.params.Params;
|
||||
@ -98,6 +99,7 @@ public class TransactionUtil {
|
||||
PayDetail payDetail = tradeData.getPayDetail();
|
||||
payDetail.setCardNo(cardDataX.getPan());
|
||||
payDetail.setEXPDate(cardDataX.getExp());
|
||||
payDetail.setTransCVM(TransCVM.SIGNATURE);
|
||||
|
||||
if(cardDataX.getPan().startsWith("4")) {
|
||||
payDetail.setAccountType(VISA_CARD_SCHEME);
|
||||
|
||||
@ -22,5 +22,6 @@ public enum FeaturesType {
|
||||
QR_INQUIRY,
|
||||
QR_REFUND,
|
||||
LOG_OUT,
|
||||
DEVICE_CONFIG
|
||||
DEVICE_CONFIG,
|
||||
CLEAR_REVERSAL
|
||||
}
|
||||
@ -3,6 +3,8 @@ package com.utsmm.kbz.util.enums;
|
||||
public enum TransactionStatus {
|
||||
|
||||
ON_SUCCESS,
|
||||
|
||||
ON_FINAL_SUCCESS,
|
||||
ON_REVERSAL,
|
||||
ON_BATCH_UPLOAD,
|
||||
ON_FAIL,
|
||||
|
||||
@ -149,6 +149,9 @@ public class TMSSetupsImpl implements TMSSetups{
|
||||
List<SiriusHost> siriusHosts = siriusResponse.getHosts();
|
||||
|
||||
List<SiriusProperty> siriusProperties = siriusResponse.getProperties();
|
||||
boolean isDualCurrencyEnabled = isDualCurrencyEnabled(siriusProperties);
|
||||
|
||||
SystemParamsOperation.getInstance().setDuelCurrencyStatus(isDualCurrencyEnabled);
|
||||
|
||||
ArrayList<String> imgUrls = new ArrayList<>();
|
||||
|
||||
@ -579,12 +582,23 @@ public class TMSSetupsImpl implements TMSSetups{
|
||||
|
||||
emvParamOperation.updatePayPassCurrencyCode(data);
|
||||
|
||||
} else if (TextUtils.equals(name,"terminal_capability")) {
|
||||
|
||||
if(!data.isEmpty()) {
|
||||
SystemParamsOperation.getInstance().setTerminalCapability(data);
|
||||
} else if (TextUtils.equals(name, "visa_terminal_capability")) {
|
||||
if(!data.isEmpty()){
|
||||
SystemParamsOperation.getInstance().setVisaTerminalCapability(data);
|
||||
}
|
||||
}else if (TextUtils.equals(name, "master_terminal_capability")) {
|
||||
if(!data.isEmpty()){
|
||||
SystemParamsOperation.getInstance().setMasterTerminalCapability(data);
|
||||
}
|
||||
}
|
||||
else if (TextUtils.equals(name, "upi_terminal_capability")) {
|
||||
if(!data.isEmpty()){
|
||||
SystemParamsOperation.getInstance().setUpiTerminalCapability(data);
|
||||
}
|
||||
} else if (TextUtils.equals(name, "jcb_terminal_capability")) {
|
||||
if(!data.isEmpty()){
|
||||
SystemParamsOperation.getInstance().setJcbTerminalCapability(data);
|
||||
}
|
||||
|
||||
} else if (TextUtils.equals(name,"upi_ttq")) {
|
||||
emvParamOperation.updateQuickPassTTQ(data);
|
||||
} else if (TextUtils.equals(name, "upi_tc_enabled")) {
|
||||
@ -631,8 +645,24 @@ public class TMSSetupsImpl implements TMSSetups{
|
||||
else if(TextUtils.equals(name,"bin_list")) {
|
||||
SystemParamsOperation.getInstance().setBinValue(data);
|
||||
}
|
||||
else if (TextUtils.equals(name, "restricted_bin_list")) {
|
||||
SystemParamsOperation.getInstance().setRestrictedBinValue(data);
|
||||
}
|
||||
else if(TextUtils.equals(name, "printer_enabled")){
|
||||
SystemParamsOperation.getInstance().setPrinterEnabled(parseBoolean(data));
|
||||
}else if(TextUtils.equals(name, "is_duel_currency")){
|
||||
SystemParamsOperation.getInstance().setDuelCurrencyStatus(parseBoolean(data));
|
||||
}
|
||||
else if(TextUtils.equals(name, "pre_auth_cancel_manual_enabled")) {
|
||||
SystemParamsOperation.getInstance().setPreAuthVoidManualEnabled(parseBoolean(data));
|
||||
}
|
||||
else if(TextUtils.equals(name, "pre_auth_complete_manual_enabled")) {
|
||||
SystemParamsOperation.getInstance().setPreAuthCompleteManualEnabled(parseBoolean(data));
|
||||
}
|
||||
else if(TextUtils.equals(name, "pre_auth_manual_enabled")) {
|
||||
SystemParamsOperation.getInstance().setPreAuthManualEnabled(parseBoolean(data));
|
||||
}else if(TextUtils.equals(name, "auto_reversal_enable")) {
|
||||
SystemParamsOperation.getInstance().setAutoReversalEnable(parseBoolean(data));
|
||||
}
|
||||
}
|
||||
|
||||
@ -645,6 +675,24 @@ public class TMSSetupsImpl implements TMSSetups{
|
||||
return EReceiptHelper.sha256(dataToHash);
|
||||
}
|
||||
|
||||
private boolean isDualCurrencyEnabled(List<SiriusProperty> siriusProperties) {
|
||||
if (siriusProperties == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (SiriusProperty siriusProperty : siriusProperties) {
|
||||
if (siriusProperty == null) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (TextUtils.equals("is_duel_currency", siriusProperty.getName())) {
|
||||
return parseBoolean(siriusProperty.getProperty());
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
private String convertToString(ArrayList<String> list) {
|
||||
|
||||
|
||||
@ -7,6 +7,7 @@ import android.text.TextUtils;
|
||||
import android.util.Log;
|
||||
|
||||
import com.kizzy.xpay.XPay;
|
||||
import com.utsmm.kbz.util.LocationUtil;
|
||||
import com.utsmyanmar.baselib.emv.EmvParamOperation;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusRequest;
|
||||
import com.utsmyanmar.baselib.network.model.sirius.SiriusResponse;
|
||||
@ -139,6 +140,7 @@ public class TMSUtil {
|
||||
|
||||
public SiriusRequest generateRequestParams(Context context,String lastTransName,String lastTransTime) {
|
||||
|
||||
|
||||
SiriusRequest siriusRequest = new SiriusRequest();
|
||||
siriusRequest.setSerial(getSerialNumber());
|
||||
siriusRequest.setAppPackage(BuildConfig.APPLICATION_ID);
|
||||
@ -148,6 +150,8 @@ public class TMSUtil {
|
||||
siriusRequest.setCurrentNetwork(getNetworkType(context));
|
||||
siriusRequest.setLastTransaction(lastTransName);
|
||||
siriusRequest.setLastTranTime(Long.parseLong(lastTransTime));
|
||||
siriusRequest.setLatitude(LocationUtil.getLat());
|
||||
siriusRequest.setLongitude(LocationUtil.getLng());
|
||||
siriusRequest.setValue("YourValueHere");
|
||||
|
||||
return siriusRequest;
|
||||
@ -219,6 +223,7 @@ public class TMSUtil {
|
||||
// featuresList.add(new Features(5, fragmentActivity.getString(R.string.menu_wavepay_inquiry), R.drawable.ic_wave_status_dash, FeaturesType.WAVE_PAY_INQUIRY, wavePayInquiryStatus));
|
||||
featuresList.add(new Features(1, fragmentActivity.getString(R.string.menu_cash_advance), R.drawable.ic_cash_advance, FeaturesType.CASH_ADVANCE, cashAdvanceStatus));
|
||||
// featuresList.add(new Features(9, fragmentActivity.getString(R.string.menu_history), R.drawable.ic_history, FeaturesType.HISTORY, true));
|
||||
featuresList.add(new Features(11, "Clear Reversal", R.drawable.ic_clear_all, FeaturesType.CLEAR_REVERSAL, true));
|
||||
featuresList.add(new Features(10, "Configs", R.drawable.ic_host, FeaturesType.DEVICE_CONFIG, true));
|
||||
}
|
||||
|
||||
|
||||
@ -39,6 +39,7 @@
|
||||
app:layout_constraintEnd_toEndOf="parent">
|
||||
|
||||
<LinearLayout
|
||||
android:visibility="@{sharedVM.amount.equals(`0`) || sharedVM.amount.equals(`0.00`) ? View.GONE : View.VISIBLE}"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
@ -141,6 +142,7 @@
|
||||
android:weightSum="3">
|
||||
|
||||
<!-- Tap Card -->
|
||||
<!-- android:onClick="@{()->click.onClickTap()}"-->
|
||||
<androidx.cardview.widget.CardView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="96dp"
|
||||
@ -149,7 +151,6 @@
|
||||
android:layout_weight="1"
|
||||
app:cardCornerRadius="12dp"
|
||||
app:cardElevation="2dp"
|
||||
android:onClick="@{()->click.onClickTap()}"
|
||||
android:backgroundTint="#fff"
|
||||
android:foreground="?android:attr/selectableItemBackground"
|
||||
android:focusable="true"
|
||||
|
||||
@ -120,16 +120,17 @@
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txt_emv_remaining_count"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="@dimen/margin_button"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:gravity="center"
|
||||
android:text="@{emv.pinRemainingCount}"
|
||||
android:textColor="@color/white"
|
||||
android:textSize="@dimen/pan_size"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toEndOf="@+id/textView3"
|
||||
app:layout_constraintTop_toBottomOf="@+id/textView20"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/txt_emv_pin_mode"
|
||||
app:layout_goneMarginTop="@dimen/margin_button"
|
||||
tools:text="3 LEFT" />
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
||||
@ -101,6 +101,7 @@
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif" />
|
||||
|
||||
|
||||
<com.google.android.material.textfield.TextInputLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
@ -155,69 +156,11 @@
|
||||
android:textStyle="bold"
|
||||
tools:fontFamily="sans-serif-medium" />
|
||||
|
||||
<!-- Terminal ID -->
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="12dp"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="Terminal ID:"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/terminalIdValue"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:fontFamily="@font/rubik_medium"
|
||||
android:text="Not configured"
|
||||
android:textColor="@color/colorTextTitle"
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif-medium" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<!-- Merchant ID -->
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="8dp"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="Merchant ID:"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/merchantIdValue"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:fontFamily="@font/rubik_medium"
|
||||
android:text="Not configured"
|
||||
android:textColor="@color/colorTextTitle"
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif-medium" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<!-- Serial Number -->
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="8dp"
|
||||
android:layout_marginTop="12dp"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
|
||||
@ -53,7 +53,7 @@
|
||||
<TextView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="@string/enter_trace_text"
|
||||
android:text="Enter Invoice Number"
|
||||
android:textAlignment="center"
|
||||
android:textColor="@color/colorPrimary"
|
||||
android:textSize="17sp"
|
||||
@ -65,7 +65,7 @@
|
||||
<TextView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="Enter the transaction trace number"
|
||||
android:text="Enter the transaction invoice number"
|
||||
android:textAlignment="center"
|
||||
android:textColor="@color/colorPrimary"
|
||||
android:textSize="12sp"
|
||||
|
||||
@ -3,6 +3,7 @@
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto">
|
||||
<data>
|
||||
<import type="android.view.View" />
|
||||
<variable
|
||||
name="sharedViewModel"
|
||||
type="com.utsmm.kbz.ui.core_viewmodel.SharedViewModel" />
|
||||
@ -93,6 +94,7 @@
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="12dp"
|
||||
android:visibility="@{sharedViewModel.printerDisabled ? View.GONE : View.VISIBLE}"
|
||||
app:cardCornerRadius="12dp"
|
||||
app:cardElevation="0dp"
|
||||
app:cardBackgroundColor="@color/white"
|
||||
|
||||
@ -187,7 +187,7 @@
|
||||
<TextView
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="@{sharedViewModel._currencyText+` `+sharedViewModel.amount}"
|
||||
android:text="@{sharedViewModel.payDetail != null ? POSUtil.getInstance().currencyCodeToText(sharedViewModel.payDetail.currencyCode)+` `+POSUtil.getInstance().getDecimalAmountVoidFormat(sharedViewModel.payDetail) : sharedViewModel._currencyText+` `+sharedViewModel.amount}"
|
||||
android:textColor="@color/colorTextTitle"
|
||||
android:textSize="14sp"
|
||||
android:textStyle="bold"
|
||||
|
||||
@ -729,7 +729,9 @@
|
||||
android:onClick="@{()->click.onReversalClick()}"
|
||||
app:cardBackgroundColor="@color/white"
|
||||
app:cardCornerRadius="16dp"
|
||||
app:cardElevation="2dp">
|
||||
app:cardElevation="2dp"
|
||||
|
||||
>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
@ -969,6 +971,81 @@
|
||||
|
||||
</androidx.cardview.widget.CardView>
|
||||
|
||||
<!-- Clear Reversal Card -->
|
||||
<androidx.cardview.widget.CardView
|
||||
android:id="@+id/clearReversalCard"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="12dp"
|
||||
android:clickable="true"
|
||||
android:foreground="?android:attr/selectableItemBackground"
|
||||
android:onClick="@{()->click.onClearReversalClick()}"
|
||||
app:cardBackgroundColor="@color/white"
|
||||
app:cardCornerRadius="16dp"
|
||||
app:cardElevation="2dp">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:padding="20dp">
|
||||
|
||||
<androidx.cardview.widget.CardView
|
||||
android:layout_width="48dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_marginEnd="16dp"
|
||||
app:cardBackgroundColor="@color/colorPrimary"
|
||||
app:cardCornerRadius="24dp"
|
||||
app:cardElevation="0dp">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="24dp"
|
||||
android:layout_height="24dp"
|
||||
android:layout_gravity="center"
|
||||
android:src="@drawable/ic_clear_all"
|
||||
app:tint="@color/white" />
|
||||
|
||||
</androidx.cardview.widget.CardView>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:orientation="vertical">
|
||||
|
||||
<TextView
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:fontFamily="@font/rubik_medium"
|
||||
android:text="@string/title_clear_reversal"
|
||||
android:textColor="@color/colorTextTitle"
|
||||
android:textSize="18sp"
|
||||
android:textStyle="bold"
|
||||
tools:fontFamily="sans-serif-medium" />
|
||||
|
||||
<TextView
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="2dp"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@string/clear_reversal_description"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<ImageView
|
||||
android:layout_width="20dp"
|
||||
android:layout_height="20dp"
|
||||
android:src="@drawable/ic_right_arrow"
|
||||
app:tint="@color/colorPrimary" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</androidx.cardview.widget.CardView>
|
||||
|
||||
<!-- TMS Server URL Card -->
|
||||
<!-- android:onClick="@{()->click.onTmsAddressClick()}"-->
|
||||
<androidx.cardview.widget.CardView
|
||||
|
||||
@ -279,7 +279,7 @@
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:text="@{sharedViewModel.payDetail.invoiceNo}"
|
||||
android:text="@{sharedViewModel.payDetail.voucherNo}"
|
||||
android:textAlignment="textEnd"
|
||||
android:textColor="@color/colorPrimary"
|
||||
android:textSize="15sp"
|
||||
@ -355,7 +355,7 @@
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:text="@{sharedViewModel.payDetail.voucherNo}"
|
||||
android:text="@{sharedViewModel.payDetail.invoiceNo}"
|
||||
android:textAlignment="textEnd"
|
||||
android:textColor="@color/colorPrimary"
|
||||
android:textSize="15sp"
|
||||
|
||||
@ -118,7 +118,7 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:background="@null"
|
||||
android:hint="@string/txt_search_by_trace"
|
||||
android:hint="Search By Invoice/RRN"
|
||||
android:textColorHint="@color/colorPrimary"
|
||||
android:alpha="0.6"
|
||||
android:text="@={manageViewModel.txtRRNTrace}"
|
||||
|
||||
@ -74,11 +74,16 @@
|
||||
android:layout_marginTop="19dp"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
@ -96,7 +101,6 @@
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@={settleViewModel.sale_count+``}"
|
||||
tools:text="5"
|
||||
|
||||
android:textSize="16sp" />
|
||||
|
||||
<TextView
|
||||
@ -109,6 +113,17 @@
|
||||
tools:text="65.00"
|
||||
android:textAlignment="textEnd"
|
||||
android:textSize="16sp" />
|
||||
</LinearLayout>
|
||||
|
||||
<TextView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="6dp"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@{settleViewModel.sale_breakdown}"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="12sp"
|
||||
tools:text="MMK 2 / 10,000.00 USD 1 / 25.00" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
@ -122,11 +137,16 @@
|
||||
android:layout_marginTop="19dp"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
@ -144,7 +164,6 @@
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@={settleViewModel.pre_count+``}"
|
||||
tools:text="0"
|
||||
|
||||
android:textSize="16sp" />
|
||||
|
||||
<TextView
|
||||
@ -157,6 +176,17 @@
|
||||
tools:text="0.00"
|
||||
android:textAlignment="textEnd"
|
||||
android:textSize="16sp" />
|
||||
</LinearLayout>
|
||||
|
||||
<TextView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="6dp"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@{settleViewModel.pre_breakdown}"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="12sp"
|
||||
tools:text="MMK 1 / 8,000.00 USD 1 / 15.00" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
@ -170,11 +200,16 @@
|
||||
android:layout_marginTop="19dp"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
@ -190,10 +225,8 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
|
||||
android:text="@={settleViewModel.refund_count+``}"
|
||||
tools:text="0"
|
||||
|
||||
android:textSize="16sp" />
|
||||
|
||||
<TextView
|
||||
@ -206,6 +239,17 @@
|
||||
tools:text="0.00"
|
||||
android:textAlignment="textEnd"
|
||||
android:textSize="16sp" />
|
||||
</LinearLayout>
|
||||
|
||||
<TextView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="6dp"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@{settleViewModel.refund_breakdown}"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="12sp"
|
||||
tools:text="MMK 0 / 0.00 USD 1 / 10.00" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
@ -219,12 +263,17 @@
|
||||
android:layout_marginTop="19dp"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal"
|
||||
android:orientation="vertical"
|
||||
android:visibility="@{settleViewModel.ca_count > 0 ? 0 : 8}"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
@ -240,10 +289,8 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
|
||||
android:text="@={settleViewModel.ca_count+``}"
|
||||
tools:text="0"
|
||||
|
||||
android:textSize="16sp" />
|
||||
|
||||
<TextView
|
||||
@ -256,6 +303,17 @@
|
||||
tools:text="0.00"
|
||||
android:textAlignment="textEnd"
|
||||
android:textSize="16sp" />
|
||||
</LinearLayout>
|
||||
|
||||
<TextView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="6dp"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="@{settleViewModel.ca_breakdown}"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="12sp"
|
||||
tools:text="MMK 1 / 5,000.00 USD 0 / 0.00" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
|
||||
@ -77,6 +77,35 @@
|
||||
tools:text="000045" />
|
||||
|
||||
</LinearLayout>
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal"
|
||||
android:paddingVertical="4dp">
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:text="Currency"
|
||||
android:textColor="@color/colorPrimary"
|
||||
android:textSize="13sp"
|
||||
android:fontFamily="monospace"
|
||||
android:textAlignment="center"
|
||||
tools:text="Currency" />
|
||||
|
||||
<TextView
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:text="@{POSUtil.getInstance().currencyCodeToText(payDetail.currencyCode)}"
|
||||
android:textColor="@color/colorPrimary"
|
||||
android:textSize="13sp"
|
||||
android:fontFamily="monospace"
|
||||
android:textAlignment="center"
|
||||
tools:text="MMK" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<!-- Data Row 3: Transaction Type and Amount -->
|
||||
<LinearLayout
|
||||
|
||||
@ -5,6 +5,7 @@
|
||||
|
||||
|
||||
<data>
|
||||
<import type="androidx.databinding.ObservableBoolean"/>
|
||||
<variable
|
||||
name="sharedViewModel"
|
||||
type="com.utsmm.kbz.ui.core_viewmodel.SharedViewModel" />
|
||||
@ -376,6 +377,84 @@
|
||||
android:textSize="16sp"
|
||||
android:textStyle="bold"
|
||||
tools:fontFamily="sans-serif-medium" />
|
||||
<!-- Pinpad Sound Card -->
|
||||
<androidx.cardview.widget.CardView
|
||||
android:id="@+id/pinpadSoundCard"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="12dp"
|
||||
android:clickable="true"
|
||||
android:foreground="?android:attr/selectableItemBackground"
|
||||
android:onClick="@{()->click.onClickPinpadSound()}"
|
||||
app:cardBackgroundColor="@color/white"
|
||||
app:cardCornerRadius="16dp"
|
||||
app:cardElevation="2dp">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_vertical"
|
||||
android:orientation="horizontal"
|
||||
android:padding="20dp">
|
||||
|
||||
<androidx.cardview.widget.CardView
|
||||
android:layout_width="48dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_marginEnd="16dp"
|
||||
app:cardBackgroundColor="@color/colorPrimary"
|
||||
app:cardCornerRadius="24dp"
|
||||
app:cardElevation="0dp">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="24dp"
|
||||
android:layout_height="24dp"
|
||||
android:layout_gravity="center"
|
||||
android:src="@drawable/ic_audio"
|
||||
app:tint="@color/white" />
|
||||
|
||||
</androidx.cardview.widget.CardView>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:orientation="vertical">
|
||||
|
||||
<TextView
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:fontFamily="@font/rubik_medium"
|
||||
android:text="Enable Pinpad Sound"
|
||||
android:textColor="@color/colorTextTitle"
|
||||
android:textSize="18sp"
|
||||
android:textStyle="bold"
|
||||
tools:fontFamily="sans-serif-medium" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/pinpadSoundSummary"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="2dp"
|
||||
android:fontFamily="@font/rubik_regular"
|
||||
android:text="Pinpad key press sound disabled"
|
||||
android:textColor="@color/colorTextContent"
|
||||
android:textSize="14sp"
|
||||
tools:fontFamily="sans-serif" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<Switch
|
||||
android:id="@+id/pinpadSoundSwitch"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="8dp"
|
||||
android:checked="@{click.pinpadSoundEnabled}"
|
||||
android:clickable="false"
|
||||
android:focusable="false" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</androidx.cardview.widget.CardView>
|
||||
|
||||
<!-- Function Card -->
|
||||
<androidx.cardview.widget.CardView
|
||||
|
||||
@ -615,7 +615,7 @@
|
||||
<string name="txt_total_qr_transactions">Total QR Transactions</string>
|
||||
<string name="txt_no_qr_transactions_to_settle">No QR transactions to settle</string>
|
||||
<string name="txt_settle_qr_transactions">Confirm</string>
|
||||
<string name="txt_search_by_trace">Search By Trace No</string>
|
||||
<string name="txt_search_by_trace">Search By Inv No</string>
|
||||
<string name="txt_continue">Continue</string>
|
||||
|
||||
</resources>
|
||||
@ -4,6 +4,7 @@ import com.utsmyanmar.baselib.util.EReceiptHelper;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import java.text.DecimalFormat;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
@ -21,6 +22,19 @@ public class GeneralTest {
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDecimalAmount() {
|
||||
long amount = 0L;
|
||||
String decimalAmount = getDecimalAmount(amount);
|
||||
System.out.println("amount :"+decimalAmount);
|
||||
}
|
||||
|
||||
private String getDecimalAmount(long amount) {
|
||||
double realAmount = amount / 100.0;
|
||||
DecimalFormat df = new DecimalFormat("0.00");
|
||||
return df.format(realAmount);
|
||||
}
|
||||
|
||||
private static String generateSignature(String timestamp) {
|
||||
String secret = "y812J21lhha11OS";
|
||||
String bodyString = "{}";
|
||||
|
||||
Binary file not shown.
Binary file not shown.
@ -11,8 +11,8 @@
|
||||
"type": "SINGLE",
|
||||
"filters": [],
|
||||
"attributes": [],
|
||||
"versionCode": 1,
|
||||
"versionName": "1.00-uat",
|
||||
"versionCode": 33,
|
||||
"versionName": "2.13-uat",
|
||||
"outputFile": "app-uat-release.apk"
|
||||
}
|
||||
],
|
||||
|
||||
@ -21,12 +21,8 @@ import com.utsmyanmar.paylibs.utils.LogUtil;
|
||||
public final class TerminalKeyUtil {
|
||||
|
||||
public static final String TAG = TerminalKeyUtil.class.getSimpleName();
|
||||
|
||||
// private static final byte[] main_key_data = ByteUtil.hexStr2Bytes("875f63741753d18811a3449090d1777b".toUpperCase()); // KBZ UAT
|
||||
private static final byte[] main_key_data = ByteUtil.hexStr2Bytes("e121249099a677e8b7d4f6a9d49fe8d1".toUpperCase()); // MPU
|
||||
private static final byte[] main_key_data = ByteUtil.hexStr2Bytes("".toUpperCase()); // KBZ PROD
|
||||
private static final byte[] work_key_data = new byte[16];
|
||||
|
||||
|
||||
public static void initNexKey() {
|
||||
byte[] IPEKByte = ByteUtil.hexStr2Bytes("5A4CFF6DE93F0488926166F3317EFD2F"); // IPEK
|
||||
byte[] IPEKKCVByte = ByteUtil.hexStr2Bytes("1F0C18");
|
||||
@ -38,6 +34,7 @@ public final class TerminalKeyUtil {
|
||||
PinPad pinPad = BaseApplication.getInstance().deviceEngine.getPinPad();
|
||||
int result = pinPad.writeMKey(9, main_key_data, main_key_data.length);
|
||||
|
||||
byte[] kcv = pinPad.calcWKeyKCV(9,WorkKeyTypeEnum.ENCRYPTIONKEY);
|
||||
|
||||
//
|
||||
// int resultPINKEY = pinPad.writeWKey(0, WorkKeyTypeEnum.PINKEY, work_key_data, work_key_data.length);
|
||||
@ -49,7 +46,8 @@ public final class TerminalKeyUtil {
|
||||
// int result = pinPad.dukptKeyInject(9, DukptKeyTypeEnum.IPEK,IPEKByte,16,KSNByte);
|
||||
// int result = pinPad.dukptKeyInject(9, DukptKeyTypeEnum.BDK,IPEKByte,16,ksn);
|
||||
|
||||
LogUtil.d(TAG, "save tmk key result: "+result);
|
||||
// LogUtil.d(TAG, "save tmk key result: "+result);
|
||||
// LogUtil.d(TAG, "save tmk kcv: "+ByteUtil.bytes2HexStr(kcv));
|
||||
|
||||
// byte[] encryptedPIK = SystemParamsOperation.getInstance().getKeyPIK().get(0);
|
||||
//
|
||||
|
||||
@ -97,6 +97,12 @@ public interface PayDetailDao {
|
||||
@Query("SELECT * FROM paydetail WHERE transactionType = 10 AND isNeedReversal = 1 AND voucherNo IN(:voucherNo)")
|
||||
LiveData<PayDetail> getReversalTransaction(String voucherNo);
|
||||
|
||||
@Query("SELECT * FROM PayDetail WHERE isNeedReversal = 1 ORDER BY PID DESC LIMIT 1")
|
||||
LiveData<PayDetail> getLastReversalTransactionLive();
|
||||
|
||||
@Query("SELECT * FROM PayDetail WHERE isNeedReversal = 1 ORDER BY PID DESC")
|
||||
LiveData<List<PayDetail>> getAllReversalTransactionsLive();
|
||||
|
||||
// @Query("SELECT * FROM paydetail WHERE transactionType != 10 ORDER BY PID DESC")
|
||||
@Query("SELECT * FROM paydetail ORDER BY PID DESC")
|
||||
LiveData<List<PayDetail>> getTransactionHistory();
|
||||
@ -137,6 +143,10 @@ public interface PayDetailDao {
|
||||
@Query(("SELECT * FROM paydetail WHERE isCanceled = 0 AND CardNo IN(:cardNo) AND referNo IN(:referNo)"))
|
||||
LiveData<PayDetail> searchPayDetail(String cardNo,String referNo);
|
||||
|
||||
@Query(("SELECT * FROM paydetail WHERE isCanceled = 0 AND isAdjust = 0 AND CardNo IN(:cardNo) AND referNo IN(:referNo)"))
|
||||
LiveData<PayDetail> searchPayDetailPreCancel(String cardNo,String referNo);
|
||||
|
||||
|
||||
@Query("SELECT * FROM paydetail WHERE isCanceled = 0 AND transactionType = 5")
|
||||
LiveData<List<PayDetail>> getPreAuthCompData();
|
||||
|
||||
|
||||
@ -254,7 +254,8 @@ public class NetworkModule {
|
||||
}
|
||||
|
||||
if (baseUrl.isEmpty()) {
|
||||
baseUrl = "http://api-uat.kbzpay.com/payment/gateway/uat/";
|
||||
// baseUrl = "http://api-uat.kbzpay.com/payment/gateway/uat/"; //UAT
|
||||
baseUrl = "https://api.kbzpay.com/payment/gateway/"; //Prod
|
||||
}
|
||||
return new Retrofit.Builder()
|
||||
.baseUrl(baseUrl)
|
||||
@ -310,8 +311,8 @@ public Retrofit provideKPayRefundRetrofit(@ApplicationContext Context context) {
|
||||
|
||||
// char[] password = "test123".toCharArray();
|
||||
|
||||
// String refundBaseUrl = "https://api.kbzpay.com:8008/payment/gateway/";
|
||||
String refundBaseUrl = "https://api-uat.kbzpay.com:18008/payment/gateway/uat/";
|
||||
String refundBaseUrl = "https://api.kbzpay.com:8008/payment/gateway/";
|
||||
// String refundBaseUrl = "https://api-uat.kbzpay.com:18008/payment/gateway/uat/";
|
||||
// String IpAddress = SystemParamsOperation.getInstance().getSecHostIpAddress();
|
||||
|
||||
|
||||
@ -325,7 +326,7 @@ public Retrofit provideKPayRefundRetrofit(@ApplicationContext Context context) {
|
||||
|
||||
String pass = SystemParamsOperation.getInstance().getCertificatePassword();
|
||||
if (TextUtils.isEmpty(pass)) {
|
||||
pass = "test123";
|
||||
pass = "";
|
||||
}
|
||||
|
||||
char[] password = pass.toCharArray();
|
||||
|
||||
@ -349,7 +349,7 @@ public class EmvParamHelper {
|
||||
private AidEntity convertContactlessAIDNex(ContactlessAid contactlessAid) {
|
||||
AidEntity aidV2 = new AidEntity();
|
||||
|
||||
aidV2.setTransType("FF");
|
||||
aidV2.setTransType("FF"); // FF
|
||||
aidV2.setOnlinePinCap(1);
|
||||
aidV2.setAsi(0);
|
||||
aidV2.setThreshold(0);
|
||||
@ -412,7 +412,8 @@ public class EmvParamHelper {
|
||||
|
||||
aidV2.setTransType("FF");
|
||||
aidV2.setOnlinePinCap(1);
|
||||
aidV2.setAsi(1);
|
||||
aidV2.setAsi(1); //1
|
||||
// aidV2.setThreshold(99);
|
||||
|
||||
if (!(contactAid.getCvmLimit() < 0)) {
|
||||
aidV2.setContactlessCvmLimit(contactAid.getCvmLimit());
|
||||
@ -464,12 +465,17 @@ public class EmvParamHelper {
|
||||
aidV2.setAppVerNum(contactAid.getApplicationVersion());
|
||||
}
|
||||
|
||||
if (contactAid.getThreshold() != null && !contactAid.getThreshold().isEmpty()) {
|
||||
aidV2.setThreshold(Long.parseLong(contactAid.getThreshold()));
|
||||
}
|
||||
|
||||
return aidV2;
|
||||
}
|
||||
|
||||
private CapkEntity convertRidNex(RidEntity ridEntity) {
|
||||
CapkEntity capkV2 = new CapkEntity();
|
||||
|
||||
|
||||
if (ridEntity.getRid() != null && !ridEntity.getRid().isEmpty()) {
|
||||
capkV2.setRid(ridEntity.getRid());
|
||||
}
|
||||
|
||||
@ -116,7 +116,7 @@ public class EmvParamOperation extends ParamOperation{
|
||||
processPayWave();
|
||||
processPayPass();
|
||||
processQuickPass();
|
||||
processJSpeedy();
|
||||
// processJSpeedy();
|
||||
processMPUCtls();
|
||||
processChips();
|
||||
processRids();
|
||||
|
||||
@ -3,15 +3,10 @@ package com.utsmyanmar.baselib.network;
|
||||
import com.utsmyanmar.baselib.network.model.KPayQRQueryRequest;
|
||||
import com.utsmyanmar.baselib.network.model.KPayQRRequest;
|
||||
import com.utsmyanmar.baselib.network.model.KPayQRResponse;
|
||||
import com.utsmyanmar.baselib.network.model.MMQRStatusResponse;
|
||||
import com.utsmyanmar.baselib.network.model.WaveQRRequest;
|
||||
import com.utsmyanmar.baselib.network.model.WaveQRResponse;
|
||||
import com.utsmyanmar.baselib.network.model.WaveStatusRequest;
|
||||
|
||||
import io.reactivex.rxjava3.core.Observable;
|
||||
import retrofit2.http.Body;
|
||||
import retrofit2.http.POST;
|
||||
import retrofit2.http.Url;
|
||||
|
||||
public interface KPayApiService {
|
||||
|
||||
@ -23,13 +18,13 @@ public interface KPayApiService {
|
||||
Observable<KPayQRQueryRequest.QRQueryResponse> checkStatus(@Body KPayQRQueryRequest.QRQueryRequest waveStatusRequest);
|
||||
|
||||
|
||||
//this accept "url" bez this api start with https and other are http in uat
|
||||
@POST
|
||||
Observable<KPayQRRequest.CloseOrderResponse> closeOrder(@Url String url, @Body KPayQRRequest.CloseOrderRequest closeOrderRequest);
|
||||
//this accepts "url" bez this api start with https and other are http in uat
|
||||
// @POST
|
||||
// Observable<KPayQRRequest.CloseOrderResponse> closeOrder(@Url String url, @Body KPayQRRequest.CloseOrderRequest closeOrderRequest);
|
||||
|
||||
|
||||
//this 2 is for production
|
||||
// @POST("closeorder")
|
||||
// Observable<KPayQRRequest.CloseOrderResponse> closeOrder(@Body KPayQRRequest.CloseOrderRequest closeOrderRequest);
|
||||
@POST("closeorder")
|
||||
Observable<KPayQRRequest.CloseOrderResponse> closeOrder(@Body KPayQRRequest.CloseOrderRequest closeOrderRequest);
|
||||
|
||||
}
|
||||
|
||||
@ -18,10 +18,19 @@ public class EReceiptCardRequest {
|
||||
private String DE11;
|
||||
private String description;
|
||||
private String DE38;
|
||||
private String batchNumber;
|
||||
private String DE55;
|
||||
private String DE14;
|
||||
private String cardLabel;
|
||||
private String DE43;
|
||||
private String DE48;
|
||||
|
||||
public EReceiptCardRequest() {}
|
||||
|
||||
// GETTERS
|
||||
public String getDE14(){ return DE14;}
|
||||
public String getCardLabel(){ return cardLabel;}
|
||||
public String getDE43(){return DE43;}
|
||||
public String getDE3() {
|
||||
return DE3;
|
||||
}
|
||||
@ -62,6 +71,8 @@ public class EReceiptCardRequest {
|
||||
return appId;
|
||||
}
|
||||
|
||||
public String getDE55(){return DE55;}
|
||||
|
||||
public String getInvoiceNumber(){
|
||||
return invoiceNumber;
|
||||
}
|
||||
@ -75,6 +86,7 @@ public class EReceiptCardRequest {
|
||||
public String getDE2(){ return DE2; }
|
||||
public String getDE38(){ return DE38; }
|
||||
public String getDE22(){ return DE22; }
|
||||
public String getBatchNumber(){ return batchNumber; }
|
||||
// SETTERS
|
||||
public void setDE3(String DE3) {
|
||||
this.DE3 = DE3;
|
||||
@ -132,4 +144,23 @@ public class EReceiptCardRequest {
|
||||
|
||||
public void setDE38(String DE38){ this.DE38 = DE38; }
|
||||
public void setDE22(String DE22){ this.DE22 = DE22; }
|
||||
|
||||
public void setBatchNumber(String batchNumber) {
|
||||
this.batchNumber = batchNumber;
|
||||
}
|
||||
public void setDE55(String DE55){
|
||||
this.DE55 = DE55;
|
||||
}
|
||||
public void setDE14(String DE14){
|
||||
this.DE14 = DE14;
|
||||
}
|
||||
public void setCardLabel(String cardLabel){
|
||||
this.cardLabel = cardLabel;
|
||||
}
|
||||
public void setDE43(String DE43){
|
||||
this.DE43 = DE43;
|
||||
}
|
||||
public void setDE48(String DE48){
|
||||
this.DE48 = DE48;
|
||||
}
|
||||
}
|
||||
|
||||
@ -18,9 +18,23 @@ public class SiriusRequest {
|
||||
private Long lastTranTime;
|
||||
|
||||
private String value;
|
||||
private double latitude;
|
||||
private double longitude;
|
||||
|
||||
public SiriusRequest() {}
|
||||
public SiriusRequest(String serial, String appPackage, String androidVersion, String firmwareVersion, String applicationVersion, String currentNetwork, String lastTransaction, Long lastTranTime, String value) {
|
||||
public SiriusRequest(
|
||||
String serial,
|
||||
String appPackage,
|
||||
String androidVersion,
|
||||
String firmwareVersion,
|
||||
String applicationVersion,
|
||||
String currentNetwork,
|
||||
String lastTransaction,
|
||||
Long lastTranTime,
|
||||
double latitude,
|
||||
double longitude,
|
||||
String value
|
||||
) {
|
||||
this.serial = serial;
|
||||
this.appPackage = appPackage;
|
||||
this.androidVersion = androidVersion;
|
||||
@ -29,6 +43,8 @@ public class SiriusRequest {
|
||||
this.currentNetwork = currentNetwork;
|
||||
this.lastTransaction = lastTransaction;
|
||||
this.lastTranTime = lastTranTime;
|
||||
this.latitude = latitude;
|
||||
this.longitude = longitude;
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
@ -100,6 +116,22 @@ public class SiriusRequest {
|
||||
return value;
|
||||
}
|
||||
|
||||
public double getLatitude(){
|
||||
return latitude;
|
||||
}
|
||||
|
||||
public double getLongitude(){
|
||||
return longitude;
|
||||
}
|
||||
|
||||
public void setLatitude(double latitude){
|
||||
this.latitude = latitude;
|
||||
}
|
||||
|
||||
public void setLongitude(double longitude){
|
||||
this.longitude = longitude;
|
||||
}
|
||||
|
||||
public void setValue(String value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
@ -86,9 +86,9 @@ public class Repository {
|
||||
}
|
||||
|
||||
public Observable<KPayQRRequest.CloseOrderResponse> qrCloseOrder(KPayQRRequest.CloseOrderRequest request){
|
||||
String url = "https://api-uat.kbzpay.com/payment/gateway/uat/closeorder"; //close this in prod
|
||||
return kPayApiService.closeOrder(url, request); // this is for local
|
||||
// return kPayApiService.closeOrder(request); //this is for prod
|
||||
// String url = "https://api-uat.kbzpay.com/payment/gateway/uat/closeorder"; //close this in prod
|
||||
// return kPayApiService.closeOrder(url, request); // this is for uat
|
||||
return kPayApiService.closeOrder(request); //this is for prod
|
||||
}
|
||||
|
||||
public Observable<KPayQRQueryRequest.QRQueryResponse> qrStatusCheck(KPayQRQueryRequest.QRQueryRequest request) {
|
||||
@ -146,6 +146,8 @@ public class Repository {
|
||||
public void updatePayDetail(PayDetail payDetail){payDetailDao.update(payDetail);}
|
||||
|
||||
public LiveData<PayDetail> getReversalTransaction(String voucherNo) { return payDetailDao.getReversalTransaction(voucherNo);}
|
||||
public LiveData<PayDetail> getLastReversalTransaction() { return payDetailDao.getLastReversalTransactionLive();}
|
||||
public LiveData<List<PayDetail>> getAllReversalTransactions() { return payDetailDao.getAllReversalTransactionsLive();}
|
||||
|
||||
public LiveData<List<PayDetail>> getTransactionHistory(){ return payDetailDao.getTransactionHistory();}
|
||||
|
||||
@ -196,6 +198,10 @@ public class Repository {
|
||||
return payDetailDao.searchPayDetail(cardNo,referNo);
|
||||
}
|
||||
|
||||
public LiveData<PayDetail> searchPayDetailPreCancel(String cardNo,String referNo) {
|
||||
return payDetailDao.searchPayDetailPreCancel(cardNo,referNo);
|
||||
}
|
||||
|
||||
public Flowable<PayDetail> searchPayDetailByRefNum(String refNum) {
|
||||
return payDetailDao.searchPayDetailByRefNum(refNum);
|
||||
}
|
||||
|
||||
@ -75,4 +75,13 @@ public class TerminalUtil {
|
||||
else
|
||||
return binParser(SystemParamsOperation.getInstance().getBinValues());
|
||||
}
|
||||
|
||||
public List<String> getRestrictedBinList() {
|
||||
if (SystemParamsOperation.getInstance().getRestrictedBinValues() == null
|
||||
|| SystemParamsOperation.getInstance().getRestrictedBinValues().isEmpty()) {
|
||||
return new ArrayList<>();
|
||||
} else {
|
||||
return binParser(SystemParamsOperation.getInstance().getRestrictedBinValues());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -30,5 +30,7 @@ public enum EmvResultStatus {
|
||||
CONFIRM_CODE_VERIFY,
|
||||
MPU_CARD,
|
||||
SEE_PHONE,
|
||||
OTHER_INTERFACE
|
||||
OTHER_INTERFACE,
|
||||
CARD_APP_BLOCKED,
|
||||
INSERT_OR_MANUAL
|
||||
}
|
||||
|
||||
@ -1,12 +1,15 @@
|
||||
package com.utsmyanmar.baselib.viewModel;
|
||||
|
||||
import android.app.AlertDialog;
|
||||
import android.graphics.Rect;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
import android.os.Message;
|
||||
import android.os.RemoteException;
|
||||
import android.util.Log;
|
||||
import android.view.View;
|
||||
import android.view.ViewTreeObserver;
|
||||
import android.widget.Toast;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.lifecycle.MutableLiveData;
|
||||
@ -23,6 +26,7 @@ import com.nexgo.oaf.apiv3.device.pinpad.PinPad;
|
||||
import com.nexgo.oaf.apiv3.device.pinpad.PinPadKeyCode;
|
||||
import com.nexgo.oaf.apiv3.device.pinpad.PinpadLayoutEntity;
|
||||
import com.nexgo.oaf.apiv3.device.reader.CardInfoEntity;
|
||||
import com.nexgo.oaf.apiv3.emv.AidEntity;
|
||||
import com.nexgo.oaf.apiv3.emv.CandidateAppInfoEntity;
|
||||
import com.nexgo.oaf.apiv3.emv.EmvCardBrandEnum;
|
||||
import com.nexgo.oaf.apiv3.emv.EmvCvmResultEnum;
|
||||
@ -105,6 +109,7 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
public MutableLiveData<Integer> pinPadVisibility = new MutableLiveData<>(8);
|
||||
|
||||
protected int pinEnterCount;
|
||||
private int offlinePinIncorrectPromptCount;
|
||||
public CustomPinPadKeyboard customPinPadKeyboard;
|
||||
|
||||
private int mWidth = 239; // Single item width of password keyboard
|
||||
@ -154,6 +159,10 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
protected static final int EMV_ERROR = 12;
|
||||
protected static final int EMV_TRY_AGAIN = 13;
|
||||
|
||||
protected static final int EMV_INSERT_OR_MANUAL = 24;
|
||||
protected static final int EMV_CARD_APP_BLOCK = 23;
|
||||
protected static final int EMV_CTLS_TRY_AGAIN = 13;
|
||||
|
||||
protected static final int EMV_CONFIRM_CODE_VERIFY = 14;
|
||||
protected static final int EMV_SUCCESS_ONLINE = 15;
|
||||
protected static final int EMV_FAILURE_ONLINE = 16;
|
||||
@ -170,8 +179,21 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
protected boolean isSecondCall = false;
|
||||
protected int mProcessStep;
|
||||
protected int mAppSelect = 0;
|
||||
|
||||
|
||||
private static final String[] RESTRICTED_BINS = {
|
||||
"624430",
|
||||
"624431",
|
||||
"624445",
|
||||
"626220",
|
||||
"623476",
|
||||
"629214",
|
||||
"623466",
|
||||
"623433",
|
||||
"62911028",
|
||||
"62441900",
|
||||
"62441901"
|
||||
};
|
||||
private boolean isMPU_UPIContactless = false;
|
||||
private boolean mMPUContactlessConfigured = false;
|
||||
private Looper mLooper = Looper.getMainLooper();
|
||||
private final Handler mHandler = new Handler(mLooper) {
|
||||
@Override
|
||||
@ -205,6 +227,9 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
}
|
||||
|
||||
public void startProcess() {
|
||||
isOfflinePinEntered = false;
|
||||
mMPUContactlessConfigured = false;
|
||||
isMPU_UPIContactless = false;
|
||||
initData();
|
||||
|
||||
// Check if initialization was successful
|
||||
@ -242,6 +267,7 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
transData.setTransTime(new SimpleDateFormat("hhmmss", Locale.getDefault()).format(new Date()));
|
||||
transData.setTraceNo(mPayDetail.getVoucherNo());
|
||||
|
||||
|
||||
transData.setEmvProcessFlowEnum(EmvProcessFlowEnum.EMV_PROCESS_FLOW_STANDARD);
|
||||
if (mPayDetail.getCardType() == CardTypeX.NFC.value) {
|
||||
transData.setEmvEntryModeEnum(EmvEntryModeEnum.EMV_ENTRY_MODE_CONTACTLESS);
|
||||
@ -251,21 +277,28 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
|
||||
|
||||
|
||||
|
||||
//for UPI
|
||||
UnionPayTransDataEntity unionPayTransDataEntity = new UnionPayTransDataEntity();
|
||||
unionPayTransDataEntity.setQpbocForGlobal(true);
|
||||
unionPayTransDataEntity.setSupportCDCVM(true);
|
||||
//if support QPS, please enable below lines
|
||||
unionPayTransDataEntity.setSupportContactlessQps(true);
|
||||
unionPayTransDataEntity.setContactlessQpsLimit("000090000000");
|
||||
unionPayTransDataEntity.setContactlessQpsLimit("000000030000");
|
||||
|
||||
transData.setUnionPayTransDataEntity(unionPayTransDataEntity);
|
||||
|
||||
|
||||
setTransactionLimitForMPUCtls(false);
|
||||
|
||||
// emvHandler.contactlessConfigKernelId(EmvCardBrandEnum.EMV_CARD_BRAND_JCB,(byte) 0x01,ByteUtils.hexString2ByteArray("06"));
|
||||
emvHandler.contactlessAppendAidIntoKernel(EmvCardBrandEnum.EMV_CARD_BRAND_MASTER, (byte) 0x08, ByteUtils.hexString2ByteArray("A000000732100123"));
|
||||
|
||||
emvHandler.contactlessConfigKernelId(EmvCardBrandEnum.EMV_CARD_BRAND_JCB,(byte) 0x01,ByteUtils.hexString2ByteArray("06"));
|
||||
emvHandler.contactlessAppendAidIntoKernel(EmvCardBrandEnum.EMV_CARD_BRAND_MASTER, (byte) 0x07, ByteUtils.hexString2ByteArray("A0000008890101"));
|
||||
// emvHandler.contactlessAppendAidIntoKernelFirst(true);
|
||||
LogUtil.d(TAG, "TransData :" + transData.getTransAmount());
|
||||
LogUtil.d(TAG, "start emv ");
|
||||
|
||||
// emvHandler.emvDebugLog(true);
|
||||
emvHandler.emvProcess(transData, emvProcessListener);
|
||||
|
||||
|
||||
@ -305,8 +338,8 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
LogUtil.d(TAG, "Selected :" + position);
|
||||
emvHandler.onSetSelAppResponse(position);
|
||||
LogUtil.d(TAG, "Selected :" + position + 1);
|
||||
emvHandler.onSetSelAppResponse(position + 1);
|
||||
} catch (Exception e) {
|
||||
LogUtil.e(TAG, "Exception during app selection: " + e.getMessage());
|
||||
e.printStackTrace();
|
||||
@ -315,76 +348,6 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
}
|
||||
}
|
||||
|
||||
private void initPayPassTlv() {
|
||||
emvParamOperation.retrievePayPassData(new ProcessSingleDataResult<PayPassEntity>() {
|
||||
@Override
|
||||
public void onSuccess(PayPassEntity data) {
|
||||
|
||||
String DF8117Value = "E0";
|
||||
String DF8118Value = "F8";
|
||||
String DF8119Value = "28";
|
||||
|
||||
if (!data.getTerminalCapability().isEmpty()) {
|
||||
DF8117Value = data.getTerminalCapability().substring(0, 2);
|
||||
DF8118Value = data.getTerminalCapability().substring(2, 4);
|
||||
DF8119Value = data.getTerminalCapability().substring(4, 6);
|
||||
}
|
||||
String DF8123Value = data.getFloorLimit();
|
||||
String DF8124Value = data.getTransLimitCDV();
|
||||
String DF8125Value = data.getTransLimit();
|
||||
String DF8126Value = ParamHelper.getInstance().convertPaddedString(data.getCvmLimit());
|
||||
String DF8120Value = data.getTacDefault();
|
||||
String DF8121Value = data.getTacDenial();
|
||||
String DF8122Value = data.getTacOnline();
|
||||
|
||||
String[] tagsPayPass = {"DF8117", "DF8118", "DF8119", "DF811F", "DF811E", "DF812C",
|
||||
"DF8123", "DF8124", "DF8125", "DF8126",
|
||||
"DF811B", "DF811D", "DF8120", "DF8121", "DF8122"};
|
||||
|
||||
String[] valuesPayPass = {DF8117Value, DF8118Value, DF8119Value, "C8", "00", "00",
|
||||
DF8123Value, DF8124Value, DF8125Value, DF8126Value,
|
||||
"30", "02", DF8120Value, DF8121Value, DF8122Value};
|
||||
// try {
|
||||
// mEMVOptV2.setTlvList(AidlConstantsV2.EMV.TLVOpCode.OP_PAYPASS, tagsPayPass, valuesPayPass);
|
||||
//
|
||||
// LogUtil.d(TAG,"<<<<< PayPass TLV data are successfully setup >>>>>");
|
||||
// } catch (RemoteException e) {
|
||||
// throw new RuntimeException(e);
|
||||
// }
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDataNotFound() {
|
||||
LogUtil.d(TAG, "PayPass Data not found!");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
protected void increasedKSN() {
|
||||
pinPad.dukptKsnIncrease(pinIndex); //3
|
||||
|
||||
LogUtil.d(TAG,"DUKPT KSN Increased!");
|
||||
}
|
||||
|
||||
private void getKSN() {
|
||||
try {
|
||||
|
||||
byte[] result = pinPad.dukptCurrentKsn(pinIndex);
|
||||
if (result != null) {
|
||||
String ksnStr = ByteUtil.bytes2HexStr(result);
|
||||
LogUtil.d(TAG, "ksnStr: " + ksnStr);
|
||||
mPayDetail.setReference(ksnStr);
|
||||
mPayDetail.tempKSN = ksnStr;
|
||||
|
||||
LogUtil.d(TAG, "final ksnStr: " + ksnStr);
|
||||
} else {
|
||||
LogUtil.e(TAG, "Result code for current KSN:" + result);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
private String getTransactionType() {
|
||||
String trnxType = "00";
|
||||
@ -422,126 +385,49 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
initKeyboard(isOnlinePin == 1);
|
||||
}
|
||||
|
||||
|
||||
|
||||
private void initKeyboard(boolean isOnlinePin) {
|
||||
|
||||
LogUtil.d(TAG,"init keyboard!");
|
||||
LogUtil.d(TAG, "init keyboard!");
|
||||
pinPadVisibility.setValue(0);
|
||||
LogUtil.d(TAG,"pin pad is visible now!");
|
||||
LogUtil.d(TAG, "pin pad is visible now!");
|
||||
|
||||
// Check if the view is already laid out
|
||||
if (customPinPadKeyboard.getWidth() > 0 && customPinPadKeyboard.getHeight() > 0) {
|
||||
// View already laid out — call setup directly
|
||||
setupPinPadLayout(isOnlinePin);
|
||||
} else {
|
||||
// View not yet laid out — wait for layout
|
||||
customPinPadKeyboard.getViewTreeObserver().addOnGlobalLayoutListener(
|
||||
new ViewTreeObserver.OnGlobalLayoutListener() {
|
||||
@Override
|
||||
public void onGlobalLayout() {
|
||||
if (customPinPadKeyboard.getWidth() > 0 && customPinPadKeyboard.getHeight() > 0) {
|
||||
customPinPadKeyboard.getViewTreeObserver().removeOnGlobalLayoutListener(this);
|
||||
setupPinPadLayout(isOnlinePin);
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
LogUtil.d(TAG,"inside the global layout!");
|
||||
private void setupPinPadLayout(boolean isOnlinePin) {
|
||||
LogUtil.d(TAG, "inside the global layout!");
|
||||
PinpadLayoutEntity pinpadLayout = new PinpadLayoutEntity();
|
||||
int[] location = new int[2];
|
||||
Rect r;
|
||||
customPinPadKeyboard.getKey_1().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_1().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_1().getHeight() + r.top;
|
||||
pinpadLayout.setKey1(r);
|
||||
|
||||
customPinPadKeyboard.getKey_2().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_2().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_2().getHeight() + r.top;
|
||||
pinpadLayout.setKey2(r);
|
||||
|
||||
customPinPadKeyboard.getKey_3().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_3().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_3().getHeight() + r.top;
|
||||
pinpadLayout.setKey3(r);
|
||||
|
||||
customPinPadKeyboard.getKey_4().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_4().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_4().getHeight() + r.top;
|
||||
pinpadLayout.setKey4(r);
|
||||
|
||||
customPinPadKeyboard.getKey_5().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_5().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_5().getHeight() + r.top;
|
||||
pinpadLayout.setKey5(r);
|
||||
|
||||
customPinPadKeyboard.getKey_6().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_6().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_6().getHeight() + r.top;
|
||||
pinpadLayout.setKey6(r);
|
||||
|
||||
customPinPadKeyboard.getKey_7().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_7().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_7().getHeight() + r.top;
|
||||
pinpadLayout.setKey7(r);
|
||||
|
||||
customPinPadKeyboard.getKey_8().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_8().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_8().getHeight() + r.top;
|
||||
pinpadLayout.setKey8(r);
|
||||
|
||||
customPinPadKeyboard.getKey_9().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_9().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_9().getHeight() + r.top;
|
||||
pinpadLayout.setKey9(r);
|
||||
|
||||
customPinPadKeyboard.getKey_0().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_0().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_0().getHeight() + r.top;
|
||||
pinpadLayout.setKey10(r);
|
||||
|
||||
customPinPadKeyboard.getKey_cancel().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_cancel().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_cancel().getHeight() + r.top;
|
||||
pinpadLayout.setKeyCancel(r);
|
||||
|
||||
customPinPadKeyboard.getKey_clear().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_clear().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_clear().getHeight() + r.top;
|
||||
pinpadLayout.setKeyClear(r);
|
||||
|
||||
customPinPadKeyboard.getKey_ok().getLocationOnScreen(location);
|
||||
r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = customPinPadKeyboard.getKey_ok().getWidth() + r.left;
|
||||
r.bottom = customPinPadKeyboard.getKey_ok().getHeight() + r.top;
|
||||
pinpadLayout.setKeyConfirm(r);
|
||||
// Helper to avoid repetition
|
||||
pinpadLayout.setKey1(getRectForView(customPinPadKeyboard.getKey_1()));
|
||||
pinpadLayout.setKey2(getRectForView(customPinPadKeyboard.getKey_2()));
|
||||
pinpadLayout.setKey3(getRectForView(customPinPadKeyboard.getKey_3()));
|
||||
pinpadLayout.setKey4(getRectForView(customPinPadKeyboard.getKey_4()));
|
||||
pinpadLayout.setKey5(getRectForView(customPinPadKeyboard.getKey_5()));
|
||||
pinpadLayout.setKey6(getRectForView(customPinPadKeyboard.getKey_6()));
|
||||
pinpadLayout.setKey7(getRectForView(customPinPadKeyboard.getKey_7()));
|
||||
pinpadLayout.setKey8(getRectForView(customPinPadKeyboard.getKey_8()));
|
||||
pinpadLayout.setKey9(getRectForView(customPinPadKeyboard.getKey_9()));
|
||||
pinpadLayout.setKey10(getRectForView(customPinPadKeyboard.getKey_0()));
|
||||
pinpadLayout.setKeyCancel(getRectForView(customPinPadKeyboard.getKey_cancel()));
|
||||
pinpadLayout.setKeyClear(getRectForView(customPinPadKeyboard.getKey_clear()));
|
||||
pinpadLayout.setKeyConfirm(getRectForView(customPinPadKeyboard.getKey_ok()));
|
||||
|
||||
|
||||
byte[] number = pinPad.setPinpadLayout(pinpadLayout);
|
||||
@ -553,8 +439,15 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
if (retCode == SdkResult.Success) {
|
||||
LogUtil.d(TAG, "Success");
|
||||
if(isOnlinePin) {
|
||||
if(ByteUtil.bytes2HexStr(data).equals("0000000000000000")) {
|
||||
mPayDetail.setPINCipher("");
|
||||
} else {
|
||||
mPayDetail.setPINCipher(ByteUtil.bytes2HexStr(data));
|
||||
}
|
||||
// mPayDetail.setPINCipher(ByteUtil.bytes2HexStr(data));
|
||||
} else {
|
||||
isOfflinePinEntered = true;
|
||||
}
|
||||
mHandler.obtainMessage(PIN_CLICK_CONFIRM).sendToTarget();
|
||||
} else if (retCode == SdkResult.Fail) {
|
||||
LogUtil.d(TAG, "Failure");
|
||||
@ -583,8 +476,9 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
LogUtil.d(TAG, "on click cancel");
|
||||
mHandler.obtainMessage(PIN_CLICK_CANCEL).sendToTarget();
|
||||
} else if (keyCode == PinPadKeyCode.KEYCODE_CONFIRM) {
|
||||
LogUtil.d(TAG, "on click confirm");
|
||||
mHandler.obtainMessage(PIN_CLICK_CONFIRM).sendToTarget();
|
||||
// Wait for onInputResult() so the PIN cipher / offline PIN state is ready
|
||||
// before EmvTransactionProcessViewModel handles PIN confirmation.
|
||||
LogUtil.d(TAG, "on click confirm - waiting for input result");
|
||||
} else {
|
||||
LogUtil.d(TAG, "on click number");
|
||||
mHandler.obtainMessage(PIN_CLICK_NUMBER, pinEnterCount, 0).sendToTarget();
|
||||
@ -598,7 +492,7 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
// customPinPadKeyboard.setKeyBoard(ByteUtil.bytes2HexStr(number));
|
||||
|
||||
LogUtil.d(TAG, "PinPad: " + ByteUtil.bytes2HexStr(number));
|
||||
int[] supperLen = new int[]{0x00, 0x04, 0x06};
|
||||
int[] supperLen = new int[]{0x00, 0x04, 0x06, 0x0c};
|
||||
|
||||
|
||||
pinPad.setPinKeyboardViewMode(PinKeyboardViewModeEnum.DEFAULT);
|
||||
@ -613,6 +507,7 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
byte[] panBytes = cardNo.substring( length- 13).getBytes(StandardCharsets.US_ASCII);
|
||||
LogUtil.d(TAG,"card num :"+cardNo);
|
||||
LogUtil.d(TAG,"Is Online Pin:"+isOnlinePin);
|
||||
|
||||
// pinPad.inputOnlinePin(supperLen, 60, pan, 0, PinAlgorithmModeEnum.ISO9564FMT0, pinPadInputListener);
|
||||
if (isOnlinePin) {
|
||||
|
||||
@ -625,16 +520,33 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
);
|
||||
|
||||
|
||||
// Reusable rect helper
|
||||
private Rect getRectForView(View view) {
|
||||
int[] location = new int[2];
|
||||
view.getLocationOnScreen(location);
|
||||
Rect r = new Rect();
|
||||
r.left = location[0];
|
||||
r.top = location[1];
|
||||
r.right = view.getWidth() + r.left;
|
||||
r.bottom = view.getHeight() + r.top;
|
||||
return r;
|
||||
}
|
||||
|
||||
private void increaseCount() {
|
||||
++pinEnterCount;
|
||||
}
|
||||
|
||||
private boolean isRestrictedBin(String cardNo) {
|
||||
if (cardNo == null || cardNo.isEmpty()) return false;
|
||||
List<String> restrictedBins = TerminalUtil.getInstance().getRestrictedBinList();
|
||||
for (String bin : restrictedBins) {
|
||||
if (cardNo.startsWith(bin)) {
|
||||
LogUtil.d(TAG, "isRestrictedBin: matched BIN " + bin);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private OnEmvProcessListener2 emvProcessListener = new OnEmvProcessListener2() {
|
||||
@Override
|
||||
@ -648,40 +560,116 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
|
||||
@Override
|
||||
public void onTransInitBeforeGPO() {
|
||||
|
||||
if (mMPUContactlessConfigured) {
|
||||
LogUtil.d(TAG, "onTransInitBeforeGPO: skipping — MPU contactless already configured");
|
||||
emvHandler.onSetTransInitBeforeGPOResponse(true);
|
||||
return;
|
||||
}
|
||||
|
||||
byte[] aid = emvHandler.getTlv(new byte[]{0x4F}, EmvDataSourceEnum.FROM_KERNEL);
|
||||
LogUtil.d(TAG, "onTransInitBeforeGPO :");
|
||||
String terminalCapability = SystemParamsOperation.getInstance().getTerminalCapability();
|
||||
// emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x33}, new byte[]{(byte) 0xE0, (byte) 0x28, (byte) 0xC8});
|
||||
emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x33}, ByteUtil.hexStr2Bytes(terminalCapability));
|
||||
LogUtil.d(TAG, "onTransInitBeforeGPO :"+ByteUtil.bytes2HexStr(aid));
|
||||
|
||||
String visaTerminalCapability = SystemParamsOperation.getInstance().getVisaTerminalCapability();
|
||||
String masterTerminalCapability = SystemParamsOperation.getInstance().getMasterTerminalCapability();
|
||||
String upiTerminalCapability = SystemParamsOperation.getInstance().getUpiTerminalCapability();
|
||||
String jcbTerminalCapability = SystemParamsOperation.getInstance().getJcbTerminalCapability();
|
||||
|
||||
|
||||
String selectedTerminalCapability = "";
|
||||
|
||||
if (aid != null) {
|
||||
String aidStr = ByteUtils.byteArray2HexString(aid).toUpperCase();
|
||||
|
||||
if (aidStr.contains("A000000003")) {
|
||||
// VISA
|
||||
selectedTerminalCapability = visaTerminalCapability;
|
||||
} else if (aidStr.contains("A000000004")) {
|
||||
// MasterCard
|
||||
selectedTerminalCapability = masterTerminalCapability;
|
||||
} else if (aidStr.contains("A000000333") || aidStr.contains("A000000025")) {
|
||||
// UPI
|
||||
selectedTerminalCapability = upiTerminalCapability;
|
||||
} else if (aidStr.contains("A00000006510") || aidStr.contains("A0000001570040")) {
|
||||
// UPI (maybe JCB)
|
||||
selectedTerminalCapability = jcbTerminalCapability;
|
||||
} else if (aidStr.contains("A000000065")){
|
||||
selectedTerminalCapability = jcbTerminalCapability;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//9F33
|
||||
emvHandler.setTlv(
|
||||
new byte[]{(byte) 0x9F, (byte) 0x33},
|
||||
ByteUtil.hexStr2Bytes(selectedTerminalCapability)
|
||||
);
|
||||
|
||||
// -------- Contactless --------
|
||||
if (mPayDetail.getCardType() == CardTypeX.NFC.value) {
|
||||
if (aid != null) {
|
||||
if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000004")) {
|
||||
//Paypass
|
||||
configPaypassParameter(aid);
|
||||
} else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000003")) {
|
||||
//Paywave
|
||||
configPaywaveParameters();
|
||||
} else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000025")) {
|
||||
//ExpressPay
|
||||
// configExpressPayParameter();
|
||||
} else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000541")) {
|
||||
configPureContactlessParameter();
|
||||
} else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000065")) {
|
||||
configJcbContactlessParameter();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
//contact terminal capability ; if different card brand(depend on aid) have different terminal capability
|
||||
if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000004")) {
|
||||
emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x33}, new byte[]{(byte) 0xE0, (byte) 0x28, (byte) 0xC8});
|
||||
emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x1D}, ByteUtils.hexString2ByteArray("6C00800000000000"));//terminal risk
|
||||
String aidStr = ByteUtils.byteArray2HexString(aid).toUpperCase();
|
||||
|
||||
if (aidStr.contains("A000000004")) {
|
||||
configPaypassParameter(aid);
|
||||
} else if (aidStr.contains("A000000003")) {
|
||||
configPaywaveParameters();
|
||||
} else if (aidStr.contains("A000000333")) {
|
||||
// configureQuickPassParamerter();
|
||||
} else if (aidStr.contains("A000000541")) {
|
||||
configPureContactlessParameter();
|
||||
} else if (aidStr.contains("A000000065")) {
|
||||
configJcbContactlessParameter();
|
||||
} else if (aidStr.contains("A000000889")) {
|
||||
configMPUContactlessParameter();
|
||||
mMPUContactlessConfigured = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
emvHandler.onSetTransInitBeforeGPOResponse(true);
|
||||
}
|
||||
|
||||
// @Override
|
||||
// public void onTransInitBeforeGPO() {
|
||||
// byte[] aid = emvHandler.getTlv(new byte[]{0x4F}, EmvDataSourceEnum.FROM_KERNEL);
|
||||
// LogUtil.d(TAG, "onTransInitBeforeGPO :");
|
||||
//// String terminalCapability = SystemParamsOperation.getInstance().getTerminalCapability();
|
||||
// String visaTerminalCapability = SystemParamsOperation.getInstance().getVisaTerminalCapability();
|
||||
// String masterTerminalCapability = SystemParamsOperation.getInstance().getMasterTerminalCapability();
|
||||
// String upiTerminalCapability = SystemParamsOperation.getInstance().getUpiTerminalCapability();
|
||||
//// LogUtil.d(TAG,"Terminal capability :"+terminalCapability);
|
||||
//// emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x33}, new byte[]{(byte) 0xE0, (byte) 0x28, (byte) 0xC8});
|
||||
// emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x33}, ByteUtil.hexStr2Bytes(terminalCapability));
|
||||
// if (mPayDetail.getCardType() == CardTypeX.NFC.value) {
|
||||
// if (aid != null) {
|
||||
// if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000004")) {
|
||||
// //Paypass
|
||||
// configPaypassParameter(aid);
|
||||
// } else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000003")) {
|
||||
// //Paywave
|
||||
// configPaywaveParameters();
|
||||
// } else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000025")) {
|
||||
// //ExpressPay
|
||||
//// configExpressPayParameter();
|
||||
// } else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000541")) {
|
||||
// configPureContactlessParameter();
|
||||
// } else if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000065")) {
|
||||
// configJcbContactlessParameter();
|
||||
// }
|
||||
// }
|
||||
// } else {
|
||||
// //contact terminal capability ; if different card brand(depend on aid) have different terminal capability
|
||||
//// if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A000000004")) {
|
||||
//// emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x33}, ByteUtil.hexStr2Bytes(terminalCapability));
|
||||
//// emvHandler.setTlv(new byte[]{(byte) 0xE0, (byte) 0x1D}, ByteUtils.hexString2ByteArray("6C00800000000000"));//terminal risk
|
||||
////
|
||||
//// }
|
||||
// }
|
||||
//
|
||||
// emvHandler.onSetTransInitBeforeGPOResponse(true);
|
||||
// }
|
||||
|
||||
@Override
|
||||
public void onConfirmCardNo(CardInfoEntity cardInfoEntity) {
|
||||
LogUtil.d(TAG, "onConfirmCardNo");
|
||||
@ -690,6 +678,17 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
|
||||
|
||||
cardNo = cardInfoEntity.getCardNo();
|
||||
|
||||
if (mPayDetail.getCardType() == CardTypeX.NFC.value) {
|
||||
if (isRestrictedBin(cardNo)) {
|
||||
isMPU_UPIContactless = true;
|
||||
LogUtil.d(TAG, "onConfirmCardNo: restricted BIN detected — " + cardNo);
|
||||
emvHandler.onSetConfirmCardNoResponse(false);
|
||||
emvHandler.emvProcessCancel();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (mPayDetail.getCardType() == CardTypeX.NFC.value) {
|
||||
cardNum.postValue(cardInfoEntity.getCardNo());
|
||||
mPayDetail.setCardNo(cardInfoEntity.getCardNo());
|
||||
@ -701,6 +700,9 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
public void onCardHolderInputPin(boolean isOnlinePin, int leftTimes) {
|
||||
LogUtil.d(TAG, "onCardHolderInputPin isOnlinePin = " + isOnlinePin);
|
||||
LogUtil.d(TAG, "onCardHolderInputPin leftTimes = " + leftTimes);
|
||||
if (isOnlinePin) {
|
||||
pinRemainingCount.postValue("");
|
||||
}
|
||||
// startPinProcess(isOnlinePin ? 1 : 0);
|
||||
mProcessStep = EMV_SHOW_PIN_PAD;
|
||||
// mHandler.obtainMessage(EMV_SHOW_PIN_PAD, isOnlinePin ? 1 : 0).sendToTarget();
|
||||
@ -739,8 +741,18 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
@Override
|
||||
public void onPrompt(PromptEnum promptEnum) {
|
||||
LogUtil.d(TAG, "onPrompt->" + promptEnum);
|
||||
if( promptEnum == PromptEnum.OFFLINE_PIN_INCORRECT_TRY_AGAIN) {
|
||||
offlinePinIncorrectPromptCount++;
|
||||
pinEnterCount = 0;
|
||||
pinText.postValue("");
|
||||
int attemptLeft = Math.max(0, 3 - offlinePinIncorrectPromptCount);
|
||||
pinRemainingCount.postValue("Please try again!\n" + attemptLeft + " attempt left!");
|
||||
emvHandler.onSetPromptResponse(false);
|
||||
|
||||
} else {
|
||||
emvHandler.onSetPromptResponse(true);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onRemoveCard() {
|
||||
@ -797,6 +809,9 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
byte[] tlv_50 = emvHandler.getTlv(new byte[]{(byte) 0x50}, EmvDataSourceEnum.FROM_KERNEL);
|
||||
LogUtil.d(TAG, "tlv_50--" + ByteUtils.byteArray2HexString(tlv_50));
|
||||
|
||||
byte[] tlv_9B = emvHandler.getTlv(new byte[]{(byte) 0x9B}, EmvDataSourceEnum.FROM_KERNEL);
|
||||
LogUtil.d(TAG, "tlv_9B--" + ByteUtils.byteArray2HexString(tlv_9B));
|
||||
|
||||
switch (retCode) {
|
||||
case SdkResult.Emv_Success_Arpc_Fail:
|
||||
case SdkResult.Success:
|
||||
@ -824,20 +839,38 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
//union pay online contactless--application should go online
|
||||
break;
|
||||
|
||||
case SdkResult.Emv_App_Block:
|
||||
case SdkResult.Emv_Card_Block:
|
||||
mHandler.sendEmptyMessage(EMV_CARD_APP_BLOCK);
|
||||
break;
|
||||
|
||||
case SdkResult.Emv_Candidatelist_Empty:// Application have no aid list
|
||||
case SdkResult.Emv_FallBack:// FallBack ,chip card reset failed
|
||||
//fallback process
|
||||
emvResultStatus.postValue(EmvResultStatus.READ_CARD_RETRY);
|
||||
if(mMPUContactlessConfigured) {
|
||||
mHandler.sendEmptyMessage(EMV_INSERT_OR_MANUAL);
|
||||
} else {
|
||||
mHandler.sendEmptyMessage(EMV_TRY_AGAIN);
|
||||
}
|
||||
|
||||
|
||||
break;
|
||||
case SdkResult.Emv_Declined:
|
||||
case SdkResult.Emv_Arpc_Fail: //
|
||||
offlineDenial();
|
||||
// mHandler.obtainMessage(EMV_ERROR, retCode, retCode, "Emv Declined!").sendToTarget();
|
||||
//// case SdkResult.Emv_Declined:
|
||||
// //online decline ,if it is in second gac, application should decide if it is need reversal the transaction
|
||||
break;
|
||||
//
|
||||
case SdkResult.Emv_Cancel:// Transaction Cancel
|
||||
// //user cancel
|
||||
if(isMPU_UPIContactless) {
|
||||
mHandler.sendEmptyMessage(EMV_INSERT_OR_MANUAL);
|
||||
} else {
|
||||
mHandler.obtainMessage(EMV_ERROR, retCode, retCode, "Canceled").sendToTarget();
|
||||
}
|
||||
|
||||
break;
|
||||
//
|
||||
// case SdkResult.Emv_Offline_Declined: //
|
||||
@ -955,6 +988,7 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
emvCardType.postValue("");
|
||||
pinText.setValue("");
|
||||
pinEnterCount = 0;
|
||||
offlinePinIncorrectPromptCount = 0;
|
||||
}
|
||||
|
||||
protected void getCardInfo() {
|
||||
@ -1210,11 +1244,11 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x1B}, new byte[]{(byte) 0x30});
|
||||
|
||||
//EMV MODE :amount >contactless cvm limit, set 60 = online pin and signature , set 20 = signature
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x18}, new byte[]{(byte) 0x28});
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x18}, new byte[]{(byte) 0xF0}); //F8 //F0
|
||||
//EMV mode :amount < contactless cvm limit, set 08 = no cvm
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x19}, new byte[]{(byte) 0x08}); //08
|
||||
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x25}, ByteUtils.hexString2ByteArray("000999999999"));
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x25}, ByteUtils.hexString2ByteArray("999999999999"));
|
||||
|
||||
if (ByteUtils.byteArray2HexString(aid).toUpperCase().contains("A0000000043060")) {
|
||||
Log.d("nexgo", "======maestro===== ");
|
||||
@ -1231,6 +1265,75 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void configMPUContactlessParameter() {
|
||||
LogUtil.d(TAG,"MPU Contactless Parameter configurations....");
|
||||
//kernel configuration, enable RRP and cdcvm
|
||||
|
||||
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x1B}, new byte[]{(byte) 0x30});
|
||||
|
||||
//EMV MODE :amount >contactless cvm limit, set 60 = online pin and signature , set 20 = signature
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x18}, new byte[]{(byte) 0xF0}); //F8
|
||||
//EMV mode :amount < contactless cvm limit, set 08 = no cvm
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x19}, new byte[]{(byte) 0x28}); //08
|
||||
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x24}, ByteUtils.hexString2ByteArray("000010000000"));
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x25}, ByteUtils.hexString2ByteArray("000010000000"));
|
||||
emvHandler.setTlv(new byte[]{(byte) 0xDF, (byte) 0x81, (byte) 0x26}, ByteUtils.hexString2ByteArray("000010000000"));
|
||||
|
||||
|
||||
|
||||
emvHandler.setTlv(new byte[]{(byte) 0x9F, (byte) 0x1d}, ByteUtils.hexString2ByteArray("6C00800000000000"));
|
||||
|
||||
setTransactionLimitForMPUCtls(true);
|
||||
|
||||
|
||||
byte[] getTLVofDF8124 = emvHandler.getTlv(ByteUtil.hexStr2Bytes("DF8124"),EmvDataSourceEnum.FROM_KERNEL);
|
||||
LogUtil.d(TAG,"DF8124: "+ByteUtil.bytes2HexStr(getTLVofDF8124));
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void setTransactionLimitForMPUCtls(boolean flag){
|
||||
if(emvHandler.getAidList() != null) {
|
||||
for (AidEntity aidEntity:emvHandler.getAidList()
|
||||
) {
|
||||
|
||||
if(aidEntity.getAid() != null) {
|
||||
if(aidEntity.getAid().equals("A00000000410") || aidEntity.getAid().equals("A0000000041010")){
|
||||
|
||||
if(flag) {
|
||||
aidEntity.setTransLimit(Long.parseLong("000010000000"));
|
||||
aidEntity.setContactlessTransLimit(Long.parseLong("000010000000"));
|
||||
} else {
|
||||
aidEntity.setTransLimit(Long.parseLong("999999999999"));
|
||||
aidEntity.setContactlessTransLimit(Long.parseLong("999999999999"));
|
||||
}
|
||||
|
||||
emvHandler.delOneAid(ByteUtil.hexStr2Bytes(aidEntity.getAid()));
|
||||
emvHandler.setAidParaList(List.of(aidEntity));
|
||||
LogUtil.d(TAG,"added AID+"+aidEntity.getAid());
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
for (AidEntity aidEntity1:emvHandler.getAidList()
|
||||
) {
|
||||
if (aidEntity1.getAid() != null) {
|
||||
if (aidEntity1.getAid().equals("A00000000410") || aidEntity1.getAid().equals("A0000000041010")) {
|
||||
|
||||
|
||||
LogUtil.d(TAG, " AID+" + aidEntity1.getAid());
|
||||
LogUtil.d(TAG, " transactionLimit+" + aidEntity1.getContactlessTransLimit());
|
||||
LogUtil.d(TAG, " transactionLimit+" + aidEntity1.getTransLimit());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void configPaywaveParameters() {
|
||||
@ -1239,13 +1342,12 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
LogUtil.d(TAG, "configPaywaveParameters, TTQ" + ByteUtils.byteArray2HexString(kernelTTQ));
|
||||
|
||||
//default TTQ value
|
||||
TTQ = ByteUtils.hexString2ByteArray("36A04000");
|
||||
TTQ = ByteUtils.hexString2ByteArray("32A04000"); // 36A04000
|
||||
kernelTTQ[0] = TTQ[0];
|
||||
kernelTTQ[1] = TTQ[1];
|
||||
kernelTTQ[2] = TTQ[2];
|
||||
kernelTTQ[3] = TTQ[3];
|
||||
|
||||
// FIXME: 2019/3/20
|
||||
//If there is no special requirements, do not change TTQ byte1
|
||||
//if online force required , can set byte2 bit 8 = 1
|
||||
emvHandler.setTlv(ByteUtils.hexString2ByteArray("9F66"), kernelTTQ);
|
||||
@ -1278,6 +1380,11 @@ public abstract class EmvBaseViewModel extends BaseViewModel {
|
||||
|
||||
}
|
||||
|
||||
private void configPureQuickPassParameter() {
|
||||
LogUtil.d(TAG, "configQuickPassParameter");
|
||||
|
||||
|
||||
}
|
||||
private void configJcbContactlessParameter() {
|
||||
LogUtil.d(TAG, "configJcbContactlessParameter");
|
||||
|
||||
|
||||
@ -1,9 +1,10 @@
|
||||
[
|
||||
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000031010",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -26,7 +27,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000032010",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -49,7 +50,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101001",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -72,7 +73,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101002",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -95,7 +96,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101003",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -118,7 +119,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101004",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -141,7 +142,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101005",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -164,7 +165,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000033010",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -187,7 +188,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000038010",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -210,7 +211,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101008",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -233,7 +234,7 @@
|
||||
"aidEnable": true,
|
||||
"aid": "A000000003101009",
|
||||
"cardScheme": "VISA",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -529,33 +530,10 @@
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000651010",
|
||||
"cardScheme": "JCB",
|
||||
"applicationVersion": "0020",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "99",
|
||||
"maxTargetPercent": "99",
|
||||
"threshold": "00000000",
|
||||
"tacDefault": "D84000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 75000,
|
||||
"transLimit": "999999999999",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
"riskManageData": "01",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aidEnable": false,
|
||||
"aid": "A00000006510",
|
||||
"cardScheme": "JCB",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -575,10 +553,33 @@
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aidEnable": false,
|
||||
"aid": "A0000000651010",
|
||||
"cardScheme": "JCB",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "99",
|
||||
"maxTargetPercent": "99",
|
||||
"threshold": "00000000",
|
||||
"tacDefault": "D84000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 75000,
|
||||
"transLimit": "999999999999",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
"riskManageData": "01",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": false,
|
||||
"aid": "A0000001570040",
|
||||
"cardScheme": "JCB",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
|
||||
@ -14,7 +14,7 @@
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 100000,
|
||||
"cvmLimit": 10000000,
|
||||
"transLimit": "000010000000",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
|
||||
@ -1,35 +1,9 @@
|
||||
[
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000041010",
|
||||
"aid": "A00000000410",
|
||||
"cardLabel": "MASTERCARD",
|
||||
"applicationVersion": "0020",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "00",
|
||||
"maxTargetPercent": "00",
|
||||
"threshold": "00000040",
|
||||
"tacDefault": "D84000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 75000,
|
||||
"transLimit": "999999999999",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "E0F8F8",
|
||||
"riskManageData": "6C7A800000000000",
|
||||
"kernelType": "02",
|
||||
"ttq": "36804000",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000041010C123456789",
|
||||
"cardLabel": "MASTERCARD",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0002",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
@ -43,7 +17,7 @@
|
||||
"cvmLimit": 75000,
|
||||
"transLimit": "999999999999",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "E0F8F8",
|
||||
"terminalCapability": "E0F8C8",
|
||||
"riskManageData": "6C7A800000000000",
|
||||
"kernelType": "02",
|
||||
"ttq": "36804000",
|
||||
@ -52,9 +26,34 @@
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000043060",
|
||||
"aid": "A0000000041010",
|
||||
"cardLabel": "MASTERCARD",
|
||||
"applicationVersion": "0020",
|
||||
"applicationVersion": "0002",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "99",
|
||||
"maxTargetPercent": "99",
|
||||
"threshold": "00000040",
|
||||
"tacDefault": "D84000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 75000,
|
||||
"transLimit": "999999999999",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "E0F8C8",
|
||||
"riskManageData": "6C7A800000000000",
|
||||
"kernelType": "02",
|
||||
"ttq": "36804000",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A0000000041010C123456789",
|
||||
"cardLabel": "MASTERCARD",
|
||||
"applicationVersion": "0002",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
|
||||
@ -173,30 +173,5 @@
|
||||
"ttq": "32A04000",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "325041592E5359532E4444463031",
|
||||
"cardLabel": "VISA",
|
||||
"applicationVersion": "0030",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "00",
|
||||
"maxTargetPercent": "00",
|
||||
"threshold": "00000000",
|
||||
"tacDefault": "DC4000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0010000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 70000,
|
||||
"transLimit": "999999999999",
|
||||
"transLimitCDV": "999999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
"riskManageData": "01",
|
||||
"kernelType": "03",
|
||||
"ttq": "32A04000",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
}
|
||||
]
|
||||
@ -14,7 +14,7 @@
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 75000,
|
||||
"cvmLimit": 30000,
|
||||
"transLimit": "9999999999",
|
||||
"transLimitCDV": "9999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
@ -39,7 +39,57 @@
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 75000,
|
||||
"cvmLimit": 30000,
|
||||
"transLimit": "9999999999",
|
||||
"transLimitCDV": "9999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
"riskManageData": "01",
|
||||
"kernelType": "01",
|
||||
"ttq": "36800000",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A000000333010105",
|
||||
"cardLabel": "UPI",
|
||||
"applicationVersion": "0002",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "99",
|
||||
"maxTargetPercent": "99",
|
||||
"threshold": "00000000",
|
||||
"tacDefault": "D84000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 30000,
|
||||
"transLimit": "9999999999",
|
||||
"transLimitCDV": "9999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
"riskManageData": "01",
|
||||
"kernelType": "01",
|
||||
"ttq": "36800000",
|
||||
"cateCode": "2701",
|
||||
"currencyCode": "0104"
|
||||
},
|
||||
{
|
||||
"aidEnable": true,
|
||||
"aid": "A000000333010106",
|
||||
"cardLabel": "UPI",
|
||||
"applicationVersion": "0002",
|
||||
"emvDDOL": "9F3704",
|
||||
"emvTDOL": "9F3704",
|
||||
"partialAidSelection": false,
|
||||
"targetPercent": "99",
|
||||
"maxTargetPercent": "99",
|
||||
"threshold": "00000000",
|
||||
"tacDefault": "D84000A800",
|
||||
"tacOnline": "DC4004F800",
|
||||
"tacDenial": "0000000000",
|
||||
"floorLimit": "000000000000",
|
||||
"cvmLimit": 30000,
|
||||
"transLimit": "9999999999",
|
||||
"transLimitCDV": "9999999999",
|
||||
"terminalCapability": "0000000000000000",
|
||||
|
||||
@ -50,6 +50,166 @@
|
||||
"expDate": "20201231",
|
||||
"checkSum": "1FF80A40173F52D7D27E0F26A146A1C8CCB29046"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "00",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "9c6be5adb10b4be3dce2099b4b210672b89656eba091204f613ecc623bedc9c6d77b660e8baeea7f7ce30f1b153879a4e36459343d1fe47acdbd41fcd710030c2ba1d9461597982c6e1bdd08554b726f5eff7913ce59e79e357295c321e26d0b8be270a9442345c753e2aa2acfc9d30850602fe6cac00c6ddf6b8d9d9b4879b2826b042a07f0e5ae526a3d3c4d22c72b9eaa52eed8893866f866387ac05a1399",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "ec0a59d35d19f031e9e8cbec56db80e22b1de130"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "01",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "C696034213D7D8546984579D1D0F0EA519CFF8DEFFC429354CF3A871A6F7183F1228DA5C7470C055387100CB935A712C4E2864DF5D64BA93FE7E63E71F25B1E5F5298575EBE1C63AA617706917911DC2A75AC28B251C7EF40F2365912490B939BCA2124A30A28F54402C34AECA331AB67E1E79B285DD5771B5D9FF79EA630B75",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "8C05A64127485B923C94B63D264AF0BF85CB45D9"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "03",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "c2490747fe17eb0584c88d47b1602704150adc88c5b998bd59ce043edebf0ffee3093ac7956ad3b6ad4554c6de19a178d6da295be15d5220645e3c8131666fa4be5b84fe131ea44b039307638b9e74a8c42564f892a64df1cb15712b736e3374f1bbb6819371602d8970e97b900793c7c2a89a4a1649a59be680574dd0b60145",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "5addf21d09278661141179cbeff272ea384b13bb"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "04",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a6da428387a502d7ddfb7a74d3f412be762627197b25435b7a81716a700157ddd06f7cc99d6ca28c2470527e2c03616b9c59217357c2674f583b3ba5c7dcf2838692d023e3562420b4615c439ca97c44dc9a249cfce7b3bfb22f68228c3af13329aa4a613cf8dd853502373d62e49ab256d2bc17120e54aedced6d96a4287acc5c04677d4a5a320db8bee2f775e5fec5",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "381a035da58b482ee2af75f4c3f2ca469ba4aa6c"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "05",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "b8048abc30c90d976336543e3fd7091c8fe4800df820ed55e7e94813ed00555b573feca3d84af6131a651d66cff4284fb13b635edd0ee40176d8bf04b7fd1c7bacf9ac7327dfaa8aa72d10db3b8e70b2ddd811cb4196525ea386acc33c0d9d4575916469c4e4f53e8e1c912cc618cb22dde7c3568e90022e6bba770202e4522a2dd623d180e215bd1d1507fe3dc90ca310d27b3efccd8f83de3052cad1e48938c68d095aac91b5f37e28bb49ec7ed597",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "ebfa0d5d06d8ce702da3eae890701d45e274c845"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "06",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "cb26fc830b43785b2bce37c81ed334622f9622f4c89aae641046b2353433883f307fb7c974162da72f7a4ec75d9d657336865b8d3023d3d645667625c9a07a6b7a137cf0c64198ae38fc238006fb2603f41f4f3bb9da1347270f2f5d8c606e420958c5f7d50a71de30142f70de468889b5e3a08695b938a50fc980393a9cbce44ad2d64f630bb33ad3f5f5fd495d31f37818c1d94071342e07f1bec2194f6035ba5ded3936500eb82dfda6e8afb655b1ef3d0d7ebf86b66dd9f29f6b1d324fe8b26ce38ab2013dd13f611e7a594d675c4432350ea244cc34f3873cba06592987a1d7e852adc22ef5a2ee28132031e48f74037e3b34ab747f",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "f910a1504d5ffb793d94f3b500765e1abcad72d9"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F1",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a0dcf4bde19c3546b4b6f0414d174dde294aabbb828c5a834d73aae27c99b0b053a90278007239b6459ff0bbcd7b4b9c6c50ac02ce91368da1bd21aaeadbc65347337d89b68f5c99a09d05be02dd1f8c5ba20e2f13fb2a27c41d3f85cad5cf6668e75851ec66edbf98851fd4e42c44c1d59f5984703b27d5b9f21b8fa0d93279fbbf69e090642909c9ea27f898959541aa6757f5f624104f6e1d3a9532f2a6e51515aead1b43b3d7835088a2fafa7be7",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "d8e68da167ab5a85d8c3d55ecb9b0517a1a5b4bb"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F3",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "98f0c770f23864c2e766df02d1e833dff4ffe92d696e1642f0a88c5694c6479d16db1537bfe29e4fdc6e6e8afd1b0eb7ea0124723c333179bf19e93f10658b2f776e829e87daeda9c94a8b3382199a350c077977c97aff08fd11310ac950a72c3ca5002ef513fccc286e646e3c5387535d509514b3b326e1234f9cb48c36ddd44b416d23654034a66f403ba511c5efa3",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "a69ac7603daf566e972dedc2cb433e07e8b01a9a"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F5",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a6e6fb72179506f860ccca8c27f99cecd94c7d4f3191d303bbee37481c7aa15f233ba755e9e4376345a9a67e7994bdc1c680bb3522d8c93eb0ccc91ad31ad450da30d337662d19ac03e2b4ef5f6ec18282d491e19767d7b24542dfdeff6f62185503532069bbb369e3bb9fb19ac6f1c30b97d249eee764e0bac97f25c873d973953e5153a42064bbfabfd06a4bb486860bf6637406c9fc36813a4a75f75c31cca9f69f8de59adecef6bde7e07800fcbe035d3176af8473e23e9aa3dfee221196d1148302677c720cfe2544a03db553e7f1b8427ba1cc72b0f29b12dfef4c081d076d353e71880aadff386352af0ab7b28ed49e1e672d11f9",
|
||||
"exponent": "010001",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "c2239804c8098170be52d6d5d4159e81ce8466bf"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F6",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a25a6bd783a5ef6b8fb6f83055c260f5f99ea16678f3b9053e0f6498e82c3f5d1e8c38f13588017e2b12b3d8ff6f50167f46442910729e9e4d1b3739e5067c0ac7a1f4487e35f675bc16e233315165cb142bfdb25e301a632a54a3371ebab6572deebaf370f337f057ee73b4ae46d1a8bc4da853ec3cc12c8cbc2da18322d68530c70b22bdac351dd36068ae321e11abf264f4d3569bb71214545005558de26083c735db776368172fe8c2f5c85e8b5b890cc682911d2de71fa626b8817fccc08922b703869f3baeac1459d77cd85376bc36182f4238314d6c4212fbdd7f23d3",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "502909ed545e3c8dbd00ea582d0617fee9f6f684"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F7",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "94ea62f6d58320e354c022addcf0559d8cf206cd92e869564905ce21d720f971b7aea374830ebe1757115a85e088d41c6b77cf5ec821f30b1d890417bf2fa31e5908ded5fa677f8c7b184ad09028fdde96b6a6109850aa800175eabcdbbb684a96c2eb6379dfea08d32fe2331fe103233ad58dcdb1e6e077cb9f24eaec5c25af",
|
||||
"exponent": "010001",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "eeb0dd9b2477bee3209a914cdba94c1c4a9bded9"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F8",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a1f5e1c9bd8650bd43ab6ee56b891ef7459c0a24fa84f9127d1a6c79d4930f6db1852e2510f18b61cd354db83a356bd190b88ab8df04284d02a4204a7b6cb7c5551977a9b36379ca3de1a08e69f301c95cc1c20506959275f41723dd5d2925290579e5a95b0df6323fc8e9273d6f849198c4996209166d9bfc973c361cc826e1",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "f06ecc6d2aaebf259b7e755a38d9a9b24e2ff3dd"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F9",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a99a6d3e071889ed9e3a0c391c69b0b804fc160b2b4bdd570c92dd5a0f45f53e8621f7c96c40224266735e1ee1b3c06238ae35046320fd8e81f8ceb3f8b4c97b940930a3ac5e790086dad41a6a4f5117ba1ce2438a51ac053eb002aed866d2c458fd73359021a12029a0c043045c11664fe0219ec63c10bf2155bb2784609a106421d45163799738c1c30909bb6c6fe52bbb76397b9740ce064a613ff8411185f08842a423ead20edffbff1cd6c3fe0c9821479199c26d8572cc8afff087a9c3",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "336712dcc28554809c6aa9b02358de6f755164db"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "FA",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a90fcd55aa2d5d9963e35ed0f440177699832f49c6bab15cdae5794be93f934d4462d5d12762e48c38ba83d8445deaa74195a301a102b2f114eada0d180ee5e7a5c73e0c4e11f67a43ddab5d55683b1474cc0627f44b8d3088a492ffaadad4f42422d0e7013536c3c49ad3d0fae96459b0f6b1b6056538a3d6d44640f94467b108867dec40faaecd740c00e2b7a8852d",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "5bed4068d96ea16d2d77e03d6036fc7a160ea99c"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "FE",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a653eac1c0f786c8724f737f172997d63d1c3251c44402049b865bae877d0f398cbfbe8a6035e24afa086befde9351e54b95708ee672f0968bcd50dce40f783322b2aba04ef137ef18abf03c7dbc5813aeaef3aa7797ba15df7d5ba1cbaf7fd520b5a482d8d3fee105077871113e23a49af3926554a70fe10ed728cf793b62a1",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "9a295b05fb390ef7923f57618a9fda2941fc34e0"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "EF",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "a191cb87473f29349b5d60a88b3eaee0973aa6f1a082f358d849fddff9c091f899eda9792caf09ef28f5d22404b88a2293eebbc1949c43bea4d60cfd879a1539544e09e0f09f60f065b2bf2a13ecc705f3d468b9d33ae77ad9d3f19ca40f23dcf5eb7c04dc8f69eba565b1ebcb4686cd274785530ff6f6e9ee43aa43fdb02ce00daec15c7b8fd6a9b394baba419d3f6dc85e16569be8e76989688efea2df22ff7d35c043338deaa982a02b866de5328519ebbcd6f03cdd686673847f84db651ab86c28cf1462562c577b853564a290c8556d818531268d25cc98a4cc6a0bdfffda2dcca3a94c998559e307fddf915006d9a987b07ddaeb3b",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "21766ebb0ee122afb65d7845b73db46bab65427a"
|
||||
},
|
||||
{
|
||||
"rid": "A000000333",
|
||||
"indx": "0A",
|
||||
@ -59,7 +219,7 @@
|
||||
"exponent": "03",
|
||||
"expDate": "3230333031323331",
|
||||
"checkSum": "C88BE6B2417C4F941C9371EA35A377158767E4E3"
|
||||
},
|
||||
},
|
||||
{
|
||||
"rid": "A000000333",
|
||||
"indx": "08",
|
||||
@ -90,6 +250,16 @@
|
||||
"expDate": "3230333031323331",
|
||||
"checkSum": "BD331F9996A490B33C13441066A09AD3FEB5F66C"
|
||||
},
|
||||
{
|
||||
"rid": "A000000065",
|
||||
"indx": "07",
|
||||
"hashInd": "01",
|
||||
"arithInd": "00",
|
||||
"modul": "B8DAB883EF1B5763E4F861F9EA3044B276635D402F3AE5E6B6C0547E368E79A36366DAC5609B6EC486DA1A8D2002CA4F4EFC2CB0EC1573A0B0917969EB60645BAEDF11C050C5D07FED817D11E84A174859A0DAE7F7935F109229C0AC4EE5BFB3D65533A679F0486C5AEFCC937379833BEC45D79DCF97B5228B1910FA03765331",
|
||||
"exponent": "010001",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "4896DD5A9EB5B11B9DCCA6DFE336C009F69F509A"
|
||||
},
|
||||
{
|
||||
"rid": "A000000065",
|
||||
"indx": "08",
|
||||
@ -97,7 +267,7 @@
|
||||
"arithInd": "00",
|
||||
"modul": "B74670DAD1DC8983652000E5A7F2F8B35DFD083EE593E5BA895C95729F2BADE9C8ABF3DD9CE240C451C6CEFFC768D83CBAC76ABB8FEA58F013C647007CFF7617BAC2AE3981816F25CC7E5238EF34C4F02D0B01C24F80C2C65E7E7743A4FA8E23206A23ECE290C26EA56DB085C5C5EAE26292451FC8292F9957BE8FF20FAD53E5",
|
||||
"exponent": "03",
|
||||
"expDate": "3230333031323331",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "DD36D5896228C8C4900742F107E2F91FE50BC7EE"
|
||||
},
|
||||
{
|
||||
@ -117,7 +287,7 @@
|
||||
"arithInd": "00",
|
||||
"modul": "99B63464EE0B4957E4FD23BF923D12B61469B8FFF8814346B2ED6A780F8988EA9CF0433BC1E655F05EFA66D0C98098F25B659D7A25B8478A36E489760D071F54CDF7416948ED733D816349DA2AADDA227EE45936203CBF628CD033AABA5E5A6E4AE37FBACB4611B4113ED427529C636F6C3304F8ABDD6D9AD660516AE87F7F2DDF1D2FA44C164727E56BBC9BA23C0285",
|
||||
"exponent": "03",
|
||||
"expDate": "3230333031323331",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "C75E5210CBE6E8F0594A0F1911B07418CADB5BAB"
|
||||
},
|
||||
{
|
||||
@ -127,7 +297,7 @@
|
||||
"arithInd": "00",
|
||||
"modul": "A2583AA40746E3A63C22478F576D1EFC5FB046135A6FC739E82B55035F71B09BEB566EDB9968DD649B94B6DEDC033899884E908C27BE1CD291E5436F762553297763DAA3B890D778C0F01E3344CECDFB3BA70D7E055B8C760D0179A403D6B55F2B3B083912B183ADB7927441BED3395A199EEFE0DEBD1F5FC3264033DA856F4A8B93916885BD42F9C1F456AAB8CFA83AC574833EB5E87BB9D4C006A4B5346BD9E17E139AB6552D9C58BC041195336485",
|
||||
"exponent": "03",
|
||||
"expDate": "3230333031323331",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "D9FD62C9DD4E6DE7741E9A17FB1FF2C5DB948BCB"
|
||||
},
|
||||
{
|
||||
@ -137,28 +307,17 @@
|
||||
"arithInd": "00",
|
||||
"modul": "AEED55B9EE00E1ECEB045F61D2DA9A66AB637B43FB5CDBDB22A2FBB25BE061E937E38244EE5132F530144A3F268907D8FD648863F5A96FED7E42089E93457ADC0E1BC89C58A0DB72675FBC47FEE9FF33C16ADE6D341936B06B6A6F5EF6F66A4EDD981DF75DA8399C3053F430ECA342437C23AF423A211AC9F58EAF09B0F837DE9D86C7109DB1646561AA5AF0289AF5514AC64BC2D9D36A179BB8A7971E2BFA03A9E4B847FD3D63524D43A0E8003547B94A8A75E519DF3177D0A60BC0B4BAB1EA59A2CBB4D2D62354E926E9C7D3BE4181E81BA60F8285A896D17DA8C3242481B6C405769A39D547C74ED9FF95A70A796046B5EFF36682DC29",
|
||||
"exponent": "03",
|
||||
"expDate": "3230333031323331",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "43A3151513B7ADCEB92DBEA2A262CEB336D26C83"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "F1",
|
||||
"rid": "A000000065",
|
||||
"indx": "13",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "A0DCF4BDE19C3546B4B6F0414D174DDE294AABBB828C5A834D73AAE27C99B0B053A90278007239B6459FF0BBCD7B4B9C6C50AC02CE91368DA1BD21AAEADBC65347337D89B68F5C99A09D05BE02DD1F8C5BA20E2F13FB2A27C41D3F85CAD5CF6668E75851EC66EDBF98851FD4E42C44C1D59F5984703B27D5B9F21B8FA0D93279FBBF69E090642909C9EA27F898959541AA6757F5F624104F6E1D3A9532F2A6E51515AEAD1B43B3D7835088A2FAFA7BE7",
|
||||
"arithInd": "00",
|
||||
"modul": "A3270868367E6E29349FC2743EE545AC53BD3029782488997650108524FD051E3B6EACA6A9A6C1441D28889A5F46413C8F62F3645AAEB30A1521EEF41FD4F3445BFA1AB29F9AC1A74D9A16B93293296CB09162B149BAC22F88AD8F322D684D6B49A12413FC1B6AC70EDEDB18EC1585519A89B50B3D03E14063C2CA58B7C2BA7FB22799A33BCDE6AFCBEB4A7D64911D08D18C47F9BD14A9FAD8805A15DE5A38945A97919B7AB88EFA11A88C0CD92C6EE7DC352AB0746ABF13585913C8A4E04464B77909C6BD94341A8976C4769EA6C0D30A60F4EE8FA19E767B170DF4FA80312DBA61DB645D5D1560873E2674E1F620083F30180BD96CA589",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "D8E68DA167AB5A85D8C3D55ECB9B0517A1A5B4BB"
|
||||
},
|
||||
{
|
||||
"rid": "A000000004",
|
||||
"indx": "EF",
|
||||
"hashInd": "01",
|
||||
"arithInd": "01",
|
||||
"modul": "A191CB87473F29349B5D60A88B3EAEE0973AA6F1A082F358D849FDDFF9C091F899EDA9792CAF09EF28F5D22404B88A2293EEBBC1949C43BEA4D60CFD879A1539544E09E0F09F60F065B2BF2A13ECC705F3D468B9D33AE77AD9D3F19CA40F23DCF5EB7C04DC8F69EBA565B1EBCB4686CD274785530FF6F6E9EE43AA43FDB02CE00DAEC15C7B8FD6A9B394BABA419D3F6DC85E16569BE8E76989688EFEA2DF22FF7D35C043338DEAA982A02B866DE5328519EBBCD6F03CDD686673847F84DB651AB86C28CF1462562C577B853564A290C8556D818531268D25CC98A4CC6A0BDFFFDA2DCCA3A94C998559E307FDDF915006D9A987B07DDAEB3B",
|
||||
"exponent": "03",
|
||||
"expDate": "20201231",
|
||||
"checkSum": "21766EBB0EE122AFB65D7845B73DB46BAB65427A"
|
||||
"checkSum": "54CFAE617150DFA09D3F901C9123524523EBEDF3"
|
||||
}
|
||||
|
||||
]
|
||||
@ -21,7 +21,7 @@ public class ExampleUnitTest {
|
||||
|
||||
@Test
|
||||
public void testCAPKIndex() {
|
||||
String index = "99";
|
||||
String index = "F1";
|
||||
int data = Integer.parseInt(index,16);
|
||||
|
||||
System.out.println("Data: "+data);
|
||||
|
||||
@ -6,6 +6,7 @@ import android.os.Looper;
|
||||
import android.os.RemoteException;
|
||||
import android.util.Log;
|
||||
|
||||
import com.nexgo.common.LogUtils;
|
||||
import com.nexgo.oaf.apiv3.SdkResult;
|
||||
import com.nexgo.oaf.apiv3.device.reader.CardInfoEntity;
|
||||
import com.nexgo.oaf.apiv3.device.reader.CardSlotTypeEnum;
|
||||
@ -106,6 +107,14 @@ public class CheckCardX {
|
||||
Log.d(TAG, "Find IC");
|
||||
} else if(cardInfoEntity.getCardExistslot() == CardSlotTypeEnum.RF) {
|
||||
checkCardResultX.onSuccess(CardTypeX.NFC,false);
|
||||
} else if(cardInfoEntity.getCardExistslot() == CardSlotTypeEnum.SWIPE) {
|
||||
LogUtils.debug(TAG,"Found Swipe");
|
||||
Bundle info = new Bundle();
|
||||
info.putString("TRACK1",cardInfoEntity.getTk1());
|
||||
info.putString("TRACK2",cardInfoEntity.getTk2());
|
||||
info.putString("TRACK3",cardInfoEntity.getTk3());
|
||||
MAGXReadCard.getInstance().setBundle(info);
|
||||
checkCardResultX.onSuccess(CardTypeX.MAG,false);
|
||||
}
|
||||
} else if( i == SdkResult.Fail) {
|
||||
checkCardResultX.onError(i,"Failure");
|
||||
|
||||
@ -1,2 +1,2 @@
|
||||
configurations.maybeCreate("default")
|
||||
artifacts.add("default", file('nexgo-smartpos-sdk-v3.08.006_20241216.aar'))
|
||||
artifacts.add("default", file('nexgo-smartpos-sdk-v3.08.013_20260416.aar'))
|
||||
BIN
nexsdk-lib/nexgo-smartpos-sdk-v3.08.013_20260416.aar
Normal file
BIN
nexsdk-lib/nexgo-smartpos-sdk-v3.08.013_20260416.aar
Normal file
Binary file not shown.
BIN
paylibs/src/main/assets/fonts/firaCode_bold.ttf
Normal file
BIN
paylibs/src/main/assets/fonts/firaCode_bold.ttf
Normal file
Binary file not shown.
@ -1,15 +1,17 @@
|
||||
package com.utsmyanmar.paylibs.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class CardSettleData {
|
||||
public class CardSettleData implements Serializable {
|
||||
|
||||
private String cardType;
|
||||
private String cardNum;
|
||||
private String expDate;
|
||||
private String invoiceNum;
|
||||
private String transType;
|
||||
private String currencyCode;
|
||||
|
||||
private long amount;
|
||||
|
||||
@ -21,12 +23,13 @@ public class CardSettleData {
|
||||
public CardSettleData() {
|
||||
|
||||
}
|
||||
public CardSettleData(String cardType, String cardNum, String expDate, String invoiceNum, String transType, long amount, String transDate, String transTime, String approvalCode) {
|
||||
public CardSettleData(String cardType, String cardNum, String expDate, String invoiceNum, String transType, String currencyCode, long amount, String transDate, String transTime, String approvalCode) {
|
||||
this.cardType = cardType;
|
||||
this.cardNum = cardNum;
|
||||
this.expDate = expDate;
|
||||
this.invoiceNum = invoiceNum;
|
||||
this.transType = transType;
|
||||
this.currencyCode = currencyCode;
|
||||
this.amount = amount;
|
||||
this.transDate = transDate;
|
||||
this.transTime = transTime;
|
||||
@ -53,6 +56,10 @@ public class CardSettleData {
|
||||
this.transType = transType;
|
||||
}
|
||||
|
||||
public void setCurrencyCode(String currencyCode) {
|
||||
this.currencyCode = currencyCode;
|
||||
}
|
||||
|
||||
public void setAmount(long amount) {
|
||||
this.amount = amount;
|
||||
}
|
||||
@ -85,6 +92,10 @@ public class CardSettleData {
|
||||
return transType;
|
||||
}
|
||||
|
||||
public String getCurrencyCode() {
|
||||
return currencyCode;
|
||||
}
|
||||
|
||||
public long getAmount() {
|
||||
return amount;
|
||||
}
|
||||
@ -114,6 +125,7 @@ public class CardSettleData {
|
||||
cardSettleData.setExpDate(pay.getEXPDate());
|
||||
cardSettleData.setInvoiceNum(pay.getInvoiceNo());
|
||||
cardSettleData.setTransType(pay.getTransType());
|
||||
cardSettleData.setCurrencyCode(pay.getCurrencyCode());
|
||||
cardSettleData.setAmount(pay.getAmount());
|
||||
cardSettleData.setTransDate(pay.getTransDate());
|
||||
cardSettleData.setTransTime(pay.getTransTime());
|
||||
|
||||
@ -1,9 +1,10 @@
|
||||
package com.utsmyanmar.paylibs.model;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class QRSettleData {
|
||||
public class QRSettleData implements Serializable {
|
||||
|
||||
private String transId;
|
||||
private String date;
|
||||
|
||||
@ -1,6 +1,8 @@
|
||||
package com.utsmyanmar.paylibs.model;
|
||||
|
||||
public class SettleData {
|
||||
import java.io.Serializable;
|
||||
|
||||
public class SettleData implements Serializable {
|
||||
|
||||
private int saleCount;
|
||||
private long saleAmount;
|
||||
|
||||
@ -1,6 +1,8 @@
|
||||
package com.utsmyanmar.paylibs.model.enums;
|
||||
|
||||
public enum TransCVM {
|
||||
import java.io.Serializable;
|
||||
|
||||
public enum TransCVM implements Serializable {
|
||||
OFFLINE_PIN("Offline PIN"),
|
||||
ONLINE_PIN("Online PIN"),
|
||||
SIGNATURE("Signature"),
|
||||
|
||||
@ -45,6 +45,7 @@ import java.time.format.DateTimeFormatter;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Comparator;
|
||||
import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
@ -122,7 +123,7 @@ public abstract class BaseXPrint {
|
||||
returnText[1] = 0x33;
|
||||
returnText[2] = (byte) height;
|
||||
Resources resources = PayLibNex.getInstance().context.getResources();
|
||||
printer.setTypeface(Typeface.createFromAsset(PayLibNex.getInstance().context.getAssets(), "fonts/fira_code_medium.ttf"));
|
||||
printer.setTypeface(Typeface.createFromAsset(PayLibNex.getInstance().context.getAssets(), "fonts/firaCode_bold.ttf"));
|
||||
printer.setGray(getGrayLevel());
|
||||
|
||||
}
|
||||
@ -212,26 +213,38 @@ public abstract class BaseXPrint {
|
||||
}
|
||||
|
||||
protected void printTransDetailSettlement(PayDetail payDetail) {
|
||||
|
||||
|
||||
SettleData settleData = payDetail.getSettleDataObj();
|
||||
int totalCount = settleData.getSaleCount() + settleData.getPreAuthCompCount() + settleData.getRefundCount() + settleData.getCashAdvanceCount();
|
||||
long totalAmount = settleData.getSaleAmount() + settleData.getPreAuthCompAmount() + settleData.getCashAdvanceAmount();
|
||||
List<CardSettleData> cardSettleDataList = payDetail.getCardSettleData();
|
||||
CurrencySettlementSummary mmkSummary = new CurrencySettlementSummary();
|
||||
CurrencySettlementSummary usdSummary = new CurrencySettlementSummary();
|
||||
|
||||
print3ColumnsString("TRX TYPE ", "CNT", "AMOUNT");
|
||||
print3ColumnsString("SALE ", countStringFormat(settleData.getSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getSaleAmount()));
|
||||
print3ColumnsString("PREAUTH COMP ", countStringFormat(settleData.getPreAuthCompCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getPreAuthCompAmount()));
|
||||
if (settleData.getCashAdvanceCount() != 0)
|
||||
print3ColumnsString("CASH ADVANCE ", countStringFormat(settleData.getCashAdvanceCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getCashAdvanceAmount()));
|
||||
print3ColumnsString("REFUND ", countStringFormat(settleData.getRefundCount()), "- " + PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getRefundAmount()));
|
||||
print3ColumnsString("TOTAL(MMK) ", countStringFormat(totalCount), PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount));
|
||||
if (cardSettleDataList != null && !cardSettleDataList.isEmpty()) {
|
||||
for (CardSettleData cardSettleData : cardSettleDataList) {
|
||||
CurrencySettlementSummary summary = "USD".equals(normalizeSettlementCurrency(cardSettleData.getCurrencyCode())) ? usdSummary : mmkSummary;
|
||||
applyCardSettlementSummary(summary, cardSettleData);
|
||||
}
|
||||
} else {
|
||||
mmkSummary.saleCount = settleData.getSaleCount();
|
||||
mmkSummary.saleAmount = settleData.getSaleAmount();
|
||||
mmkSummary.preAuthCompCount = settleData.getPreAuthCompCount();
|
||||
mmkSummary.preAuthCompAmount = settleData.getPreAuthCompAmount();
|
||||
mmkSummary.refundCount = settleData.getRefundCount();
|
||||
mmkSummary.refundAmount = settleData.getRefundAmount();
|
||||
mmkSummary.cashAdvanceCount = settleData.getCashAdvanceCount();
|
||||
mmkSummary.cashAdvanceAmount = settleData.getCashAdvanceAmount();
|
||||
}
|
||||
|
||||
printSettlementCurrencySection("MMK", mmkSummary);
|
||||
if (usdSummary.hasAnyValue()) {
|
||||
emptyLine(1);
|
||||
printSettlementCurrencySection("USD", usdSummary);
|
||||
}
|
||||
|
||||
emptyLine(2);
|
||||
|
||||
|
||||
}
|
||||
|
||||
protected void printTransDetailSettlement(PayDetail payDetail, List<CardSettleData> cardSettleDataList) {
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
|
||||
lineBreak();
|
||||
print2SideStringMargin("CARD TYPE ","CARD NUMBER");
|
||||
@ -243,7 +256,7 @@ public abstract class BaseXPrint {
|
||||
for (CardSettleData cardSettleData:cardSettleDataList) {
|
||||
print2SideStringMargin(cardSettleData.getCardType(),PrintUtils.getInstance().maskCardNumberPciDss(cardSettleData.getCardNum()));
|
||||
print2SideStringMargin("XX/XX",cardSettleData.getInvoiceNum());
|
||||
print2SideStringMargin(cardSettleData.getTransType(),"MMK "+PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount(),true));
|
||||
print2SideStringMargin(cardSettleData.getTransType(),"MMK "+PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount(), isDecimalEnabled));
|
||||
print2SideStringMargin(cardSettleData.getApprovalCode(),cardSettleData.getTransDate() + " " + cardSettleData.getTransTime() );
|
||||
emptyLine(1);
|
||||
}
|
||||
@ -254,28 +267,95 @@ public abstract class BaseXPrint {
|
||||
long totalAmount = settleData.getSaleAmount() + settleData.getPreAuthCompAmount() + settleData.getCashAdvanceAmount();
|
||||
|
||||
print3ColumnsString("TRX TYPE ", "CNT", "AMOUNT");
|
||||
print3ColumnsString("SALE ", countStringFormat(settleData.getSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getSaleAmount()));
|
||||
print3ColumnsString("VOID SALE ", countStringFormat(settleData.getVoidSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getVoidSaleAmount()));
|
||||
print3ColumnsString("PREAUTH COMP ", countStringFormat(settleData.getPreAuthCompCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getPreAuthCompAmount()));
|
||||
print3ColumnsString("SALE ", countStringFormat(settleData.getSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getSaleAmount(), isDecimalEnabled));
|
||||
print3ColumnsString("VOID SALE ", countStringFormat(settleData.getVoidSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getVoidSaleAmount(), isDecimalEnabled));
|
||||
print3ColumnsString("PREAUTH COMP ", countStringFormat(settleData.getPreAuthCompCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getPreAuthCompAmount(), isDecimalEnabled));
|
||||
if (settleData.getCashAdvanceCount() != 0)
|
||||
print3ColumnsString("CASH ADV ", countStringFormat(settleData.getCashAdvanceCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getCashAdvanceAmount()));
|
||||
print3ColumnsString("REFUND ", countStringFormat(settleData.getRefundCount()), "- " + PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getRefundAmount()));
|
||||
print3ColumnsString("CASH ADV ", countStringFormat(settleData.getCashAdvanceCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getCashAdvanceAmount(), isDecimalEnabled));
|
||||
print3ColumnsString("REFUND ", countStringFormat(settleData.getRefundCount()), "- " + PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getRefundAmount(), isDecimalEnabled));
|
||||
emptyLine(1);
|
||||
printer.appendPrnStr("GRAND TOTAL", fontLarge, AlignEnum.LEFT,true);
|
||||
emptyLine(1);
|
||||
// print3ColumnsString("TOTAL(MMK) ", countStringFormat(totalCount), PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount));
|
||||
print3ColumnsString("TRX TYPE ", "CNT", "AMOUNT");
|
||||
print3ColumnsString("SALE ", countStringFormat(settleData.getSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getSaleAmount()));
|
||||
print3ColumnsString("VOID SALE ", countStringFormat(settleData.getVoidSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getVoidSaleAmount()));
|
||||
print3ColumnsString("PREAUTH COMP ", countStringFormat(settleData.getPreAuthCompCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getPreAuthCompAmount()));
|
||||
print3ColumnsString("SALE ", countStringFormat(settleData.getSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getSaleAmount(), isDecimalEnabled));
|
||||
print3ColumnsString("VOID SALE ", countStringFormat(settleData.getVoidSaleCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getVoidSaleAmount(), isDecimalEnabled));
|
||||
print3ColumnsString("PREAUTH COMP ", countStringFormat(settleData.getPreAuthCompCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getPreAuthCompAmount(), isDecimalEnabled));
|
||||
if (settleData.getCashAdvanceCount() != 0)
|
||||
print3ColumnsString("CASH ADV ", countStringFormat(settleData.getCashAdvanceCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getCashAdvanceAmount()));
|
||||
print3ColumnsString("REFUND ", countStringFormat(settleData.getRefundCount()), "- " + PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getRefundAmount()));
|
||||
print3ColumnsString("CASH ADV ", countStringFormat(settleData.getCashAdvanceCount()), PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getCashAdvanceAmount(), isDecimalEnabled));
|
||||
print3ColumnsString("REFUND ", countStringFormat(settleData.getRefundCount()), "- " + PrintUtils.getInstance().getSeparatorNumberFormat(settleData.getRefundAmount(), isDecimalEnabled));
|
||||
emptyLine(2);
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void printSettlementCurrencySection(String currencyLabel, CurrencySettlementSummary summary) {
|
||||
if (!summary.hasAnyValue()) {
|
||||
return;
|
||||
}
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
|
||||
int totalCount = summary.saleCount + summary.preAuthCompCount + summary.refundCount + summary.cashAdvanceCount;
|
||||
long totalAmount = summary.saleAmount + summary.preAuthCompAmount + summary.cashAdvanceAmount - summary.refundAmount;
|
||||
|
||||
printString("CURRENCY : " + currencyLabel, true);
|
||||
print3ColumnsString("TRX TYPE ", "CNT", "AMOUNT");
|
||||
print3ColumnsString("SALE ", countStringFormat(summary.saleCount), PrintUtils.getInstance().getSeparatorNumberFormat(summary.saleAmount, isDecimalEnabled));
|
||||
print3ColumnsString("PREAUTH COMP ", countStringFormat(summary.preAuthCompCount), PrintUtils.getInstance().getSeparatorNumberFormat(summary.preAuthCompAmount, isDecimalEnabled));
|
||||
if (summary.cashAdvanceCount != 0) {
|
||||
print3ColumnsString("CASH ADVANCE ", countStringFormat(summary.cashAdvanceCount), PrintUtils.getInstance().getSeparatorNumberFormat(summary.cashAdvanceAmount, isDecimalEnabled));
|
||||
}
|
||||
print3ColumnsString("REFUND ", countStringFormat(summary.refundCount), "- " + PrintUtils.getInstance().getSeparatorNumberFormat(summary.refundAmount, isDecimalEnabled));
|
||||
print3ColumnsString("TOTAL(" + currencyLabel + ") ", countStringFormat(totalCount), PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount, isDecimalEnabled));
|
||||
}
|
||||
|
||||
private void applyCardSettlementSummary(CurrencySettlementSummary summary, CardSettleData cardSettleData) {
|
||||
String transType = cardSettleData.getTransType() == null ? "" : cardSettleData.getTransType().trim().toUpperCase(Locale.getDefault());
|
||||
long amount = cardSettleData.getAmount();
|
||||
|
||||
if ("SALE".equals(transType)) {
|
||||
summary.saleCount++;
|
||||
summary.saleAmount += amount;
|
||||
} else if ("PREAUTH COMPLETION".equals(transType) || "PRE_AUTH_COMPLETE".equals(transType)) {
|
||||
summary.preAuthCompCount++;
|
||||
summary.preAuthCompAmount += amount;
|
||||
} else if ("REFUND".equals(transType)) {
|
||||
summary.refundCount++;
|
||||
summary.refundAmount += amount;
|
||||
} else if ("CASH_OUT".equals(transType) || "CASH_ADVANCE".equals(transType)) {
|
||||
summary.cashAdvanceCount++;
|
||||
summary.cashAdvanceAmount += amount;
|
||||
}
|
||||
}
|
||||
|
||||
private String normalizeSettlementCurrency(String currencyCode) {
|
||||
if (currencyCode == null) {
|
||||
return "MMK";
|
||||
}
|
||||
|
||||
String value = currencyCode.trim().toUpperCase(Locale.getDefault());
|
||||
if ("840".equals(value) || "USD".equals(value)) {
|
||||
return "USD";
|
||||
}
|
||||
return "MMK";
|
||||
}
|
||||
|
||||
private static class CurrencySettlementSummary {
|
||||
int saleCount;
|
||||
long saleAmount;
|
||||
int preAuthCompCount;
|
||||
long preAuthCompAmount;
|
||||
int refundCount;
|
||||
long refundAmount;
|
||||
int cashAdvanceCount;
|
||||
long cashAdvanceAmount;
|
||||
|
||||
boolean hasAnyValue() {
|
||||
return saleCount > 0 || preAuthCompCount > 0 || refundCount > 0 || cashAdvanceCount > 0
|
||||
|| saleAmount > 0 || preAuthCompAmount > 0 || refundAmount > 0 || cashAdvanceAmount > 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private String currencyCodeToText(String currencyCode) {
|
||||
String currencyText = "MMK";
|
||||
@ -324,7 +404,7 @@ public abstract class BaseXPrint {
|
||||
print2ColumnsStringNoSpace("ENTRY MODE :", PrintUtils.getInstance().getEntryType(payDetail.getCardType()));
|
||||
print2ColumnsStringNoSpace("EXP DATE :",PrintUtils.getInstance().getFormatExpDate(payDetail.getEXPDate()));
|
||||
print2ColumnsStringNoSpace("CARD TYPE :", payDetail.getAccountType());
|
||||
print2ColumnsStringNoSpace("TRACE NUM :", payDetail.getVoucherNo());
|
||||
print2ColumnsStringNoSpace("TRACE NUM :", payDetail.getInvoiceNo());
|
||||
|
||||
if (payDetail.getCardType() != BaseCardType.MAGNETIC.getValue()) {
|
||||
print2ColumnsStringNoSpace("CARD HOLDER:", firsLineName);
|
||||
@ -350,10 +430,11 @@ public abstract class BaseXPrint {
|
||||
|
||||
|
||||
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
if (payDetail.getTradeAnswerCode().equals("00") || payDetail.getTradeAnswerCode().equals("000")) {
|
||||
if (payDetail.getTransactionType() == TransactionType.CASH_ADVANCE) {
|
||||
print2ColumnsStringNoSpace("TXN AMOUNT", ":" + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount()));
|
||||
print2ColumnsStringNoSpace("TXN FEES", ":" + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAdditionalAmount()));
|
||||
print2ColumnsStringNoSpace("TXN AMOUNT", ":" + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount(), isDecimalEnabled));
|
||||
print2ColumnsStringNoSpace("TXN FEES", ":" + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAdditionalAmount(), isDecimalEnabled));
|
||||
}
|
||||
}
|
||||
dotBreak();
|
||||
@ -364,12 +445,12 @@ public abstract class BaseXPrint {
|
||||
printer.appendPrnStr("MMK " + PrintUtils.getInstance().getBalanceInquiryNumberFormat(payDetail.getAmount()), fontNormal, AlignEnum.LEFT,false);
|
||||
|
||||
} else if (payDetail.getTransactionType() == TransactionType.VOID || payDetail.getTransactionType() == TransactionType.REFUND || payDetail.getTransactionType() == TransactionType.PRE_SALE_CANCEL || payDetail.getTransactionType() == TransactionType.PRE_SALE_COMPLETE_VOID) {
|
||||
print2SideString("AMT:" + currencySign, "- " + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount()));
|
||||
print2SideString("AMT:" + currencySign, "- " + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount(), isDecimalEnabled));
|
||||
} else if (payDetail.getTransactionType() == TransactionType.CASH_ADVANCE) {
|
||||
long totalAmount = payDetail.getAmount() + payDetail.getAdditionalAmount();
|
||||
print2SideString("AMT:" + currencySign, PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount));
|
||||
print2SideString("AMT:" + currencySign, PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount, isDecimalEnabled));
|
||||
} else {
|
||||
print2SideString("AMT:" + currencySign, PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount()));
|
||||
print2SideString("AMT:" + currencySign, PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount(), isDecimalEnabled));
|
||||
}
|
||||
dotBreak();
|
||||
} else {
|
||||
@ -446,15 +527,14 @@ public abstract class BaseXPrint {
|
||||
printer.appendPrnStr("BTH NO:" + batchNum, fontNormal, AlignEnum.LEFT,false);
|
||||
} else {
|
||||
// printer.printColumnsString(new String[]{"BATCH NO :" + batchNum, "INV NO: " + invoiceNo}, new int[]{2, 2}, new int[]{0, 2}, null);
|
||||
printer.appendPrnStr("BTH NO:" + batchNum + " TRACE NO:" + traceNo, fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr("BTH NO:" + batchNum + " INV NO:" + traceNo, fontNormal, AlignEnum.LEFT,false);
|
||||
}
|
||||
|
||||
|
||||
printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
// printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr(transType.replace("_", " "), fontNormal, AlignEnum.CENTER,true);
|
||||
printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
// printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
// printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
|
||||
}
|
||||
|
||||
@ -496,7 +576,7 @@ public abstract class BaseXPrint {
|
||||
print2ColumnsStringNoSpace("ENTRY MODE:", PrintUtils.getInstance().getEntryType(payDetail.getCardType()));
|
||||
print2ColumnsStringNoSpace("EXP DATE :",PrintUtils.getInstance().getFormatExpDate(payDetail.getEXPDate()));
|
||||
print2ColumnsStringNoSpace("CARD TYPE :", payDetail.getAccountType());
|
||||
print2ColumnsStringNoSpace("TRACE NUM :", payDetail.getVoucherNo());
|
||||
print2ColumnsStringNoSpace("TRACE NUM :", payDetail.getInvoiceNo());
|
||||
|
||||
if (payDetail.getCardType() != BaseCardType.MAGNETIC.getValue()) {
|
||||
print2ColumnsStringNoSpace("CARD HOLDER:", firsLineName);
|
||||
@ -516,26 +596,27 @@ public abstract class BaseXPrint {
|
||||
|
||||
print2ColumnsStringNoSpace("AID :", payDetail.getAID());
|
||||
|
||||
lineBreak();
|
||||
dotBreak();
|
||||
// check is pin change
|
||||
if (payDetail.getTradeAnswerCode().equals("00") || payDetail.getTradeAnswerCode().equals("000")) {
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
|
||||
String currencySign = currencyCodeToText(payDetail.getCurrencyCode());
|
||||
// CurrencyType currencySign = currencyTextToCurrencyType(payDetail.getCurrencyCode());
|
||||
if (payDetail.getTransactionType() == TransactionType.BALANCE_INQUIRY) {
|
||||
printer.appendPrnStr("MMK " + PrintUtils.getInstance().getBalanceInquiryNumberFormat(payDetail.getAmount()), fontNormal, AlignEnum.LEFT,true);
|
||||
} else {
|
||||
print2SideString("AMOUNT:" + currencySign, PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount()));
|
||||
print2SideString("AMT:" + currencySign, PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount(), isDecimalEnabled));
|
||||
// printer.appendPrnStr("AMOUNT:" + currencySign + " " + PrintUtils.getInstance().getSeparatorNumberFormat(payDetail.getAmount()), fontNormal, AlignEnum.LEFT,true);
|
||||
}
|
||||
lineBreak();
|
||||
dotBreak();
|
||||
} else {
|
||||
|
||||
// lineBreak();
|
||||
emptyLine(1);
|
||||
printer.appendPrnStr(BaseErrorCode.getCode(payDetail.getTradeAnswerCode()), fontNormal, AlignEnum.CENTER,true);
|
||||
emptyLine(1);
|
||||
lineBreak();
|
||||
dotBreak();
|
||||
}
|
||||
|
||||
emptyLine(1);
|
||||
@ -545,11 +626,12 @@ public abstract class BaseXPrint {
|
||||
|
||||
private void printColumnString(String label, int count, long amount, boolean isNegative) {
|
||||
if (count > 0) {
|
||||
String amountString = PrintUtils.getInstance().getSeparatorNumberFormat(amount);
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
String amountString = PrintUtils.getInstance().getSeparatorNumberFormat(amount, isDecimalEnabled);
|
||||
if (isNegative) {
|
||||
amountString = "-" + amountString;
|
||||
}
|
||||
printer.appendPrnStr(label + countStringFormat(count) + MMK + " " + PrintUtils.getInstance().getSeparatorNumberFormat(amount), fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr(label + countStringFormat(count) + MMK + " " + amountString, fontNormal, AlignEnum.LEFT,false);
|
||||
}
|
||||
|
||||
}
|
||||
@ -683,6 +765,296 @@ public abstract class BaseXPrint {
|
||||
|
||||
}
|
||||
|
||||
class TempSummary {
|
||||
int saleCount, voidSaleCount, refundCount, cashOutCount;
|
||||
int preAuthSaleCount, preAuthVoidCount;
|
||||
int qrPayCount, qrRefundCount;
|
||||
int preAuthCompCount, preAuthCompVoidCount;
|
||||
|
||||
long saleAmount, voidSaleAmount, refundAmount, cashOutAmount;
|
||||
long preAuthSaleAmount, preAuthVoidAmount;
|
||||
long qrPayAmount, qrRefundAmount;
|
||||
long preAuthCompAmount, preAuthCompVoidAmount;
|
||||
}
|
||||
|
||||
private void applyTempSummary(TempSummary summary, PayDetail item) {
|
||||
int transactionType = item.getTransactionType();
|
||||
long amount = item.getAmount();
|
||||
|
||||
if (transactionType == TransactionsType.SALE.value) {
|
||||
summary.saleCount++;
|
||||
summary.saleAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.VOID.value) {
|
||||
summary.voidSaleCount++;
|
||||
summary.voidSaleAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.REFUND.value) {
|
||||
summary.refundCount++;
|
||||
summary.refundAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.CASH_OUT.value) {
|
||||
summary.cashOutCount++;
|
||||
summary.cashOutAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.PRE_AUTH_SALE.value) {
|
||||
summary.preAuthSaleCount++;
|
||||
summary.preAuthSaleAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.PRE_AUTH_VOID.value) {
|
||||
summary.preAuthVoidCount++;
|
||||
summary.preAuthVoidAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.MMQR.value) {
|
||||
summary.qrPayCount++;
|
||||
summary.qrPayAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.MMQR_REFUND.value) {
|
||||
summary.qrRefundCount++;
|
||||
summary.qrRefundAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.PRE_AUTH_COMPLETE.value) {
|
||||
summary.preAuthCompCount++;
|
||||
summary.preAuthCompAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
if (transactionType == TransactionsType.PRE_AUTH_COMPLETE_VOID.value) {
|
||||
summary.preAuthCompVoidCount++;
|
||||
summary.preAuthCompVoidAmount += amount;
|
||||
return;
|
||||
}
|
||||
|
||||
String transType = item.getTransType() == null ? "" : item.getTransType().trim().toUpperCase(Locale.getDefault());
|
||||
|
||||
switch (transType) {
|
||||
case "SALE":
|
||||
summary.saleCount++;
|
||||
summary.saleAmount += amount;
|
||||
break;
|
||||
|
||||
case "VOID SALE":
|
||||
case "VOID_SALE":
|
||||
summary.voidSaleCount++;
|
||||
summary.voidSaleAmount += amount;
|
||||
break;
|
||||
|
||||
case "REFUND":
|
||||
summary.refundCount++;
|
||||
summary.refundAmount += amount;
|
||||
break;
|
||||
|
||||
case "PRE-AUTH":
|
||||
case "PRE_AUTH_SALE":
|
||||
summary.preAuthSaleCount++;
|
||||
summary.preAuthSaleAmount += amount;
|
||||
break;
|
||||
|
||||
case "PREAUTH CANCELLATION":
|
||||
case "PRE_AUTH_VOID":
|
||||
summary.preAuthVoidCount++;
|
||||
summary.preAuthVoidAmount += amount;
|
||||
break;
|
||||
|
||||
case "CASH OUT":
|
||||
case "CASH_OUT":
|
||||
case "CASH_ADVANCE":
|
||||
summary.cashOutCount++;
|
||||
summary.cashOutAmount += amount;
|
||||
break;
|
||||
|
||||
case "QR_PAY":
|
||||
summary.qrPayCount++;
|
||||
summary.qrPayAmount += amount;
|
||||
break;
|
||||
|
||||
case "QR_REFUND":
|
||||
summary.qrRefundCount++;
|
||||
summary.qrRefundAmount += amount;
|
||||
break;
|
||||
|
||||
case "PREAUTH COMPLETION":
|
||||
case "PRE_AUTH_COMPLETE":
|
||||
case "PREAUTH_COMP":
|
||||
summary.preAuthCompCount++;
|
||||
summary.preAuthCompAmount += amount;
|
||||
break;
|
||||
|
||||
case "VOID PREAUTH COMPLETE":
|
||||
case "PRE_AUTH_COMPLETE_VOID":
|
||||
case "PREAUTH_COMP_VOID":
|
||||
summary.preAuthCompVoidCount++;
|
||||
summary.preAuthCompVoidAmount += amount;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean matchesSummaryHostType(PayDetail item, HostType hostType) {
|
||||
if (hostType == null || item == null) {
|
||||
return true;
|
||||
}
|
||||
|
||||
int transactionType = item.getTransactionType();
|
||||
|
||||
if (hostType == HostType.QR) {
|
||||
return transactionType == TransactionsType.MMQR.value
|
||||
|| transactionType == TransactionsType.MMQR_REFUND.value;
|
||||
}
|
||||
|
||||
if (hostType == HostType.MPU || hostType == HostType.VISA_MASTER) {
|
||||
return transactionType != TransactionsType.MMQR.value
|
||||
&& transactionType != TransactionsType.MMQR_REFUND.value;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
protected void printTransDetailSummary(PayDetail payDetail, List<PayDetail> list) {
|
||||
printTransDetailSummary(payDetail, list, null);
|
||||
}
|
||||
|
||||
protected void printTransDetailSummary(PayDetail payDetail, List<PayDetail> list, HostType hostType) {
|
||||
|
||||
if (list == null || list.isEmpty()) {
|
||||
printErrorBlock("NO TRANSACTION FOUND");
|
||||
printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
return;
|
||||
}
|
||||
|
||||
Map<String, TempSummary> currencyMap = new HashMap<>();
|
||||
|
||||
for (PayDetail item : list) {
|
||||
|
||||
if (item == null) continue;
|
||||
if (!matchesSummaryHostType(item, hostType)) continue;
|
||||
|
||||
String currency = item.getCurrencyCode();
|
||||
TempSummary s = currencyMap.get(currency);
|
||||
|
||||
if (s == null) {
|
||||
s = new TempSummary();
|
||||
currencyMap.put(currency, s);
|
||||
}
|
||||
|
||||
applyTempSummary(s, item);
|
||||
}
|
||||
|
||||
if (currencyMap.isEmpty()) {
|
||||
printErrorBlock("NO TRANSACTION FOUND");
|
||||
printer.appendPrnStr("\n", fontNormal, AlignEnum.LEFT,false);
|
||||
return;
|
||||
}
|
||||
|
||||
boolean isQrDecimalEnabled = SystemParamsOperation.getInstance().isQrDecimalEnable();
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
|
||||
for (String currency : currencyMap.keySet()) {
|
||||
|
||||
TempSummary data = currencyMap.get(currency);
|
||||
boolean isQrHost = hostType == HostType.QR;
|
||||
|
||||
printer.appendPrnStr( currencyCodeToText(currency) + " " +"Transactions", fontNormal, AlignEnum.LEFT, false);
|
||||
emptyLine(1);
|
||||
|
||||
// printer.appendPrnStr("(COUNT)TRANS", "AMOUNT(" + currencyCodeToText(currency) + ")", fontNormal, false);
|
||||
print3ColumnsStringWithAlign("COUNT", "TRANS", "AMOUNT" + "(" + currencyCodeToText(currency) + ")", fontNormal, false);
|
||||
|
||||
if (isQrHost) {
|
||||
if (data.qrPayCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.qrPayCount + ")",
|
||||
"QR PAY",
|
||||
PrintUtils.getInstance().getSeparatorNumberFormat(data.qrPayAmount, isQrDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.qrRefundCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.qrRefundCount + ")",
|
||||
"QR REFUND",
|
||||
"- " + PrintUtils.getInstance().getSeparatorNumberFormat(data.qrRefundAmount, isQrDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
} else {
|
||||
if (data.saleCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.saleCount + ")",
|
||||
"SALES",
|
||||
PrintUtils.getInstance().getSeparatorNumberFormat(data.saleAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.voidSaleCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.voidSaleCount + ")",
|
||||
"VOID",
|
||||
"- " + PrintUtils.getInstance().getSeparatorNumberFormat(data.voidSaleAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.cashOutCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.cashOutCount + ")",
|
||||
"CASH ADV",
|
||||
PrintUtils.getInstance().getSeparatorNumberFormat(data.cashOutAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.preAuthSaleCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.preAuthSaleCount + ")",
|
||||
"PRE-AUTH",
|
||||
PrintUtils.getInstance().getSeparatorNumberFormat(data.preAuthSaleAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.preAuthVoidCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.preAuthVoidCount + ")",
|
||||
"PREAUTH VOID",
|
||||
"- " + PrintUtils.getInstance().getSeparatorNumberFormat(data.preAuthVoidAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.refundCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.refundCount + ")",
|
||||
"REFUND",
|
||||
"- " + PrintUtils.getInstance().getSeparatorNumberFormat(data.refundAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
|
||||
if (data.preAuthCompCount > 0) {
|
||||
print3ColumnsStringWithAlign("(" + data.preAuthCompCount + ")",
|
||||
"PREAUTH COMP",
|
||||
PrintUtils.getInstance().getSeparatorNumberFormat(data.preAuthCompAmount, isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
}
|
||||
}
|
||||
|
||||
dotBreak();
|
||||
|
||||
long totalAmount = isQrHost
|
||||
? data.qrPayAmount - data.qrRefundAmount
|
||||
: (data.saleAmount + data.cashOutAmount + data.preAuthSaleAmount + data.preAuthCompAmount)
|
||||
- (data.voidSaleAmount + data.preAuthVoidAmount + data.refundAmount + data.preAuthCompVoidAmount);
|
||||
|
||||
printer.appendPrnStr( "TOTAL"+ " " + currencyCodeToText(currency),
|
||||
PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount, isQrHost ? isQrDecimalEnabled : isDecimalEnabled),
|
||||
fontNormal, false);
|
||||
|
||||
emptyLine(2);
|
||||
}
|
||||
}
|
||||
|
||||
/* private void backup(){
|
||||
SettleData settleData = payDetail.getSettleDataObj();
|
||||
|
||||
@ -776,47 +1148,59 @@ public abstract class BaseXPrint {
|
||||
printer.appendPrnStr(first + " " + second + " " + third, fontNormal, AlignEnum.LEFT,isBold);
|
||||
}
|
||||
|
||||
protected void dotBreak(){
|
||||
printer.appendPrnStr(new String(new char[29]).replace("\0", "."), fontNormal, AlignEnum.LEFT, false);
|
||||
protected void print3ColumnsStringWithAlign(String first, String second, String third, int font, boolean isBold){
|
||||
String fixedSizeString = String.format("%-5s", first);
|
||||
printer.appendPrnStr(fixedSizeString + " " + second, third, font, isBold);
|
||||
}
|
||||
|
||||
protected void dotBreak(){
|
||||
printer.appendPrnStr(new String(new char[29]).replace("\0", "."), fontNormal, AlignEnum.CENTER, false);
|
||||
}
|
||||
|
||||
class CurrencySummary {
|
||||
long total = 0;
|
||||
int count = 0;
|
||||
}
|
||||
protected void printTransDetailReport(List<PayDetail> lists, HostType hostType) {
|
||||
|
||||
|
||||
if (hostType == HostType.MPU || hostType == HostType.VISA_MASTER) {
|
||||
// Use the same line-by-line style as QR detail report
|
||||
} else if (hostType == HostType.QR) {
|
||||
// print2ColumnsString("PAYMENT NAME", "");
|
||||
// print2ColumnsString("DATE", "TIME");
|
||||
// print2ColumnsString("TRANSACTION", "TRACE NO");
|
||||
// print2ColumnsString("TRXN ID", "");
|
||||
// print2ColumnsString("AMOUNT", "");
|
||||
// ✅ Summary holder (total + count per currency)
|
||||
class CurrencySummary {
|
||||
long total = 0;
|
||||
int count = 0;
|
||||
}
|
||||
|
||||
|
||||
// breakingLine();
|
||||
|
||||
long totalAmount = 0;
|
||||
Map<String, CurrencySummary> currencyMap = new HashMap<>();
|
||||
|
||||
for (PayDetail pay : lists) {
|
||||
boolean isNeedMinusSign = pay.getTransactionType() == TransactionsType.VOID.value || pay.getTransactionType() == TransactionsType.REFUND.value || pay.getTransactionType() == TransactionsType.MMQR_REFUND.value;
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().isQrDecimalEnable();
|
||||
|
||||
boolean isNeedMinusSign =
|
||||
pay.getTransactionType() == TransactionsType.VOID.value ||
|
||||
pay.getTransactionType() == TransactionsType.REFUND.value ||
|
||||
pay.getTransactionType() == TransactionsType.MMQR_REFUND.value;
|
||||
|
||||
boolean isDecimalEnabledQr = SystemParamsOperation.getInstance().isQrDecimalEnable();
|
||||
String currency = currencyCodeToText(pay.getCurrencyCode());
|
||||
|
||||
// =============================
|
||||
// PRINT DETAIL
|
||||
// =============================
|
||||
if (hostType == HostType.MPU || hostType == HostType.VISA_MASTER) {
|
||||
|
||||
boolean isDecimalEnabledCard = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
|
||||
printString("CARD TYPE:" + pay.getAccountType());
|
||||
printString("CARD NO :" + PrintUtils.getInstance().maskCardNumberPciDss(pay.getCardNo()));
|
||||
printString("TRACE NO :" + pay.getVoucherNo());
|
||||
printString("INV NO :" + pay.getVoucherNo());
|
||||
printString("RRN :" + pay.getReferNo());
|
||||
printString("DATE :" + POSUtil.getInstance().formatDisplayDate(pay.getTransDate()) + " " + pay.getTransTime());
|
||||
printString("DATE :" + POSUtil.getInstance().formatDisplayDate(pay.getTransDate()));
|
||||
printString(" " + pay.getTransTime());
|
||||
printString("TYPE :" + pay.getTransType().replace("_", " "));
|
||||
printString("AMOUNT :" +
|
||||
(isNeedMinusSign
|
||||
? "-" + PrintUtils.getInstance()
|
||||
.getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabledCard)
|
||||
: PrintUtils.getInstance()
|
||||
.getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabledCard))
|
||||
+ " " + "MMK");
|
||||
? "-" + PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabledCard)
|
||||
: PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabledCard))
|
||||
+ " " + currency);
|
||||
|
||||
dotBreak();
|
||||
|
||||
} else if (hostType == HostType.QR) {
|
||||
@ -826,62 +1210,89 @@ public abstract class BaseXPrint {
|
||||
printString("SOURCE :" +
|
||||
(pay.getTransactionType() == TransactionsType.MMQR_REFUND.value
|
||||
? "QR PAYMENT"
|
||||
: pay.getCustomerMobile())
|
||||
);
|
||||
// printString("TXN NAME:" + pay.getTransType().replace("_", " "));
|
||||
printString("DATE :" + POSUtil.getInstance().formatDisplayDate(pay.getTransDate()) + " " + pay.getTransTime());
|
||||
printString("TRACE NO:" + pay.getVoucherNo());
|
||||
: pay.getCustomerMobile()));
|
||||
printString("DATE :" + POSUtil.getInstance().formatDisplayDate(pay.getTransDate()));
|
||||
printString(" " + pay.getTransTime());
|
||||
printString("INV NO :" + pay.getVoucherNo());
|
||||
|
||||
if (pay.getTransactionType() == TransactionsType.MMQR_REFUND.value) {
|
||||
printString("RRN :" + pay.getReferNo());
|
||||
}
|
||||
|
||||
printString("AMOUNT :" +
|
||||
(isNeedMinusSign
|
||||
? "-" + PrintUtils.getInstance()
|
||||
.getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabled)
|
||||
: PrintUtils.getInstance()
|
||||
.getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabled))
|
||||
+ " " +"MMK");
|
||||
? "-" + PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabledQr)
|
||||
: PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabledQr))
|
||||
+ " " + currency);
|
||||
|
||||
dotBreak();
|
||||
|
||||
// if (pay.getTransactionType() == TransactionsType.MMQR_REFUND.value) {
|
||||
// print2ColumnsString("QR PAYMENT", "");
|
||||
// } else {
|
||||
// print2ColumnsString(pay.getCustomerMobile(), "");
|
||||
// }
|
||||
// print2ColumnsString(pay.getTransDate(), pay.getTransTime());
|
||||
// print2ColumnsString(pay.getTransType().replace("_", " "), pay.getVoucherNo());
|
||||
// if (pay.getTransactionType() == TransactionsType.MMQR_REFUND.value) {
|
||||
// print2ColumnsString(pay.getReferNo() + "(RRN)", "");
|
||||
// print2ColumnsString(isNeedMinusSign ? "-" + PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabled) : "" + PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabled), "");
|
||||
// } else {
|
||||
// print2ColumnsString(pay.getQrTransId(), "");
|
||||
// print2ColumnsString(isNeedMinusSign ? "-" + PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabled) : "" + PrintUtils.getInstance().getSeparatorNumberFormat(pay.getAmount(), isDecimalEnabled) , "");
|
||||
// }
|
||||
|
||||
}
|
||||
|
||||
emptyLine(1);
|
||||
|
||||
// =============================
|
||||
// ✅ ACCUMULATE TOTAL + COUNT PER CURRENCY
|
||||
// =============================
|
||||
CurrencySummary summary = currencyMap.getOrDefault(currency, new CurrencySummary());
|
||||
|
||||
if (isNeedMinusSign) {
|
||||
totalAmount -= pay.getAmount();
|
||||
summary.total -= pay.getAmount();
|
||||
} else {
|
||||
totalAmount += pay.getAmount();
|
||||
}
|
||||
summary.total += pay.getAmount();
|
||||
}
|
||||
|
||||
if (hostType == HostType.MPU || hostType == HostType.VISA_MASTER) {
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
print2ColumnsString("CARD", "");
|
||||
print3ColumnsString("TYPE ", "COUNT", "AMOUNT");
|
||||
print3ColumnsString("CARD", " " + countStringFormat(lists.size()), "MMK " + PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount, isDecimalEnabled), true);
|
||||
} else if (hostType == HostType.QR) {
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().isQrDecimalEnable();
|
||||
print2ColumnsString("PAYMENT", "");
|
||||
print3ColumnsString("TYPE ", "COUNT", "AMOUNT");
|
||||
// emptyLine(1);
|
||||
print3ColumnsString("QR PAY", " "+ countStringFormat(lists.size()), "MMK " + PrintUtils.getInstance().getSeparatorNumberFormat(totalAmount, isDecimalEnabled), true);
|
||||
summary.count++; // ✅ count per currency
|
||||
|
||||
currencyMap.put(currency, summary);
|
||||
}
|
||||
|
||||
// =============================
|
||||
// PRINT SUMMARY
|
||||
// =============================
|
||||
if (hostType == HostType.MPU || hostType == HostType.VISA_MASTER) {
|
||||
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().getDecimalEnable();
|
||||
|
||||
print2ColumnsString("CARD", "");
|
||||
print3ColumnsStringWithAlign("TYPE ", "COUNT", "AMOUNT", fontNormal, true);
|
||||
|
||||
for (Map.Entry<String, CurrencySummary> entry : currencyMap.entrySet()) {
|
||||
|
||||
String currency = entry.getKey();
|
||||
CurrencySummary summary = entry.getValue();
|
||||
|
||||
print3ColumnsStringWithAlign(
|
||||
"CARD",
|
||||
" " + countStringFormat(summary.count),
|
||||
currency + " " + PrintUtils.getInstance()
|
||||
.getSeparatorNumberFormat(summary.total, isDecimalEnabled),
|
||||
fontNormal,
|
||||
false
|
||||
);
|
||||
}
|
||||
|
||||
} else if (hostType == HostType.QR) {
|
||||
|
||||
boolean isDecimalEnabled = SystemParamsOperation.getInstance().isQrDecimalEnable();
|
||||
|
||||
print2ColumnsString("PAYMENT", "");
|
||||
print3ColumnsStringWithAlign("TYPE ", "COUNT", "AMOUNT", fontNormal, true);
|
||||
|
||||
for (Map.Entry<String, CurrencySummary> entry : currencyMap.entrySet()) {
|
||||
|
||||
String currency = entry.getKey();
|
||||
CurrencySummary summary = entry.getValue();
|
||||
|
||||
print3ColumnsStringWithAlign(
|
||||
"QR PAY",
|
||||
" " + countStringFormat(summary.count),
|
||||
currency + " " + PrintUtils.getInstance()
|
||||
.getSeparatorNumberFormat(summary.total, isDecimalEnabled),
|
||||
fontNormal,
|
||||
false
|
||||
);
|
||||
}
|
||||
}
|
||||
// emptyLine(2);
|
||||
}
|
||||
|
||||
protected void printQRSettlementTransDetail(List<QRSettleData> lists) {
|
||||
@ -1162,6 +1573,7 @@ public abstract class BaseXPrint {
|
||||
String transType = payDetail.getTransType();
|
||||
String batchNum = "";
|
||||
String traceNum = payDetail.getVoucherNo();
|
||||
boolean isDuelCurrency = SystemParamsOperation.getInstance().getDuelCurrencyStatus();
|
||||
|
||||
String currencySign = currencyCodeToText(payDetail.getCurrencyCode());
|
||||
boolean isSettlement = payDetail.getTransactionType() == TransactionsType.SETTLEMENT.value;
|
||||
@ -1176,7 +1588,7 @@ public abstract class BaseXPrint {
|
||||
if (payDetail.getTransactionType() == TransactionsType.MMQR.value && payDetail.getQrTransStatus() == 1) {
|
||||
printer.appendPrnStr("TRACE NO :" + traceNum , fontNormal, AlignEnum.LEFT,false);
|
||||
} else if (!payDetail.getTransType().equals(SETTLEMENT) && !payDetail.getTransType().equals(SUMMARY) && payDetail.getTransactionType() != TransactionsType.MMQR_REFUND.value && payDetail.getTransactionType() != TransactionsType.MMQR.value) {
|
||||
printer.appendPrnStr("BTH NO:" + batchNum + " INV NO:" + invoiceNo, fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr("BTH NO:" + batchNum + " INV NO:" + traceNum, fontNormal, AlignEnum.LEFT,false);
|
||||
} else if (payDetail.getTransType().equals(SUMMARY)) {
|
||||
printer.appendPrnStr("HOST :" + HOST_NAME_MPU + "", fontNormal, AlignEnum.LEFT,false);
|
||||
}
|
||||
@ -1186,9 +1598,17 @@ public abstract class BaseXPrint {
|
||||
if (payDetail.getTransactionType() == TransactionsType.MMQR.value || payDetail.getTransactionType() == TransactionsType.MMQR_REFUND.value){
|
||||
printer.appendPrnStr("SHORT CODE :" + payDetail.getMerchantNo(), fontNormal, AlignEnum.LEFT,false);
|
||||
}else{
|
||||
|
||||
if(isSettlement && isDuelCurrency){
|
||||
printer.appendPrnStr("MID :" + safe(SystemParamsOperation.getInstance().getMerchantId()), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("TID :" + safe(SystemParamsOperation.getInstance().getTerminalId()), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("MID :" + safe(SystemParamsOperation.getInstance().getThirdHostMerchantId()), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("TID :" + safe(SystemParamsOperation.getInstance().getThirdHostTerminalId()), fontNormal, AlignEnum.LEFT, false);
|
||||
}else{
|
||||
printer.appendPrnStr("MID :" + payDetail.getMerchantNo(), fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr("TID :" + payDetail.getTerminalNo(), fontNormal, AlignEnum.LEFT,false);
|
||||
}
|
||||
}
|
||||
|
||||
if(isSettlement) {
|
||||
printer.appendPrnStr("BATCH :" + batchNum, fontNormal, AlignEnum.LEFT,false);
|
||||
@ -1257,7 +1677,7 @@ public abstract class BaseXPrint {
|
||||
// printer.appendPrnStr("INV NO :" + invoiceNo , fontNormal, AlignEnum.LEFT,false);
|
||||
printer.appendPrnStr("TRACE NO :" + traceNum , fontNormal, AlignEnum.LEFT,false);
|
||||
} else if (!payDetail.getTransType().equals(SETTLEMENT) && !payDetail.getTransType().equals(SUMMARY) && payDetail.getTransactionType() != TransactionsType.MMQR_REFUND.value && payDetail.getTransactionType() != TransactionsType.MMQR.value) {
|
||||
// printer.appendPrnStr("BTH NO :" + batchNum + " INV NO:" + invoiceNo, fontNormal, AlignEnum.LEFT,false);
|
||||
// printer.appendPrnStr("BTH NO :" + batchNum + " INV NO:" + traceNum, fontNormal, AlignEnum.LEFT,false);
|
||||
} else if (payDetail.getTransType().equals(SUMMARY)) {
|
||||
printer.appendPrnStr("HOST :" + HOST_NAME_MPU + "", fontNormal, AlignEnum.LEFT,false);
|
||||
}
|
||||
@ -1316,18 +1736,19 @@ public abstract class BaseXPrint {
|
||||
protected void printTerminalConfiguration() {
|
||||
|
||||
SystemParamsOperation sp = SystemParamsOperation.getInstance();
|
||||
|
||||
// ---------- PRIMARY HOST ----------
|
||||
printer.appendPrnStr("PRIMARY HOST", fontNormal, AlignEnum.LEFT, true);
|
||||
printer.appendPrnStr("Name : " + sp.getHostName(), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("TID : " + sp.getTerminalId(), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("MID : " + sp.getMerchantId(), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Name : " + safe(sp.getHostName()), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("TID : " + safe(sp.getTerminalId()), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("MID : " + safe(sp.getMerchantId()), fontNormal, AlignEnum.LEFT, false);
|
||||
String[] ipPort = splitIpAndPort(sp.getIpAddress());
|
||||
printer.appendPrnStr("Primary Ip : " + ipPort[0], fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Primary IP : " + ipPort[0], fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Primary Port : " + ipPort[1], fontNormal, AlignEnum.LEFT, false);
|
||||
String[] secIpPort = splitIpAndPort(sp.getSecIpAddress());
|
||||
printer.appendPrnStr("Secondary Ip : " + secIpPort[0], fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Secondary IP : " + secIpPort[0], fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Secondary Port: " + secIpPort[1], fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Currency Code : " + sp.getCurrencyType(), fontNormal, AlignEnum.LEFT, false);
|
||||
printer.appendPrnStr("Currency : " + normalizeHostCurrency(sp.getCurrencyType() == null ? "" : sp.getCurrencyType().toString()), fontNormal, AlignEnum.LEFT, false);
|
||||
dotBreak();
|
||||
// ---------- SECONDARY HOST (optional) ----------
|
||||
if (!TextUtils.isEmpty(sp.getSecHostName())) {
|
||||
|
||||
@ -20,6 +20,8 @@ public interface PrintX {
|
||||
|
||||
void printSmileSummaryReport(PayDetail payDetail, HostType hostType, PrintXStatus printXStatus);
|
||||
|
||||
void printSmileSummaryReport(PayDetail payDetail, List<PayDetail> list, HostType hostType, PrintXStatus printXStatus);
|
||||
|
||||
void printSmileSettlementReport(PayDetail payDetail,PrintXStatus printXStatus);
|
||||
|
||||
void printQRSettlementReport(PayDetail payDetail, List<QRSettleData> list, PrintXStatus printXStatus);
|
||||
|
||||
@ -223,6 +223,8 @@ public class PrintXImpl extends BaseXPrint implements PrintX {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Override
|
||||
public void printDetailReport(PayDetail payDetail, List<PayDetail> lists, HostType hostType,PrintXStatus printXStatus) {
|
||||
this.callbackStatus = printXStatus;
|
||||
@ -431,7 +433,6 @@ public class PrintXImpl extends BaseXPrint implements PrintX {
|
||||
this.callbackStatus = printXStatus;
|
||||
try {
|
||||
// LogUtil.d(TAG, payDetail.getSettleDataObj().toString());
|
||||
|
||||
setHeight(0x12);
|
||||
printLogo();
|
||||
printMerchantHeader();
|
||||
@ -447,6 +448,21 @@ public class PrintXImpl extends BaseXPrint implements PrintX {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void printSmileSummaryReport(PayDetail payDetail, List<PayDetail> list, HostType hostType, PrintXStatus printXStatus) {
|
||||
this.callbackStatus = printXStatus;
|
||||
try {
|
||||
setHeight(0x12);
|
||||
printLogo();
|
||||
printMerchantHeader();
|
||||
printTranHeader("SUMMARY REPORT");
|
||||
printTransDetailSummary(payDetail, list, hostType);
|
||||
startPrintNex();
|
||||
} catch (RemoteException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void printTerminalConfig(PrintXStatus printXStatus) {
|
||||
this.callbackStatus = printXStatus;
|
||||
|
||||
@ -59,6 +59,9 @@ public class PrintXReceipt {
|
||||
public void printSmileSummaryReport(PayDetail payDetail, HostType hostType, PrintXStatus printXStatus) {
|
||||
printX.printSmileSummaryReport(payDetail, hostType, printXStatus);
|
||||
}
|
||||
public void printSmileSummaryReport(PayDetail payDetail,List<PayDetail> list, HostType hostType, PrintXStatus printXStatus) {
|
||||
printX.printSmileSummaryReport(payDetail, list, hostType, printXStatus);
|
||||
}
|
||||
|
||||
public void printTerminalHostConfig(PrintXStatus printXStatus){
|
||||
printX.printTerminalConfig(printXStatus);
|
||||
|
||||
@ -434,6 +434,7 @@ public class TransactionsOperation {
|
||||
} else {
|
||||
boolean equals = TextUtils.equals(resultStr, Constant.ANSWER_CODE_ACCEPT) || TextUtils.equals(resultStr, Constant.ANSWER_CODE_APPROVED);
|
||||
EmvOnlineResultEntity emvOnlineResult = new EmvOnlineResultEntity();
|
||||
emvOnlineResult.setRejCode("00");
|
||||
// MsgField field38,field39,field55;
|
||||
// if (resp != null) {
|
||||
// field38 = resp.get("F038");
|
||||
@ -455,7 +456,10 @@ public class TransactionsOperation {
|
||||
// }
|
||||
//
|
||||
// }
|
||||
|
||||
if(equals) {
|
||||
emvOnlineResult.setRejCode("00");
|
||||
emvOnlineResult.setRecvField55(null);
|
||||
importOnlineProcessStatus(SdkResult.Success,emvOnlineResult);
|
||||
} else {
|
||||
importOnlineProcessStatus(SdkResult.Fail,emvOnlineResult);
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user