230 lines
9.8 KiB
Java
230 lines
9.8 KiB
Java
package com.tenwa.reckon.executor;
|
||
|
||
import java.math.BigDecimal;
|
||
import java.util.ArrayList;
|
||
import java.util.List;
|
||
|
||
import com.amarsoft.are.jbo.JBOTransaction;
|
||
import com.tenwa.comm.exception.BusinessException;
|
||
import com.tenwa.reckon.bean.ConditionBean;
|
||
import com.tenwa.reckon.bean.FundRentPlanBean;
|
||
import com.tenwa.reckon.bean.KnowingConfigBean;
|
||
import com.tenwa.reckon.bean.SubsectionBean;
|
||
import com.tenwa.reckon.bean.TabCalBean;
|
||
import com.tenwa.reckon.help.CalYearRateFromRent;
|
||
import com.tenwa.reckon.util.DateUtil;
|
||
import com.tenwa.reckon.util.DictTools;
|
||
|
||
public class EvenSubsectionExecutor extends FundRentPlanExecutor {
|
||
|
||
public EvenSubsectionExecutor(JBOTransaction tx) {
|
||
super(tx);
|
||
}
|
||
|
||
|
||
@Override
|
||
public FundRentPlanBean create(TabCalBean tcb,Integer startList) throws Exception {
|
||
FundRentPlanBean fpb = new FundRentPlanBean();
|
||
//删除租金计划
|
||
this.deleteRentPlan(tcb.getRentPlan_tb(), tcb, startList);
|
||
this.getPmtRentPlan(tcb.getCb(), fpb,tcb);
|
||
this.addRentPlan(fpb, tcb, startList);
|
||
return fpb;
|
||
}
|
||
|
||
|
||
public void getPmtRentPlan(ConditionBean cb, FundRentPlanBean frpb,TabCalBean tcb) throws Exception {
|
||
|
||
List<SubsectionBean> list=tcb.getSubsections();
|
||
FundRentPlanExecutor executor;
|
||
BigDecimal cleanLeaseMoney=new BigDecimal(cb.getCleanLeaseMoney());//融资额
|
||
int incomeNumber=cb.getIncomeNumber();
|
||
String startDate=cb.getStartDate();//开始日期
|
||
int leaseTerm=0;//租赁期限
|
||
for(int i=0;i<list.size();i++){
|
||
|
||
SubsectionBean sub=list.get(i);
|
||
if(cleanLeaseMoney.compareTo(BigDecimal.ZERO)<=0){
|
||
throw new BusinessException("开始期次:"+sub.startList+",该段前测算条件已回笼所有融资额,请检查测算规则再进行测算!");
|
||
}
|
||
if(incomeNumber==sub.getEndList()&&sub.getAppointMoney()!=null&&sub.getAppointMoney().length()>0){
|
||
if(sub.getSettleMethod().equals("even_corpus")){
|
||
if("appoint_type.1".equals(sub.getAppointType())){//指定每期本金
|
||
if(cleanLeaseMoney.compareTo(new BigDecimal(sub.getEndList()-sub.getStartList()+1).multiply(new BigDecimal(sub.getAppointMoney())))!=0)
|
||
{
|
||
throw new BusinessException("最后一期指定本金总和必须等于剩余融资额("+cleanLeaseMoney+")");
|
||
}
|
||
}else if("appoint_type.4".equals(sub.getAppointType())){//指定偿还本金
|
||
if(cleanLeaseMoney.compareTo(new BigDecimal(sub.getAppointMoney()))!=0){
|
||
throw new BusinessException("最后一期指定偿还本金必须等于剩余融资额("+cleanLeaseMoney+")");
|
||
}
|
||
}else{
|
||
if(new BigDecimal(sub.getAppointMoney()).compareTo(BigDecimal.ZERO)!=0){
|
||
throw new BusinessException("最后一期指定剩余本金必须等于0");
|
||
}
|
||
}
|
||
}else{
|
||
if("appoint_type.2".equals(sub.getAppointType())){//指定每期本金
|
||
if(cleanLeaseMoney.compareTo(new BigDecimal(sub.getEndList()-sub.getStartList()+1).multiply(new BigDecimal(sub.getAppointMoney())))>0)
|
||
{
|
||
throw new BusinessException("最后一期指定租金总和必须大于等于剩余融资额("+cleanLeaseMoney+")");
|
||
}
|
||
}
|
||
}
|
||
}else if(sub.getAppointMoney()!=null&&sub.getAppointMoney().length()>0){//不是最后一期 指定金额校验
|
||
if(sub.getSettleMethod().equals("even_corpus")){
|
||
if("appoint_type.1".equals(sub.getAppointType())){//指定每期本金
|
||
if(cleanLeaseMoney.compareTo(new BigDecimal(sub.getEndList()-sub.getStartList()+1).multiply(new BigDecimal(sub.getAppointMoney())))<=0)
|
||
{
|
||
throw new BusinessException("不是最后一期指定本金总和小于剩余融资额("+cleanLeaseMoney+")");
|
||
}
|
||
}else if("appoint_type.4".equals(sub.getAppointType())){//指定偿还本金
|
||
if(cleanLeaseMoney.compareTo(new BigDecimal(sub.getAppointMoney()))<=0){
|
||
throw new BusinessException("不是最后一期指定偿还本金必须小于剩余融资额("+cleanLeaseMoney+")");
|
||
}
|
||
}else{
|
||
if(new BigDecimal(sub.getAppointMoney()).compareTo(cleanLeaseMoney)>=0){
|
||
throw new BusinessException("不是最后一期指定剩余本金必须小于剩余融资额("+cleanLeaseMoney+")");
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
ConditionBean cbNew=(ConditionBean)cb.clone();
|
||
String settleMethod=sub.getSettleMethod();
|
||
if (settleMethod.equals("even_interest")) {
|
||
executor = new EvenInterestExecutor(tx);
|
||
} else if (settleMethod.equals("even_corpus")) {
|
||
executor = new EvenCorpusExecutor(tx);
|
||
}else if(settleMethod.equals("even_rent_day")){
|
||
executor=new EvenRentDayExecutor(tx);
|
||
}else if(settleMethod.equals("even_subsection")){
|
||
executor=new EvenSubsectionExecutor(tx);
|
||
} else {
|
||
executor = new EvenRentExecutor(tx);
|
||
}
|
||
//******************************************重新封装 测算条件 开始
|
||
cbNew.setCleanLeaseMoney(cleanLeaseMoney.toString());//融资额
|
||
cbNew.setSettleMethod(settleMethod);//测算方法
|
||
if(settleMethod.equals("even_interest")&&incomeNumber!=sub.getEndList()){
|
||
throw new BusinessException("均息法只支持最后一段!");
|
||
}
|
||
if(settleMethod.equals("even_rent")||settleMethod.equals("even_rent_day")||settleMethod.equals("even_interest")){//等额租金 等额本金按日利率
|
||
if(sub.getAppointType()!=null&&sub.getAppointType().length()>0){
|
||
cbNew.setRentOrRate("rent");//按租金算年利率
|
||
cbNew.setRentValue(sub.getAppointMoney());//每期租金
|
||
}else{
|
||
cbNew.setRentOrRate("rate");//按利率
|
||
cbNew.setYearRate(sub.getAppointRate());//年利率
|
||
}
|
||
|
||
cbNew.setIncomeNumber(incomeNumber-sub.getStartList()+1);//期数
|
||
cbNew.setLastPlanDayRate(false);
|
||
}else if(settleMethod.equals("even_corpus")){//等额本金
|
||
if(sub.getAppointType()!=null&&sub.getAppointType().length()>0){
|
||
BigDecimal corpus=BigDecimal.ZERO;//每期本金
|
||
BigDecimal corpus2=cleanLeaseMoney;//如果不是最后一段 在最后一期后面加一期本金 避免最后一期被调整
|
||
BigDecimal corpus3=BigDecimal.ZERO;//调整改段最后一期本金
|
||
int incomeNumber2=sub.getEndList()-sub.getStartList()+1;//期数
|
||
if("appoint_type.1".equals(sub.getAppointType())){//指定每期本金
|
||
corpus=new BigDecimal(sub.getAppointMoney());
|
||
corpus3=new BigDecimal(sub.getAppointMoney());
|
||
}else if("appoint_type.4".equals(sub.getAppointType())){//指定偿还本金
|
||
corpus=new BigDecimal(sub.getAppointMoney()).divide(new BigDecimal(incomeNumber2),2,BigDecimal.ROUND_HALF_UP);
|
||
corpus3=new BigDecimal(sub.getAppointMoney()).subtract(corpus.multiply(new BigDecimal(incomeNumber2-1)));
|
||
}else{
|
||
corpus=cleanLeaseMoney.subtract(new BigDecimal(sub.getAppointMoney())).divide(new BigDecimal(incomeNumber2),2,BigDecimal.ROUND_HALF_UP);
|
||
corpus3=cleanLeaseMoney.subtract(new BigDecimal(sub.getAppointMoney())).subtract(corpus.multiply(new BigDecimal(incomeNumber2-1)));
|
||
}
|
||
corpus2=corpus2.subtract(corpus.multiply(new BigDecimal(incomeNumber2)));
|
||
|
||
|
||
cbNew.setRentOrRate("knowing_corpus");//已知本金规则
|
||
List<KnowingConfigBean> knowingConfigs=new ArrayList<KnowingConfigBean>();
|
||
KnowingConfigBean config=new KnowingConfigBean();
|
||
config.setStartList(1);
|
||
config.setEndList(sub.getEndList()-sub.getStartList());
|
||
config.setPlanMoney(corpus);
|
||
knowingConfigs.add(config);
|
||
|
||
KnowingConfigBean config3=new KnowingConfigBean();
|
||
config3.setStartList(sub.getEndList()-sub.getStartList()+1);
|
||
config3.setEndList(sub.getEndList()-sub.getStartList()+1);
|
||
config3.setPlanMoney(corpus3);
|
||
knowingConfigs.add(config3);
|
||
|
||
cbNew.setIncomeNumber(sub.getEndList()-sub.getStartList()+1);//期数
|
||
if(incomeNumber!=sub.getEndList()){
|
||
//补最后期本金
|
||
KnowingConfigBean config2=new KnowingConfigBean();
|
||
config2.setStartList(sub.getEndList()-sub.getStartList()+2);
|
||
config2.setEndList(sub.getEndList()-sub.getStartList()+2);
|
||
config2.setPlanMoney(corpus2);
|
||
knowingConfigs.add(config2);
|
||
cbNew.setIncomeNumber(sub.getEndList()-sub.getStartList()+2);//期数
|
||
}
|
||
|
||
tcb.setKnowingConfigs(knowingConfigs);//已知规则
|
||
cbNew.setYearRate(sub.getAppointRate());//年利率
|
||
}else{
|
||
cbNew.setRentOrRate("rate");//按租金算年利率
|
||
cbNew.setYearRate(sub.getAppointRate());//年利率
|
||
cbNew.setIncomeNumber(incomeNumber-sub.getStartList()+1);//期数
|
||
}
|
||
|
||
cbNew.setLastPlanDayRate(false);
|
||
}
|
||
//宽限期
|
||
int grace=cb.getGrace();
|
||
int startList=sub.getStartList();
|
||
cbNew.setIncomeNumberYear(sub.getIncomeNumberYear());//还款间隔
|
||
cbNew.setIncomeIntervalMonth(sub.getIncomeIntervalMonth());//还款间隔(月)
|
||
cbNew.setStartDate(startDate);//起租日
|
||
if(sub.getStartList()>1){
|
||
startList+=grace;
|
||
grace=0;
|
||
cbNew.setGrace(0);//宽限期
|
||
cbNew.setPeriodType("period_type_0");
|
||
cbNew.setFirstPlanDate(DateUtil.addDate(startDate,DateUtil.TIME_MONTH, sub.getIncomeIntervalMonth()));//第一期计划还款日
|
||
cbNew.setSecondPlanDate(DateUtil.addDate(startDate,DateUtil.TIME_MONTH, sub.getIncomeIntervalMonth()*2));//第二期计划还款日
|
||
}
|
||
int leaseTerm2=sub.getIncomeIntervalMonth()*(sub.getEndList()-sub.getStartList()+1);
|
||
|
||
cbNew.setLeaseTerm(leaseTerm2);//租赁期限
|
||
|
||
|
||
CalYearRateFromRent calYearRate = CalYearRateFromRent.getInstance();
|
||
calYearRate.calDo(cbNew,tcb);
|
||
tcb.setCb(cbNew);
|
||
DictTools.setYearRate(tcb);
|
||
DictTools.getReversDict(cbNew);
|
||
//******************************************重新封装 测算条件 结束
|
||
|
||
FundRentPlanBean rentPlan=executor.create(tcb,startList);
|
||
//生成
|
||
leaseTerm+=leaseTerm2;
|
||
List<String> corpus=rentPlan.getCorpusBusinessList();
|
||
List<String> dateList=rentPlan.getPlanDateList();
|
||
for(int planlist=0;planlist<sub.getEndList()-sub.getStartList()+1+grace;planlist++){
|
||
cleanLeaseMoney=cleanLeaseMoney.subtract(new BigDecimal(corpus.get(planlist)));
|
||
}
|
||
if(sub.getStartList()==1){
|
||
startDate=dateList.get(sub.getEndList()-sub.getStartList()+grace);
|
||
}else{
|
||
startDate=dateList.get(sub.getEndList()-sub.getStartList());
|
||
}
|
||
if(sub.getStartList()==1&&sub.getEndList()>=2){
|
||
cb.setFirstPlanDate(dateList.get(0));
|
||
cb.setSecondPlanDate(dateList.get(1));
|
||
}else if(sub.getStartList()==1){
|
||
cb.setFirstPlanDate(dateList.get(0));
|
||
}else if(sub.getStartList()==2){
|
||
cb.setSecondPlanDate(dateList.get(0));
|
||
}
|
||
}
|
||
cb.setLeaseTerm(leaseTerm);
|
||
tcb.setCb(cb);
|
||
}
|
||
|
||
}
|