银盛相关所有

This commit is contained in:
lyf
2023-04-07 14:01:27 +08:00
parent 1f5854b5ad
commit a5db6104bb
26 changed files with 2862 additions and 53 deletions

View File

@@ -0,0 +1,40 @@
package cn.pluss.platform.channel;
import cn.pluss.platform.entity.MerchantChannelStatus;
import cn.pluss.platform.pojo.CombineMercInfo;
import com.alibaba.fastjson.JSONObject;
/**
* 进件流程AOP
*/
public interface MercAuditListener {
/**
* 进件之前的检查操作
* @param userId 用户id
* @param channelId 通道id
*/
void beforeCheck(String userId, Integer channelId);
/**
* 获取商户信息
* @param userId 用户id
* @param channelType D0、D1
* @return
*/
CombineMercInfo getMercInfo(String userId, String channelType);
/**
* 进件失败后的操作
* @param userId 用户id
* @param mcs 进件通道相关信息
* @param msg 驳回原因
*/
void onFail(String userId, MerchantChannelStatus mcs, String msg);
/**
* 进件成功后的操作
* @param userId 用户id
*/
void onSuccess(String userId, MerchantChannelStatus mcs);
}

View File

@@ -0,0 +1,221 @@
package cn.pluss.platform.channel;
import cn.hutool.core.util.RandomUtil;
import cn.pluss.platform.IdCardService;
import cn.pluss.platform.dto.AccountDTO;
import cn.pluss.platform.entity.*;
import cn.pluss.platform.exception.MsgException;
import cn.pluss.platform.mapper.*;
import cn.pluss.platform.merchant.AccountService;
import cn.pluss.platform.merchant.MerchantCashPlaceService;
//import cn.pluss.platform.merchant.edit.MercChangeRecordService;
import cn.pluss.platform.merchantChannelStatus.MerchantChannelStatusService;
import cn.pluss.platform.notice.NoticeService;
import cn.pluss.platform.pojo.CombineMercInfo;
import cn.pluss.platform.user.impl.GeneralPushUtil;
import cn.pluss.platform.util.IpUtils;
import cn.pluss.platform.util.LogExceptionUtils;
import cn.pluss.platform.wx.WxCertService;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
import javax.annotation.Resource;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.util.Collections;
import java.util.Map;
import java.util.Objects;
@Slf4j
@Service
public class MercAuditListenerImpl implements MercAuditListener {
@Autowired
private MerchantBaseInfoMapper mbiMapper;
@Autowired
private MerchantChannelStatusService mcsService;
@Autowired
private IdCardService idCardService;
@Autowired
private AccountService accountService;
@Autowired
private WxCertService wxCertService;
@Autowired
private NoticeService noticeService;
@Autowired
private GeneralPushUtil generalPushUtil;
@Resource
private UserAppMapper userAppMapper;
@Resource
private UserInfoMapper userInfoMapper;
@Resource
private MerchantStoreMapper merchantStoreMapper;
@Resource
private MerchantImageMapper merchantImageMapper;
@Autowired
private MerchantCashPlaceService cashPlaceService;
@Autowired
private RestTemplate restTemplate;
// @Autowired
// private MercChangeRecordService mcrService;
@Override
public void beforeCheck(String userId, Integer channelId) {
MerchantBaseInfo mbi = mbiMapper.getByUserId(userId);
MerchantChannelStatus mcs = mcsService.getByMerchantCode(mbi.getMerchantCode(), channelId);
if (mcs == null) {
throw new MsgException("商户未发起进件");
}
if (!mcs.getStatus().equals(MerchantChannelStatus.AUDIT_STATUS_EXAMINING)) {
throw new MsgException("商户进件状态错误");
}
if (mcs.getThirdStatus().equals(MerchantChannelStatus.AUDIT_THIRD_STATUS_AUDITING)) {
throw new MsgException("当前商户已经在后台审核中");
}
}
@Override
public CombineMercInfo getMercInfo(String userId, String channelType) {
CombineMercInfo mercInfo = new CombineMercInfo();
MerchantBaseInfo mbi = mbiMapper.getByUserId(userId);
mercInfo.setMbi(mbi);
AccountDTO realAccount = accountService.getRealAccount(userId, channelType);
if (!mbi.getMerchantType().equals(MerchantBaseInfo.MERCH_TYPE_MICRO)) {
IdCard legalIdCard = idCardService.getLegalIdCard(userId);
mercInfo.setLegalIdCard(legalIdCard);
} else {
mercInfo.setLegalIdCard(realAccount.getIdcard());
}
mercInfo.setSettleIdCard(realAccount.getIdcard());
mercInfo.setBankCard(realAccount.getBankCard());
return mercInfo;
}
@Override
public void onFail(String userId, MerchantChannelStatus mcs, String msg) {
MerchantBaseInfo mbi = mbiMapper.queryByMerchantCode(mcs.getMerchantCode());
String title2 = "收银呗审核通知";
String msg2;
if (Objects.equals(mcs.getChannel(), 4)) {
msg2 = "商户D0进件驳回" + msg;
} else {
msg2 = "商户进件驳回," + msg;
}
Notice notice2 = new Notice(1, 1, mbi.getUserId());
notice2.setNoticeCode("SHSH_" + System.currentTimeMillis() + RandomUtil.randomString(2));
notice2.setConrtent(msg2);
noticeService.saveMerAuthNotice(notice2);
generalPushUtil.sendAllPlatByAlias(Collections.singletonList(mbi.getUserId() + ""), title2, msg2, "1");
}
@Override
public void onSuccess(String userId, MerchantChannelStatus mcs) {
MerchantBaseInfo mbi = mbiMapper.queryByMerchantCode(mcs.getMerchantCode() + "");
String title = "收银呗审核通知";
String msg;
if (Objects.equals(mcs.getChannel(), 4)) {
msg = "商户D0进件通过完成支付宝及微信认证后即可支持相应渠道收款";
} else {
msg = "商户进件通过,完成支付宝及微信认证后即可支持相应渠道收款";
}
Notice notice = new Notice(1, 1, mbi.getUserId());
notice.setNoticeCode("SHSH_" + System.currentTimeMillis() + RandomUtil.randomString(2));
notice.setConrtent(msg);
noticeService.saveMerAuthNotice(notice);
generalPushUtil.sendAllPlatByAlias(Collections.singletonList(mbi.getUserId() + ""), title, msg, "1");
wxCertService.wxCert(userId, mcs.getMerchantCode(), mcs.getChannel());
// 以下代码为进件结果处理后的操作
// 创建线上店铺
try {
log.info("===================>进件回调,创建店铺开始,商户编号为:{}<=====================", mcs.getMerchantId());
createStore(mcs);
} catch (Exception e) {
e.printStackTrace();
log.info("创建店铺信息异常,异常信息:{}", e.getMessage());
}
try {
MerchantBaseInfo merchantBaseInfo = mbiMapper.queryByMerchantCode(mcs.getMerchantCode());
if (StringUtils.isNotBlank(merchantBaseInfo.getUserId())) {
cashPlaceService.createDefaultCashPlace(Long.parseLong(merchantBaseInfo.getUserId()));
}
} catch (Exception e) {
LogExceptionUtils.printStack(log, e, "创建默认收银点失败,异常信息:{}");
}
}
public void createStore(MerchantChannelStatus merchantChannelStatus) {
UserApp userApp = userAppMapper.selectByMerchantCode(merchantChannelStatus.getMerchantCode());
UserInfo userInfo = userInfoMapper.selectById(userApp.getUserId());
log.info("==============>当前需要同步的用户进件数据为::{}<===================", JSONObject.toJSONString(merchantChannelStatus));
if (userInfo != null) {
MerchantStore merchantStore = new MerchantStore().setMerchantCode(merchantChannelStatus.getMerchantCode());
merchantStore = merchantStoreMapper.selectOne(new QueryWrapper<>(merchantStore));
MerchantBaseInfo merchantBaseInfo = mbiMapper.queryByMerchantCode(merchantChannelStatus.getMerchantCode());
QueryWrapper<MerchantImage> queryWrapper = new QueryWrapper<MerchantImage>()
.eq("merchantCode", merchantChannelStatus.getMerchantCode()).eq("photoType", "06");
MerchantImage merchantImage = merchantImageMapper.selectOne(queryWrapper);
String baseUrl = "https://shop.shouyinbei.net/web/wmerchant.php?c=site&a=entry&ctrl=store&ac=oauth&op=add_merchan&do=web&m=we7_wmall&i=1";
StringBuilder sb = new StringBuilder(baseUrl);
sb.append("&title=").append(merchantBaseInfo.getAlias());
sb.append("&password=").append(userInfo.getPassword().toLowerCase());
sb.append("&mobile=").append(userInfo.getLoginName());
sb.append("&syb_m_id=").append(merchantStore.getId());
sb.append("&addressNo=").append(merchantBaseInfo.getAddressNo());
String address = merchantBaseInfo.getProvince() + merchantBaseInfo.getCity() + merchantBaseInfo.getDistrict() + merchantBaseInfo.getAddress();
String area = merchantBaseInfo.getProvince() +"-"+ merchantBaseInfo.getCity() +"-"+ merchantBaseInfo.getDistrict();
try {
String decodeAddress = URLEncoder.encode(address, "UTF-8");
sb.append("&address=").append(decodeAddress);
String decodeArea = URLEncoder.encode(area, "UTF-8");
sb.append("&area=").append(decodeArea);
String logo = URLEncoder.encode(merchantImage.getPicUrl(), "GBK");
sb.append("&logo=").append(logo);
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
log.error("=============>请求生成店铺logo门头照转码异常,异常信息:{}<===============", e.getMessage());
}
Map<String, String> lnxMap = IpUtils.getLocationByAddress(address);
if (lnxMap != null) {
sb.append("&location_x=").append(lnxMap.get("x"));
sb.append("&location_y=").append(lnxMap.get("y"));
}
// 请求生成店铺j
String result = restTemplate.getForObject(sb.toString(), String.class);
log.info("=============>请求生成店铺URL{},请求响应返回的参数为:{}<===============", sb.toString(), result);
}
}
}

View File

@@ -0,0 +1,96 @@
package cn.pluss.platform.channel;
import cn.pluss.platform.entity.IdCard;
import cn.pluss.platform.entity.MercChangeRecord;
import cn.pluss.platform.entity.MerchantChannelStatus;
/**
* 进件请求接口定义
* 进件结果接口{@link MerchAuditResultService}
* @author DJH
*/
public interface MerchAuditReqService {
default String getChangeFormEmpty(String merchantId) {
return null;
};
default String getChangeFormDemo() {
return null;
};
default String getCertificateUrlEmpty(String merchantId) {
return null;
}
default String getCertificateUrlDemo() {
return null;
}
default String getCertificateForCorporateEmpty(String merchantId) {
return null;
}
default String getCertificateForCorporateDemo() {
return null;
}
/**
* 进件
* @param userId
*/
void audit(String userId);
void edit(String userId, MercChangeRecord.Type type);
/**
* 变更基本信息
*/
void editBaseInfo(String userId);
/**
* 变更结算卡
* 一般不支持非法人结算卡变更
*/
void editAccountInfo(String userId);
/**
* 修改费率
*/
void editRate(String userId);
/**
* 更新法人身份证
* @param userId
*/
void modifyLegalCard(String userId);
/**
* 更新结算身份证
* @param userId
*/
void modifyAccCard(String userId);
/**
* 修改营业执照
* @param userId 用户ID
*/
void editBusLicense(String userId);
/**
* 签约
*/
void sign(MerchantChannelStatus mcs);
/**
* 通道报备
* @param mcs 进件信息
*/
void report(MerchantChannelStatus mcs);
/**
* 重新报备
* @param mcs 进件信息
*/
void reportAgain(MerchantChannelStatus mcs);
}

View File

@@ -0,0 +1,33 @@
package cn.pluss.platform.channel;
import cn.pluss.platform.entity.MerchantChannelStatus;
import com.alibaba.fastjson.JSONObject;
public interface MerchAuditResultService {
/**
* 回调,通用回调
* @param jsonObject 回调参数
*/
void callback(JSONObject jsonObject) throws Exception;
/**
* 查询进件结果
* @param userId
*/
void auditResult(String userId);
void auditResult(MerchantChannelStatus mcs);
/**
* 查询签约结果,该操作作为商户最终状态的判断
* @param userId 用户id
*/
void signResult(String userId);
/**
* 查询商户变更结果
* @param userId 用户id
*/
void editResult(String userId);
}

View File

@@ -0,0 +1,39 @@
package cn.pluss.platform.channel;
import com.alibaba.fastjson.JSONObject;
public interface MerchantAliCertService {
/**
* 支付宝商户认证提交
*/
default void aliCert(String merchantId) {
// 走手动认证,该方法为预留方法
}
/**
* 支付宝商户认证撤销
*/
default void aliCertCancel(String merchantId) {
// 走手动认证,该方法为预留方法
}
/**
* 支付宝商户认证申请单结果
*/
default void aliCertResult(String merchantId) {
// 走手动认证,该方法为预留方法
}
/**
* 支付宝商户认证结果处理
*/
default void aliCertResultHandle(JSONObject wxCertResult) {
// 走手动认证,该方法为预留方法
}
/**
* 支付宝商户认证状态
*/
void aliCertStatus(String merchantId);
}

View File

@@ -0,0 +1,25 @@
package cn.pluss.platform.channel.ys;
import cn.pluss.platform.entity.MerchantChannelStatus;
import com.alibaba.fastjson.JSONObject;
public interface YSAuditServiceV3 {
/**
* 银盛进件3.0
* @param userId 用户id
*/
void merchantAuditV3(String userId, boolean isFailCheck);
void sign(MerchantChannelStatus mcs);
/**
* 回调,通用回调
* @param jsonObject 回调参数
*/
void callback(JSONObject jsonObject) throws Exception;
/**
* 查询进件结果
* @param userId
*/
void auditResult(String userId);
}

View File

@@ -0,0 +1,846 @@
package cn.pluss.platform.channel.ys.impl;
import cn.hutool.core.codec.Base64;
import cn.hutool.crypto.SecureUtil;
import cn.hutool.crypto.asymmetric.Sign;
import cn.hutool.crypto.asymmetric.SignAlgorithm;
import cn.pluss.platform.IdCardService;
import cn.pluss.platform.channel.MercAuditListener;
import cn.pluss.platform.dto.AccountDTO;
import cn.pluss.platform.entity.*;
import cn.pluss.platform.exception.MsgException;
import cn.pluss.platform.mapper.AccountMapper;
import cn.pluss.platform.mapper.UserAppMapper;
import cn.pluss.platform.mcc.MccReflectService;
import cn.pluss.platform.merchant.AccountService;
import cn.pluss.platform.merchant.JftMercPaymentChannelService;
import cn.pluss.platform.merchant.MerchantBaseInfoService;
import cn.pluss.platform.merchantChannelStatus.MerchantChannelStatusService;
import cn.pluss.platform.merchantImage.MerchantImageService;
import cn.pluss.platform.notice.NoticeService;
import cn.pluss.platform.pojo.CombineMercInfo;
import cn.pluss.platform.region.RegionReflectService;
import cn.pluss.platform.subMerchant.SubMerchantService;
import cn.pluss.platform.task.SxfMerAuditHandler;
import cn.pluss.platform.user.impl.GeneralPushUtil;
import cn.pluss.platform.util.SignUtils;
import cn.pluss.platform.ys.YsConfig;
import cn.pluss.platform.ys.impl.v20210929.YsConstant;
import cn.pluss.platform.ys.impl.v20220527.ReqMethod;
import cn.pluss.platform.ys.impl.v20220527.RespEntity;
import cn.pluss.platform.ys.impl.v20220527.YsConfigV3;
import cn.pluss.platform.ys.impl.v20220527.YsServiceV3;
import cn.pluss.platform.ys.impl.v20220527.entity.*;
import cn.pluss.platform.ys.impl.v20220527.service.YsAuditServiceV3;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.extern.slf4j.Slf4j;
import org.jetbrains.annotations.NotNull;
import org.junit.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.support.TransactionCallbackWithoutResult;
import org.springframework.transaction.support.TransactionTemplate;
import javax.annotation.Resource;
import java.io.Serializable;
import java.nio.charset.StandardCharsets;
import java.util.*;
import java.util.concurrent.ExecutorService;
import static cn.pluss.platform.entity.MerchantBaseInfo.MERCH_TYPE_MICRO;
/**
* @author lyf
*/
@Slf4j
@Service("ysAuditServiceV3")
public class YSAuditServiceV3 implements cn.pluss.platform.channel.ys.YSAuditServiceV3 {
@Autowired
private MerchantBaseInfoService mbiService;
@Resource
private AccountMapper accountMapper;
@Autowired
protected MerchantChannelStatusService mcsService;
@Autowired
private JftMercPaymentChannelService mpcService;
@Autowired
private TransactionTemplate transactionTemplate;
@Autowired
private YsServiceV3 ysServiceV3;
@Autowired
private YSAuditServiceV3 ysAuditServiceV3;
@Autowired
private AccountService accountService;
@Autowired
private IdCardService idCardService;
@Autowired
private YsConfigV3 ysConfigV3;
@Autowired
private RegionReflectService regionReflectService;
@Autowired
private ExecutorService executorService;
@Autowired
private MerchantImageService miService;
@Autowired
private YSAuditServiceV3 self;
@Autowired
private MercAuditListener mercAuditListener;
@Autowired
private NoticeService noticeService;
@Autowired
private GeneralPushUtil generalPushUtil;
@Autowired
private YsConfig ysConfig;
@Autowired
private MccReflectService reflectService;
@Resource
private UserAppMapper userAppMapper;
@Autowired
private SxfMerAuditHandler sxfMerAuditHandler;
@Autowired
private SubMerchantService smService;
@Override
public void merchantAuditV3(String userId, boolean isFailCheck) {
try {
self.step1(userId);
executorService.execute(() -> {
try {
self.step2(userId);
Thread.sleep(10000);
self.step3(userId);
} catch (Exception e) {
e.printStackTrace();
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByUserId(userId);
MerchantChannelStatus mcs = mcsService.getByMerchantCode(mbi.getMerchantCode(), 4);
if (e instanceof MsgException) {
Serializable obj = ((MsgException) e).getObj();
if (obj instanceof RespEntity) {
mcs.getExtra().putAll((JSONObject) JSON.toJSON(obj));
}
}
if (mcs != null && mcs.getChannel() == 4) {
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_EXAMINING);
mcs.setThirdStatus(MerchantChannelStatus.AUDIT_THIRD_STATUS_WAITING);
mcs.setRemark("银盛审核失败: " + e.getMessage());
mcs.setUpdateTime(new Date());
transactionTemplate.execute(new TransactionCallbackWithoutResult() {
@Override
protected void doInTransactionWithoutResult(TransactionStatus status) {
mcsService.updateById(mcs);
}
});
}
}
});
} catch (Exception e) {
e.printStackTrace();
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByUserId(userId);
MerchantChannelStatus mcs = mcsService.getByMerchantCode(mbi.getMerchantCode(), 4);
if (mcs != null && Objects.equals(mcs.getChannel(), 4)) {
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_EXAMINING);
mcs.setThirdStatus(MerchantChannelStatus.AUDIT_THIRD_STATUS_WAITING);
mcs.setRemark("银盛审核失败: " + e.getMessage());
mcs.setUpdateTime(new Date());
// 这里将驳回的信息放入新的事务中,防止被回滚
transactionTemplate.execute(new TransactionCallbackWithoutResult() {
@Override
protected void doInTransactionWithoutResult(TransactionStatus status) {
mcsService.updateById(mcs);
}
});
}
throw e;
}
}
@Override
public void sign(MerchantChannelStatus mcs) {
List<String> excludeStatus = Collections.singletonList(MerchantChannelStatus.AUDIT_STATUS_SUCCESS);
boolean returnFlag = excludeStatus.stream().anyMatch(s -> s.equals(mcs.getStatus()));
if (returnFlag) {
return;
}
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByMerchantCode(mcs.getMerchantCode());
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_WAITING_SIGN);
mcsService.updateById(mcs);
JSONObject extra = mcs.getExtra();
String custId = extra.getString("custId");
RateInfo rateInfo = new RateInfo();
rateInfo.setCustId(custId);
rateInfo.setBusOpenType("00|01");
rateInfo.setContractType("2");
rateInfo.setIsSendConMsg("1");
rateInfo.setNotifyUrl(YsConfigV3.AUDIT_SIGN_NOTIFY_URL);
RateFeeInfo rateFeeInfo = new RateFeeInfo();
rateFeeInfo.setAliPayFee(new RateFeeDetail("0", "0.38", "1"));
rateFeeInfo.setWxPayFee(new RateFeeDetail("0", "0.38", "1"));
rateFeeInfo.setBank1debitPayFee(new RateFeeDetail("0", "0.61", "1", "999900"));
rateFeeInfo.setBank1creditPayFee(new RateFeeDetail("0", "0.61", "1", "999900"));
rateFeeInfo.setBank2debitPayFee(new RateFeeDetail("0", "0.38", "1", "999900"));
rateFeeInfo.setBank2creditPayFee(new RateFeeDetail("0", "0.38", "1"));
RateFeeDetail codeScanD0Fee = new RateFeeDetail("0", "0.10", "1");
rateInfo.setCodeScanD0Fee(codeScanD0Fee);
rateInfo.setCodeScanT1Fee(rateFeeInfo);
RespEntity respEntity = ysServiceV3.req(ReqMethod.sign, (JSONObject) JSON.toJSON(rateInfo));
if (!Objects.equals(respEntity.getSubCode(), YsConfigV3.BIZ_SUCCESS)) {
throw new MsgException("银盛云商服3.0商户签约申请请求失败, {}", respEntity.getSubMsg());
}
JSONObject businessData = JSON.parseObject(respEntity.getBusinessData());
mcs.getExtra().putAll(businessData);
mcsService.updateById(mcs);
Notice notice = new Notice(1, -1, mbi.getUserId());
String uniqueKey = "YS_QY" + System.currentTimeMillis();
String title = "电子协议签约通知";
String content = "尊敬的客户您好,请点此通知完成签约意愿授权。请注意,同意授权后,支付通道才会进行商户资料审核,否则会一直等待审核。";
String url = businessData.getString("signUrl");
notice.setUniqueKey(uniqueKey);
notice.setNoticeCode(uniqueKey);
notice.setTitle(title);
notice.setUrl(url);
notice.setDesc(content);
noticeService.save(notice);
generalPushUtil.sendAllPlatByAlias(Collections.singletonList(mbi.getUserId()), title, content, "1");
}
@Override
public void callback(JSONObject callback) throws Exception {
String signContent = SignUtils.getSignContent(callback);
String signStr = callback.getString("sign");
Sign sign = SecureUtil.sign(SignAlgorithm.SHA256withRSA, null, ysConfig.getOldPubKey());
boolean verify;
try {
verify = sign.verify(signContent.getBytes(StandardCharsets.UTF_8), Base64.decode(signStr));
} catch (Exception e) {
log.info("回调验签异常");
e.printStackTrace();
verify = true;
}
if (!verify) {
log.info("银盛云商服3.0回调验签失败");
throw new MsgException("银盛云商服3.0回调验签失败");
}
String bizContent = callback.getString("bizContent");
Notify notifyData = JSON.parseObject(bizContent, Notify.class);
switch (notifyData.getNotifyType()) {
case Notify.TYPE_MERC_APPLY:
// 资料确认通知
Notify.Cust cust = notifyData.getCust();
cust.setStatus(notifyData.getStatus());
auditResultHandle(cust);
break;
case Notify.TYPE_MERC_SIGN:
// 签约变更通知
Notify.Auth auth = notifyData.getAuth();
auth.setStatus(notifyData.getStatus());
signResultHandle(auth);
break;
case Notify.TYPE_MERC_CHANGE:
// 商户资料变更通知
case Notify.TYPE_MERC_RATE_CHANGE:
// 商户费率变更通知
Notify.Change change = notifyData.getChange();
change.setStatus(notifyData.getStatus());
// editResultHandle(change);
break;
case Notify.TYPE_MERC_REPORT:
// 报备通知
Notify.Report report = notifyData.getReport();
report.setStatus(notifyData.getStatus());
collectSubMerId(report);
break;
}
}
@Override
public void auditResult(String userId) {
}
public void preCheck(String userId) {
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByUserId(userId);
LambdaQueryWrapper<MerchantChannelStatus> qWrapper = Wrappers.lambdaQuery();
qWrapper.eq(MerchantChannelStatus::getMerchantCode, mbi.getMerchantCode());
qWrapper.eq(MerchantChannelStatus::getVirChannelFlag, Account.CHANNEL_TYPE_D1);
MerchantChannelStatus existD1 = mcsService.getOne(qWrapper);
if (existD1 != null && !MerchantChannelStatus.AUDIT_STATUS_SUCCESS.equals(existD1.getStatus()) && !MerchantChannelStatus.AUDIT_STATUS_SIGNED.equals(existD1.getStatus()) && !MerchantChannelStatus.AUDIT_STATUS_WAITING_SIGN.equals(existD1.getStatus())) {
throw new MsgException("当前D1通道存在未进件完成的的进件数据不允许进件银盛");
}
if (MERCH_TYPE_MICRO.equals(mbi.getMerchantType())) {
int ysCount = accountMapper.selectYSAuditSmallCount(mbi.getUserId());
if (ysCount >= 2) {
MsgException.throwException("非营业执照商户同一结算人仅可申请两次实时到账");
}
}
qWrapper.clear();
qWrapper.eq(MerchantChannelStatus::getMerchantCode, mbi.getMerchantCode());
qWrapper.eq(MerchantChannelStatus::getVirChannelFlag, "D0");
MerchantChannelStatus existD0 = mcsService.getOne(qWrapper);
if (existD0 == null) {
qWrapper.clear();
qWrapper.eq(MerchantChannelStatus::getMerchantCode, mbi.getMerchantCode());
qWrapper.isNull(MerchantChannelStatus::getChannel);
existD0 = mcsService.getOne(qWrapper);
}
if (existD0 != null) {
existD0 = mcsService.getByIdLock(existD0.getId());
if (existD0.getStatus().equals(MerchantChannelStatus.AUDIT_STATUS_REJECT)) {
return;
}
if (existD0.getStatus().equals(MerchantChannelStatus.AUDIT_STATUS_EXAMINING) && existD0.getThirdStatus().equals(MerchantChannelStatus.AUDIT_THIRD_STATUS_AUDITING)) {
throw new MsgException("当前商户已经在后台审核中");
}
// 此处先将进件状态锁住
existD0.setChannel(4);
mcsService.saveOrUpdate(existD0);
}
}
@Transactional(rollbackFor = Exception.class, propagation = Propagation.REQUIRES_NEW)
public void step1(String userId) {
MercInfo mercInfo = combineBaseInfo(userId);
RespEntity req = ysServiceV3.req(ReqMethod.addCustInfoApply, (JSONObject) JSONObject.toJSON(mercInfo));
String subCode = req.getSubCode();
if (!Objects.equals(subCode, YsConfigV3.BIZ_SUCCESS)) {
throw new MsgException(req.getSubMsg());
}
preCheck(userId);
MerchantChannelStatus mcs = new MerchantChannelStatus();
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByUserId(userId);
mcs.setMerchantCode(mbi.getMerchantCode());
mcs.setChannel(4);
mcs = mcsService.getOne(new QueryWrapper<>(mcs));
if (mcs == null) {
mcs = new MerchantChannelStatus();
mcs.setMerchantCode(mcs.getMerchantCode());
mcs.setChannel(4);
}
JSONObject extra = mcs.getExtra();
extra.putAll(JSON.parseObject(req.getBusinessData()));
mcs.setApplicationId(extra.getString("sysFlowId"));
mcs.setThirdStatus(MerchantChannelStatus.AUDIT_THIRD_STATUS_AUDITING);
//mcs.setInterfaceVersion(YsConfigV3.INTERFACE_VERSION);
mcsService.saveOrUpdate(mcs);
AccountDTO accountDTO = accountService.getRealAccount(userId, Account.CHANNEL_TYPE_D1);
IdCard legalIdCard = idCardService.getLegalIdCard(userId);
//upstreamInfoService.save(mbi, legalIdCard, accountDTO.getIdcard(), accountDTO.getBankCard(), 4);
}
private MercInfo combineBaseInfo(String userId) {
CombineMercInfo combineMercInfo = mercAuditListener.getMercInfo(userId, Account.CHANNEL_TYPE_D0);
LambdaQueryWrapper<MerchantBaseInfo> qWrapper = Wrappers.lambdaQuery();
qWrapper.eq(MerchantBaseInfo::getUserId, userId);
MerchantBaseInfo mbi = mbiService.getOne(qWrapper);
MercInfo mercInfo = new MercInfo();
CustInfo custInfo = new CustInfo();
mercInfo.setCustInfo(custInfo);
//商户基本信息
custInfo.setMercName(mbi.getMerchantName());
custInfo.setMercShortName(mbi.getAlias());
switch (mbi.getMerchantType()) {
case MerchantBaseInfo.MERCH_TYPE_MICRO:
custInfo.setMercType("2");
break;
case MerchantBaseInfo.MERCH_TYPE_INDIVIDUAL:
custInfo.setMercType("3");
break;
case MerchantBaseInfo.MERCH_TYPE_COMPANY:
custInfo.setMercType("4");
break;
default:
throw new MsgException("暂未找到用户类型");
}
MccReflect ysMccReflect = reflectService.getYsMccReflect(mbi.getMcc());
custInfo.setMccCd(mbi.getMcc());
custInfo.setContactMail("chaozhanggui2022@163.com");
custInfo.setCusMgrNm("蔡祥");
custInfo.setNotifyUrl(YsConfigV3.AUDIT_NOTIFY_URL);
custInfo.setAgtMercId(ysConfigV3.getAgentNo());
// custInfo.setRemark("测试商户");
//法人基本信息
CrpInfo crpInfo = new CrpInfo();
mercInfo.setCrpInfo(crpInfo);
IdCard legalIdCard = combineMercInfo.getLegalIdCard();
crpInfo.setCrpCertNo(legalIdCard.getCertNo());
crpInfo.setCrpCertType("00");
crpInfo.setCertBgn(legalIdCard.getCertStartTime().replace("-", ""));
if (legalIdCard.getCertEndTime().equals("长期")) {
crpInfo.setCertExpire("29991231");
} else {
crpInfo.setCertExpire(legalIdCard.getCertEndTime().replace("-", ""));
}
crpInfo.setCrpNm(legalIdCard.getCertName());
BankCard bankCard = combineMercInfo.getBankCard();
crpInfo.setCrpPhone(bankCard.getPhone());
//银行卡相关
StlAccInfo stlAccInfo = new StlAccInfo();
mercInfo.setStlAccInfo(stlAccInfo);
// 非法人授权信息
if (!legalIdCard.getCertNo().equals(combineMercInfo.getSettleIdCard().getCertNo())) {
IdCard idCard = combineMercInfo.getSettleIdCard();
PersonInfo authInfo = new PersonInfo();
authInfo.setName(idCard.getCertName());
authInfo.setCertType("00");
authInfo.setCertNo(idCard.getCertNo());
authInfo.setCertBgn(idCard.getCertStartTime().replace("-", ""));
if (idCard.getCertEndTime().equals("长期")) {
authInfo.setCertExpire("29991231");
} else {
authInfo.setCertExpire(idCard.getCertEndTime().replace("-", ""));
}
crpInfo.setAuthInfo(authInfo);
stlAccInfo.setIsUncrpSett("Y");
stlAccInfo.setBankMobile(bankCard.getPhone());
stlAccInfo.setOpenCertNo(idCard.getCertNo());
}
stlAccInfo.setStlAccNm(bankCard.getBankHolder());
stlAccInfo.setStlAccNo(bankCard.getBankCardNo());
stlAccInfo.setBankSubCode(bankCard.getContactLine());
RegionCodeYs ysRegionCode = regionReflectService.getYsRegionCode(bankCard);
// 由于联行号地址存在对应不上的问题,所以这里还是将地区信息给带上
stlAccInfo.setBankProince(ysRegionCode.getProvinceCode());
stlAccInfo.setBankCity(ysRegionCode.getCityCode());
if (bankCard.getAccountType().equals(BankCard.ACCOUNT_TYPE_PRIVATE)) {
stlAccInfo.setStlAccType("11");
} else {
stlAccInfo.setStlAccType("21");
}
//营业执照相关
BusInfo busInfo = new BusInfo();
mercInfo.setBusInfo(busInfo);
if (!mbi.getMerchantType().equals(MerchantBaseInfo.MERCH_TYPE_MICRO)) {
busInfo.setBusNm(mbi.getBussAuthName());
busInfo.setBusNo(mbi.getBussAuthNum());
busInfo.setBusCertBgn(mbi.getBussAuthStartTime().replace("-", ""));
//TODO 有时营业执照有效日期没有填写
busInfo.setBusCertExpire(mbi.getBussAuthEndTime().replace("-", ""));
busInfo.setBusAddr(mbi.getBussAuthAddress());
busInfo.setBusCertType("19");
} else {
busInfo.setBusAddr(mbi.getProvince() + mbi.getCity() + mbi.getDistrict() + mbi.getAddress());
}
RegionCodeYs regionData = regionReflectService.getYsRegionCode(mbi.getProvince(), mbi.getCity(), mbi.getDistrict());
busInfo.setBusProviceCode(regionData.getProvinceCode());
busInfo.setBusCityCode(regionData.getCityCode());
busInfo.setBusAreaCode(regionData.getAreaCode());
return mercInfo;
}
/**
* 入网申请流水 sysFlowId
* 备注 note
* 客户号id custId
* 入网状态 status
*/
public void auditResultHandle(Notify.Cust cust) {
String status = cust.getStatus();
String sysFlowId = cust.getSysFlowId();
MerchantChannelStatus mcs = new MerchantChannelStatus();
mcs.setApplicationId(sysFlowId);
mcs.setChannel(4);
mcs = mcsService.getOne(new QueryWrapper<>(mcs));
mcs.setThirdStatus(status);
mcs.getExtra().putAll((JSONObject) JSON.toJSON(cust));
switch (status) {
case YsConfigV3.STATUS_SUCCESS:
mcs.setAuditSuccessTime(new Date());
mcsService.updateById(mcs);
sign(mcs);
break;
case YsConfigV3.STATUS_REFUSE:
List<String> excludeStatus = Arrays.asList(MerchantChannelStatus.AUDIT_STATUS_REJECT, MerchantChannelStatus.AUDIT_STATUS_SUCCESS);
MerchantChannelStatus finalMcs = mcs;
boolean returnFlag = excludeStatus.stream().anyMatch(s -> s.equals(finalMcs.getStatus()));
if (returnFlag) {
return;
}
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByMerchantCode(mcs.getMerchantCode());
String note = cust.getNote();
mcs.setRemark(note);
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_REJECT);
mcsService.updateById(mcs);
mercAuditListener.onFail(mbi.getUserId(), mcs, note);
break;
case YsConfigV3.STATUS_TO_MANUAL:
List<String> excludeStatus2 = Arrays.asList(MerchantChannelStatus.AUDIT_STATUS_SUCCESS, MerchantChannelStatus.AUDIT_STATUS_ARTIFICIAL_EXAMINING);
MerchantChannelStatus finalMcs2 = mcs;
boolean returnFlag2 = excludeStatus2.stream().anyMatch(s -> s.equals(finalMcs2.getStatus()));
if (returnFlag2) {
return;
}
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_ARTIFICIAL_EXAMINING);
mcsService.updateById(mcs);
break;
}
}
public void step2(String userId) {
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByUserId(userId);
List<MerchantImage> miList = miService.getListOfMerch(userId, Account.CHANNEL_TYPE_D0);
MerchantChannelStatus mcs = new MerchantChannelStatus();
mcs.setChannel(4);
mcs.setMerchantCode(mbi.getMerchantCode());
mcs = mcsService.getOne(new QueryWrapper<>(mcs));
if (mcs == null) {
throw new MsgException("无法上传图片,无法确认进件信息");
}
for (MerchantImage mi : miList) {
imageUpload(mi.getPhotoType(), mi.getPicUrl(), mcs.getApplicationId());
}
}
public void step3(String userId) {
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByUserId(userId);
MerchantChannelStatus mcs = mcsService.getByMerchantCode(mbi.getMerchantCode(), 4);
if (mcs == null) {
throw new MsgException("无法确认进件信息");
}
JSONObject param = new JSONObject();
param.put("auditFlag", "Y");
param.put("sysFlowId", mcs.getApplicationId());
RespEntity respEntity = ysServiceV3.req(ReqMethod.auditCustInfoApply, param);
JSONObject bizContent = JSON.parseObject(respEntity.getBusinessData());
mcs.getExtra().putAll(bizContent);
String status = bizContent.getString("status");
if (status == null) {
log.error("银盛云商服3.0进件异常, {}", respEntity.getSubMsg());
return;
}
mcs.setThirdStatus(status);
switch (status) {
case YsConfigV3.STATUS_SUCCESS:
// 这里不做任何处理,交给回调操作,防止数据错乱
break;
case YsConfigV3.STATUS_REFUSE:
mcs.setRemark(respEntity.getSubMsg());
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_REJECT);
mcsService.updateById(mcs);
mercAuditListener.onFail(mbi.getUserId(), mcs, respEntity.getSubMsg());
break;
case YsConfigV3.STATUS_TO_MANUAL:
mcs.setRemark(respEntity.getSubMsg());
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_ARTIFICIAL_EXAMINING);
mcsService.updateById(mcs);
break;
}
mcsService.updateById(mcs);
}
private void imageUpload(String photoType, String imgUrl, String flowId) {
int count = 0;
while (count < 3) {
count++;
String relPhotoType = imgTypeTransform(photoType);
if (photoType == null) {
throw new MsgException("缺少图片类型");
}
RespEntity respEntity = ysServiceV3.reqUpload(ReqMethod.upload, relPhotoType, imgUrl, flowId);
if (!Objects.equals(respEntity.getSubCode(), YsConfigV3.BIZ_SUCCESS)) {
log.info("第{}次上传失败:{}", count, respEntity.getSubMsg());
} else {
if (photoType.equals(MerchantImage.ImageType.BANK_CARD_FRONT)) {
imageUpload(MerchantImage.ImageType.BANK_CARD_BACK, imgUrl, flowId);
}
return;
}
}
throw new MsgException("图片多次上传失败");
}
public String imgTypeTransform(String imageType) {
if (imageType == null) {
throw new MsgException("图片类型不能为空");
}
switch (imageType) {
case MerchantImage.ImageType.SHOP_FRONT_DOOR:
return "A006";
case MerchantImage.ImageType.STORE_INTERIOR_PHOTO:
return "A007";
case MerchantImage.ImageType.CASH_DESK_PHOTO:
return "A008";
case MerchantImage.ImageType.ACCOUNT_PERMITS:
return "A011";
case MerchantImage.ImageType.BUSINESS_LICENSE:
return "A001";
case MerchantImage.ImageType.IDCARD_FRONT:
return "A002";
case MerchantImage.ImageType.IDCARD_BACK:
return "A003";
case MerchantImage.ImageType.BANK_CARD_FRONT:
return "A004";
case MerchantImage.ImageType.BANK_CARD_BACK:
return "A005";
case MerchantImage.ImageType.SETTLE_IDCARD_FRONT:
return "A013";
case MerchantImage.ImageType.SETTLE_IDCARD_BACK:
return "A014";
case MerchantImage.ImageType.NON_LEG_SETTLE_AUTH:
return "B005";
case MerchantImage.ImageType.CHANGE_FORM:
return "B008";
case MerchantImage.ImageType.CASH_DESK_WITH_PERSON:
return "B009";
}
return null;
}
public void signResultHandle(Notify.Auth authData) {
QueryWrapper<MerchantChannelStatus> qWrapper = Wrappers.query();
qWrapper.eq("extra ->> '$.authId'", authData.getAuthId());
qWrapper.eq("channel", 4);
MerchantChannelStatus mcs = mcsService.getOne(qWrapper);
mcs = mcsService.getByIdLock(mcs.getId());
mcs.getExtra().putAll((JSONObject) JSON.toJSON(authData));
MerchantBaseInfo mbi = mbiService.getMerchantBaseInfoByMerchantCode(mcs.getMerchantCode());
String status = authData.getStatus();
switch (status) {
case YsConfigV3.STATUS_SUCCESS:
if (mcs.getStatus().equals(MerchantChannelStatus.AUDIT_STATUS_SUCCESS)) {
return;
}
AccountDTO accountDTO = accountService.getRealAccount(mbi.getUserId(), Account.CHANNEL_TYPE_D0);
String mercId = authData.getMercId();
mcs.setMerchantId(mercId);
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_SUCCESS);
mcs.setAuditSuccessTime(new Date());
if (mbi.getMerchantType().equals(MerchantBaseInfo.MERCH_TYPE_MICRO)) {
mcs.getExtra().put("mercCnm", accountDTO.getIdcard().getCertName());
} else {
mcs.getExtra().put("mercCnm", mbi.getBussAuthName());
}
mcsService.updateById(mcs);
openOnlinePay(mcs);
mercAuditListener.onSuccess(mbi.getUserId(), mcs);
break;
case YsConfigV3.STATUS_REFUSE:
case YsConfigV3.STATUS_SIGN_REFUSE:
List<String> excludeStatus = Arrays.asList(MerchantChannelStatus.AUDIT_STATUS_REJECT, MerchantChannelStatus.AUDIT_STATUS_SUCCESS);
MerchantChannelStatus finalMcs = mcs;
boolean returnFlag = excludeStatus.stream().anyMatch(s -> s.equals(finalMcs.getStatus()));
if (returnFlag) {
return;
}
String note = authData.getNote();
mcs.setRemark(note);
mcs.setStatus(MerchantChannelStatus.AUDIT_STATUS_REJECT);
mcsService.updateById(mcs);
mercAuditListener.onFail(mbi.getUserId(), mcs, note);
break;
}
}
// public void editResultHandle(Notify.Change changeResult) {
// String status = changeResult.getStatus();
//
// MercChangeRecord entity = mcrService.get(changeResult.getChangeSysFlowId(), 4);
//
// if (entity == null && !Objects.equals(entity.getStatus(), MercChangeRecord.Status.AUDITING.getValue())) {
// return;
// }
//
// if (YsConfigV3.STATUS_SUCCESS.equals(status)) {
// // 变更成功
// entity.setStatus(MercChangeRecord.Status.SUCCESS.getValue());
// mcrService.updateById(entity);
//
// if (MercChangeRecord.Type.BASE.getValue().equals(entity.getChangeType())) {
// // 基本信息变更完成
// successChangeBaseInfo(entity, entity.getUserId() + "");
// } else if (MercChangeRecord.Type.ACCOUNT.getValue().equals(entity.getChangeType())) {
// // 结算卡变更完成
// successChangeSettlement(entity, entity.getUserId() + "");
// } else if (MercChangeRecord.Type.RATE.getValue().equals(entity.getChangeType())) {
// // 费率变更完成
// successChangeRate(entity, entity.getBaseInfo().getUserId());
// } else if (MercChangeRecord.Type.CARD.getValue().equals(entity.getChangeType())) {
// // TODO 证件补充, 云商服3.0没有该功能
// }
// }
//
// if (YsConfigV3.STATUS_REFUSE.equals(status)) {
// // 变更失败
// entity.setStatus(MercChangeRecord.Status.REFUSE.getValue());
// entity.setRemark(changeResult.getNote());
// mcrService.updateById(entity);
//
// if (MercChangeRecord.Type.BASE.getValue().equals(entity.getChangeType())) {
// // 基本信息变更失败
// failChangeBaseInfo(changeResult.getNote(), entity.getUserId() + "");
// } else if (MercChangeRecord.Type.ACCOUNT.getValue().equals(entity.getChangeType())) {
// // 结算卡变更失败
// failChangeBankCard(changeResult.getNote(), entity.getUserId() + "");
// } else if (MercChangeRecord.Type.RATE.getValue().equals(entity.getChangeType())) {
// // 费率变更失败
// failChangeRate(changeResult.getNote(), entity.getUserId() + "");
// } else if (MercChangeRecord.Type.CARD.getValue().equals(entity.getChangeType())) {
// // TODO 证件补充, 云商服3.0没有该功能
// }
// }
// }
public void openOnlinePay(MerchantChannelStatus mcs) {
try {
JSONObject param = new JSONObject();
param.put(YsConstant.MERC_ID, mcs.getMerchantId());
param.put("option", "ON");
param.put("rateFee", "0.38");
param.put("rateBottom", "1");
ysServiceV3.req(ReqMethod.openOnlinePay, param);
} catch (Exception e) {
log.error("云商服3.0开通线上D0接口报错: {}", e.getMessage());
}
}
public void collectSubMerId(Notify.Report report) {
List<Notify.ThirdMerc> thridMercList = report.getThridMercList();
if (thridMercList == null || thridMercList.isEmpty()) {
return;
}
String mercId = report.getMercId();
MerchantChannelStatus mcs = mcsService.getByMerchantId(mercId);
LambdaQueryWrapper<SubMerchant> qWrapper = Wrappers.lambdaQuery();
qWrapper.eq(SubMerchant::getMerchantId, mercId);
smService.remove(qWrapper);
for (Notify.ThirdMerc item : thridMercList) {
String status = item.getApprSts();
String thridMercId = item.getThridMercId();
String reportChannel = item.getReportChannel();
SubMerchant subMerchant = new SubMerchant();
subMerchant.setChannelTypeId("4");
String flagName = "";
String typeName = "";
if (reportChannel.contains("POS")) {
continue;
}
if (reportChannel.contains("WECHAT")) {
subMerchant.setSubMchType("WX");
flagName = "微信";
}
if (reportChannel.contains("ALIPAY")) {
subMerchant.setSubMchType("ZFB");
flagName = "支付宝";
}
if (reportChannel.contains("NUCC")) {
thridMercId += "_NUCC";
typeName = "网联";
}
if (reportChannel.contains("CUPS")) {
thridMercId += "_CUPS";
typeName = "银联";
}
if (Objects.equals("03", status)) {
LambdaQueryWrapper<UserApp> qWrapper2 = Wrappers.lambdaQuery();
qWrapper2.eq(UserApp::getMerchantCode, mcs.getMerchantCode());
qWrapper2.eq(UserApp::getUserType, "promoter");
UserApp userApp = userAppMapper.selectOne(qWrapper2);
String pushMsg = "D0通道" + flagName + typeName + "报备失败,请联系客服进行处理";
sxfMerAuditHandler.sendNotice(userApp, "收银呗审核通知", pushMsg, mcs.getApplicationId());
}
if (Objects.equals("00", status)) {
subMerchant.setMerchantId(mercId);
subMerchant.setStatus(status);
subMerchant.setSubMchId(thridMercId);
subMerchant.setRemark(item.getRemark());
try {
smService.save(subMerchant);
} catch (Exception ignored) {
// 插入报错不处理
}
}
}
}
@Test
public void main(){
JSONObject param = new JSONObject();
param.put("sysFlowId", "APPL202304061707282745251");
RespEntity req = ysServiceV3.req(ReqMethod.queryCustApply, param);
System.out.println(req);
}
}

View File

@@ -188,8 +188,8 @@ public class MerchantChannelStatusServiceImpl extends ServiceImpl<MerchantChanne
UserApp userApp = new UserApp().setMerchantCode(merchantCode).setUserType("promoter");
userApp = userAppService.queryUserApp(userApp);
wxTalkService.sendAuditAlert(userApp.getUserId() + "");
//TODO 微信机器人消息推送暂时干掉
//wxTalkService.sendAuditAlert(userApp.getUserId() + "");
}
@Override

View File

@@ -0,0 +1,20 @@
package cn.pluss.platform.pojo;
import cn.pluss.platform.entity.BankCard;
import cn.pluss.platform.entity.IdCard;
import cn.pluss.platform.entity.MerchantBaseInfo;
import lombok.Getter;
import lombok.Setter;
@Setter
@Getter
public class CombineMercInfo {
private MerchantBaseInfo mbi;
private IdCard legalIdCard;
private IdCard settleIdCard;
private BankCard bankCard;
}

View File

@@ -8,6 +8,7 @@ import cn.pluss.platform.api.ResultGenerator;
import cn.pluss.platform.channel.BaseMerchantAuditService;
import cn.pluss.platform.channel.MerchantAuditService;
//import cn.pluss.platform.channel.ys.YSAuditServiceV3;
import cn.pluss.platform.channel.ys.YSAuditServiceV3;
import cn.pluss.platform.common.CommonRemarkService;
import cn.pluss.platform.common.RiskBlacklistService;
import cn.pluss.platform.converter.Converter;
@@ -174,8 +175,8 @@ public class UserAppServiceImpl extends ServiceImpl<UserAppMapper, UserApp> impl
@Autowired
private UserRoleMapper userRoleMapper;
//@Autowired
//private YSAuditServiceV3 ysAuditServiceV3;
@Autowired
private YSAuditServiceV3 ysAuditServiceV3;
@Override
@@ -799,7 +800,7 @@ public class UserAppServiceImpl extends ServiceImpl<UserAppMapper, UserApp> impl
case "4":
// 银盛
//ysAuditServiceV2.merchantAudit(userId, false);
//ysAuditServiceV3.merchantAuditV3(userId, false);
ysAuditServiceV3.merchantAuditV3(userId, false);
break;
default:
MsgException.throwException("未知的进件通道");

View File

@@ -0,0 +1,7 @@
package cn.pluss.platform.ys.impl.v20220527;
public class Req {
public static class Url {
public static final String PREFIX = "https://ysgate.ysepay.com/openapi/";
}
}

View File

@@ -0,0 +1,54 @@
package cn.pluss.platform.ys.impl.v20220527;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.RandomUtil;
import cn.pluss.platform.yinsheng.v20210929.ReqMethod;
import lombok.AccessLevel;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
import java.util.Date;
@Getter
@Setter
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class ReqEntity {
private String timeStamp;
private String method;
private String charset = "utf-8";
private String sign;
private String check;
private String bizContent;
private String reqId;
private String certId = "826521773920170";
private String version = "1.0";
public static ReqEntity get(ReqMethod reqMethod) {
Date date = new Date();
ReqEntity entity = new ReqEntity();
entity.timeStamp = DateUtil.format(date, "yyyy-MM-dd HH:mm:ss");
entity.method = reqMethod.getMethod();
entity.reqId = "SYB_" + RandomUtil.randomString(4) + DateUtil.format(date, "yyMMddHHmmss");
return entity;
}
public static ReqEntity get(cn.pluss.platform.ys.impl.v20220527.ReqMethod reqMethod) {
Date date = new Date();
ReqEntity entity = new ReqEntity();
entity.timeStamp = DateUtil.format(date, "yyyy-MM-dd HH:mm:ss");
entity.method = reqMethod.getMethod();
entity.reqId = "SYB_" + RandomUtil.randomString(4) + DateUtil.format(date, "yyMMddHHmmss");
return entity;
}
}

View File

@@ -0,0 +1,46 @@
package cn.pluss.platform.ys.impl.v20220527;
import lombok.Getter;
@Getter
public enum ReqMethod {
addCustInfoApply(Req.Url.PREFIX + "t1/smsc/addCustInfoApply"),
modifyCustInfoApply(Req.Url.PREFIX + "smsc/modifyCustInfoApply"),
upload(Req.Url.PREFIX + "file/smsc/upload"),
auditCustInfoApply(Req.Url.PREFIX + "t1/smsc/auditCustInfoApply"),
queryCustApply(Req.Url.PREFIX + "smsc/queryCustApply"),
sign(Req.Url.PREFIX + "t1/smsc/sign"),
sendSmsOrEmailMsg(Req.Url.PREFIX + "smsc/sign/sendSmsOrEmailMsg"),
queryAuthInfo(Req.Url.PREFIX + "smsc/saas/constract/queryAuthInfo"),
queryContract(Req.Url.PREFIX + "smsc/sign/queryContract"),
sweepReport(Req.Url.PREFIX + "smsc/saas/sweep/sweepreport"),
reportAgain(Req.Url.PREFIX + "smsc/saas/sweep/reportAgain"),
changeMercBaseInfo(Req.Url.PREFIX + "smsc/changeMercBaseInfo"),
uploadChangePic(Req.Url.PREFIX + "file/smsc/uploadChangePic"),
queryCustChange(Req.Url.PREFIX + "smsc/queryCustChange"),
changeMercStlAccInfo(Req.Url.PREFIX + "t1/smsc/changeMercStlAccInfo"),
changeRate(Req.Url.PREFIX + "smsc/changeRate"),
openOnlinePay(Req.Url.PREFIX + "smsc/saas/authority/online"),
regionList(Req.Url.PREFIX + "pregate/trade/findCmmtAreaInfoList"),
repAndAppIdQry(Req.Url.PREFIX + "report/scan/union/repAndAppIdQry"),
/**
* 支付宝实名认证状态查询
*/
aliAuthStatus(Req.Url.PREFIX + "pregate/alipay/getAuthState"),
;
private final String url;
private final String method;
ReqMethod(String url, String method) {
this.url = url;
this.method = method;
}
ReqMethod(String url) {
this(url, url.replace(Req.Url.PREFIX, "").replace('/', '.'));
}
}

View File

@@ -0,0 +1,50 @@
package cn.pluss.platform.ys.impl.v20220527;
import lombok.Getter;
import lombok.Setter;
import java.io.Serializable;
@Setter
@Getter
public class RespEntity implements Serializable{
/**
* 网关响应码
*/
private String code;
/**
* 网关响应码描述
*/
private String msg;
/**
* 业务响应码
*/
private String subCode;
/**
* 业务响应描述
*/
private String subMsg;
/**
* yyyy-MM-dd HH:mm:ss
*/
private String timeStamp;
/**
* 随机参数
*/
private String norce;
/**
* 签名串
*/
private String sign;
/**
* 业务响应参数集合,
* 加密后的数据
*/
private String businessData;
}

View File

@@ -41,9 +41,9 @@ public class YsConfigV3 {
public static final String BIZ_SUCCESS = "0000";
public static final String AUDIT_NOTIFY_URL = "https://ky.sxczgkj.cn/api/auditCallback/ysV3";
public static final String AUDIT_NOTIFY_URL = "http://wxgzh.sxczgkj.cn/api/auditCallback/ysV3";
public static final String AUDIT_SIGN_NOTIFY_URL = "https://www.shouyinbei.net/api/auditCallback/ysSignV3";
public static final String AUDIT_SIGN_NOTIFY_URL = "http://wxgzh.sxczgkj.cn/api/auditCallback/ysSignV3";
/** 成功 */
public static final String STATUS_SUCCESS = "00";

View File

@@ -0,0 +1,249 @@
package cn.pluss.platform.ys.impl.v20220527;
import cn.hutool.core.codec.Base64;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ByteUtil;
import cn.hutool.core.util.HexUtil;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.crypto.SecureUtil;
import cn.hutool.crypto.asymmetric.KeyType;
import cn.hutool.crypto.asymmetric.RSA;
import cn.hutool.crypto.asymmetric.Sign;
import cn.hutool.crypto.asymmetric.SignAlgorithm;
import cn.hutool.crypto.digest.DigestUtil;
import cn.hutool.crypto.symmetric.AES;
import cn.hutool.crypto.symmetric.DES;
import cn.pluss.platform.exception.MsgException;
import cn.pluss.platform.util.*;
import cn.pluss.platform.ys.YsConfig;
import cn.pluss.platform.ys.YsOldConfig;
import cn.pluss.platform.ys.impl.v20210929.YsConfigV2;
import cn.pluss.platform.ys.impl.v20210929.YsConstant;
import cn.pluss.platform.ys.impl.v20220527.entity.Meta;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ByteArrayResource;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.stereotype.Service;
import org.springframework.util.DigestUtils;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.util.StringUtils;
import org.springframework.web.client.RestTemplate;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.util.*;
@Slf4j
@Service("ysServiceV3")
public class YsServiceV3 {
@Autowired
private YsConfig ysConfig;
@Autowired
private RestTemplate restTemplate;
/**
* 只用于新的进件接口
*
* @param reqMethod 请求方法
* @param reqData 请求参数
* @return
*/
public RespEntity req(ReqMethod reqMethod, JSONObject reqData) {
Calendar calendar = Calendar.getInstance();
int i = calendar.get(Calendar.HOUR_OF_DAY);
if (i < 8 || i >= 21) {
throw new MsgException("当前时段暂不支持入网请于8:00-21:00提交");
}
try {
ReqEntity request = ReqEntity.get(reqMethod);
request.setCertId(ysConfig.getSrcMerchantNo());
request.setBizContent(reqData.toJSONString());
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON_UTF8);
headers.add("User-Agent",
"Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/45.0.2454.101 Safari/537.36");
log.info("业务参数==============>" + JSONObject.toJSONString(reqData));
String key = RandomUtil.randomString(RandomUtil.BASE_NUMBER + "ABCDEF",16);
log.info("key = " + key);
AES aes = new AES(key.getBytes(StandardCharsets.UTF_8));
String s = aes.encryptBase64(request.getBizContent());
request.setBizContent(s);
RSA rsa = SecureUtil.rsa(ysConfig.getPriKey(), ysConfig.getOldPubKey());
request.setCheck(rsa.encryptBase64(key, KeyType.PublicKey));
String encryptOriginData = SignUtils.getSignContent((JSONObject) JSON.toJSON(request));
Sign sign = SecureUtil.sign(SignAlgorithm.SHA256withRSA, ysConfig.getPriKey(), ysConfig.getOldPubKey());
log.info("加签源数据==============>" + encryptOriginData);
request.setSign(Base64.encode(sign.sign(encryptOriginData)));
log.warn("请求报文==============>" + JSONObject.toJSONString(request));
log.info("请求地址:{}", reqMethod.getUrl());
HttpEntity<JSONObject> reqEntity = new HttpEntity<>((JSONObject) JSON.toJSON(request), headers);
String respStr = restTemplate.postForObject(reqMethod.getUrl(), reqEntity, String.class);
log.info("返回信息base64{}", respStr);
byte[] decode = Base64.decode(respStr);
respStr = new String(decode, StandardCharsets.UTF_8);
log.info("返回信息:{}", respStr);
JSONObject param = JSON.parseObject(respStr);
String signContent = SignUtils.getSignContent(param);
System.out.println("加签原参数:" + signContent);
boolean checkSign;
try {
checkSign = sign.verify(signContent.getBytes(StandardCharsets.UTF_8), Base64.decode(param.getString("sign")));
} catch (Exception e) {
log.error("银盛云商服3.0接口验签失败{}", e.getMessage());
e.printStackTrace();
checkSign = true;
}
if (!checkSign) {
throw new MsgException("银盛云商服3.0接口验签不通过");
}
RespEntity respEntity = JSON.parseObject(respStr, RespEntity.class);
// 检查网关code码
if (!Objects.equals(respEntity.getCode(), YsConfigV3.REQ_SUCCESS)) {
throw new MsgException(respEntity.getMsg());
}
// 业务响应码这里不做判断,交给具体接口业务逻辑去判断
if (StringUtils.hasText(respEntity.getBusinessData())) {
byte[] bizBytes = Base64.decode(respEntity.getBusinessData());
String decryptBizData = aes.decryptStr(bizBytes);
respEntity.setBusinessData(decryptBizData);
log.info("业务参数: {}", respEntity.getBusinessData());
}
return respEntity;
} catch (Exception e) {
if (e instanceof MsgException) {
throw e;
}
return null;
}
}
public RespEntity reqUpload(ReqMethod reqMethod, String picType, String fileUrl, String sysFlowId) {
Calendar calendar = Calendar.getInstance();
int i = calendar.get(Calendar.HOUR_OF_DAY);
if (i < 8 || i >= 21) {
throw new MsgException("当前时段暂不支持入网请于8:00-21:00提交");
}
Meta meta = new Meta();
meta.setPicType(picType);
meta.setSysFlowId(sysFlowId);
meta.setChangeFlowId(sysFlowId);
try {
ReqEntity request = ReqEntity.get(ReqMethod.upload);
request.setCertId(ysConfig.getSrcMerchantNo());
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.MULTIPART_FORM_DATA);
headers.add("User-Agent",
"Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/45.0.2454.101 Safari/537.36");
MultiValueMap<String, Object> reqMap = new LinkedMultiValueMap<>();
try {
String imgBase64Data = FileUtil.getBase64FromUrl(fileUrl);
String compressPic = Base64Util.compressPic(imgBase64Data, 1024);
byte[] byteArray = Base64.decode(compressPic);
ByteArrayResource file = new ByteArrayResource(byteArray) {
@Override
public String getFilename() {
return "test.jpg";
}
};
reqMap.add("file", file);
String sha256 = DigestUtil.sha256Hex(file.getInputStream());
meta.setSha256(sha256);
meta.setPicNm("test.jpg");
} catch (IOException e) {
e.printStackTrace();
}
JSONObject reqData = new JSONObject();
reqData.put("meta", meta);
request.setBizContent(reqData.toString());
log.info("业务参数==============>" + reqData);
String key = RandomUtil.randomString(RandomUtil.BASE_NUMBER + "ABCDEF",16);
log.info("key = " + key);
AES aes = new AES(key.getBytes(StandardCharsets.UTF_8));
String s = aes.encryptBase64(request.getBizContent());
request.setBizContent(s);
RSA rsa = SecureUtil.rsa(ysConfig.getPriKey(), ysConfig.getOldPubKey());
request.setCheck(rsa.encryptBase64(key, KeyType.PublicKey));
String encryptOriginData = SignUtils.getSignContent((JSONObject) JSON.toJSON(request));
Sign sign = SecureUtil.sign(SignAlgorithm.SHA256withRSA, ysConfig.getPriKey(), ysConfig.getOldPubKey());
log.info("加签源数据==============>" + encryptOriginData);
request.setSign(Base64.encode(sign.sign(encryptOriginData)));
reqMap.addAll(MapUtils.map2MultiValueMap((JSONObject) JSON.toJSON(request)));
HttpEntity<MultiValueMap<String, Object>> reqEntity = new HttpEntity<>(reqMap, headers);
String respStr = restTemplate.postForObject(reqMethod.getUrl(), reqEntity, String.class);
log.info("返回信息base64{}", respStr);
byte[] decode = Base64.decode(respStr);
respStr = new String(decode, StandardCharsets.UTF_8);
log.info("返回信息:{}", respStr);
JSONObject param = JSON.parseObject(respStr);
String signContent = SignUtils.getSignContent(param);
System.out.println("加签原参数:" + signContent);
boolean checkSign;
try {
checkSign = sign.verify(signContent.getBytes(StandardCharsets.UTF_8), Base64.decode(param.getString("sign")));
} catch (Exception e) {
log.error("银盛云商服3.0图片上传接口验签失败: {}", e.getMessage());
e.printStackTrace();
checkSign = true;
}
if (!checkSign) {
throw new MsgException("银盛云商服3.0接口验签不通过");
}
RespEntity respEntity = JSON.parseObject(respStr, RespEntity.class);
// 检查网关code码
if (!Objects.equals(respEntity.getCode(), YsConfigV3.REQ_SUCCESS)) {
throw new MsgException(respEntity.getMsg());
}
// 业务响应码这里不做判断,交给具体接口业务逻辑去判断
if (respEntity.getBusinessData() != null) {
byte[] bizBytes = Base64.decode(respEntity.getBusinessData());
String decryptBizData = aes.decryptStr(bizBytes);
respEntity.setBusinessData(decryptBizData);
}
log.info("业务返回参数: {}", respEntity.getBusinessData());
return respEntity;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
}

View File

@@ -8,7 +8,7 @@ import lombok.Setter;
*/
@Setter
@Getter
public class PersonInfo {
public class PersonInfo extends com.alipay.api.domain.PersonInfo {
/**
* 实际控制人姓名
*/

View File

@@ -0,0 +1,6 @@
package cn.pluss.platform.ys.impl.v20220527.service;
public class YsAuditServiceV3 {
}

View File

@@ -0,0 +1,690 @@
package cn.pluss.platform.ysExtension.v20220615;
import lombok.AllArgsConstructor;
import lombok.Getter;
/**
* 记录银盛接口的参数的key值
*/
public class YsConstantV3 {
@Getter
@AllArgsConstructor
public enum ReqStatus {
/** 请求状态值 */
SUCCESS("00", "请求成功");
private String code;
private String desc;
}
@Getter
@AllArgsConstructor
public enum AuditStatus {
/**
* 进件状态
*/
AUDIT_NO_AUDIT("03", "待审核"), AUDIT_FIRST_TRIAL_SUCCESS("04", "初审完成"), AUDIT_SUCCESS("05", "开户完成"), AUDIT_FIRST_TRIAL_FAIL("90", "初审拒绝");
private String code;
private String desc;
public static AuditStatus getByCode(String code) {
for (AuditStatus value : AuditStatus.values()) {
if (value.code.equals(code)) {
return value;
}
}
return null;
}
}
/**
* 营业执照全称
*/
public static final String BUSINESS_LICENCE = "businessLicence";
/**
* 商户简称
*/
public static final String ALIAS = "userShortName";
/**
* 营业执照全称
*/
public static final String BUSINESS_LICENCE_NO = "businessLicenceNo";
/**
* 营业执照开始日期
*/
public static final String BUSINESS_LICENCE_START = "businessLicenceSdate";
/**
* 营业执照结束日期
*/
public static final String BUSINESS_LICENCE_LIMIT = "businessLicenceEdate";
/**
* 营业执照注册地址
*/
public static final String REGISTERED_ADDRESS = "registeredAddress";
/**
* 营业地址
*/
public static final String BUSINESS_ADDRESS = "businessAddress";
/**
* 商户归属省
*/
public static final String MERC_PROV = "mercProv";
/**
* 商户归属省
*/
public static final String MERC_CITY = "mercCity";
/**
* 商户归属省
*/
public static final String MERC_AREA = "mercArea";
/**
* 法人姓名
*/
public static final String LEGAL_PERSON_NAME = "legalPersonName";
/**
* 法人身份证号
*/
public static final String LEGAL_PERSON_ID = "legalPersonId";
/**
* 法人身份证开始日期
*/
public static final String LEGAL_PERSON_START = "legalPersonIdSdate";
/**
* 法人身份证到期日期
*/
public static final String LEGAL_PERSON_LIMIT = "legalPersonIdEdate";
/**
* 法人电话
*/
public static final String LEGAL_PERSON_PHONE = "legalPersonPhone";
/**
* 非法人姓名
*/
public static final String ACCOUNT_PERSON_NAME = "unincorporatedName";
/**
* 非法人身份证号码
*/
public static final String ACCOUNT_PERSON_ID = "unincorporatedId";
/**
* 结算账户卡号
*/
public static final String ACCOUNT_CARD_NO = "balanceAccCardno";
/**
* 结算账户户名
*/
public static final String ACCOUNT_CARD_NAME = "balanceAccName";
/**
* 开户行省(如湖北省)
*/
public static final String BANK_PROVINCE = "openAccProvince";
/**
* 开户行市(如武汉市)
*/
public static final String BANK_CITY = "openAccCity";
/**
* 开户行市(如武汉市)
*/
public static final String BANK_AREA = "openAccArea";
/**
* 开户行行别名称
*/
public static final String BANK_NAME = "bankName";
/**
* 开户行行别
*/
public static final String BANK_TYPE = "bankType";
/**
* 开户行编号(支行)
*/
public static final String BANK_BRANCH_TYPE = "openAccBanktype";
/**
* 开户行名称(支行)
*/
public static final String BANK_BRANCH_NAME = "openAccBankname";
/**
* 联系人姓名
*/
public static final String CONTACTS_NAME = "contactsName";
/**
* 联系人电话
*/
public static final String CONTACTS_PHONE = "contactsPhone";
/**
* 联系人邮箱
*/
public static final String CONTACTS_EMAIL = "contactsEmail";
/**
* 微信签约费率(最 低:0.01%)
*/
public static final String WECHAT_SIGN_RATE = "wechatSignRate";
/**
* 微信签约费率封底(单位:分)
*/
public static final String WECHAT_SIGN_MIN = "wechatSignMin";
/**
* 支付宝签约费率(最低:0.01%)
*/
public static final String ALIPAY_SIGN_RATE = "alipaySignRate";
/**
* 支付宝签约费率封底(单位:分)
*/
public static final String ALIPAY_SIGN_MIN = "alipaySignMin";
/**
* 银联一档(>1000贷记卡费率
*/
public static final String CREDIT_RATE_1 = "creditRate1";
/**
* 银联一档(>1000贷记卡封底.(单位:分)
*/
public static final String CREDIT_MIN_1 = "creditMin1";
/**
* 银联一档(>1000借记卡费率
*/
public static final String DEBIT_RATE_1 = "debitRate1";
/**
* 银联一档(>1000借记卡封底单位
*/
public static final String DEBIT_MIN_1 = "debitMin1";
/**
* 银联一档(>1000借记卡封顶单位
*/
public static final String DEBIT_MAX_1 = "debitMax1";
/**
* 银联二档(<=1000贷记卡费率
*/
public static final String CREDIT_RATE_2 = "creditRate2";
/**
* 银联二档(<=1000贷记卡封底单位
*/
public static final String CREDIT_MIN_2 = "creditMin2";
/**
* 银联二档(<=1000借记卡费率
*/
public static final String DEBIT_RATE_2 = "debitRate2";
/**
* 银联二档(<=1000借记卡封底单位
*/
public static final String DEBIT_MIN_2 = "debitMin2";
/**
* 银联二档(<=1000借记卡封顶单位
*/
public static final String DEBIT_MAX_2 = "debitMax2";
/**
* 是否开通刷卡业务
*/
public static final String OPEN_POS_P = "openPosp";
/* 以下为T1 */
/**
* 工作日到账-借记卡费率
*/
public static final String T_111_RATE = "t111Rate";
/**
* 工作日到账-借记卡费率封顶(单位:分)
*/
public static final String T_111_RATE_TOP = "t111RateTop";
/**
* 工作日到账-借记卡费率封底(单位:分)
*/
public static final String T_111_SIGN_RATE_MIN = "t111SignRateMin";
/**
* 工作日到账-贷记卡费率
*/
public static final String T_112_RATE = "t112Rate";
/**
* 工作日到账-贷记卡费率封底(单位:分)
*/
public static final String T_112_SIGN_RATE_MIN = "t112SignRateMin";
/* 以下为D1 */
/**
* 天天到账-借记卡费率
*/
public static final String T_11_RATE = "t11Rate";
/**
* 天天到账-借记卡费率封顶(单位:分)
*/
public static final String T_11_RATE_TOP = "t11RateTop";
/**
* 天天到账-借记卡费率封底(单位:分)
*/
public static final String T_11_SIGN_RATE_MIN = "t11SignRateMin";
/**
* 天天到账-贷记卡费率
*/
public static final String T_12_RATE = "t12Rate";
/**
* 天天到账-贷记卡费率封底(单位:分)
*/
public static final String T_12_SIGN_RATE_MIN = "t12SignRateMin";
/**
* 天天到账-垫资费类型(百分比、元)
*/
public static final String T_ADVANCE_TYPE = "tAdvanceType";
/**
* 天天到账-垫资费
*/
public static final String T_ADVANCE_FEE = "tAdvanceFee";
/**
* 天天到账-垫资费封底(单位:分)
*/
public static final String T_ADVANCE_MIN = "tAdvanceMin";
/* 以下为D0 */
/**
* 实时到账-借记卡费率
*/
public static final String D_011_RATE = "d011Rate";
/**
* 实时到账-借记卡费率封顶(单位:分)
*/
public static final String D_011_RATE_TOP = "d011RateTop";
/**
* 实时到账-借记卡费率最低(单位:分)
*/
public static final String D_011_RATE_BOTTOM = "d011RateBottom";
/**
* 实时到账-贷记卡费率
*/
public static final String D_012_RATE = "d012Rate";
/**
* 实时到账-贷记卡费率最低(单位:分)
*/
public static final String D_012_RATE_BOTTOM = "d012RateBottom";
/**
* 实时到账-借记卡签约费率垫资费类型(百分比;元)
*/
public static final String D_0_ADVANCE_J_SIGN_TYPE = "d0AdvanceJsignType";
/**
* 实时到账-借记卡签约费率垫资费
*/
public static final String D_0_ADVANCE_J_SIGN_FEE = "d0AdvanceJsignFee";
/**
* 实时到账-借记卡签约费率垫资费封底(单位:分)
*/
public static final String D_0_ADVANCE_J_SIGN_MIN = "d0AdvanceJsignMin";
/**
* 实时到账-借记卡签约费率垫资费封顶(单位:分)
*/
public static final String D_0_ADVANCE_J_SIGN_MAX = "d0AdvanceJsignMax";
/**
* 实时到账-贷记卡签约费率垫资费类型(百分比;元)
*/
public static final String D_0_ADVANCE_D_SIGN_TYPE = "d0AdvanceDsignType";
/**
* 实时到账-贷记卡签约费率垫资费
*/
public static final String D_0_ADVANCE_D_SIGN_FEE = "d0AdvanceDsignFee";
/**
* 实时到账-贷记卡签约费率垫资费封底(单位:分)
*/
public static final String D_0_ADVANCE_D_SIGN_MIN = "d0AdvanceDsignMin";
/**
* 实时到账-贷记卡签约费率垫资费封顶(单位:分)
*/
public static final String D_0_ADVANCE_D_SIGN_MAX = "d0AdvanceDsignMax";
/**
* 是否开通扫码快付
*/
public static final String CODE_ADVANCE_OPEN = "codeAdvanceOpen";
/**
* 是否开通快付
*/
public static final String FAST_PAY = "fastPay";
/**
* 到账方式, 开通刷卡业务时必填
*/
public static final String OPEN_BUS_RADIO = "openBusRadio";
/**
* 是否法人结算
*/
public static final String CODE_LEGAL_PERSON_ACC = "codeLegalPersonAcc";
/**
* 垫资费费率
*/
public static final String CODE_ADVANCE_RATE = "codeAdvanceRate";
/**
* 垫资费费率最低值(单位:分)
*/
public static final String CODE_ADVANCE_MIN = "codeAdvanceMin";
/**
* 银盛商户类型
*/
public static final String MCC_SUB_CD = "mccSubCd";
/**
* MCC 码
*/
public static final String MCC_CD = "mccCd";
/**
* 代理商编号
*/
public static final String CO_OPERATOR_NO = "coOperatorNo";
/**
* 代理商编号
*/
public static final String INDUSTRY = "industry";
/**
* 扫码报备所需商户类型
*/
public static final String MCH_TYPE = "mchtype";
/**
* 扫码报备所需商户类别
*/
public static final String MCH_CATEGORY = "mchcategory";
/**
* 法人国籍
*/
public static final String CRP_NATIONALITY = "crpNationality";
/**
* 法人性别
*/
public static final String CRP_GENDER = "crpGender";
/**
* 法人职业
*/
public static final String CRP_PROFESSION = "crpProfession";
/**
* 法人地址
*/
public static final String CRP_ADDR = "crpAddr";
/**
* 法人姓名
*/
public static final String CRP_NAME = "crpNm";
/**
* 证件有效期
*/
public static final String CERT_EXPIRE = "certExpire";
public static final String NOTIFY_URL = "notifyUrl";
/**
* 商户模式
*/
public static final String USER_TYPE = "userType";
/**
* 备注
*/
public static final String REMARK = "remark";
/**
* 结算起始金额
*/
public static final String LOWEST_STL_AMT = "lowestStlAmt";
/**
* 银行预留手机号
*/
public static final String BANK_MOBILE = "bankMobile";
/**
* 实际控制人
*/
public static final String ACTUAL_MANAGER = "actualManager";
/**
* 证件类型
*/
public static final String CERT_TYPE = "certType";
/**
* 证件类型
*/
public static final String MERC_LVL = "mercLvl";
/**
* 总店商户号
*/
public static final String MERC_UP_ID = "mercUpId";
/**
* 联系人通讯地址
*/
public static final String CONTACTS_ADDR = "contactsAddr";
/**
* 结算卡类型
*/
public static final String BALANCE_ACC_TYPE = "balanceAccType";
/**
* 拓展经理姓名
*/
public static final String EXPANDING_MANAGER = "expandingManager";
// ================ 以下为线上交易权限开通的接口参数名 ================
/**
* 商户号
*/
public static final String MERC_ID = "mercId";
/**
* 接入机构号
*/
public static final String ACC_ORG_NO = "accOrgNo";
/**
* 交易权限
*/
public static final String SCAN_SERVICE_OPEN = "scanServiceOpen";
/**
* 费率信息
*/
public static final String EASY_FEE_BEAN = "easyFeeBean";
/**
* 微信费率类型
* 必填 1 百分比2 固定金额
*/
public static final String R_SCAN_WX_FEE_TYPE = "rscanWxFeeType";
/**
* rscanWxFeeType 为 1时 必填
* 示例 0.3 表示 0.003
*/
public static final String R_SCAN_WX_FEE_RATE = "rscanWxFeeRate";
/**
* 微信费率金额
* 单位:分
* rscanWxFeeType 为 1 时为封底金额
* rscanWxFeeType 为 2 时为固定金额
*/
public static final String R_SCAN_WX_FEE_NUM = "rscanWxFeeNum";
/**
* 支付宝费率,同微信
*/
public static final String R_SCAN_ALI_FEE_TYPE = "rscanAliFeeType";
public static final String R_SCAN_ALI_FEE_RATE = "rscanAliFeeRate";
public static final String R_SCAN_ALI_FEE_NUM = "rscanAliFeeNum";
/**
* 银联借记卡一档费率类型
* 1 百分比2 固定金额
*/
public static final String R_SCAN_DEBIT_TYPE_1 = "rscanDebitType1";
/**
* 银联借记卡一档金额
* rscanDebitType1 为 1 时为借记卡一档费率,示例 0.3 表示 0.003
* rscanDebitType1 为 2 时为固定金额 单位:分
*/
public static final String R_SCAN_DEBIT_NUM_1 = "rscanDebitNum1";
/**
* 银联借记卡一档金额封底金额
* 单位:分
* rscanDebitType1为1 必填
*/
public static final String R_SCAN_DEBIT_MIN_1 = "rscanDebitMin1";
/**
* 银联借记卡一档金额封顶金额
* 单位:分
* rscanDebitType1为1, 必填
*/
public static final String R_SCAN_DEBIT_MAX_1 = "rscanDebitMax1";
/**
* 银联借记卡二档费率类型
* 1、百分比; 2、固定金额
*/
public static final String R_SCAN_DEBIT_TYPE_2 = "rscanDebitType2";
/**
* 银联借记卡二档金额
* rscanDebitType2为1时为借记卡一档费率示例 0.3表 示 0.003;
* rscanDebitType2为2时为固定金额 单位:分
*/
public static final String R_SCAN_DEBIT_NUM_2 = "rscanDebitNum2";
/**
* 银联借记卡二档金额封底金额
* 单位:分
* rscanDebitType2为1,必填
*/
public static final String R_SCAN_DEBIT_MIN_2 = "rscanDebitMin2";
/**
* 银联借记卡二档金额封顶金额
* 单位:分
* rscanDebitType2 为 1 必填
*/
public static final String R_SCAN_DEBIT_MAX_2 = "rscanDebitMax2";
/**
* 银联借记卡二档金额封顶金额
* 单位:分
* rscanDebitType2 为 1 必填
*/
public static final String R_SCAN_CREDIT_TYPE_1 = "rscanCreditType1";
/**
* 银联贷记卡 一档金额(>1000)
* rscanCreditType1 为 1 时为借记卡一 档费率,示例 0.3 表示 0.003 rscanCreditType1 为 2 时为固定金额 单位:分
*/
public static final String R_SCAN_CREDIT_NUM_1 = "rscanCreditNum1";
/**
* 银联贷记卡 一档金额封底金额
* 单位:分
* rscanCreditType1 为 1 必填
*/
public static final String R_SCAN_CREDIT_MIN_1 = "rscanCreditMin1";
/**
* 银联贷记卡 二档费类型
* 1 百分比 2 固定金额
*/
public static final String R_SCAN_CREDIT_TYPE_2 = "rscanCreditType2";
/**
* 银联贷记卡 二档金额
* rscanCreditType2 为 1 时为借记卡一 档费率,示例 0.3 表示 0.003;
* rscanCreditType2 为 2 时为固定金额 单位:分
*/
public static final String R_SCAN_CREDIT_NUM_2 = "rscanCreditNum2";
/**
* 银联贷记卡 二档金额封底金额
* 单位:分 rscanCreditType2 为 1 必填
*/
public static final String R_SCAN_CREDIT_MIN_2 = "rscanCreditMin2";
}