SalesControllerInvoice - product and contract end date treating buggy
authorPaul Mehrer <p.mehrer@metaways.de>
Mon, 29 Jun 2015 16:12:30 +0000 (18:12 +0200)
committerPhilipp Schüle <p.schuele@metaways.de>
Wed, 1 Jul 2015 16:32:58 +0000 (18:32 +0200)
fixed that
changed interval to look for already closed contracts from 12 to 6 months

Change-Id: Ieb29a597d2335fb6d99010ff40e6ae0cc7ec027c
Reviewed-on: http://gerrit.tine20.com/customers/1998
Tested-by: Jenkins CI (http://ci.tine20.com/)
Reviewed-by: Philipp Schüle <p.schuele@metaways.de>
tine20/Sales/Backend/Contract.php
tine20/Sales/Controller/Invoice.php

index f854d22..8c5f1b2 100644 (file)
@@ -58,7 +58,7 @@ class Sales_Backend_Contract extends Tinebase_Backend_Sql_Abstract
         $date->setTimezone('UTC');
         $date->setDate($date->format('Y'), $date->format('m'), 1);
         $date->setTime(0,0,0);
-        $date->submonth(12);
+        $date->submonth(6);
 
         $be = new Sales_Backend_Contract();
         $db = $be->getAdapter();
@@ -66,7 +66,7 @@ class Sales_Backend_Contract extends Tinebase_Backend_Sql_Abstract
         $sql = 'SELECT ' . $db->quoteIdentifier('id') . ' FROM ' . $db->quoteIdentifier(SQL_TABLE_PREFIX . 'sales_contracts') .
         ' WHERE (' . $db->quoteInto($db->quoteIdentifier('end_date') . ' >= ?', $date) . ' OR ' . $db->quoteIdentifier('end_date') . ' IS NULL ) ';
         
-        $date->addMonth(13);
+        $date->addMonth(7);
         $date->subSecond(1);
         $sql .= ' AND '   . $db->quoteInto($db->quoteIdentifier('start_date') . ' <= ?', $date);
     
index 0f478bb..d06479d 100644 (file)
@@ -307,15 +307,33 @@ class Sales_Controller_Invoice extends Sales_Controller_NumberableAbstract
             // is null, if this is the first time to bill the product aggregate
             $lastBilled = $productAggregate->last_autobill == NULL ? NULL : clone $productAggregate->last_autobill;
             $productEnded = false;
+            $endDate = NULL;
+            
+            if (NULL != $productAggregate->end_date)
+                $endDate = clone $productAggregate->end_date;
+            if ($this->_currentBillingContract->end_date != NULL && (NULL === $endDate || $endDate->isLater($this->_currentBillingContract->end_date)))
+                $endDate = clone $this->_currentBillingContract->end_date;
             
             // if the product has been billed already, add the interval
             if ($lastBilled) {
-                if (NULL != $productAggregate->end_date && $lastBilled->isLaterOrEquals($productAggregate->end_date)) {
-                    $productEnded = true;
-                } else {
-                    $nextBill = $lastBilled;
-                    $nextBill->setDate($nextBill->format('Y'), $nextBill->format('m'), 1);
-                    $nextBill->addMonth($productAggregate->interval);
+                $nextBill = $lastBilled;
+                $nextBill->setDate($nextBill->format('Y'), $nextBill->format('m'), 1);
+                $nextBill->addMonth($productAggregate->interval);
+                if (NULL !== $endDate && $endDate->isEarlier($nextBill)) {
+                    if ($productAggregate->billing_point == 'end') {
+                        if ($productAggregate->last_autobill->isEarlier($endDate)) {
+                            // ok, fix nextBill to be close to endDate
+                            $nextBill = $endDate;
+                            $nextBill->setDate($nextBill->format('Y'), $nextBill->format('m'), 1);
+                            $nextBill->addMonth(1);
+                        } else {
+                            // not ok, ignore
+                            $productEnded = true;
+                        }
+                    } else {
+                        // not ok, ignore
+                        $productEnded = true;
+                    }
                 }
             } else {
                 // it hasn't been billed already
@@ -329,29 +347,24 @@ class Sales_Controller_Invoice extends Sales_Controller_NumberableAbstract
                 // add interval, if the billing point is at the end of the interval
                 if ($productAggregate->billing_point == 'end') {
                     $nextBill->addMonth($productAggregate->interval);
+                    if (NULL !== $endDate && $endDate->isEarlier($nextBill))
+                    {
+                        // ok, fix nextBill to be close to endDate
+                        $nextBill = $endDate;
+                        $nextBill->setDate($nextBill->format('Y'), $nextBill->format('m'), 1);
+                        $nextBill->addMonth(1);
+                    }
                 }
             }
             
-            $product = $this->_cachedProducts->getById($productAggregate->product_id);
+            $nextBill->setTime(0,0,0);
             
+            $product = $this->_cachedProducts->getById($productAggregate->product_id);
             if (! $product) {
                 $product = Sales_Controller_Product::getInstance()->get($productAggregate->product_id);
                 $this->_cachedProducts->addRecord($product);
             }
             
-            if (!$productEnded) {
-                if (NULL != $productAggregate->end_date && $nextBill->isLater($productAggregate->end_date)) {
-                    $nextBill = clone $productAggregate->end_date;
-                }
-                
-                // assure creating the last bill if a contract has been terminated
-                if (($this->_currentBillingContract->end_date !== NULL) && $nextBill->isLater($this->_currentBillingContract->end_date)) {
-                    $nextBill = clone $this->_currentBillingContract->end_date;
-                }
-                
-                $nextBill->setTime(0,0,0);
-            }
-            
             // find out if this model has to be billed or skipped
             if (! $productEnded && $this->_currentMonthToBill->isLaterOrEquals($nextBill)) {
                 if (($product->accountable == 'Sales_Model_Product') || ($product->accountable == '')) {