/**
  * the singleton pattern
  *
  * @return Sales_Controller_Product
  */
 public static function getInstance()
 {
     if (self::$_instance === NULL) {
         self::$_instance = new self();
     }
     return self::$_instance;
 }
 /**
  * lazy init of uit
  *
  * @return Sales_Controller_Product
  */
 public function getUit()
 {
     if ($this->_uit === null) {
         $this->_uit = Sales_Controller_Product::getInstance();
     }
     return $this->_uit;
 }
Пример #3
0
 /**
  * the singleton pattern
  *
  * @return Sales_Controller_Product
  */
 public static function getInstance()
 {
     if (self::$_instance === NULL) {
         self::$_instance = new Sales_Controller_Product();
     }
     return self::$_instance;
 }
 /**
  * returns the product aggregate for a given accountable
  * 
  * @param Sales_Model_Accountable_Interface $record
  */
 public function findProductAggregate(Sales_Model_Accountable_Interface $record)
 {
     $accountableClassName = get_class($record);
     $filter = new Sales_Model_ProductFilter(array());
     $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'accountable', 'operator' => 'equals', 'value' => $accountableClassName)));
     $products = Sales_Controller_Product::getInstance()->search($filter);
     $filter = new Sales_Model_ProductAggregateFilter(array());
     $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'product_id', 'operator' => 'in', 'value' => $products->getId())));
     $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'contract_id', 'operator' => 'equals', 'value' => $this->getId())));
     $pas = Sales_Controller_ProductAggregate::getInstance()->search($filter);
     if ($pas->count() < 1) {
         throw new Tinebase_Exception_Data('A contract aggregate could not be found!');
     } elseif ($pas->count() > 1) {
         throw new Tinebase_Exception_Data('At the moment a contract may have only one product aggregate for the same product, not more!');
     }
     return $pas->getFirstRecord();
 }
 /**
  * add body rows
  * 
  * @alternate, kind of POC or VIP, overwrites the default one
  *
  * @param Tinebase_Record_RecordSet $records
  */
 public function processIteration($_records)
 {
     $json = new Tinebase_Convert_Json();
     $productAggregateIds = $_records->accountable_id;
     $paFilter = new Sales_Model_ProductAggregateFilter();
     $paFilter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'id', 'operator' => 'in', 'value' => $productAggregateIds)));
     $productAggregates = Sales_Controller_ProductAggregate::getInstance()->search($paFilter);
     $pFilter = new Sales_Model_ProductFilter();
     $pFilter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'id', 'operator' => 'in', 'value' => array_unique($productAggregates->product_id))));
     $products = Sales_Controller_Product::getInstance()->search($pFilter);
     $resolved = $json->fromTine20RecordSet($_records);
     foreach ($resolved as $record) {
         $record['accountable_id'] = $productAggregates->getById($record['accountable_id'])->toArray();
         $record['product_id'] = $products->getById($record['accountable_id']['product_id'])->toArray();
         $row = $this->_activeTable->appendRow();
         $i18n = $this->_translate->getAdapter();
         foreach ($this->_config->columns->column as $field) {
             $identifier = $field->identifier;
             // TODO: use ModelConfig here to get the POC
             // get type and value for cell
             $cellType = $this->_getCellType($field->type);
             switch ($identifier) {
                 case 'quantity':
                     $value = intval($record[$identifier]) * intval($record['accountable_id']['quantity']);
                     break;
                 case 'month':
                     $value = $record[$identifier];
                     break;
                 default:
                     $value = $record['product_id'][$identifier];
             }
             // create cell with type and value and add style
             $cell = $row->appendCell($value, $cellType);
             if ($field->customStyle) {
                 $cell->setStyle((string) $field->customStyle);
             }
         }
     }
 }
 /**
  * inspects delete action
  *
  * @param array $_ids
  * @return array of ids to actually delete
  */
 protected function _inspectDelete(array $_ids)
 {
     $records = $this->_backend->getMultiple($_ids);
     $records->setTimezone(Tinebase_Core::getUserTimezone());
     $invoicePositionController = Sales_Controller_InvoicePosition::getInstance();
     $contractController = Sales_Controller_Contract::getInstance();
     foreach ($records as $record) {
         if (!$record->is_auto) {
             continue;
         }
         if ($record->cleared == 'CLEARED') {
             // cleared invoices must not be deleted
             throw new Sales_Exception_InvoiceAlreadyClearedDelete();
         } else {
             // try to find a invoice after this one
             // there should be a contract
             $contractRelation = Tinebase_Relations::getInstance()->getRelations('Sales_Model_Invoice', 'Sql', $record->getId(), NULL, array(), TRUE, array('Sales_Model_Contract'))->getFirstRecord();
             if ($contractRelation) {
                 $contract = $contractRelation->related_record;
                 $contract->setTimezone(Tinebase_Core::getUserTimezone());
                 // get all invoices related to this contract. throw exception if a follwing invoice has been found
                 $invoiceRelations = Tinebase_Relations::getInstance()->getRelations('Sales_Model_Contract', 'Sql', $contract->getId(), NULL, array(), TRUE, array('Sales_Model_Invoice'));
                 foreach ($invoiceRelations as $invoiceRelation) {
                     $invoiceRelation->related_record->setTimezone(Tinebase_Core::getUserTimezone());
                     if ($record->getId() !== $invoiceRelation->related_record->getId() && $record->creation_time < $invoiceRelation->related_record->creation_time) {
                         throw new Sales_Exception_DeletePreviousInvoice();
                     }
                 }
                 $this->_currentBillingContract = $contract;
                 $productAggregates = $this->_findProductAggregates();
             } else {
                 if (Tinebase_Core::isLogLevel(Zend_Log::NOTICE)) {
                     Tinebase_Core::getLogger()->notice(__METHOD__ . '::' . __LINE__ . ' Could not find contract relation -> skip contract handling');
                 }
                 $contract = null;
                 $productAggregates = array();
             }
             // remove invoice_id from billables
             $filter = new Sales_Model_InvoicePositionFilter(array());
             $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'invoice_id', 'operator' => 'equals', 'value' => $record->getId())));
             $invoicePositions = $invoicePositionController->search($filter);
             $allModels = array_unique($invoicePositions->model);
             foreach ($allModels as $model) {
                 if ($model == 'Sales_Model_ProductAggregate') {
                     continue;
                 }
                 $filteredInvoicePositions = $invoicePositions->filter('model', $model);
                 $billableControllerName = $model::getBillableControllerName();
                 $billableFilterName = $model::getBillableFilterName();
                 $filterInstance = new $billableFilterName(array());
                 $filterInstance->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'invoice_id', 'operator' => 'equals', 'value' => $record->getId())));
                 $billableControllerName::getInstance()->updateMultiple($filterInstance, array('invoice_id' => NULL));
                 // set invoice ids of the timeaccounts
                 if ($model == 'Timetracker_Model_Timeaccount') {
                     $filterInstance = new Timetracker_Model_TimeaccountFilter(array());
                     $filterInstance->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'invoice_id', 'operator' => 'equals', 'value' => $record->getId())));
                     Timetracker_Controller_Timeaccount::getInstance()->updateMultiple($filterInstance, array('invoice_id' => NULL));
                 }
             }
             // delete invoice positions
             $invoicePositionController->delete($invoicePositions->getId());
             // set last_autobill a period back
             if ($contract) {
                 //find the month of each productAggregate we have to set it back to
                 $undoProductAggregates = array();
                 $paController = Sales_Controller_ProductAggregate::getInstance();
                 foreach ($invoicePositions as $inPos) {
                     if ($inPos->model != 'Sales_Model_ProductAggregate') {
                         continue;
                     }
                     //if we didnt find a month for the productAggreagte yet or if the month found is greater than the one we have at hands
                     if (!isset($undoProductAggregates[$inPos->accountable_id]) || strcmp($undoProductAggregates[$inPos->accountable_id], $inPos->month) > 0) {
                         $undoProductAggregates[$inPos->accountable_id] = $inPos->month;
                     }
                 }
                 foreach ($productAggregates as $productAggregate) {
                     if (!$productAggregate->last_autobill) {
                         continue;
                     }
                     if (!isset($undoProductAggregates[$productAggregate->id])) {
                         $product = $this->_cachedProducts->getById($productAggregate->product_id);
                         if (!$product) {
                             $product = Sales_Controller_Product::getInstance()->get($productAggregate->product_id);
                             $this->_cachedProducts->addRecord($product);
                         }
                         if ($product->accountable == 'Sales_Model_Product' || $record->date != null && $record->date->isLater($productAggregate->last_autobill)) {
                             continue;
                         }
                         $productAggregate->last_autobill->subMonth($productAggregate->interval);
                     } else {
                         $productAggregate->last_autobill = new Tinebase_DateTime($undoProductAggregates[$productAggregate->id] . '-01 00:00:00', Tinebase_Core::getUserTimezone());
                         if ($productAggregate->billing_point == 'begin') {
                             $productAggregate->last_autobill->subMonth($productAggregate->interval);
                         }
                         if ($productAggregate->start_date && $productAggregate->last_autobill < $productAggregate->start_date) {
                             $tmp = clone $productAggregate->start_date;
                             $tmp->setTimezone(Tinebase_Core::getUserTimezone());
                             $tmp->setDate($tmp->format('Y'), $tmp->format('m'), 1);
                             $tmp->setTime(0, 0, 0);
                             if ($productAggregate->last_autobill < $tmp || $productAggregate->billing_point == 'end' && $productAggregate->last_autobill == $tmp) {
                                 $productAggregate->last_autobill = NULL;
                             }
                         }
                     }
                     $productAggregate->setTimezone('UTC');
                     $paController->update($productAggregate);
                     $productAggregate->setTimezone(Tinebase_Core::getUserTimezone());
                 }
             }
         }
     }
     return $_ids;
 }
 /**
  * creates products
  * 
  * @param string $productArray
  */
 protected function _createProducts($productArray = NULL)
 {
     // 1.1.20xx
     $startDate = clone $this->_referenceDate;
     $endDate = clone $startDate;
     // 1.8.20xx
     $endDate->addMonth(7);
     if (!$productArray) {
         $productArray = array(array('name' => 'billhalfyearly', 'description' => 'bill this 2 times a year', 'price' => '102', 'accountable' => 'Sales_Model_Product'), array('name' => 'billeachquarter', 'description' => 'bill this each quarter', 'price' => '102', 'accountable' => 'Sales_Model_Product'), array('name' => 'Hours', 'description' => 'timesheets', 'price' => '100', 'accountable' => 'Timetracker_Model_Timeaccount'));
     }
     $default = array('manufacturer' => 'Unittest', 'category' => 'Tine');
     $productController = Sales_Controller_Product::getInstance();
     $this->_productRecords = new Tinebase_Record_RecordSet('Sales_Model_Product');
     foreach ($productArray as $product) {
         $p = new Sales_Model_Product(array_merge($product, $default));
         $p->setTimezone('UTC');
         $this->_productRecords->addRecord($productController->create($p));
     }
 }
 /**
  * processTransferBillingInformation
  *
  * @param Tinebase_Record_RecordSet $contracts
  */
 public function processTransferBillingInformation($contracts)
 {
     $billingPoints = array('Timetracker_Model_Timeaccount' => 'end', 'Sales_Model_Product' => 'end');
     foreach ($contracts as $contract) {
         // iterate relations, look for customer, cost center and accountables
         // find accountables
         $models = array();
         $filter = new Sales_Model_ProductAggregateFilter(array());
         $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'contract_id', 'operator' => 'equals', 'value' => $contract->getId())));
         $usedPAs = Sales_Controller_ProductAggregate::getInstance()->search($filter);
         foreach ($contract->relations as $relation) {
             if (in_array('Sales_Model_Accountable_Interface', class_implements($relation->related_record))) {
                 $models[] = $relation->related_model;
             }
             $models = array_unique($models);
         }
         foreach ($models as $model) {
             $filter = new Sales_Model_ProductFilter(array(array('field' => 'accountable', 'operator' => 'equals', 'value' => $model)));
             $product = Sales_Controller_Product::getInstance()->search($filter)->getFirstRecord();
             if (!$product) {
                 if (Tinebase_Core::isLogLevel(Zend_Log::INFO)) {
                     Tinebase_Core::getLogger()->info(__METHOD__ . '::' . __LINE__ . ' ' . ' Create Product for ' . $relation->related_model);
                 }
                 $product = Sales_Controller_Product::getInstance()->create(new Sales_Model_Product(array('name' => $model, 'accountable' => $model, 'description' => 'auto generated for invoicing')));
             }
             if (Tinebase_Core::isLogLevel(Zend_Log::INFO)) {
                 Tinebase_Core::getLogger()->info(__METHOD__ . '::' . __LINE__ . ' ' . ' Create ProductAggregate for ' . $model . ' contract: ' . $contract->getId());
             }
             if ($usedPAs->filter('product_id', $product->getId())->count() < 1) {
                 $productAggregate = Sales_Controller_ProductAggregate::getInstance()->create(new Sales_Model_ProductAggregate(array('product_id' => $product->getId(), 'contract_id' => $contract->getId(), 'interval' => $contract->interval, 'last_autobill' => $contract->last_autobill ? clone $contract->last_autobill : NULL, 'quantity' => 1, 'billing_point' => $billingPoints[$model])));
             }
         }
     }
 }
 /**
  * Return a single record
  *
  * @param   string $id
  * @return  array record data
  */
 public function getInvoice($id)
 {
     $invoice = $this->_get($id, Sales_Controller_Invoice::getInstance());
     $json = new Tinebase_Convert_Json();
     $resolvedProducts = new Tinebase_Record_RecordSet('Sales_Model_Product');
     $productController = Sales_Controller_Product::getInstance();
     foreach ($invoice['relations'] as &$relation) {
         if ($relation['related_model'] == "Sales_Model_ProductAggregate") {
             if (!($product = $resolvedProducts->getById($relation['related_record']['product_id']))) {
                 $product = $productController->get($relation['related_record']['product_id']);
                 $resolvedProducts->addRecord($product);
             }
             $relation['related_record']['product_id'] = $json->fromTine20Model($product);
         }
     }
     return $invoice;
 }
 /**
  * creates the contracts - no containers, just "shared"
  */
 protected function _createSharedContracts()
 {
     $cNumber = 1;
     $container = $this->_contractController->getSharedContractsContainer();
     $cid = $container->getId();
     $ccs = array($this->_developmentCostCenter, $this->_marketingCostCenter);
     $i = 0;
     $this->_setReferenceDate();
     $customers = Sales_Controller_Customer::getInstance()->getAll();
     $addresses = Sales_Controller_Address::getInstance()->getAll();
     $customersCount = $customers->count();
     $ccIndex = 0;
     while ($i < $customersCount) {
         $costcenter = $ccs[$i % 2];
         $i++;
         $customer = $customers->getByIndex($ccIndex);
         $address = $addresses->filter('customer_id', $customer->getId())->filter('type', 'billing')->getFirstRecord();
         $addressId = $address ? $address->getId() : NULL;
         $title = self::$_de ? 'Vertrag für KST ' . $costcenter->number . ' - ' . $costcenter->remark : 'Contract for costcenter ' . $costcenter->number . ' - ' . $costcenter->remark . ' ' . Tinebase_Record_Abstract::generateUID(3);
         $ccid = $costcenter->getId();
         $contract = new Sales_Model_Contract(array('number' => $cNumber, 'title' => $title, 'description' => 'Created by Tine 2.0 DemoData', 'container_id' => $cid, 'status' => 'OPEN', 'cleared' => 'NOT_YET_CLEARED', 'start_date' => clone $this->_referenceDate, 'billing_address_id' => $addressId));
         $relations = array(array('own_model' => 'Sales_Model_Contract', 'own_backend' => Tasks_Backend_Factory::SQL, 'own_id' => NULL, 'own_degree' => Tinebase_Model_Relation::DEGREE_SIBLING, 'related_model' => 'Sales_Model_CostCenter', 'related_backend' => Tasks_Backend_Factory::SQL, 'related_id' => $ccid, 'type' => 'LEAD_COST_CENTER'), array('own_model' => 'Sales_Model_Contract', 'own_backend' => Tasks_Backend_Factory::SQL, 'own_id' => NULL, 'own_degree' => Tinebase_Model_Relation::DEGREE_SIBLING, 'related_model' => 'Sales_Model_Customer', 'related_backend' => Tasks_Backend_Factory::SQL, 'related_id' => $customer->getId(), 'type' => 'CUSTOMER'));
         $genericProduct = Sales_Controller_Product::getInstance()->create(new Sales_Model_Product(self::$_de ? array('name' => 'Generisches Produkt', 'description' => 'ein generisches produkt aus den demo daten', 'price' => 100) : array('name' => 'Generic Product', 'description' => 'this is a generic product used in demo data', 'price' => 100)));
         $contract->products = array(array('product_id' => $genericProduct->getId(), 'quantity' => 1));
         $contract->relations = $relations;
         $this->_contractController->create($contract);
         $cNumber++;
         $ccIndex++;
         if ($ccIndex == $customersCount) {
             $ccIndex = 0;
         }
     }
 }
 /**
  * @param Sales_Model_ProductAggregate $productAggregate
  * @return null|Tinebase_Record_RecordSet
  * @throws Tinebase_Exception_AccessDenied
  * @throws Tinebase_Exception_NotFound
  */
 protected function _getProductAccountables(Sales_Model_ProductAggregate $productAggregate)
 {
     $json_attributes = $productAggregate->json_attributes;
     if (!is_array($json_attributes) || !isset($json_attributes['assignedAccountables'])) {
         return null;
     }
     $product = Sales_Controller_Product::getInstance()->get($productAggregate->product_id);
     if ($product->accountable == '') {
         return null;
     }
     $app = Tinebase_Core::getApplicationInstance($product->accountable, '');
     return $app->getMultiple($json_attributes['assignedAccountables']);
 }
 /**
  * tests if a product interval of 36 is possible and if an empty string gets converted to null
  */
 public function testContract()
 {
     $product = Sales_Controller_Product::getInstance()->create($this->_getProduct());
     $contract = array('id' => NULL, 'number' => 1, 'title' => 'test123', 'products' => array(array('product_id' => $product->getId(), 'interval' => 36, 'billing_point' => 'begin', 'quantity' => '')));
     $contract = $this->_instance->saveContract($contract);
     $this->assertEquals(NULL, $contract['products'][0]['quantity']);
     $this->assertEquals(36, $contract['products'][0]['interval']);
 }
Пример #13
0
 /**
  * try to add a lead and link a contact
  *
  */
 public function testAddGetSearchDeleteLead()
 {
     // create lead with task and contact
     $contact = $this->_getContact();
     $task = $this->_getTask();
     $lead = $this->_getLead();
     $product = $this->_getProduct();
     $price = 200;
     $leadData = $lead->toArray();
     $leadData['relations'] = array(array('type' => 'TASK', 'related_record' => $task->toArray()), array('type' => 'PARTNER', 'related_record' => $contact->toArray()), array('type' => 'PRODUCT', 'related_record' => $product->toArray(), 'remark' => array('price' => $price)));
     // add note
     $note = array('note_type_id' => 1, 'note' => 'phpunit test note');
     $leadData['notes'] = array($note);
     $savedLead = $this->_instance->saveLead($leadData);
     $getLead = $this->_instance->getLead($savedLead['id']);
     $searchLeads = $this->_instance->searchLeads($this->_getLeadFilter(), '');
     //print_r($searchLeads);
     // assertions
     $this->assertEquals($getLead, $savedLead);
     $this->assertEquals($getLead['notes'][0]['note'], $note['note']);
     $this->assertTrue($searchLeads['totalcount'] > 0);
     $this->assertTrue(isset($searchLeads['totalleadstates']) && count($searchLeads['totalleadstates']) > 0);
     $this->assertEquals($lead->description, $searchLeads['results'][0]['description']);
     $this->assertEquals($price, $searchLeads['results'][0]['turnover'], 'turnover has not been calculated using product prices');
     $this->assertEquals($searchLeads['results'][0]['turnover'] * $lead->probability / 100, $searchLeads['results'][0]['probableTurnover']);
     $this->assertTrue(count($searchLeads['results'][0]['relations']) == 3, 'did not get all relations');
     // get related records and check relations
     foreach ($searchLeads['results'][0]['relations'] as $relation) {
         switch ($relation['type']) {
             case 'PRODUCT':
                 //print_r($relation);
                 $this->assertEquals(200, $relation['remark']['price'], 'product price (remark) does not match');
                 $relatedProduct = $relation['related_record'];
                 break;
             case 'TASK':
                 $relatedTask = $relation['related_record'];
                 break;
             case 'PARTNER':
                 $relatedContact = $relation['related_record'];
                 break;
         }
     }
     $this->assertTrue(isset($relatedContact), 'contact not found');
     $this->assertEquals($contact->n_fn, $relatedContact['n_fn'], 'contact name does not match');
     $this->assertTrue(isset($relatedTask), 'task not found');
     $this->assertEquals($task->summary, $relatedTask['summary'], 'task summary does not match');
     $defaultTaskContainerId = Tinebase_Core::getPreference('Tasks')->getValue(Tasks_Preference::DEFAULTTASKLIST);
     $this->assertEquals($defaultTaskContainerId, $relatedTask['container_id']);
     $this->assertTrue(isset($relatedProduct), 'product not found');
     $this->assertEquals($product->name, $relatedProduct['name'], 'product name does not match');
     // delete all
     $this->_instance->deleteLeads($savedLead['id']);
     Addressbook_Controller_Contact::getInstance()->delete($relatedContact['id']);
     Sales_Controller_Product::getInstance()->delete($relatedProduct['id']);
     // check if delete worked
     $result = $this->_instance->searchLeads($this->_getLeadFilter(), '');
     $this->assertEquals(0, $result['totalcount']);
     // check if linked task got removed as well
     $this->setExpectedException('Tinebase_Exception_NotFound');
     $task = Tasks_Controller_Task::getInstance()->get($relatedTask['id']);
 }
 /**
  * (non-PHPdoc)
  * @see Tinebase_Record_Abstract::getTitle()
  */
 public function getTitle()
 {
     $p = Sales_Controller_Product::getInstance()->get($this->product_id);
     return $p->name;
 }
 /**
  * returns a temporarily productaggregate which contains the
  * default billing information of this accountable
  * 
  * @param Sales_Model_Contract $contract
  * @return Sales_Model_ProductAggregate
  */
 public function getDefaultProductAggregate(Sales_Model_Contract $contract)
 {
     $startDate = clone $contract->start_date;
     if ($contract->start_date->format('d') !== 1) {
         $startDate->setDate($startDate->format('Y'), $startDate->format('m'), 1);
     }
     $accountable = get_class($this);
     $filter = new Sales_Model_ProductFilter(array(array('field' => 'accountable', 'operator' => 'equals', 'value' => $accountable)));
     $product = Sales_Controller_Product::getInstance()->search($filter)->getFirstRecord();
     // create product, if no product is found
     if (!$product) {
         if (Tinebase_Core::isLogLevel(Zend_Log::INFO)) {
             Tinebase_Core::getLogger()->info(__METHOD__ . '::' . __LINE__ . ' ' . ' Create Product for ' . $accountable);
         }
         $product = Sales_Controller_Product::getInstance()->create(new Sales_Model_Product(array('name' => $accountable, 'accountable' => $accountable, 'description' => 'auto generated on invoicing')));
     }
     if (Tinebase_Core::isLogLevel(Zend_Log::INFO)) {
         Tinebase_Core::getLogger()->info(__METHOD__ . '::' . __LINE__ . ' ' . ' Create ProductAggregate for ' . $accountable . ' contract: ' . $contract->getId());
     }
     $endDate = clone $startDate;
     $endDate->addMonth($this->_defaultInterval);
     $pa = new Sales_Model_ProductAggregate(array('interval' => $this->_defaultInterval, 'billing_point' => $this->_defaultBillingPoint, 'contract_id' => $contract->getId(), 'start_date' => $startDate, 'end_date' => NULL, 'last_autobill' => NULL, 'product_id' => $product->getId(), 'quantity' => $product->accountable ? NULL : 1));
     return $pa;
 }
 /**
  * if no productaggregates are defined for a contract, but 
  * accountables are related, use default billing Info from accountable
  * (product will be created if it does not exist - is needed in the invoice position)
  */
 public function testDefaultAutobillInterval()
 {
     $startDate = clone $this->_referenceDate;
     $startDate->subYear(1);
     $this->_createCustomers(1);
     $this->_createCostCenters();
     $this->_createTimeaccounts(array(array('title' => 'TA', 'description' => 'blabla', 'is_open' => 1, 'status' => 'to bill', 'budget' => 100)));
     $addressId = $this->_addressRecords->filter('customer_id', $this->_customerRecords->filter('name', 'Customer1')->getFirstRecord()->getId())->filter('type', 'billing')->getFirstRecord()->getId();
     // this contract begins 6 months before the first invoice will be created
     $this->_createContracts(array(array('number' => 100, 'title' => 'MyContract', 'description' => 'unittest', 'container_id' => $this->_sharedContractsContainerId, 'billing_point' => 'begin', 'billing_address_id' => $addressId, 'start_date' => $startDate, 'end_date' => NULL)));
     $startDate = clone $this->_referenceDate;
     $startDate->subMonth(1);
     $startDate = clone $this->_referenceDate;
     $startDate->addDay(5);
     $result = $this->_invoiceController->createAutoInvoices($startDate);
     $this->assertEquals(1, $result['created_count']);
     $filter = new Sales_Model_ProductFilter(array());
     $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'accountable', 'operator' => 'equals', 'value' => 'Timetracker_Model_Timeaccount')));
     $products = Sales_Controller_Product::getInstance()->search($filter);
     $this->assertEquals(1, $products->count());
     $this->assertEquals('Timetracker_Model_Timeaccount', $products->getFirstRecord()->accountable);
     $filter = new Sales_Model_InvoicePositionFilter(array());
     $filter->addFilter(new Tinebase_Model_Filter_Text(array('field' => 'invoice_id', 'operator' => 'equals', 'value' => $result['created'][0])));
     $invoicePositions = Sales_Controller_InvoicePosition::getInstance()->search($filter);
     $this->assertEquals(1, $invoicePositions->count());
 }
 /**
  * try to add/search/delete a lead with linked contact, task and product
  * 
  * @see 0007214: if lead with linked task is saved, alarm is discarded
  */
 public function testAddGetSearchDeleteLead()
 {
     $savedLead = $this->_saveLead();
     $getLead = $this->_instance->getLead($savedLead['id']);
     $searchLeads = $this->_instance->searchLeads($this->_getLeadFilter(), '');
     // test manual resolving of organizer in related_record and set it back for following tests
     for ($i = 0; $i < count($getLead['relations']); $i++) {
         if (isset($getLead['relations'][$i]['related_record']['organizer'])) {
             $this->assertTrue(is_array($getLead['relations'][$i]['related_record']['organizer']));
             $getLead['relations'][$i]['related_record']['organizer'] = $getLead['relations'][$i]['related_record']['organizer']['accountId'];
         }
     }
     // assertions
     $this->assertEquals($getLead, $savedLead);
     $this->assertEquals($getLead['notes'][0]['note'], 'phpunit test note');
     $this->assertTrue($searchLeads['totalcount'] > 0);
     $this->assertTrue(isset($searchLeads['totalleadstates']) && count($searchLeads['totalleadstates']) > 0);
     $this->assertEquals($getLead['description'], $searchLeads['results'][0]['description']);
     $this->assertEquals(200, $searchLeads['results'][0]['turnover'], 'turnover has not been calculated using product prices');
     $this->assertEquals($searchLeads['results'][0]['turnover'] * $getLead['probability'] / 100, $searchLeads['results'][0]['probableTurnover']);
     // now we need 2 relations here (frontend search shall return relations with related_model Addressbook_Model_Contact or Sales_Model_Product
     $this->assertEquals(2, count($searchLeads['results'][0]['relations']), 'did not get all relations');
     $relatedTask = null;
     foreach ($getLead['relations'] as $rel) {
         if ($rel['type'] == 'TASK') {
             $relatedTask = $rel['related_record'];
         }
     }
     $this->assertTrue($relatedTask !== null);
     $this->assertEquals($this->_getTask()->summary, $relatedTask['summary'], 'task summary does not match');
     $defaultTaskContainerId = Tinebase_Core::getPreference('Tasks')->getValue(Tasks_Preference::DEFAULTTASKLIST);
     $this->assertEquals($defaultTaskContainerId, $relatedTask['container_id']);
     $this->assertTrue(isset($relatedTask['alarms']) && count($relatedTask['alarms']) === 1, 'alarm missing in related task: ' . print_r($relatedTask, TRUE));
     $relatedTaskId = $relatedTask['id'];
     $relatedTask = NULL;
     // get related records and check relations
     foreach ($searchLeads['results'][0]['relations'] as $relation) {
         switch ($relation['type']) {
             case 'PRODUCT':
                 //print_r($relation);
                 $this->assertEquals(200, $relation['remark']['price'], 'product price (remark) does not match');
                 $relatedProduct = $relation['related_record'];
                 break;
             case 'TASK':
                 $relatedTask = $relation['related_record'];
                 break;
             case 'PARTNER':
                 $relatedContact = $relation['related_record'];
                 break;
         }
     }
     $this->assertTrue(isset($relatedContact), 'contact not found');
     $this->assertEquals($this->_getContact()->n_fn, $relatedContact['n_fn'], 'contact name does not match');
     $this->assertFalse(is_array($relatedTask), 'task must not be found');
     $this->assertTrue(isset($relatedProduct), 'product not found');
     $this->assertEquals($this->_getProduct()->name, $relatedProduct['name'], 'product name does not match');
     // delete all
     $this->_instance->deleteLeads($savedLead['id']);
     Addressbook_Controller_Contact::getInstance()->delete($relatedContact['id']);
     Sales_Controller_Product::getInstance()->delete($relatedProduct['id']);
     // check if delete worked
     $result = $this->_instance->searchLeads($this->_getLeadFilter(), '');
     $this->assertEquals(0, $result['totalcount']);
     // check if linked task got removed as well
     $this->setExpectedException('Tinebase_Exception_NotFound');
     Tasks_Controller_Task::getInstance()->get($relatedTaskId);
 }
Пример #18
0
 /**
  * the constructor
  *
  */
 public function __construct()
 {
     $this->_applicationName = 'Sales';
     $this->_contractController = Sales_Controller_Contract::getInstance();
     $this->_productController = Sales_Controller_Product::getInstance();
 }