fix: teamer dashboard crashing on isContractDue() without deadline

489aafed made isContractDue() and isInvoiceDue() take the deadline days,
but teamer/index.html.twig still called them as bare getters, throwing an
ArgumentCountError for every teamer with an upcoming disposition. The
controller now resolves which reason applies and hands it to the template.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
This commit is contained in:
frommeandClaude Opus 5.5 committed 2026-10-06 15:01:00 +02:00
1 parent 849da8d471
commit c3cebae494
2 files changed
+36 -28

No files matched your search

+14 -5
View File
@@ -78,19 +78,28 @@ class IndexController extends AbstractController
]);
}
/**
* @return list<array{disposition: Disposition, reason: 'contract_due'|'contract_rejected'|'invoice_due'}>
*/
private function processDocuments(array $upcomingDispositions): array
{
$contractUploadDeadlineDays = (int) $this->getParameter('contract_upload_deadline_days');
$invoiceUploadDeadlineDays = (int) $this->getParameter('invoice_upload_deadline_days');
$dispositions = [];
// The due checks need the configured deadlines, which the template cannot pass, so the
// reason is resolved here. Order matters: the first matching reason is the one shown.
foreach ($upcomingDispositions as $disposition) {
/** @var Disposition $disposition */
if ($disposition->isContractDue($contractUploadDeadlineDays)
|| $disposition->isContractRejected()
|| $disposition->isInvoiceDue($invoiceUploadDeadlineDays)
) {
$dispositions[] = $disposition;
$reason = match (true) {
$disposition->isContractDue($contractUploadDeadlineDays) => 'contract_due',
$disposition->isContractRejected() => 'contract_rejected',
$disposition->isInvoiceDue($invoiceUploadDeadlineDays) => 'invoice_due',
default => null,
};
if (null !== $reason) {
$dispositions[] = ['disposition' => $disposition, 'reason' => $reason];
}
}
+22 -23
View File
@@ -48,31 +48,30 @@
Meine Dokumente
</h2>
<ul class="divide-y divide-gray-200">
{% for disposition in dispositionDocuments %}
{% for document in dispositionDocuments %}
{% set disposition = document.disposition %}
{% set assignment = disposition.assignment %}
{% if disposition.contractDue or disposition.invoiceDue or disposition.contractRejected %}
<li class="py-2 first:pt-0 last:pb-0">
<a href="{{ path('app_teamer_disposition_detail', { 'uuid': disposition.uuid }) }}">
<div class="flex items-center space-x-1">
{{ icon('alert', 'w-4 h-4 shrink-0') }}
<div class="flex items-center space-x-1 truncate">
<span class="whitespace-nowrap">{{ assignment.destination.dateFrom|date('d.m.y') }} - {{ assignment.destination.dateTo|date('d.m.y') }}</span>
{% include '_partials/_dot.html.twig' %}
<span class="whitespace-nowrap">{{ assignment.destination.hotel }}</span>
</div>
<li class="py-2 first:pt-0 last:pb-0">
<a href="{{ path('app_teamer_disposition_detail', { 'uuid': disposition.uuid }) }}">
<div class="flex items-center space-x-1">
{{ icon('alert', 'w-4 h-4 shrink-0') }}
<div class="flex items-center space-x-1 truncate">
<span class="whitespace-nowrap">{{ assignment.destination.dateFrom|date('d.m.y') }} - {{ assignment.destination.dateTo|date('d.m.y') }}</span>
{% include '_partials/_dot.html.twig' %}
<span class="whitespace-nowrap">{{ assignment.destination.hotel }}</span>
</div>
<div class="pl-5 whitespace-nowrap text-red-500">
{%- if disposition.contractDue -%}
Honorarvertrag fällig
{%- elseif disposition.contractRejected %}
Honorarvertrag muss erneut hochgeladen werden
{%- elseif disposition.invoiceDue -%}
Honorarnote fällig
{%- endif %}
</div>
</a>
</li>
{% endif %}
</div>
<div class="pl-5 whitespace-nowrap text-red-500">
{%- if document.reason == 'contract_due' -%}
Honorarvertrag fällig
{%- elseif document.reason == 'contract_rejected' %}
Honorarvertrag muss erneut hochgeladen werden
{%- elseif document.reason == 'invoice_due' -%}
Honorarnote fällig
{%- endif %}
</div>
</a>
</li>
{% else %}
<li class="py-2 first:pt-0 last:pb-0">
-