Commit 4890a28 folded templates/partials/app-flash.phtml into
app-toast-stack.phtml, which the base layout now mounts itself. 14
helpdesk views still required the deleted partial and crashed every
helpdesk page with a 500 (Failed opening required app-flash.phtml).
Remove the redundant requires; the unified toast stack continues to
render flash messages via the layout.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
524 lines
26 KiB
PHTML
524 lines
26 KiB
PHTML
<?php
|
|
|
|
/**
|
|
* @var string $customerNo
|
|
* @var array $customer
|
|
* @var bool $hasError
|
|
* @var string $errorMessage
|
|
* @var string $customerName
|
|
* @var string $backUrl
|
|
*/
|
|
|
|
$customerNo = $customerNo ?? '';
|
|
$customer = is_array($customer ?? null) ? $customer : [];
|
|
$hasError = $hasError ?? false;
|
|
$errorMessage = $errorMessage ?? '';
|
|
$customerName = $customerName ?? '';
|
|
$backUrl = $backUrl ?? lurl('helpdesk');
|
|
|
|
$searchToolbarFilterSchema = is_array($searchToolbarFilterSchema ?? null) ? $searchToolbarFilterSchema : [];
|
|
$drawerToolbarFilterSchema = is_array($drawerToolbarFilterSchema ?? null) ? $drawerToolbarFilterSchema : [];
|
|
$toolbarFilterState = is_array($toolbarFilterState ?? null) ? $toolbarFilterState : [];
|
|
$toolbarOptionSets = is_array($toolbarOptionSets ?? null) ? $toolbarOptionSets : [];
|
|
$filterChipMeta = is_array($filterChipMeta ?? null) ? $filterChipMeta : [];
|
|
$clientFilterSchema = is_array($clientFilterSchema ?? null) ? $clientFilterSchema : [];
|
|
$searchConfig = is_array($searchConfig ?? null) ? $searchConfig : null;
|
|
|
|
?>
|
|
<div class="app-details-container"
|
|
data-app-component="helpdesk-detail"
|
|
data-customer-no="<?php e($customerNo); ?>"
|
|
data-customer-name="<?php e($customerName); ?>"
|
|
data-support-dashboard-url="<?php e(lurl('helpdesk/debitor-support-dashboard-data')); ?>"
|
|
data-contacts-url="<?php e(lurl('helpdesk/debitor-contacts-data')); ?>"
|
|
data-tickets-url="<?php e(lurl('helpdesk/debitor-tickets-data')); ?>"
|
|
data-ticket-base-url="<?php e(lurl('helpdesk/ticket/')); ?>"
|
|
data-communication-url="<?php e(lurl('helpdesk/debitor-communication-data')); ?>"
|
|
data-file-download-url="<?php e(lurl('helpdesk/ticket-file-data')); ?>"
|
|
data-sales-dashboard-url="<?php e(lurl('helpdesk/debitor-sales-dashboard-data')); ?>"
|
|
data-meetings-url="<?php e(lurl('helpdesk/debitor-meetings-data')); ?>"
|
|
data-controlling-dashboard-url="<?php e(lurl('helpdesk/debitor-controlling-dashboard-data')); ?>"
|
|
>
|
|
<section>
|
|
<?php
|
|
$titlebarActions = [];
|
|
if (!$hasError && $customer !== []) {
|
|
$titlebarActions[] = [
|
|
'label' => t('Refresh data'),
|
|
'type' => 'button',
|
|
'name' => 'support-refresh',
|
|
'class' => 'secondary outline',
|
|
];
|
|
}
|
|
|
|
$titlebar = [
|
|
'title' => $customerName,
|
|
'backHref' => $backUrl,
|
|
'backTitle' => t('Back'),
|
|
'actions' => $titlebarActions,
|
|
];
|
|
require templatePath('partials/app-details-titlebar.phtml');
|
|
?>
|
|
|
|
<?php if ($hasError): ?>
|
|
<div class="notice" data-variant="error" role="alert">
|
|
<p><?php e(t('Could not connect to Business Central.')); ?></p>
|
|
<?php if ($errorMessage !== ''): ?>
|
|
<small><?php e($errorMessage); ?></small>
|
|
<?php endif; ?>
|
|
</div>
|
|
<?php elseif ($customer !== []): ?>
|
|
|
|
<!-- Tabs: Support / Sales / Controlling -->
|
|
<div class="app-tabs" data-tabs data-app-component="tabs" data-tabs-param="tab" data-tabs-storage-key="helpdesk-debitor-detail">
|
|
<div class="app-tabs-nav">
|
|
<button type="button" data-tab="support" data-tab-default>
|
|
<?php e(t('Support')); ?>
|
|
</button>
|
|
<button type="button" data-tab="sales">
|
|
<?php e(t('Sales')); ?>
|
|
</button>
|
|
<button type="button" data-tab="controlling">
|
|
<?php e(t('Controlling')); ?>
|
|
</button>
|
|
</div>
|
|
|
|
<!-- Support panel -->
|
|
<div data-tab-panel="support">
|
|
<div id="support-loading">
|
|
<div class="helpdesk-support-metrics">
|
|
<?php for ($i = 0; $i < 4; $i++): ?>
|
|
<div class="helpdesk-skeleton-kpi">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-label"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-value"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-trend"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div class="helpdesk-skeleton-divider"></div>
|
|
<?php for ($i = 0; $i < 4; $i++): ?>
|
|
<div class="helpdesk-skeleton-row">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div id="support-content" hidden>
|
|
<section>
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Tickets')); ?></h3>
|
|
<div class="helpdesk-support-metrics">
|
|
<article class="helpdesk-support-metric helpdesk-kpi-clickable" data-kpi-filter="open">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Open tickets')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="support-kpi-open-tickets">—</p>
|
|
<p class="helpdesk-support-metric-trend" id="support-kpi-open-trend"></p>
|
|
</article>
|
|
<article class="helpdesk-support-metric helpdesk-kpi-clickable" data-kpi-filter="">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('New (30d)')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="support-kpi-created-30d">—</p>
|
|
<p class="helpdesk-support-metric-trend" id="support-kpi-created-trend"></p>
|
|
</article>
|
|
<article class="helpdesk-support-metric helpdesk-kpi-clickable" data-kpi-filter="closed">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Resolved (30d)')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="support-kpi-closed-30d">—</p>
|
|
<p class="helpdesk-support-metric-trend" id="support-kpi-closed-trend"></p>
|
|
</article>
|
|
<article class="helpdesk-support-metric helpdesk-kpi-clickable" data-kpi-sort="Last_Activity_Date:asc">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Avg. age open')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="support-kpi-avg-age">—</p>
|
|
<p class="helpdesk-support-metric-trend" id="support-kpi-age-hint"></p>
|
|
</article>
|
|
</div>
|
|
</section>
|
|
|
|
<section id="support-recommendations-wrapper" hidden>
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Attention needed')); ?></h3>
|
|
<div id="support-system-recommendations"></div>
|
|
</section>
|
|
|
|
<section class="helpdesk-support-ticket-list">
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Ticket list')); ?></h3>
|
|
<?php
|
|
$filterUiNamespace = 'helpdesk-tickets';
|
|
require templatePath('partials/app-list-filters.phtml');
|
|
?>
|
|
<div id="helpdesk-tickets-grid"></div>
|
|
</section>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Sales panel -->
|
|
<div data-tab-panel="sales" hidden>
|
|
<div id="sales-loading">
|
|
<div class="helpdesk-support-metrics">
|
|
<?php for ($i = 0; $i < 4; $i++): ?>
|
|
<div class="helpdesk-skeleton-kpi">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-label"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-value"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-trend"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div class="helpdesk-skeleton-divider"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-line" style="width:30%;margin-bottom:0.75rem"></div>
|
|
<?php for ($i = 0; $i < 3; $i++): ?>
|
|
<div class="helpdesk-skeleton-row">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div id="sales-content" hidden>
|
|
<section>
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Contracts & products')); ?></h3>
|
|
<div class="helpdesk-support-metrics">
|
|
<article class="helpdesk-support-metric">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Monthly volume')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="sales-kpi-monthly-volume">0</p>
|
|
<p class="helpdesk-support-metric-trend" id="sales-kpi-monthly-volume-trend"></p>
|
|
</article>
|
|
<article class="helpdesk-support-metric">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Active contracts')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="sales-kpi-active-contracts">0</p>
|
|
<p class="helpdesk-support-metric-trend" id="sales-kpi-active-contracts-trend"></p>
|
|
</article>
|
|
<article class="helpdesk-support-metric">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Avg. contract value')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="sales-kpi-avg-value">0</p>
|
|
<p class="helpdesk-support-metric-trend" id="sales-kpi-avg-value-trend"></p>
|
|
</article>
|
|
<article class="helpdesk-support-metric">
|
|
<p class="helpdesk-support-metric-label"><?php e(t('Next invoicing')); ?></p>
|
|
<p class="helpdesk-support-metric-value" id="sales-kpi-next-invoicing">—</p>
|
|
<p class="helpdesk-support-metric-trend" id="sales-kpi-next-invoicing-trend"></p>
|
|
</article>
|
|
</div>
|
|
</section>
|
|
|
|
<section id="sales-trend-section">
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Contract trend')); ?></h3>
|
|
<div id="sales-trend-chart"></div>
|
|
</section>
|
|
|
|
<div class="helpdesk-sales-split">
|
|
<section id="sales-contacts-section" class="helpdesk-sales-split-main">
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Contacts')); ?></h3>
|
|
<?php
|
|
$filterUiNamespace = 'helpdesk-contacts';
|
|
$searchToolbarFilterSchema = $contactsSearchToolbarFilterSchema;
|
|
$drawerToolbarFilterSchema = $contactsDrawerToolbarFilterSchema;
|
|
$toolbarFilterState = $contactsToolbarFilterState;
|
|
$toolbarOptionSets = $contactsToolbarOptionSets;
|
|
require templatePath('partials/app-list-filters.phtml');
|
|
?>
|
|
<div id="helpdesk-contacts-grid"></div>
|
|
</section>
|
|
|
|
<section id="sales-meetings-section" class="helpdesk-sales-split-aside">
|
|
<h3 class="helpdesk-support-section-title"><?php e(t('Meetings')); ?></h3>
|
|
<div id="meetings-loading">
|
|
<?php for ($i = 0; $i < 3; $i++): ?>
|
|
<div class="helpdesk-skeleton-row">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div id="meetings-content" hidden>
|
|
<div id="meetings-timeline"></div>
|
|
</div>
|
|
<div id="meetings-empty" hidden></div>
|
|
<div id="meetings-error" hidden></div>
|
|
</section>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Controlling panel -->
|
|
<div data-tab-panel="controlling" hidden>
|
|
<div id="controlling-spinner">
|
|
<div class="helpdesk-support-metrics">
|
|
<?php for ($i = 0; $i < 4; $i++): ?>
|
|
<div class="helpdesk-skeleton-kpi">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-label"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-value"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-kpi-trend"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div class="helpdesk-skeleton-divider"></div>
|
|
<div class="helpdesk-skeleton" style="height:10rem;margin-bottom:1rem"></div>
|
|
<div class="helpdesk-skeleton-divider"></div>
|
|
<?php for ($i = 0; $i < 3; $i++): ?>
|
|
<div class="helpdesk-skeleton-row">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-cell helpdesk-skeleton-cell-narrow"></div>
|
|
</div>
|
|
<?php endfor; ?>
|
|
</div>
|
|
<div id="controlling-content" hidden>
|
|
<div class="helpdesk-segment-control" id="controlling-period-selector">
|
|
<input type="radio" name="controlling-period" id="controlling-period-30" value="30">
|
|
<label for="controlling-period-30"><?php e(t('30 days')); ?></label>
|
|
<input type="radio" name="controlling-period" id="controlling-period-90" value="90" checked>
|
|
<label for="controlling-period-90"><?php e(t('90 days')); ?></label>
|
|
<input type="radio" name="controlling-period" id="controlling-period-180" value="180">
|
|
<label for="controlling-period-180"><?php e(t('6 months')); ?></label>
|
|
<input type="radio" name="controlling-period" id="controlling-period-365" value="365">
|
|
<label for="controlling-period-365"><?php e(t('1 year')); ?></label>
|
|
</div>
|
|
|
|
<div class="helpdesk-support-metrics" id="controlling-kpis">
|
|
<div class="helpdesk-support-metric">
|
|
<div class="helpdesk-support-metric-label"><?php e(t('Ticket volume')); ?></div>
|
|
<div class="helpdesk-support-metric-value" id="controlling-kpi-volume">—</div>
|
|
<p class="helpdesk-support-metric-trend" id="controlling-kpi-volume-trend"></p>
|
|
</div>
|
|
<div class="helpdesk-support-metric">
|
|
<div class="helpdesk-support-metric-label"><?php e(t('Close rate')); ?> <span class="helpdesk-kpi-info" data-tooltip="<?php e(t('kpi_tooltip_close_rate')); ?>" data-tooltip-pos="top" tabindex="0">i</span></div>
|
|
<div class="helpdesk-support-metric-value" id="controlling-kpi-closerate">—</div>
|
|
<p class="helpdesk-support-metric-trend" id="controlling-kpi-closerate-trend"></p>
|
|
</div>
|
|
<div class="helpdesk-support-metric">
|
|
<div class="helpdesk-support-metric-label"><?php e(t('Avg. resolution')); ?> <span class="helpdesk-kpi-info" data-tooltip="<?php e(t('kpi_tooltip_resolution')); ?>" data-tooltip-pos="top" tabindex="0">i</span></div>
|
|
<div class="helpdesk-support-metric-value" id="controlling-kpi-resolution">—</div>
|
|
<p class="helpdesk-support-metric-trend" id="controlling-kpi-resolution-trend"></p>
|
|
</div>
|
|
<div class="helpdesk-support-metric">
|
|
<div class="helpdesk-support-metric-label"><?php e(t('Open backlog')); ?> <span class="helpdesk-kpi-info" data-tooltip="<?php e(t('kpi_tooltip_backlog')); ?>" data-tooltip-pos="top" tabindex="0">i</span></div>
|
|
<div class="helpdesk-support-metric-value" id="controlling-kpi-backlog">—</div>
|
|
<p class="helpdesk-support-metric-trend" id="controlling-kpi-backlog-trend"></p>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="app-stats-table">
|
|
<div class="app-stats-table-header"><?php e(t('Ticket trend')); ?></div>
|
|
<div class="helpdesk-controlling-chart" id="controlling-trend-chart"></div>
|
|
</div>
|
|
|
|
<div class="app-stats-table">
|
|
<div class="app-stats-table-header"><?php e(t('Risk assessment')); ?></div>
|
|
<div id="controlling-risk-indicators"></div>
|
|
</div>
|
|
</div>
|
|
<div id="controlling-error" hidden></div>
|
|
<div id="controlling-empty" hidden></div>
|
|
</div>
|
|
</div>
|
|
<?php endif; ?>
|
|
</section>
|
|
|
|
<?php if (!$hasError && $customer !== []): ?>
|
|
<aside id="app-details-aside-section">
|
|
<div class="app-details-aside-section helpdesk-comm-aside">
|
|
<hgroup>
|
|
<h2><?php e(t('Ticket communication')); ?></h2>
|
|
<p><?php e(t('Last 5 tickets')); ?></p>
|
|
</hgroup>
|
|
<hr>
|
|
<div id="debitor-communication-loading">
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-aside-bubble helpdesk-skeleton-aside-bubble-short"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-aside-bubble helpdesk-skeleton-aside-bubble-alt"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-aside-bubble"></div>
|
|
<div class="helpdesk-skeleton helpdesk-skeleton-aside-bubble helpdesk-skeleton-aside-bubble-alt" style="width:50%"></div>
|
|
</div>
|
|
<div id="debitor-communication-content" hidden>
|
|
<div id="debitor-communication-feed"></div>
|
|
</div>
|
|
</div>
|
|
</aside>
|
|
<?php endif; ?>
|
|
</div>
|
|
|
|
<!-- Grid.js tickets config -->
|
|
<script type="application/json" id="page-config-helpdesk-tickets"><?php gridJsonForJs([
|
|
'dataUrl' => lurl('helpdesk/debitor-tickets-data'),
|
|
'categoryOptionsUrl' => lurl('helpdesk/debitor-ticket-categories-data'),
|
|
'customerNo' => $customerNo,
|
|
'customerName' => $customerName,
|
|
'ticketBaseUrl' => lurl('helpdesk/ticket/'),
|
|
'gridLang' => gridLang(),
|
|
'labels' => [
|
|
'ticketNo' => t('Ticket No.'),
|
|
'description' => t('Description'),
|
|
'status' => t('Status'),
|
|
'category' => t('Category'),
|
|
'contact' => t('Contact'),
|
|
'support' => t('Support'),
|
|
'created' => t('Created'),
|
|
'lastActivity' => t('Last activity'),
|
|
],
|
|
'gridSearch' => $searchConfig,
|
|
'filterSchema' => $clientFilterSchema,
|
|
'filterChipMeta' => $filterChipMeta,
|
|
]); ?></script>
|
|
|
|
<!-- Grid.js contacts config -->
|
|
<script type="application/json" id="page-config-helpdesk-contacts"><?php gridJsonForJs([
|
|
'dataUrl' => lurl('helpdesk/debitor-contacts-data'),
|
|
'customerNo' => $customerNo,
|
|
'customerName' => $customerName,
|
|
'gridLang' => gridLang(),
|
|
'labels' => [
|
|
'name' => t('Name'),
|
|
'type' => t('Type'),
|
|
'jobTitle' => t('Job title'),
|
|
'email' => t('E-Mail'),
|
|
'phone' => t('Phone'),
|
|
'mobile' => t('Mobile'),
|
|
],
|
|
'gridSearch' => $contactsSearchConfig,
|
|
'filterSchema' => $contactsClientFilterSchema,
|
|
'filterChipMeta' => $contactsFilterChipMeta,
|
|
]); ?></script>
|
|
|
|
<!-- i18n strings for JS rendering -->
|
|
<script type="application/json" id="helpdesk-i18n"><?php gridJsonForJs([
|
|
'Ticket No.' => t('Ticket No.'),
|
|
'Description' => t('Description'),
|
|
'Status' => t('Status'),
|
|
'Sales' => t('Sales'),
|
|
'Controlling' => t('Controlling'),
|
|
'Category' => t('Category'),
|
|
'Contact' => t('Contact'),
|
|
'Support' => t('Support'),
|
|
'Created' => t('Created'),
|
|
'Last activity' => t('Last activity'),
|
|
'No.' => t('No.'),
|
|
'Name' => t('Name'),
|
|
'Type' => t('Type'),
|
|
'Job title' => t('Job title'),
|
|
'E-Mail' => t('E-Mail'),
|
|
'Phone' => t('Phone'),
|
|
'Mobile' => t('Mobile'),
|
|
'No open tickets' => t('No open tickets'),
|
|
'No tickets found' => t('No tickets found'),
|
|
'No tickets are linked to this debtor in Business Central.' => t('No tickets are linked to this debtor in Business Central.'),
|
|
'No contacts found' => t('No contacts found'),
|
|
'No contacts are linked to this debtor in Business Central.' => t('No contacts are linked to this debtor in Business Central.'),
|
|
'Total tickets' => t('Total tickets'),
|
|
'Critical (>48h)' => t('Critical (>48h)'),
|
|
'Oldest open' => t('Oldest open'),
|
|
'Ticket list' => t('Ticket list'),
|
|
'Attention needed' => t('Attention needed'),
|
|
'No system recommendations right now.' => t('No system recommendations right now.'),
|
|
'helpdesk.recommendation.escalation_overdue' => t('Escalation SLA exceeded by {overdue_hours}h ({escalation_code}).'),
|
|
'helpdesk.recommendation.high_risk_aging' => t('High-risk ticket ({escalation_code}) is open for {age_hours}h.'),
|
|
'helpdesk.recommendation.unassigned_open' => t('Ticket is unassigned for {age_hours}h.'),
|
|
'helpdesk.recommendation.stale_open' => t('No activity for {age_hours}h.'),
|
|
'helpdesk.recommendation.customer_backlog' => t('Customer backlog: {open_tickets} open tickets.'),
|
|
'Contracts & products' => t('Contracts & products'),
|
|
'No contracts found for this customer.' => t('No contracts found for this customer.'),
|
|
'Contract No.' => t('Contract No.'),
|
|
'Product type' => t('Product type'),
|
|
'Amount' => t('Amount'),
|
|
'Active contracts' => t('Active contracts'),
|
|
'Total contracts' => t('Total contracts'),
|
|
'Could not load contracts.' => t('Could not load contracts.'),
|
|
'Escalation code' => t('Escalation code'),
|
|
'Ticket volume' => t('Ticket volume'),
|
|
'Close rate' => t('Close rate'),
|
|
'Avg. resolution' => t('Avg. resolution'),
|
|
'Open backlog' => t('Open backlog'),
|
|
'Backlog shrinking' => t('Backlog shrinking'),
|
|
'Backlog growing' => t('Backlog growing'),
|
|
'unassigned' => t('unassigned'),
|
|
'Ticket trend' => t('Ticket trend'),
|
|
'Risk assessment' => t('Risk assessment'),
|
|
'vs. prev. period' => t('vs. prev. period'),
|
|
'Low' => t('Low'),
|
|
'Medium' => t('Medium'),
|
|
'High' => t('High'),
|
|
'All checks passed' => t('All checks passed'),
|
|
'of' => t('of'),
|
|
'checks flagged' => t('checks flagged'),
|
|
'Limit' => t('Limit'),
|
|
'No controlling data available.' => t('No controlling data available.'),
|
|
'Resolution time' => t('Resolution time'),
|
|
'Oldest open ticket' => t('Oldest open ticket'),
|
|
'Unassigned' => t('Unassigned'),
|
|
'risk_desc_ticket_volume' => t('risk_desc_ticket_volume'),
|
|
'risk_desc_resolution_time' => t('risk_desc_resolution_time'),
|
|
'risk_desc_open_aging' => t('risk_desc_open_aging'),
|
|
'risk_desc_unassigned' => t('risk_desc_unassigned'),
|
|
'Could not load controlling dashboard.' => t('Could not load controlling dashboard.'),
|
|
'Without assignee' => t('Without assignee'),
|
|
'Created' => t('Created'),
|
|
'Closed' => t('Closed'),
|
|
'30 days' => t('30 days'),
|
|
'90 days' => t('90 days'),
|
|
'6 months' => t('6 months'),
|
|
'1 year' => t('1 year'),
|
|
'Oldest open' => t('Oldest open'),
|
|
'Open ticket without activity for' => t('Open ticket without activity for'),
|
|
'hours' => t('hours'),
|
|
'Open ticket without assigned support user' => t('Open ticket without assigned support user'),
|
|
'Follow up oldest open ticket' => t('Follow up oldest open ticket'),
|
|
'Could not load contacts.' => t('Could not load contacts.'),
|
|
'Could not load tickets.' => t('Could not load tickets.'),
|
|
'Ticket communication' => t('Ticket communication'),
|
|
'Last 5 tickets' => t('Last 5 tickets'),
|
|
'No communication found.' => t('No communication found.'),
|
|
'Could not load communication history.' => t('Could not load communication history.'),
|
|
'Some ticket communications could not be loaded completely.' => t('Some ticket communications could not be loaded completely.'),
|
|
'Unknown user' => t('Unknown user'),
|
|
'Unknown time' => t('Unknown time'),
|
|
'Ticket' => t('Ticket'),
|
|
'Activity' => t('Activity'),
|
|
'Message' => t('Message'),
|
|
'Status change' => t('Status change'),
|
|
'Forwarded' => t('Forwarded'),
|
|
'attached a file' => t('attached a file'),
|
|
'logged an activity' => t('logged an activity'),
|
|
'on' => t('on'),
|
|
'SOAP' => t('SOAP'),
|
|
'Activity fallback' => t('Activity fallback'),
|
|
'Loading...' => t('Loading...'),
|
|
'Refresh data' => t('Refresh data'),
|
|
'Active contracts' => t('Active contracts'),
|
|
'Monthly volume' => t('Monthly volume'),
|
|
'Support hours' => t('Support hours'),
|
|
'Next invoicing' => t('Next invoicing'),
|
|
'Contract trend' => t('Contract trend'),
|
|
'New contracts' => t('New contracts'),
|
|
'Ended contracts' => t('Ended contracts'),
|
|
'active' => t('active'),
|
|
'ended' => t('ended'),
|
|
'No contract details available.' => t('No contract details available.'),
|
|
'Could not load sales dashboard.' => t('Could not load sales dashboard.'),
|
|
'Meetings' => t('Meetings'),
|
|
'Released' => t('Released'),
|
|
'Pending' => t('Pending'),
|
|
'Upcoming meetings' => t('Upcoming meetings'),
|
|
'Past meetings' => t('Past meetings'),
|
|
'No meetings found for this customer.' => t('No meetings found for this customer.'),
|
|
'Could not load meetings.' => t('Could not load meetings.'),
|
|
'Quantity' => t('Quantity'),
|
|
'Unit price' => t('Unit price'),
|
|
'Line amount' => t('Line amount'),
|
|
'Line state' => t('Line state'),
|
|
'Starting date' => t('Starting date'),
|
|
'Invoicing period' => t('Invoicing period'),
|
|
'Salesperson' => t('Salesperson'),
|
|
'Contacts' => t('Contacts'),
|
|
'positions' => t('positions'),
|
|
'Last invoicing' => t('Last invoicing'),
|
|
'Close' => t('Close'),
|
|
'New (30d)' => t('New (30d)'),
|
|
'Resolved (30d)' => t('Resolved (30d)'),
|
|
'Avg. age open' => t('Avg. age open'),
|
|
'vs. prev. 30d' => t('vs. prev. 30d'),
|
|
'net (30d)' => t('net (30d)'),
|
|
'critical' => t('critical'),
|
|
'Analysis' => t('Analysis'),
|
|
'Open tickets' => t('Open tickets'),
|
|
'Avg. contract value' => t('Avg. contract value'),
|
|
'of {total} total' => t('of {total} total'),
|
|
'in {days} days' => t('in {days} days'),
|
|
'largest' => t('largest'),
|
|
]); ?></script>
|
|
|
|
<script src="<?php e(assetVersion('vendor/gridjs/gridjs.umd.js')); ?>"></script>
|