Скрипт глобальный отмены перехода на тарифы при неоплате
Материал из BiTel WiKi
Версия от 08:48, 10 декабря 2009; DimOn (Обсуждение | вклад)
import bitel.billing.server.util.*; import bitel.billing.server.contract.bean.*; import java.sql.*; import java.math.*; import bitel.billing.server.admin.eventbus.*; import bitel.billing.server.admin.eventbus.event.*; /* Условие перевода на данный тариф - наличие полной оплаты за предыдущий месяц. К примеру выставлен новый тариф с 01.11.09, значит надо 1 ноября проверить баланс: исходящее сальдо на конец октября должно быть (по модулю) меньше или равно сумме наработки и расхода за октябрь. Если это условие не выполняется, то перевод на новый тариф аннулируется. Желательно с сохранением истории. */ /* Исходящий остаток ноября если брать, то он будет включать наработку и расход ноября, обязятельства по оплате которых наступают только в конце декабря. Нам нужно, чтобы октябрь был оплачен полностью. ноябрь 2009 Входящий остаток на начало месяца -11617.05 ноябрь 2009 Приход за месяц 11617.05 ноябрь 2009 Наработка за месяц 11005.54 ноябрь 2009 Расход за месяц 0.00 ноябрь 2009 Исходящий остаток на конец месяца -11005.54 сальдо на 1 ноября + платежи ноября= -11617,05+11617,05=0 */ /** если стоит флаг, то работа в тестовом режиме - только пишется что сделано, но по факту не делается - не удаляется дата платежа, не удаляется тариф и т.п.*/ final static boolean IS_TEST = true; /** комментарий, который прибавляется к предыдущему тарифу, в случае отмены перехода на новый */ final static String CANCEL_COMMENT = "Отмена перевода на тариф \"%s\", невыполнение условий тарифа."; /** список id тарифов, на которые действует скрипт. в кавычках, через запятую */ final static String TARIFFS = "25,1,2"; public void main( setup, con, conSlave ) { print( "запуск скрипта..." ); BalanceUtils balanceManager = new BalanceUtils( con ); ContractTariffManager contractTariffManager = new ContractTariffManager( con ); // вычисляем даты , начало месяца и предыдущий день Calendar curMonthBegin = new GregorianCalendar(); curMonthBegin.set( Calendar.DATE, curMonthBegin.getActualMinimum( Calendar.DATE ) ); Calendar prevMonthEnd = curMonthBegin.clone(); prevMonthEnd.add( Calendar.DATE, -1 ); print( "текущее начало месяца: " + TimeUtils.formatDate( curMonthBegin ) + ", конец предыдущего месяца: " + TimeUtils.formatDate( prevMonthEnd ) ); // делаем запрос всех договоров, у которых сегодня начинается новый тариф String query = "SELECT `contract_tariff`.*, `contract`.`title` as contract_title, `tariff_plan`.`title` as tariff_plan_title "+ "FROM `contract_tariff` "+ "LEFT JOIN `contract` ON `contract`.`id`=`contract_tariff`.`cid` "+ "LEFT JOIN `tariff_plan` ON `tariff_plan`.`id`=`contract_tariff`.`tpid` "+ "WHERE `contract_tariff`.`date1`=? AND `tariff_plan`.`id` in ("+TARIFFS+")"; PreparedStatement ps = con.prepareStatement( query ); ps.setDate( 1, TimeUtils.convertDateToSqlDate( curMonthBegin.getTime() ) ); ResultSet rs = ps.executeQuery(); while( rs.next() ) { // получаем данные о конкретном догогоре int id=rs.getInt("id"); int cid=rs.getInt("cid"); String contractTitle=rs.getString("contract_title"); String comment=rs.getString("comment"); String tariffTitle=rs.getString("tariff_plan_title"); print("=> договор '"+contractTitle+"' хочет " + TimeUtils.formatDate( curMonthBegin ) + " изменить тариф на '"+tariffTitle+"' (комментарий тарифа договора: '"+comment+"')"); // ищем "предыдущий" тариф, тот у которого вчера закончился срок int id_prev=-1; String query2 = "SELECT `contract_tariff`.*, `tariff_plan`.`title` as tariff_plan_title "+ "FROM `contract_tariff` "+ "LEFT JOIN `tariff_plan` ON `tariff_plan`.`id`=`contract_tariff`.`tpid` "+ "WHERE `contract_tariff`.`date2`=? AND `contract_tariff`.`cid`=?"; PreparedStatement ps2 = con.prepareStatement( query2 ); ps2.setDate( 1, TimeUtils.convertDateToSqlDate( prevMonthEnd.getTime() ) ); ps2.setInt( 2, cid ); ResultSet rs2 = ps2.executeQuery(); if( rs2.next() ) { id_prev=rs2.getInt("id"); print( "найден предыдуший тариф - '"+rs2.getString("tariff_plan_title")+"', заканчивающийся "+TimeUtils.formatDate( prevMonthEnd )+"." ); } else { print( "внимание! не найдено предыдущего тарифа, заканчивающегося "+TimeUtils.formatDate( prevMonthEnd )+". Ничего не будем делать." ); continue; } // если есть ещё один такой же - пишем, что произошёл казус if( rs2.next() ) { print( "внимание! существует как минимум ещё один тариф - '"+rs2.getString("tariff_plan_title")+"', заканчивающийся "+TimeUtils.formatDate( prevMonthEnd )+". ничего не будем делать." ); continue; } rs2.close(); ps2.close(); // проверяем условие для смены тарифа BigDecimal summa1 = balanceManager.getBalanceSumma1( prevMonthEnd.getTime(), cid ); print( "входящий остаток : " + summa1.toPlainString() ); BigDecimal saldo = balanceManager.getSaldo( prevMonthEnd.getTime(), cid ); print( "входящий остаток + приход : " + saldo.toPlainString() ); // если условие выполняется - ничего не делаем if( saldo.compareTo( BigDecimal.ZERO ) >= 0 ) //TODO { print( "условие выполняется, ничего не делаем." ); } // иначе - отменяем else { print( "внимание! условие не выполняется, отменяем переход." ); // удаляем тариф print( "удаляем новый тариф '"+tariffTitle+"' из contract_tariff{id='"+id+"'}..." ); if( !IS_TEST ) { contractTariffManager.deleteContractTariff( id ); } // правим предыдущий print( "правим предыдущий тариф из contract_tariff{id='"+id_prev+"'}..." ); ContractTariff contractTariff = contractTariffManager.getContractTariffByID( id_prev ); contractTariff.setDate2( null ); contractTariff.setComment( contractTariff.getComment()+CANCEL_COMMENT.replaceAll("%s",tariffTitle) ); if( !IS_TEST ) { contractTariffManager.updateContractTariff( contractTariff ); } // на всякий случай BillingEventBus.publish( new TariffChangedEvent( cid ) ); } } rs.close(); ps.close(); }
сделано для 4.6, вешается на глобальный тариф, запускается в начале месяца.
--dimOn 08:48, 10 декабря 2009 (UTC)