2026-08-14 18:02:25 +02:00
{% extends "base.html" %}
{% block title %}{{ lot.name }} — GMAO{% endblock %}
{% block content %}
< div class = "container-fluid" >
< div class = "row mb-4" >
< div class = "col" >
< nav aria-label = "breadcrumb" >
< ol class = "breadcrumb" >
< li class = "breadcrumb-item" > < a href = "{{ url_for('lots.index') }}" > Lots< / a > < / li >
< li class = "breadcrumb-item active" > {{ lot.name }}< / li >
< / ol >
< / nav >
< h1 class = "h3" >
< i class = "fas fa-layer-group me-2" > < / i > {{ lot.name }}
< / h1 >
{% if lot.company %}
< p class = "text-muted" >
< i class = "fas fa-building me-1" > < / i > {{ lot.company.trade_name or lot.company.specialty }}
< / p >
{% endif %}
< / div >
< div class = "col-auto" >
< a href = "{{ url_for('lots.edit', id=lot.id) }}" class = "btn btn-outline-primary" >
< i class = "fas fa-edit me-1" > < / i > Modifier
< / a >
< / div >
< / div >
< div class = "row" >
< div class = "col-lg-8" >
2026-08-14 19:21:03 +02:00
{% if lot.needs_equipment_attention %}
< div class = "alert alert-warning" >
< i class = "bi bi-exclamation-triangle me-1" > < / i >
< strong > Lot présent sans équipement.< / strong > Rattachez au moins un équipement ou marquez ce lot comme non présent.
< / div >
{% elif not lot.is_present %}
< div class = "alert alert-secondary" >
< i class = "bi bi-dash-circle me-1" > < / i >
< strong > Ce lot n’ est pas présent dans l’ établissement.< / strong >
{% if lot.absence_reason %}< div class = "mt-1" > {{ lot.absence_reason }}< / div > {% endif %}
< / div >
{% endif %}
2026-08-14 18:02:25 +02:00
< div class = "card mb-4" >
< div class = "card-header" >
< h5 class = "mb-0" > Informations< / h5 >
< / div >
< div class = "card-body" >
< dl class = "row" >
< dt class = "col-sm-4" > Nom< / dt >
< dd class = "col-sm-8" > {{ lot.name }}< / dd >
2026-08-14 19:21:03 +02:00
< dt class = "col-sm-4" > Présence< / dt >
< dd class = "col-sm-8" >
{% if lot.is_present %}< span class = "badge bg-success" > Présent< / span >
{% else %}< span class = "badge bg-secondary" > Non présent< / span > {% endif %}
< / dd >
2026-08-14 18:02:25 +02:00
{% if lot.description %}
< dt class = "col-sm-4" > Description< / dt >
< dd class = "col-sm-8" > {{ lot.description }}< / dd >
{% endif %}
{% if lot.company %}
< dt class = "col-sm-4" > Entreprise< / dt >
< dd class = "col-sm-8" >
< a href = "{{ url_for('companies.detail', id=lot.company.id) }}" >
{{ lot.company.trade_name or lot.company.specialty }}
< / a >
< / dd >
{% endif %}
< dt class = "col-sm-4" > Catégorie< / dt >
< dd class = "col-sm-8" >
{% if lot.category %}
< a href = "{{ url_for('equipments.category_detail', id=lot.category.id) }}" >
{{ lot.category.name }}
< / a >
{% else %}
< span class = "text-muted" > Non assignée< / span >
{% endif %}
< / dd >
< / dl >
< / div >
< / div >
2026-08-14 19:21:03 +02:00
{% if not lot.active_equipment_count %}
< div class = "card mb-4" >
< div class = "card-header" > Statut du lot< / div >
< div class = "card-body" >
< form method = "POST" action = "{{ url_for('lots.set_presence', id=lot.id) }}" >
< input type = "hidden" name = "csrf_token" value = "{{ csrf_token() }}" >
{% if lot.is_present %}
< input type = "hidden" name = "action" value = "absent" >
< div class = "mb-3" >
< label class = "form-label" for = "absence_reason" > Raison facultative< / label >
< input class = "form-control" id = "absence_reason" name = "absence_reason" placeholder = "Ex. aucun ascenseur dans l’ établissement" >
< / div >
< button class = "btn btn-outline-secondary" > Marquer le lot comme non présent< / button >
{% else %}
< input type = "hidden" name = "action" value = "present" >
< button class = "btn btn-outline-success" > Marquer le lot comme présent< / button >
{% endif %}
< / form >
< / div >
< / div >
{% endif %}
2026-08-20 00:49:15 +02:00
< div class = "card mb-4" >
< div class = "card-header d-flex justify-content-between align-items-center" >
< div > < h5 class = "mb-0" > < i class = "bi bi-calendar2-check me-2" > < / i > Maintenance préventive< / h5 > < small class = "text-muted" > Le lot définit les règles héritées par ses équipements.< / small > < / div >
< a class = "btn btn-sm btn-primary" href = "{{ url_for('lots.task_create', lot_id=lot.id) }}" > < i class = "bi bi-plus-lg" > < / i > Ajouter une tâche< / a >
< / div >
< div class = "card-body border-bottom" >
< div class = "row text-center g-2" >
< div class = "col" > < div class = "fw-bold fs-4" > {{ lot.tasks|length }}< / div > < small class = "text-muted" > règles< / small > < / div >
< div class = "col" > < div class = "fw-bold fs-4 text-primary" > {{ task_counts.planned }}< / div > < small class = "text-muted" > planifiées< / small > < / div >
< div class = "col" > < div class = "fw-bold fs-4 text-warning" > {{ task_counts.suspended }}< / div > < small class = "text-muted" > suspendues< / small > < / div >
< div class = "col" > < div class = "fw-bold fs-4 text-danger" > {{ task_counts.overdue }}< / div > < small class = "text-muted" > en retard< / small > < / div >
< / div >
< / div >
{% if lot.tasks %}< div class = "table-responsive" > < table class = "table table-sm align-middle mb-0" > < thead > < tr > < th > N°< / th > < th > Tâche< / th > < th > Déclenchement< / th > < th > Portée< / th > < th > Indisponibilité< / th > < th > < / th > < / tr > < / thead > < tbody >
{% for task in lot.tasks %}< tr class = "{{ 'table-secondary' if not task.is_active }}" > < td > {{ task.num_tache or '—' }}< / td > < td > < strong > {{ task.tache or 'Tâche sans nom' }}< / strong > < div class = "small text-muted" > {{ task.periodicite or (task.jours_entre_interventions|string + ' jours' if task.jours_entre_interventions else 'Périodicité à définir') }}< / div > {% if task.is_safety_critical %}< span class = "badge bg-danger" > Sécurité< / span > {% endif %}< / td > < td > {{ task.trigger_type|replace('calendar','calendrier')|replace('season','saison')|replace('event','événement')|replace('weather','météo')|replace('meter','compteur')|title }}< / td > < td > {{ {'auto':'Automatique','group':'Groupe / salle','unit':'Par unité'}.get(task.application_scope, task.application_scope) }}< / td > < td > {{ {'suspend':'Suspendre','keep':'Maintenir','postpone':'Reporter'}.get(task.unavailable_policy, task.unavailable_policy) }}< / td > < td > < a class = "btn btn-sm btn-outline-primary" href = "{{ url_for('lots.task_edit', lot_id=lot.id, task_id=task.id) }}" > < i class = "bi bi-pencil" > < / i > < / a > < / td > < / tr > {% endfor %}
< / tbody > < / table > < / div > {% else %}< div class = "card-body text-muted" > Aucune règle préventive. Ajoutez-en une pour générer les échéances.< / div > {% endif %}
< div class = "card-footer" > < form method = "post" action = "{{ url_for('lots.generate_tasks', lot_id=lot.id) }}" > < input type = "hidden" name = "csrf_token" value = "{{ csrf_token() }}" > < button class = "btn btn-success" { % if not lot . is_present % } disabled { % endif % } > < i class = "bi bi-magic" > < / i > Générer les échéances maintenant< / button > < / form > < / div >
< / div >
2026-08-14 18:02:25 +02:00
{# Équipements du lot #}
{% if equipments %}
< div class = "card mb-4" >
< div class = "card-header d-flex justify-content-between align-items-center" >
< h5 class = "mb-0" > < i class = "bi bi-hdd-stack me-2" > < / i > Équipements ({{ equipments|length }})< / h5 >
< / div >
< div class = "card-body p-0" >
< div class = "table-responsive" >
< table class = "table table-sm table-hover mb-0" >
< thead >
< tr >
< th > Nom< / th >
< th > Localisation< / th >
< th > Statut< / th >
< th > Compteurs< / th >
< th > < / th >
< / tr >
< / thead >
< tbody >
{% for eq in equipments %}
< tr >
< td >
< a href = "{{ url_for('equipments.detail', id=eq.id) }}" >
{{ eq.name }}
< / a >
< / td >
< td >
{% if eq.room %}
2026-08-14 21:18:39 +02:00
< a href = "{{ url_for('rooms.detail', id=eq.room.id) }}" >
2026-08-14 18:02:25 +02:00
{{ eq.room.name }}
< / a >
{% elif eq.location %}
{{ eq.location }}
{% else %}
< span class = "text-muted" > —< / span >
{% endif %}
< / td >
< td >
{% if eq.status == 'active' %}
< span class = "badge bg-success" > En service< / span >
{% elif eq.status == 'inactive' %}
< span class = "badge bg-secondary" > Inactif< / span >
{% elif eq.status == 'maintenance' %}
< span class = "badge bg-warning text-dark" > Maintenance< / span >
{% elif eq.status == 'retired' %}
< span class = "badge bg-danger" > Retiré< / span >
{% else %}
< span class = "badge bg-secondary" > {{ eq.status }}< / span >
{% endif %}
< / td >
< td >
{% if eq.meters %}
{% for meter in eq.meters %}
< a href = "{{ url_for('meters.detail', meter_id=meter.id) }}"
class="badge bg-info text-dark text-decoration-none me-1">
{{ meter.name }}: {{ meter.current_value }} {{ meter.unit }}
< / a >
{% endfor %}
{% else %}
< span class = "text-muted" > —< / span >
{% endif %}
< / td >
< td >
< a href = "{{ url_for('equipments.detail', id=eq.id) }}"
class="btn btn-sm btn-outline-primary">
< i class = "bi bi-eye" > < / i >
< / a >
< / td >
< / tr >
{% endfor %}
< / tbody >
< / table >
< / div >
< / div >
< / div >
{% else %}
< div class = "card mb-4" >
< div class = "card-body text-muted" >
< i class = "bi bi-info-circle me-2" > < / i > Aucun équipement dans ce lot.
< a href = "{{ url_for('equipments.index') }}" > Rechercher un équipement< / a > pour l'ajouter à ce lot.
< / div >
< / div >
{% endif %}
< / div >
< div class = "col-lg-4" >
< div class = "card" >
< div class = "card-header" >
< h5 class = "mb-0" > Actions< / h5 >
< / div >
< div class = "card-body" >
< div class = "d-grid gap-2" >
< a href = "{{ url_for('lots.edit', id=lot.id) }}" class = "btn btn-outline-primary" >
< i class = "fas fa-edit me-1" > < / i > Modifier le lot
< / a >
2026-08-20 00:49:15 +02:00
< a href = "{{ url_for('equipments.lifecycle_dashboard', status='all') }}" class = "btn btn-outline-secondary" > < i class = "bi bi-activity" > < / i > Cycle de vie< / a >
2026-08-14 18:02:25 +02:00
< form method = "POST" action = "{{ url_for('lots.delete', id=lot.id) }}"
onsubmit="return confirm('Confirmer la suppression ?');">
< input type = "hidden" name = "csrf_token" value = "{{ csrf_token() }}" >
< button type = "submit" class = "btn btn-outline-danger w-100" >
< i class = "fas fa-trash me-1" > < / i > Supprimer
< / button >
< / form >
< / div >
< / div >
< / div >
< / div >
< / div >
< / div >
2026-08-14 19:21:03 +02:00
{% endblock %}