feat: list upcoming season assignments among a teamer's dispositions

This commit is contained in:
fromme committed 2026-10-20 17:13:45 +02:00
1 parent 300bb2058f
commit c00dd86eb4
17 files changed
+386 -97

No files matched your search

@@ -0,0 +1,2 @@
{# Marks a season assignment listed among dispositions. #}
<span class="inline-block py-1 px-2 text-xs bg-primary text-white">Saison</span>
@@ -11,15 +11,15 @@
sich nicht mehr anmelden. Bestehende Einsätze, Dokumente und Feedbacks bleiben erhalten
und weiterhin sichtbar.
</div>
{% if pendingApplicationCount > 0 or upcomingDispositionCount > 0 %}
{% if pendingApplicationCount > 0 or upcomingPlacementCount > 0 %}
<div class="p-4 bg-red-50 border border-red-200 rounded-md">
<div class="font-bold pb-2">Achtung: offene Vorgänge</div>
<ul class="list-disc list-inside">
{% if pendingApplicationCount > 0 %}
<li>{{ pendingApplicationCount }} offene Bewerbung(en)</li>
{% endif %}
{% if upcomingDispositionCount > 0 %}
<li>{{ upcomingDispositionCount }} anstehende(r) Einsatz/Einsätze</li>
{% if upcomingPlacementCount > 0 %}
<li>{{ upcomingPlacementCount }} anstehende(r) Einsatz/Einsätze</li>
{% endif %}
</ul>
<div class="pt-2">
@@ -28,24 +28,41 @@
</tr>
</thead>
<tbody>
{% for disposition in pagination %}
{% for row in pagination %}
<tr>
<td>
{{ disposition.assignment.destination.dateFrom|date('d.m.Y') }} - {{ disposition.assignment.destination.dateTo|date('d.m.Y') }}
</td>
<td>
{{ disposition.assignment.destination.product }}
<br>
{{ disposition.assignment.destination.hotel }}
</td>
<td>
{{ disposition.assignment.jobProfile.name }}
{{ row.dateFrom|date('d.m.Y') }} - {{ row.dateTo|date('d.m.Y') }}
</td>
{% if row.seasonAssignment is not null %}
{% set seasonAssignment = row.seasonAssignment %}
<td>
{% include '_partials/_season_badge.html.twig' %}
<a href="{{ path('app_administrative_season_assignment_detail', { 'uuid': seasonAssignment.uuid, 'r': return_url() }) }}"
class="underline">
{{ seasonAssignment|season_assignment_label }}
</a>
</td>
<td>
{{ seasonAssignment.jobProfile.name }}
</td>
{% else %}
{% set assignment = row.disposition.assignment %}
<td>
{{ assignment.destination.product }}
<br>
{{ assignment.destination.hotel }}
</td>
<td>
{{ assignment.jobProfile.name }}
</td>
{% endif %}
</tr>
{% else %}
<td colspan="3">
Keine Daten...
</td>
<tr>
<td colspan="3">
Keine Daten...
</td>
</tr>
{% endfor %}
</tbody>
</table>
@@ -0,0 +1,35 @@
{% set assignment = disposition.assignment %}
<div class="relative flex flex-col justify-between rounded-md border border-gray-200 bg-gray-100 p-4">
<div class="flex flex-col space-y-2 pb-2">
<div class="flex items-start space-x-2">
{{ icon('flag-' ~ assignment.destination.country, 'w-5 h-5 shrink-0') }}
<span class="flex-1 font-bold">{{ assignment.destination.product }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('calendar', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ assignment.destination.dateFrom|date('d.m.Y') }} - {{ assignment.destination.dateTo|date('d.m.Y') }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('profile', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ assignment.jobProfile.name }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('house', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ assignment.destination.hotel }}</span>
</div>
{% if assignment.pickup %}
{% set pickup = assignment.destination.pickup(assignment.pickup) %}
{% if pickup is not null %}
<div class="flex items-start space-x-2">
{{ icon('bus', 'w-5 h-5 shrink-0') }}
<span>{{ pickup.city }}, {{ pickup.time }} Uhr</span>
</div>
{% endif %}
{% endif %}
</div>
<a href="{{ path('app_teamer_disposition_detail', { 'uuid': disposition.uuid, 'r': return_url() }) }}"
class="btn btn--small flex items-center space-x-2">
{{ icon('info', 'w-4 h-4 shrink-0') }}
<span>Details</span>
</a>
</div>
+1 -35
View File
@@ -1,40 +1,6 @@
<div class="grid sm:grid-cols-2 md:grid-cols-3 gap-4 pb-4">
{% for disposition in pagination %}
{% set assignment = disposition.assignment %}
<div class="relative flex flex-col justify-between rounded-md border border-gray-200 bg-gray-100 p-4">
<div class="flex flex-col space-y-2 pb-2">
<div class="flex items-start space-x-2">
{{ icon('flag-' ~ assignment.destination.country, 'w-5 h-5 shrink-0') }}
<span class="flex-1 font-bold">{{ assignment.destination.product }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('calendar', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ assignment.destination.dateFrom|date('d.m.Y') }} - {{ assignment.destination.dateTo|date('d.m.Y') }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('profile', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ assignment.jobProfile.name }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('house', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ assignment.destination.hotel }}</span>
</div>
{% if assignment.pickup %}
{% set pickup = assignment.destination.pickup(assignment.pickup) %}
{% if pickup is not null %}
<div class="flex items-start space-x-2">
{{ icon('bus', 'w-5 h-5 shrink-0') }}
<span>{{ pickup.city }}, {{ pickup.time }} Uhr</span>
</div>
{% endif %}
{% endif %}
</div>
<a href="{{ path('app_teamer_disposition_detail', { 'uuid': disposition.uuid, 'r': return_url() }) }}"
class="btn btn--small flex items-center space-x-2">
{{ icon('info', 'w-4 h-4 shrink-0') }}
<span>Details</span>
</a>
</div>
{% include 'teamer/disposition/_card.html.twig' %}
{% else %}
Keine Einträge...
{% endfor %}
@@ -0,0 +1,29 @@
{# A season assignment among the upcoming dispositions. Linked only when it is the one the season
page shows - that page resolves a single assignment and 404s for any other. #}
<div class="relative flex flex-col justify-between rounded-md border border-gray-200 bg-gray-100 p-4">
<div class="flex flex-col space-y-2 pb-2">
<div class="flex items-start space-x-2">
<span class="flex-1 font-bold">{{ seasonAssignment|season_assignment_label }}</span>
{% include '_partials/_season_badge.html.twig' %}
</div>
<div class="flex items-start space-x-2">
{{ icon('calendar', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ seasonAssignment.dateFrom|date('d.m.Y') }} - {{ seasonAssignment.dateTo|date('d.m.Y') }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('profile', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ seasonAssignment.jobProfile.name }}</span>
</div>
<div class="flex items-start space-x-2">
{{ icon('house', 'w-5 h-5 shrink-0') }}
<span class="flex-1">{{ seasonAssignment.hotelCode|house_label }}</span>
</div>
</div>
{% if seasonAssignment is same as(linkedSeasonAssignment) %}
<a href="{{ path('app_teamer_season_index') }}"
class="btn btn--small flex items-center space-x-2">
{{ icon('info', 'w-4 h-4 shrink-0') }}
<span>Details</span>
</a>
{% endif %}
</div>
@@ -6,5 +6,16 @@
<h1 class="text-2xl font-bold pb-8">
Meine nächsten Einsätze
</h1>
{% include 'teamer/disposition/_list.html.twig' %}
{% endblock %}
<div class="grid sm:grid-cols-2 md:grid-cols-3 gap-4 pb-4">
{% for row in pagination %}
{% if row.seasonAssignment is not null %}
{% include 'teamer/disposition/_season_card.html.twig' with { 'seasonAssignment': row.seasonAssignment } %}
{% else %}
{% include 'teamer/disposition/_card.html.twig' with { 'disposition': row.disposition } %}
{% endif %}
{% else %}
Keine Einträge...
{% endfor %}
</div>
{{ knp_pagination_render(pagination, 'paginator/sliding_boxes.html.twig') }}
{% endblock %}
+34 -12
View File
@@ -116,20 +116,42 @@
Meine Einsätze
</h2>
<ul class="divide-y divide-gray-200">
{% for disposition in upcomingDispositions %}
{% set assignment = disposition.assignment %}
{% for row in upcomingPlacements %}
<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('check', '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>
{% if row.seasonAssignment is not null %}
{% set seasonAssignment = row.seasonAssignment %}
{% set content %}
<div class="flex items-center space-x-1">
{{ icon('check', 'w-4 h-4 shrink-0') }}
<div class="flex items-center space-x-1 truncate">
<span class="whitespace-nowrap">{{ row.dateFrom|date('d.m.y') }} - {{ row.dateTo|date('d.m.y') }}</span>
{% include '_partials/_dot.html.twig' %}
<span class="whitespace-nowrap">{{ seasonAssignment.hotelCode|house_label }}</span>
{% include '_partials/_season_badge.html.twig' %}
</div>
</div>
</div>
<div class="pl-5 whitespace-nowrap">{{ assignment.jobProfile.name }}</div>
</a>
<div class="pl-5 whitespace-nowrap">{{ seasonAssignment.jobProfile.name }}</div>
{% endset %}
{% if seasonAssignment is same as(linkedSeasonAssignment) %}
<a href="{{ path('app_teamer_season_index') }}">{{ content }}</a>
{% else %}
{{ content }}
{% endif %}
{% else %}
{% set disposition = row.disposition %}
{% set assignment = disposition.assignment %}
<a href="{{ path('app_teamer_disposition_detail', { 'uuid': disposition.uuid }) }}">
<div class="flex items-center space-x-1">
{{ icon('check', '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>
<div class="pl-5 whitespace-nowrap">{{ assignment.jobProfile.name }}</div>
</a>
{% endif %}
</li>
{% else %}
<li class="py-2 first:pt-0 last:pb-0">