/**
  * Runs the migration action
  */
 public function run()
 {
     $this->legacyContainer = new LegacyContainer();
     $searchClient = $this->legacyContainer->get('rrp.legacy.datasource.search');
     $policyNumberManager = $this->legacyContainer->get('rrp.legacy.manager.policy_number');
     $this->policyNotes = $this->legacyContainer->get('rrp.legacy.datasource.policy_notes');
     $this->rates = $this->legacyContainer->get('rrp.legacy.datasource.rrp_rates');
     $renewalInvitePeriod = $this->legacyContainer->get('rrp.config.renewal_invite_period');
     $insightStatusInsight = $this->legacyContainer->get('rrp.legacy.const.insight_status_insight');
     $insightStatusException = $this->legacyContainer->get('rrp.legacy.const.insight_status_exception');
     $policyOptionRrp = $this->legacyContainer->get('rrp.legacy.const.policy_option_rrp');
     $policyOptionRrpNilExcess = $this->legacyContainer->get('rrp.legacy.const.policy_option_rrp-nilexcess');
     $this->customerAddress1 = $this->legacyContainer->get('rrp.legacy.const.customer_address1');
     $this->customerAddress2 = $this->legacyContainer->get('rrp.legacy.const.customer_address2');
     $this->customerAddress3 = $this->legacyContainer->get('rrp.legacy.const.customer_address3');
     $this->customerAgent = $this->legacyContainer->get('rrp.legacy.const.customer_agent');
     $this->customerLegacyIdentifier = $this->legacyContainer->get('rrp.legacy.const.customer_legacy_identifier');
     $this->statusPolicy = $this->legacyContainer->get('rrp.legacy.const.status_policy');
     $this->underwritingQuestionSetID = $this->legacyContainer->get('rrp.config.underwriting_question_set_id');
     $this->riskArea = $this->legacyContainer->get('rrp.config.risk_area');
     $this->iptPercent = $this->legacyContainer->get('rrp.config.ipt_percent');
     $this->payStatusReferred = $this->legacyContainer->get('rrp.legacy.const.pay_status_referred');
     $this->payStatusUpToDate = $this->legacyContainer->get('rrp.legacy.const.pay_status_up-to-date');
     $this->rrpContainer = new RRPContainer();
     $now = new \DateTime();
     $renewalDate = $now;
     $renewalDate->add(new \DateInterval($renewalInvitePeriod));
     $dateString = $now->format('Y-m-d H:i:s');
     $referral = new RentRecoveryPlusReferral();
     // Initialise the report data
     $this->initialiseReportData();
     // Send assumptive renewals
     $isRenewalInvite = false;
     $policyList = $searchClient->searchForInsightByEndDate($renewalDate, $insightStatusInsight, $isRenewalInvite);
     /** @var \RRP\Application\Decorators\RentRecoveryPlusInsight $insightPolicy */
     $insightPolicy = ApplicationDecoratorFactory::getDecorator('RentRecoveryPlusInsight');
     foreach ($policyList as $rrpPolicyNumber) {
         if (!$insightPolicy->populateByPolicyNumber($rrpPolicyNumber)) {
             $this->addToReport(self::POLICY_TYPE_EXCEPTION, $rrpPolicyNumber);
         } else {
             $newPolicyNumber = $policyNumberManager->generateApplicationNumber($policyNumberManager::POLICY_IDENTIFIER);
             if ($insightPolicy->getAppData()->getAgentRateSetID() === null) {
                 $isReferralRequired = true;
             } else {
                 $propertyRental = PolicyOptionsManager::getOption($insightPolicy->getAppData()->getPolicyOptions(), $policyOptionRrp, $insightPolicy->getAppData()->getAmountsCovered());
                 $isNilExcess = PolicyOptionsManager::isOptionSet($insightPolicy->getAppData()->getPolicyOptions(), $policyOptionRrpNilExcess, $insightPolicy->getAppData()->getAmountsCovered());
                 $rateDate = \DateTime::createFromFormat('Y-m-d', $insightPolicy->getAppData()->getEndDate());
                 $rateDate->add(new \DateInterval('P1D'));
                 try {
                     $rateManager = RateDecoratorFactory::getDecorator('RentRecoveryPlus', $insightPolicy->getAppData()->getAgentRateSetID(), $this->riskArea, $this->iptPercent, $propertyRental, $isNilExcess, $insightPolicy->getRrpData()->getReferenceType(), $insightPolicy->getAppData()->getPolicyLength(), $insightPolicy->getAppData()->isPayMonthly(), $rateDate);
                     $insightPolicy->setPolicyOptions($propertyRental, $rateManager->getPremium(), $rateManager->getNilExcessOption())->getAppData()->setPremium($rateManager->getPremium())->setIpt($rateManager->getIpt())->setQuote($rateManager->getQuote())->setRateSetID($rateManager->getRateSetID());
                     $referral->setFromRrpPolicy($insightPolicy->getRrpData(), $insightPolicy->getAllUnderwritingAnswers(), $now->format('Y-m-d'), $rateManager->getPremium(), $propertyRental, true);
                     $isReferralRequired = $referral->isReferralRequired();
                 } catch (\Exception $ex) {
                     error_log($ex->getMessage());
                     $isReferralRequired = true;
                 }
             }
             $policyNote = "Policy invite sent on renewal for previous Insight policy number {$rrpPolicyNumber}\n" . "Underwriting answers for 'Rent in advance', 'No claims logged' and 'Deposit sum'" . " are all assumed for migration from Insight but please check if a claim arises\n";
             try {
                 $this->migratePolicy($insightPolicy, $rrpPolicyNumber, $newPolicyNumber, $policyNumberManager::WHITE_LABEL_HOMELET, $dateString, $isReferralRequired, $referral->getReferralReason(), $policyNote, $isRenewalInvite);
             } catch (\Exception $ex) {
                 error_log($ex->getMessage());
                 $isReferralRequired = true;
             }
             if ($isReferralRequired) {
                 $this->addToReport(self::POLICY_TYPE_REFERRED, $rrpPolicyNumber, $newPolicyNumber);
             } else {
                 $this->addToReport(self::POLICY_TYPE_MIGRATED, $rrpPolicyNumber, $newPolicyNumber);
             }
         }
     }
     // Now do exceptions
     $policyList = $searchClient->searchForInsightByEndDate($now, $insightStatusException);
     foreach ($policyList as $rrpPolicyNumber) {
         $insightPolicy->populateByPolicyNumber($rrpPolicyNumber);
         $newPolicyNumber = $policyNumberManager->generateApplicationNumber($policyNumberManager::POLICY_IDENTIFIER);
         $insightPolicy->getAppData()->setPayStatus($this->legacyContainer->get('rrp.legacy.const.pay_status_referred'));
         $policyNote = 'Policy referred as it has changed in Insight since the data was migrated from previous Insight policy number ' . $rrpPolicyNumber;
         try {
             $this->migratePolicy($insightPolicy, $rrpPolicyNumber, $newPolicyNumber, $policyNumberManager::WHITE_LABEL_HOMELET, $dateString, true, $policyNote, $policyNote);
         } catch (\Exception $ex) {
             error_log($ex->getMessage());
         }
         $this->addToReport(self::POLICY_TYPE_EXCEPTION, $rrpPolicyNumber, $newPolicyNumber);
     }
     // Now send a report
     $this->sendReport();
 }
 /**
  * @inheritdoc
  */
 public function accept($policyNumber, $mtaId)
 {
     /** @var \RRP\Application\Decorators\RentRecoveryPlusPolicy $policy */
     $policy = ApplicationDecoratorFactory::getDecorator('RentRecoveryPlusPolicy');
     $policy->populateByPolicyNumber($policyNumber);
     $this->legacyMtaData = $this->legacyMta->getByMtaID($mtaId);
     $this->rrpMtaData = $this->rrpMta->getRentRecoveryPlusMta($mtaId);
     $proRataPremium = $policy->getAppData()->getPremium() + $this->legacyMtaData->getPremium();
     $proRataQuote = $policy->getAppData()->getQuote() + $this->legacyMtaData->getQuote();
     $proRataIpt = $policy->getAppData()->getIpt() + $this->legacyMtaData->getIpt();
     $propertyRental = PolicyOptionsManager::getOption($this->legacyMtaData->getPolicyOptions(), $this->getContainer()->get('rrp.legacy.const.policy_option_rrp'), $this->legacyMtaData->getAmountscovered());
     $isNilExcess = PolicyOptionsManager::isOptionSet($this->legacyMtaData->getPolicyOptions(), $this->getContainer()->get('rrp.legacy.const.policy_option_rrp-nilexcess'), $this->legacyMtaData->getAmountscovered());
     $policyPremium = PolicyOptionsManager::getOption($policy->getAppData()->getPolicyOptions(), $this->getContainer()->get('rrp.legacy.const.policy_option_rrp'), $policy->getAppData()->getOptionPremiums());
     $mtaPremium = PolicyOptionsManager::getOption($this->legacyMtaData->getPolicyOptions(), $this->getContainer()->get('rrp.legacy.const.policy_option_rrp'), $this->legacyMtaData->getOptionPremiums());
     $optionPremiums = PolicyOptionsManager::addPolicyOption($policyPremium + $mtaPremium);
     if ($isNilExcess) {
         $policyNilExcessOption = PolicyOptionsManager::getOption($policy->getAppData()->getPolicyOptions(), $this->getContainer()->get('rrp.legacy.const.policy_option_rrp-nilexcess'), $policy->getAppData()->getOptionPremiums());
         $mtaNilExcessOption = PolicyOptionsManager::getOption($this->legacyMtaData->getPolicyOptions(), $this->getContainer()->get('rrp.legacy.const.policy_option_rrp-nilexcess'), $this->legacyMtaData->getOptionPremiums());
         $optionPremiums = PolicyOptionsManager::addPolicyOption($policyNilExcessOption + $mtaNilExcessOption, $optionPremiums);
     }
     $policy->getAppData()->setPolicyOptions($this->legacyMtaData->getPolicyOptions())->setAmountsCovered($this->legacyMtaData->getAmountscovered())->setOptionPremiums($optionPremiums)->setPremium($proRataPremium)->setQuote($proRataQuote)->setIpt($proRataIpt);
     $policy->getRrpData()->setClaimInfo($this->rrpMtaData->getClaimInfo());
     $disbData = $this->disbursement->getDisbursement($policy->getAppData()->getWhiteLabelID(), $policy->getAppData()->getRateSetID());
     if (!$disbData) {
         $message = sprintf('Disbursement data not found (WhiteLabelId = %s, RateSetID = %d)', $policy->getAppData()->getWhiteLabelID(), $policy->getAppData()->getRateSetID());
         throw new \RuntimeException($message);
     }
     $getter = sprintf('getRrpi%s%dm', ReferenceTypes::isFullReference($policy->getRrpData()->getReferenceType()) ? 'FullRef' : 'CreditCheck', $policy->getAppData()->getPolicyLength());
     if ($isNilExcess) {
         $getter .= '0xs';
     }
     if (!method_exists($disbData, $getter)) {
         $message = sprintf('Unknown disbursement type (%s)', $getter);
         throw new \RuntimeException($message);
     }
     $disbursement = $disbData->{$getter}();
     if (empty($disbursement)) {
         $message = sprintf('Disbursement data not set (WhiteLabelId = %s, RateSetID = %d, %s)', $policy->getAppData()->getWhiteLabelID(), $policy->getAppData()->getRateSetID(), $getter);
         throw new \RuntimeException($message);
     }
     $termData = $this->policyTerm->getPolicyTerm($policy->getAppData()->getPolicyNumber(), $policy->getAppData()->getStartDate());
     if (!$termData->id) {
         throw new \RuntimeException('Invalid Term Id');
     }
     if ($propertyRental < RentRecoveryPlus::BAND_A_LIMIT) {
         $band = $disbData::BAND_A;
         $transBand = RentRecoveryPlus::BAND_A;
     } else {
         $band = $disbData::BAND_B;
         $transBand = RentRecoveryPlus::BAND_B;
     }
     $insuranceNetAmount = $disbData->extractBandDisbursement($disbursement, $band);
     $proRataCalcs = new ProRataCalculations($policy->getAppData()->getStartDate(), $this->legacyMtaData->getDateOnRisk());
     $netPremium = $proRataCalcs->getProRata($policy->getAppData()->getPolicyLength(), $policy->getAppData()->getPolicyLength(), $insuranceNetAmount, $termData->netPremium);
     $this->policyTerm->updatePolicyTerm($policy->getAppData(), $termData->term, array('netPremium' => $netPremium));
     $this->policyNotes->addNote($policyNumber, $this->legacyMtaData->getDisplayNotes());
     if ($policy->save()) {
         if ($this->legacyMta->updateStatus($policyNumber, $mtaId, $this->mtaStatusLive)) {
             $coverOptions = array();
             foreach ($policy->getAppData()->getValidPolicyOptionNames() as $optionName) {
                 if (PolicyOptionsManager::isOptionSet($policy->getAppData()->getPolicyOptions(), $optionName, $policy->getAppData()->getAmountsCovered())) {
                     $optionId = $this->policyOptions->fetchOptionsByName($optionName);
                     $sumInsured = PolicyOptionsManager::getOption($policy->getAppData()->getPolicyOptions(), $optionName, $policy->getAppData()->getAmountsCovered());
                     $premium = PolicyOptionsManager::getOption($policy->getAppData()->getPolicyOptions(), $optionName, $policy->getAppData()->getOptionPremiums());
                     $coverOptions[] = array('policyNumber' => $policyNumber, 'policyOptionID' => $optionId, 'sumInsured' => $sumInsured, 'premium' => $premium);
                 }
             }
             $this->policyCover->setCover($policyNumber, $coverOptions);
             if ($this->legacyMtaData->getPremium() == 0) {
                 //If no premium change there's no need to store anything in the transaction
                 return true;
             }
             $transaction = TransactionDecoratorFactory::getDecorator(TransactionDecoratorFactory::TRANSACTION_UPDATE, $policy->getAppData()->getPremium(), $insuranceNetAmount, $termData->id, $mtaId, $transBand, $this->legacyMtaData->getDateOnRisk(), $policy->getAppData());
             $transaction->processAllTransactions();
             return true;
         }
     }
     return false;
 }