3 * Table Definition for expense
5 require_once 'DB/DataObject.php';
7 class Pman_Xtuple_DataObjects_Expense extends DB_DataObject
10 /* the code below is auto generated do not remove the above tag */
12 public $__table = 'expense'; // table name
13 public $expense_id; // int4(4) not_null default_nextval%28%28expense_id_seq%29%3A%3Aregclass%29 primary_key
14 public $expense_accnt_id; // int4(4)
15 public $expense_emp_id; // int4(4) not_null
16 public $expense_number; // text(-1) not_null
17 public $expense_trandate; // timestamptz(8)
18 public $expense_created; // timestamptz(8)
19 public $expense_modified; // timestamptz(8)
20 public $expense_duedate; // timestamptz(8)
21 public $expense_memo; // text(-1)
22 public $expense_status; // text(-1)
23 public $expense_advance; // numeric(-1) default_0.000
24 public $expense_amount; // numeric(-1) default_0.000
25 public $expense_tax; // numeric(-1) default_0.000
26 public $expense_total; // numeric(-1) default_0.000
27 public $expense_posted; // numeric(-1) default_0.000
28 public $expense_comments;
32 * Getter / Setter for $expense_accnt_id
34 * @param mixed (optional) value to assign
37 public function accnt() {
38 return $this->link('expense_accnt_id', func_get_args());
42 * Getter / Setter for $expense_emp_id
44 * @param mixed (optional) value to assign
47 public function emp() {
48 return $this->link('expense_emp_id', func_get_args());
52 /* the code above is auto generated do not remove the tag below */
54 function applyFilters($q, $au, $roo)
56 // alway sapply perms.
58 if (!$roo->hasPerm('Xtuple.ExpensesAll','S')) {
59 $au->cntct(); /// make sure an employee exists..
61 $this->expense_emp_id = $au->emp()->pid();
67 (SELECT curr_name from curr_symbol where curr_id = basecurrid() LIMIT 1 ) as base_curr_name,
68 basecurrid() as base_curr_id,
70 (select expcat_id from expcat where expcat_descrip = 'Expenses' LIMIT 1) as def_expcat_id,
71 (select expcat_descrip from expcat where expcat_descrip = 'Expenses' LIMIT 1) as def_expcat_descrip,
73 expense_amount as expense_amount_ro,
74 expense_tax as expense_tax_ro,
75 expense_total as expense_total_ro
79 if (!empty($q['_asExcel'])) {
80 // DB_DataObject::debugLevel(1);
81 $this->expense_id = $q['expense_id'];
92 'expense_status' => 'Draft'
98 function beforeInsert($request,$roo)
100 if (empty($this->expense_accnt_id)) {
101 $this->expense_accnt_id = $this->sqlValue('NULL');
103 // only needed on insert..
104 if (empty($this->expense_emp_id)) {
105 $this->expense_emp_id = $roo->authUser->emp()->pid();
107 foreach($this->defaults() as $k=>$v) {
108 if (empty($this->$k)) {
117 $this->expense_number = "EXP-".strtoupper(substr($this->database(), -2)) . '-'. $this->pid() ;
118 $t = DB_DataObject::Factory('expense');
119 $t->query("UPDATE expense SET expense_number = '{$this->expense_number}'
120 WHERE expense_id = {$this->pid()}"
126 function beforeUpdate($old, $request,$roo)
131 if (empty($this->expense_accnt_id)) {
132 $this->expense_accnt_id = $this->sqlValue('NULL');
137 if ($this->expense_posted) {
138 $roo->jerr("you can not modify a posted expense");
140 if ($this->expense_status =='Paid In Full') {
141 $roo->jerr("you can not modify a posted expense");
146 function onUpdate($old,$q, $roo)
149 if (!empty($q['_post'])) {
158 $ci = DB_DataObject::factory('expitem');
160 $ci->expitem_expense_id = $this->pid();
161 $ci->orderBy('expitem_row ASC');
162 //$ci->applyFilters(array( ), $roo->authUser, $roo);
163 return $ci->fetchAll();
167 function beforeDelete($dependants_array, $roo)
169 if ($this->expense_posted) {
170 $roo->jerr("you can not delete a posted expense");
173 if ($this->expense_status =='Paid In Full') {
174 $roo->jerr("you can not modify a posted expense");
177 /// delete depenedants...
178 if (strlen($this->expense_status ) && $this->expense_status != 'Draft') {
179 $roo->jerr("you can only delete draft expense reports");
181 // in theory check perms... - but not implemented...
183 $ei = $this->items();
196 if ($this->expense_status != 'Pending Accounting Approval') {
197 $roo->jerr("expenses are not pending approval by accounts");
200 $xx = DB_DataObject::Factory('expense');
201 $xx->get($this->pid());
204 if (empty($xx->expense_accnt_id)) {
205 $roo->jerr("no bank specified");
207 $items= $this->items() ;
208 // next... verify that the rows have accounts.
211 foreach($items as $i) {
212 if (empty($i->expitem_expcat_id)) {
213 $roo->jerr("one of the lines is missing an expense category.");
216 if (empty($i->expitem_memo)) {
217 $roo->jerr("one of the lines is missing a description.");
219 $tot = bcadd($tot, round($i->expitem_total,2), 2);
224 $cur = DB_DAtaObject::Factory('curr_symbol');
225 $base_cur = $cur->base();
227 // finally try and post the thing..
229 $cn = $base_cur->curr_name;
230 $vi = DB_DataObject::Factory('vendinfo');
231 $vi->vend_number = "STAFF-{$cn}";
232 if (!$vi->find(true)) {
233 $roo->jerr("An vendor account 'STAFF-{$cn}' does not exist");
237 $taxtype = DB_DataObject::Factory('taxtype');
238 $taxtype->get('taxtype_name', 'Taxable');
241 // verify that tax zone is correct.
243 $taxzone = DB_DataObject::Factory('taxzone'); // we use vend info..
244 $taxzone->get('taxzone_code', 'NO TAX');
245 if ($taxzone->pid() == $vi->vend_taxzone_id && $this->expense_tax > 0.0) {
246 $roo->jerr("change the taxzone of the vendor 'STAFF-{$cn}' to not tax free ");
249 $vohead = DB_DataObject::Factory('vohead');
250 $vohead ->query('SELECT fetchVoNumber() AS vouchernumber');
252 $vn = $vohead->vouchernumber;
254 $vohead = DB_DataObject::Factory('vohead');
256 $vohead->setFrom($vohead->defaults());
258 $vohead->setFrom(array(
261 'vohead_number'=> $vn ,
262 'vohead_invcnumber' => $this->expense_number,
263 'vohead_docdate'=> $this->expense_trandate,
264 'vohead_distdate'=> $this->expense_trandate,
265 'vohead_duedate'=> $this->expense_trandate,
267 'vohead_amount'=> $tot,
268 'vohead_terms_id'=> $vi->vend_terms_id,
269 'vohead_notes'=> 'Created from expense report',
270 'vohead_curr_id'=> $base_cur->pid(),
271 //'vohead_pohead_id' => $po->pohead_id,
272 'vohead_vend_id' => $vi->pid(),
273 'vohead_taxtype_id'=> $taxtype->pid(),
274 'vohead_taxzone_id'=>$vi->vend_taxzone_id,
280 //$roo->jerr("total : $tot");
281 //$roo->jerr(print_R($this,true));
286 foreach($items as $i) {
287 $vodist = DB_DataObject::Factory('vodist');
289 $vodist->createFromExpItem($roo, $vohead, $i);
291 //$roo->jerr(print_r($vohead->distitems(),true));
294 if ($this->expense_tax > 0.0) {
295 $vodist = DB_DataObject::Factory('vodist');
296 $vodist->createFromExpTax($roo, $vohead, $this->expense_tax);
298 $vd = DB_DataObject::Factory('vodist');
299 $vd->query("SELECT postVoucher({$vohead->pid()},
300 fetchJournalNumber('AP-VO'), TRUE) AS result");
302 if (!$vd->result || $vd->result < 0) {
303 $roo->jerr("postVoucher() return $vd->result");
306 $xx->expense_posted = 1;
307 $xx->expense_status = 'Paid In Full';
315 function toExcel($roo)
319 //$ci->applyFilters(array( ), $roo->authUser, $roo);
320 $data = $this->items();
322 $endrow = 11 + count($data);
324 //echo '<PRE>';print_r($data);
325 require_once 'Pman/Core/SimpleExcel.php';
327 //print_R($this);exit;
329 $x = new Pman_Core_SimpleExcel(
334 'left' => array('Align'=>'left'),
335 'money' => array('NumFormat' => '$#,##0.00;[RED]-$#,##0.00'),
336 'date' => array('NumFormat' => 'D/M/YYYY', 'Align'=>'left'),
337 'header' => array('Size' => 16, 'Bold' => 1)
340 'workbook' => 'Expense Report' . $this->expense_number,
342 array("","","","","","", array("Expense Report", 'header')),
343 array("","","","", "","","Ref#", $this->expense_number),
344 array("","","","", "","","Employee:", $this->expense_emp_id_emp_name),
345 array("","","","", "","","Due:", array( Pman_Core_SimpleExcel::date($this->expense_trandate),'date')),
346 array("","","","", "","","Status:", $this->expense_status),
347 array("Summary:", $this->expense_memo),
355 'dataIndex' => 'expitem_row',
363 'dataIndex' => 'expitem_date',
367 'dataIndex' => 'expitem_expcat_id_expcat_descrip',
368 'header' => 'Category',
372 'dataIndex' => 'expitem_memo',
373 'header' => 'Description',
378 'dataIndex' => 'expitem_curr_id_curr_name',
379 'header' => 'Currency',
385 'header' => 'Amount',
387 'dataIndex' => 'expitem_amount_fc',
393 'dataIndex' => 'expitem_tax',
396 'header' => 'Total (in base currency)',
398 'dataIndex' => 'expitem_total',
407 array("","","","","","", "Total", array(
408 "=SUM(H11:H{$endrow})",
415 $x->send($this->expense_number.'-'.date('Y-m-d').'.xls');