$left_joins .= " left join tt_clients c on (c.id = l.client_id)";
if (($user->canManageTeam() || $user->isClient()) && $bean->getAttribute('chinvoice'))
$left_joins .= " left join tt_invoices i on (i.id = l.invoice_id and i.status = 1)";
- if ($user->canManageTeam() || $user->isClient() || in_array('ex', explode(',', $user->plugins)))
+ if ($user->canManageTeam() || $user->isClient() || $user->isPluginEnabled('ex'))
$left_joins .= " left join tt_users u on (u.id = l.user_id)";
if ($bean->getAttribute('chproject') || 'project' == $group_by_option)
$left_joins .= " left join tt_projects p on (p.id = l.project_id)";
// with an exception of sorting part, that is added in the end.
// However, when we have expenses, we need to do a union with a separate query for expense items from tt_expense_items table.
- if ($bean->getAttribute('chcost') && in_array('ex', explode(',', $user->plugins))) { // if ex(penses) plugin is enabled
+ if ($bean->getAttribute('chcost') && $user->isPluginEnabled('ex')) { // if ex(penses) plugin is enabled
$fields = array(); // An array of fields for database query.
array_push($fields, 'ei.id');
$left_joins .= " left join tt_clients c on (c.id = l.client_id)";
if (($user->canManageTeam() || $user->isClient()) && $report['show_invoice'])
$left_joins .= " left join tt_invoices i on (i.id = l.invoice_id and i.status = 1)";
- if ($user->canManageTeam() || $user->isClient() || in_array('ex', explode(',', $user->plugins)))
+ if ($user->canManageTeam() || $user->isClient() || $user->isPluginEnabled('ex'))
$left_joins .= " left join tt_users u on (u.id = l.user_id)";
if ($report['show_project'] || 'project' == $group_by_option)
$left_joins .= " left join tt_projects p on (p.id = l.project_id)";
// with an exception of sorting part, that is added in the end.
// However, when we have expenses, we need to do a union with a separate query for expense items from tt_expense_items table.
- if ($report['show_cost'] && in_array('ex', explode(',', $user->plugins))) { // if ex(penses) plugin is enabled
+ if ($report['show_cost'] && $user->isPluginEnabled('ex')) { // if ex(penses) plugin is enabled
$fields = array(); // An array of fields for database query.
array_push($fields, 'ei.id');
// By now we have sql for time items.
// However, when we have expenses, we need to do a union with a separate query for expense items from tt_expense_items table.
- if ($bean->getAttribute('chcost') && in_array('ex', explode(',', $user->plugins))) { // if ex(penses) plugin is enabled
+ if ($bean->getAttribute('chcost') && $user->isPluginEnabled('ex')) { // if ex(penses) plugin is enabled
// Determine group by field and a required join.
$group_join = null;
// By now we have sql for time items.
// However, when we have expenses, we need to do a union with a separate query for expense items from tt_expense_items table.
- if ($report['show_cost'] && in_array('ex', explode(',', $user->plugins))) { // if ex(penses) plugin is enabled
+ if ($report['show_cost'] && $user->isPluginEnabled('ex')) { // if ex(penses) plugin is enabled
// Determine group by field and a required join.
$group_join = null;
$sql = "select sum(time_to_sec(l.duration)) as time, null as cost, null as expenses from tt_log l $where";
// If we have expenses, query becomes a bit more complex.
- if ($bean->getAttribute('chcost') && in_array('ex', explode(',', $user->plugins))) {
+ if ($bean->getAttribute('chcost') && $user->isPluginEnabled('ex')) {
$where = ttReportHelper::getExpenseWhere($bean);
$sql_for_expenses = "select null as time, sum(cost) as cost, sum(cost) as expenses from tt_expense_items ei $where";
// Create a combined query.
// Execute query.
$res = $mdb2->query($sql);
- if (!is_a($res, 'PEAR_Error')) {
- $val = $res->fetchRow();
- $total_time = $val['time'] ? sec_to_time_fmt_hm($val['time']) : null;
- if ($bean->getAttribute('chcost')) {
- $total_cost = $val['cost'];
- if (!$total_cost) $total_cost = '0.00';
- if ('.' != $user->decimal_mark)
- $total_cost = str_replace('.', $user->decimal_mark, $total_cost);
- $total_expenses = $val['expenses'];
- if (!$total_expenses) $total_expenses = '0.00';
- if ('.' != $user->decimal_mark)
- $total_expenses = str_replace('.', $user->decimal_mark, $total_expenses);
- }
- } else
- die($res->getMessage());
+ if (is_a($res, 'PEAR_Error')) die($res->getMessage());
+
+ $val = $res->fetchRow();
+ $total_time = $val['time'] ? sec_to_time_fmt_hm($val['time']) : null;
+ if ($bean->getAttribute('chcost')) {
+ $total_cost = $val['cost'];
+ if (!$total_cost) $total_cost = '0.00';
+ if ('.' != $user->decimal_mark)
+ $total_cost = str_replace('.', $user->decimal_mark, $total_cost);
+ $total_expenses = $val['expenses'];
+ if (!$total_expenses) $total_expenses = '0.00';
+ if ('.' != $user->decimal_mark)
+ $total_expenses = str_replace('.', $user->decimal_mark, $total_expenses);
+ }
if ($bean->getAttribute('period'))
$period = new Period($bean->getAttribute('period'), new DateAndTime($user->date_format));
static function getFavTotals($report)
{
global $user;
-
+
$mdb2 = getConnection();
-
+
$where = ttReportHelper::getFavWhere($report);
-
+
// Start with a query for time items.
if ($report['show_cost']) {
if (MODE_TIME == $user->tracking_mode) {
sum(cast(l.billable * coalesce(upb.rate, 0) * time_to_sec(l.duration)/3600 as decimal(10,2))) as cost,
null as expenses
from tt_log l
- left join tt_user_project_binds upb on (l.user_id = upb.user_id and l.project_id = upb.project_id) $where";
+ left join tt_user_project_binds upb on (l.user_id = upb.user_id and l.project_id = upb.project_id) $where";
}
} else
$sql = "select sum(time_to_sec(l.duration)) as time, null as cost, null as expenses from tt_log l $where";
-
+
// If we have expenses, query becomes a bit more complex.
- if ($report['show_cost'] && in_array('ex', explode(',', $user->plugins))) {
+ if ($report['show_cost'] && $user->isPluginEnabled('ex')) {
$where = ttReportHelper::getFavExpenseWhere($report);
$sql_for_expenses = "select null as time, sum(cost) as cost, sum(cost) as expenses from tt_expense_items ei $where";
// Create a combined query.
$sql = "select sum(time) as time, sum(cost) as cost, sum(expenses) as expenses from (($sql) union all ($sql_for_expenses)) t";
- }
+ }
- // Execute query.
+ // Execute query.
$res = $mdb2->query($sql);
- if (!is_a($res, 'PEAR_Error')) {
- $val = $res->fetchRow();
- $total_time = $val['time'] ? sec_to_time_fmt_hm($val['time']) : null;
- if ($report['show_cost']) {
- $total_cost = $val['cost'];
- if (!$total_cost) $total_cost = '0.00';
- if ('.' != $user->decimal_mark)
- $total_cost = str_replace('.', $user->decimal_mark, $total_cost);
-
- $total_expenses = $val['expenses'];
- if (!$total_expenses) $total_expenses = '0.00';
- if ('.' != $user->decimal_mark)
- $total_expenses = str_replace('.', $user->decimal_mark, $total_expenses);
- }
- } else
- die($res->getMessage());
-
+ if (is_a($res, 'PEAR_Error')) die($res->getMessage());
+
+ $val = $res->fetchRow();
+ $total_time = $val['time'] ? sec_to_time_fmt_hm($val['time']) : null;
+ if ($report['show_cost']) {
+ $total_cost = $val['cost'];
+ if (!$total_cost) $total_cost = '0.00';
+ if ('.' != $user->decimal_mark)
+ $total_cost = str_replace('.', $user->decimal_mark, $total_cost);
+ $total_expenses = $val['expenses'];
+ if (!$total_expenses) $total_expenses = '0.00';
+ if ('.' != $user->decimal_mark)
+ $total_expenses = str_replace('.', $user->decimal_mark, $total_expenses);
+ }
+
if ($report['period'])
$period = new Period($report['period'], new DateAndTime($user->date_format));
else {
}
$totals['start_date'] = $period->getBeginDate();
- $totals['end_date'] = $period->getEndDate();
- $totals['time'] = $total_time;
- $totals['cost'] = $total_cost;
- $totals['expenses'] = $total_expenses;
+ $totals['end_date'] = $period->getEndDate();
+ $totals['time'] = $total_time;
+ $totals['cost'] = $total_cost;
+ $totals['expenses'] = $total_expenses;
return $totals;
}
-
+
// The assignToInvoice assigns a set of records to a specific invoice.
static function assignToInvoice($invoice_id, $time_log_ids, $expense_item_ids)
{
- $mdb2 = getConnection();
- if ($time_log_ids) {
+ $mdb2 = getConnection();
+ if ($time_log_ids) {
$sql = "update tt_log set invoice_id = ".$mdb2->quote($invoice_id).
" where id in(".join(', ', $time_log_ids).")";
$affected = $mdb2->exec($sql);
- if (is_a($affected, 'PEAR_Error'))
- die($affected->getMessage());
- }
+ if (is_a($affected, 'PEAR_Error')) die($affected->getMessage());
+ }
if ($expense_item_ids) {
$sql = "update tt_expense_items set invoice_id = ".$mdb2->quote($invoice_id).
" where id in(".join(', ', $expense_item_ids).")";
$affected = $mdb2->exec($sql);
- if (is_a($affected, 'PEAR_Error'))
- die($affected->getMessage());
- }
+ if (is_a($affected, 'PEAR_Error')) die($affected->getMessage());
+ }
}
// prepareReportBody - prepares an email body for report.
if ($group_by && 'no_grouping' != $group_by)
$subtotals = ttReportHelper::getSubtotals($bean);
$totals = ttReportHelper::getTotals($bean);
-
+
// Use custom fields plugin if it is enabled.
- if (in_array('cf', explode(',', $user->plugins)))
+ if ($user->isPluginEnabled('cf'))
$custom_fields = new CustomFields($user->team_id);
// Define some styles to use in email.
$cellRightAligned = 'text-align: right; vertical-align: top;';
$cellLeftAlignedSubtotal = 'font-weight: bold; text-align: left; vertical-align: top;';
$cellRightAlignedSubtotal = 'font-weight: bold; text-align: right; vertical-align: top;';
-
+
// Start creating email body.
$body = '<html>';
$body .= '<head><meta http-equiv="content-type" content="text/html; charset='.CHARSET.'"></head>';
$body .= '<body>';
-
+
// Output title.
$body .= '<p style="'.$style_title.'">'.$i18n->getKey('form.mail.report_subject').': '.$totals['start_date'].' - '.$totals['end_date'].'</p>';
-
+
// Output comment.
if ($comment) $body .= '<p>'.htmlspecialchars($comment).'</p>';
if ($bean->getAttribute('chtotalsonly')) {
// Totals only report. Output subtotals.
-
+
// Determine group_by header.
if ('cf_1' == $group_by)
$group_by_header = htmlspecialchars($custom_fields->fields[0]['label']);
$key = 'label.'.$group_by;
$group_by_header = $i18n->getKey($key);
}
-
+
$body .= '<table border="0" cellpadding="4" cellspacing="0" width="100%">';
$body .= '<tr>';
$body .= '<td style="'.$tableHeader.'">'.$group_by_header.'</td>';
}
$body .= '</tr>';
}
-
+
// Print totals.
$body .= '<tr><td> </td></tr>';
$body .= '<tr style="'.$rowSubtotal.'">';
$body .= '<td style="'.$cellLeftAlignedSubtotal.'">'.$i18n->getKey('label.total').'</td>';
if ($bean->getAttribute('chduration')) {
- $body .= '<td style="'.$cellRightAlignedSubtotal.'">';
- if ($totals['time'] <> '0:00') $body .= $totals['time'];
- $body .= '</td>';
+ $body .= '<td style="'.$cellRightAlignedSubtotal.'">';
+ if ($totals['time'] <> '0:00') $body .= $totals['time'];
+ $body .= '</td>';
}
if ($bean->getAttribute('chcost')) {
- $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
+ $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
$body .= ($user->canManageTeam() || $user->isClient()) ? $totals['cost'] : $totals['expenses'];
- $body .= '</td>';
+ $body .= '</td>';
}
$body .= '</tr>';
-
+
$body .= '</table>';
} else {
// Regular report.
-
+
// Print table header.
$body .= '<table border="0" cellpadding="4" cellspacing="0" width="100%">';
$body .= '<tr>';
if ($bean->getAttribute('chinvoice'))
$body .= '<td style="'.$tableHeader.'">'.$i18n->getKey('label.invoice').'</td>';
$body .= '</tr>';
-
+
// Initialize variables to print subtotals.
if ($items && 'no_grouping' != $group_by) {
$print_subtotals = true;
$prev_date = '';
$cur_date = '';
$row_style = $rowItem;
-
+
// Print report items.
if (is_array($items)) {
foreach ($items as $record) {
if ($bean->getAttribute('chduration')) $body .= '<td style="'.$cellRightAlignedSubtotal.'">'.$subtotals[$prev_grouped_by]['time'].'</td>';
if ($bean->getAttribute('chnote')) $body .= '<td></td>';
if ($bean->getAttribute('chcost')) {
- $body .= '<td style="'.$cellRightAlignedSubtotal.'">';
- $body .= ($user->canManageTeam() || $user->isClient()) ? $subtotals[$prev_grouped_by]['cost'] : $subtotals[$prev_grouped_by]['expenses'];
- $body .= '</td>';
+ $body .= '<td style="'.$cellRightAlignedSubtotal.'">';
+ $body .= ($user->canManageTeam() || $user->isClient()) ? $subtotals[$prev_grouped_by]['cost'] : $subtotals[$prev_grouped_by]['expenses'];
+ $body .= '</td>';
}
if ($bean->getAttribute('chinvoice')) $body .= '<td></td>';
$body .= '</tr>';
}
$first_pass = false;
}
-
+
// Print a regular row.
if ($cur_date != $prev_date)
$row_style = ($row_style == $rowItem) ? $rowItemAlt : $rowItem;
if ($bean->getAttribute('chinvoice'))
$body .= '<td style="'.$cellRightAligned.'">'.htmlspecialchars($record['invoice']).'</td>';
$body .= '</tr>';
-
+
$prev_date = $record['date'];
if ($print_subtotals)
$prev_grouped_by = $record['grouped_by'];
}
}
-
+
// Print a terminating subtotal.
if ($print_subtotals) {
$body .= '<tr style="'.$rowSubtotal.'">';
if ($bean->getAttribute('chinvoice')) $body .= '<td></td>';
$body .= '</tr>';
}
-
+
// Print totals.
$body .= '<tr><td> </td></tr>';
$body .= '<tr style="'.$rowSubtotal.'">';
if ($bean->getAttribute('chduration')) $body .= '<td style="'.$cellRightAlignedSubtotal.'">'.$totals['time'].'</td>';
if ($bean->getAttribute('chnote')) $body .= '<td></td>';
if ($bean->getAttribute('chcost')) {
- $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
- $body .= ($user->canManageTeam() || $user->isClient()) ? $totals['cost'] : $totals['expenses'];
- $body .= '</td>';
+ $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
+ $body .= ($user->canManageTeam() || $user->isClient()) ? $totals['cost'] : $totals['expenses'];
+ $body .= '</td>';
}
if ($bean->getAttribute('chinvoice')) $body .= '<td></td>';
$body .= '</tr>';
-
+
$body .= '</table>';
}
-
+
// Output footer.
if (!defined('REPORT_FOOTER') || !(REPORT_FOOTER == false))
$body .= '<p style="text-align: center;">'.$i18n->getKey('form.mail.footer').'</p>';
return $body;
}
-
-// prepareFavReportBody - prepares an email body for a favorite report.
+
+ // prepareFavReportBody - prepares an email body for a favorite report.
static function prepareFavReportBody($report)
{
- global $user;
- global $i18n;
-
- $items = ttReportHelper::getFavItems($report);
+ global $user;
+ global $i18n;
+
+ $items = ttReportHelper::getFavItems($report);
$group_by = $report['group_by'];
- if ($group_by && 'no_grouping' != $group_by)
- $subtotals = ttReportHelper::getFavSubtotals($report);
- $totals = ttReportHelper::getFavTotals($report);
-
+ if ($group_by && 'no_grouping' != $group_by)
+ $subtotals = ttReportHelper::getFavSubtotals($report);
+ $totals = ttReportHelper::getFavTotals($report);
+
// Use custom fields plugin if it is enabled.
- if (in_array('cf', explode(',', $user->plugins)))
+ if ($user->isPluginEnabled('cf'))
$custom_fields = new CustomFields($user->team_id);
// Define some styles to use in email.
$cellRightAligned = 'text-align: right; vertical-align: top;';
$cellLeftAlignedSubtotal = 'font-weight: bold; text-align: left; vertical-align: top;';
$cellRightAlignedSubtotal = 'font-weight: bold; text-align: right; vertical-align: top;';
-
+
// Start creating email body.
$body = '<html>';
$body .= '<head><meta http-equiv="content-type" content="text/html; charset='.CHARSET.'"></head>';
$body .= '<body>';
-
+
// Output title.
$body .= '<p style="'.$style_title.'">'.$i18n->getKey('form.mail.report_subject').': '.$totals['start_date'].' - '.$totals['end_date'].'</p>';
if ($report['show_totals_only']) {
// Totals only report. Output subtotals.
-
+
// Determine group_by header.
if ('cf_1' == $group_by)
$group_by_header = htmlspecialchars($custom_fields->fields[0]['label']);
$key = 'label.'.$group_by;
$group_by_header = $i18n->getKey($key);
}
-
+
$body .= '<table border="0" cellpadding="4" cellspacing="0" width="100%">';
$body .= '<tr>';
$body .= '<td style="'.$tableHeader.'">'.$group_by_header.'</td>';
}
$body .= '</tr>';
}
-
+
// Print totals.
$body .= '<tr><td> </td></tr>';
$body .= '<tr style="'.$rowSubtotal.'">';
$body .= '<td style="'.$cellLeftAlignedSubtotal.'">'.$i18n->getKey('label.total').'</td>';
if ($report['show_duration']) {
- $body .= '<td style="'.$cellRightAlignedSubtotal.'">';
- if ($totals['time'] <> '0:00') $body .= $totals['time'];
- $body .= '</td>';
+ $body .= '<td style="'.$cellRightAlignedSubtotal.'">';
+ if ($totals['time'] <> '0:00') $body .= $totals['time'];
+ $body .= '</td>';
}
if ($report['show_cost']) {
- $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
+ $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
$body .= ($user->canManageTeam() || $user->isClient()) ? $totals['cost'] : $totals['expenses'];
- $body .= '</td>';
+ $body .= '</td>';
}
$body .= '</tr>';
-
+
$body .= '</table>';
} else {
// Regular report.
-
+
// Print table header.
$body .= '<table border="0" cellpadding="4" cellspacing="0" width="100%">';
$body .= '<tr>';
if ($report['show_invoice'])
$body .= '<td style="'.$tableHeader.'">'.$i18n->getKey('label.invoice').'</td>';
$body .= '</tr>';
-
+
// Initialize variables to print subtotals.
if ($items && 'no_grouping' != $group_by) {
$print_subtotals = true;
$prev_date = '';
$cur_date = '';
$row_style = $rowItem;
-
+
// Print report items.
if (is_array($items)) {
foreach ($items as $record) {
}
if ($report['show_invoice']) $body .= '<td></td>';
$body .= '</tr>';
- $body .= '<tr><td> </td></tr>';
+ $body .= '<tr><td> </td></tr>';
}
$first_pass = false;
- }
-
+ }
+
// Print a regular row.
if ($cur_date != $prev_date)
$row_style = ($row_style == $rowItem) ? $rowItemAlt : $rowItem;
if ($report['show_invoice'])
$body .= '<td style="'.$cellRightAligned.'">'.htmlspecialchars($record['invoice']).'</td>';
$body .= '</tr>';
-
+
$prev_date = $record['date'];
if ($print_subtotals)
$prev_grouped_by = $record['grouped_by'];
}
}
-
+
// Print a terminating subtotal.
if ($print_subtotals) {
$body .= '<tr style="'.$rowSubtotal.'">';
if ($report['show_invoice']) $body .= '<td></td>';
$body .= '</tr>';
}
-
+
// Print totals.
$body .= '<tr><td> </td></tr>';
$body .= '<tr style="'.$rowSubtotal.'">';
if ($report['show_duration']) $body .= '<td style="'.$cellRightAlignedSubtotal.'">'.$totals['time'].'</td>';
if ($report['show_note']) $body .= '<td></td>';
if ($report['show_cost']) {
- $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
- $body .= ($user->canManageTeam() || $user->isClient()) ? $totals['cost'] : $totals['expenses'];
- $body .= '</td>';
+ $body .= '<td nowrap style="'.$cellRightAlignedSubtotal.'">'.htmlspecialchars($user->currency).' ';
+ $body .= ($user->canManageTeam() || $user->isClient()) ? $totals['cost'] : $totals['expenses'];
+ $body .= '</td>';
}
if ($report['show_invoice']) $body .= '<td></td>';
$body .= '</tr>';
-
+
$body .= '</table>';
}
-
+
// Output footer.
if (!defined('REPORT_FOOTER') || !(REPORT_FOOTER == false))
$body .= '<p style="text-align: center;">'.$i18n->getKey('form.mail.footer').'</p>';
return $body;
}
-
+
// sendFavReport - sends a favorite report to a specified email, called from cron.php
static function sendFavReport($report, $email) {
// We are called from cron.php, we have no $bean in session.
// cron.php set global $user and $i18n objects to match our favorite report user.
global $user;
global $i18n;
-
+
// Prepare report body.
$body = ttReportHelper::prepareFavReportBody($report);
-
+
import('mail.Mailer');
$mailer = new Mailer();
$mailer->setCharSet(CHARSET);
$mailer->setSendType(MAIL_MODE);
if (!$mailer->send($report['name'], $body))
return false;
-
+
return true;
}
}