14-04-2026
This commit is contained in:
parent
f58c709945
commit
0f82fea88a
72 changed files with 7414 additions and 148 deletions
|
|
@ -0,0 +1,45 @@
|
|||
<div class="timeline">
|
||||
@forelse($incident->activities as $activity)
|
||||
<div class="timeline-item {{ $activity->type === 'status_change' ? 'timeline-item-secondary' : '' }}">
|
||||
<div class="timeline-indicator bg-{{ match($activity->type) {
|
||||
'status_change' => 'info',
|
||||
'email' => 'primary',
|
||||
'call' => 'success',
|
||||
'ticket' => 'warning',
|
||||
'provider_response' => 'secondary',
|
||||
default => 'light border'
|
||||
} }}">
|
||||
<i class="ion {{ $activity->type_icon }}"></i>
|
||||
</div>
|
||||
<div class="timeline-content">
|
||||
<div class="d-flex justify-content-between align-items-start">
|
||||
<div>
|
||||
<span class="badge badge-light">{{ $activity->type_label }}</span>
|
||||
<strong class="ml-1">{{ $activity->title }}</strong>
|
||||
</div>
|
||||
<small class="text-muted text-nowrap ml-2">
|
||||
{{ $activity->created_at->format('d.m.Y H:i') }}
|
||||
— {{ $activity->author }}
|
||||
</small>
|
||||
</div>
|
||||
@if($activity->content)
|
||||
<div class="mt-1 text-muted">{{ $activity->content }}</div>
|
||||
@endif
|
||||
</div>
|
||||
</div>
|
||||
@empty
|
||||
<p class="text-muted">Noch keine Aktivitäten.</p>
|
||||
@endforelse
|
||||
</div>
|
||||
|
||||
<style>
|
||||
.timeline { position: relative; padding-left: 2.5rem; }
|
||||
.timeline::before { content: ''; position: absolute; left: 1rem; top: 0; bottom: 0; width: 2px; background: #e9ecef; }
|
||||
.timeline-item { position: relative; margin-bottom: 1.25rem; }
|
||||
.timeline-indicator {
|
||||
position: absolute; left: -2.5rem; width: 2rem; height: 2rem;
|
||||
border-radius: 50%; display: flex; align-items: center; justify-content: center;
|
||||
font-size: 0.875rem; color: #fff;
|
||||
}
|
||||
.timeline-content { background: #f8f9fa; border-radius: 0.375rem; padding: 0.75rem 1rem; }
|
||||
</style>
|
||||
|
|
@ -0,0 +1,100 @@
|
|||
<div class="modal fade" id="createIncidentModal" tabindex="-1" role="dialog">
|
||||
<div class="modal-dialog modal-lg" role="document">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<h5 class="modal-title">Neuen Incident anlegen</h5>
|
||||
<button type="button" class="close" data-dismiss="modal">
|
||||
<span>×</span>
|
||||
</button>
|
||||
</div>
|
||||
<form method="POST" action="{{ route('admin.payment-dashboard.store') }}">
|
||||
@csrf
|
||||
<div class="modal-body">
|
||||
@if($errors->any())
|
||||
<div class="alert alert-danger">
|
||||
<ul class="mb-0">
|
||||
@foreach($errors->all() as $error)
|
||||
<li>{{ $error }}</li>
|
||||
@endforeach
|
||||
</ul>
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<div class="form-row">
|
||||
<div class="form-group col-md-8">
|
||||
<label>Titel <span class="text-danger">*</span></label>
|
||||
<input type="text" name="title" class="form-control" value="{{ old('title') }}" required>
|
||||
</div>
|
||||
<div class="form-group col-md-4">
|
||||
<label>Erkannt am <span class="text-danger">*</span></label>
|
||||
<input type="datetime-local" name="detected_at" class="form-control"
|
||||
value="{{ old('detected_at', now()->format('Y-m-d\TH:i')) }}" required>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-row">
|
||||
<div class="form-group col-md-4">
|
||||
<label>Anbieter <span class="text-danger">*</span></label>
|
||||
<select name="provider" class="custom-select" required>
|
||||
<option value="payone" {{ old('provider', 'payone') === 'payone' ? 'selected' : '' }}>PAYONE</option>
|
||||
{{-- <option value="stripe" {{ old('provider') === 'stripe' ? 'selected' : '' }}>Stripe</option> --}}
|
||||
<option value="paypal" {{ old('provider') === 'paypal' ? 'selected' : '' }}>PayPal</option>
|
||||
{{-- <option value="mollie" {{ old('provider') === 'mollie' ? 'selected' : '' }}>Mollie</option> --}}
|
||||
<option value="other" {{ old('provider') === 'other' ? 'selected' : '' }}>Sonstige</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="form-group col-md-4">
|
||||
<label>Typ <span class="text-danger">*</span></label>
|
||||
<select name="type" class="custom-select" required>
|
||||
<option value="outage" {{ old('type') === 'outage' ? 'selected' : '' }}>Ausfall</option>
|
||||
<option value="ipn_error" {{ old('type') === 'ipn_error' ? 'selected' : '' }}>IPN-Fehler</option>
|
||||
<option value="payment_failure" {{ old('type', 'payment_failure') === 'payment_failure' ? 'selected' : '' }}>Zahlungsfehler</option>
|
||||
<option value="slow_response" {{ old('type') === 'slow_response' ? 'selected' : '' }}>Langsame Antwort</option>
|
||||
<option value="other" {{ old('type') === 'other' ? 'selected' : '' }}>Sonstiges</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="form-group col-md-4">
|
||||
<label>Schwere <span class="text-danger">*</span></label>
|
||||
<select name="severity" class="custom-select" required>
|
||||
<option value="low" {{ old('severity') === 'low' ? 'selected' : '' }}>Niedrig</option>
|
||||
<option value="medium" {{ old('severity', 'medium') === 'medium' ? 'selected' : '' }}>Mittel</option>
|
||||
<option value="high" {{ old('severity') === 'high' ? 'selected' : '' }}>Hoch</option>
|
||||
<option value="critical" {{ old('severity') === 'critical' ? 'selected' : '' }}>Kritisch</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-row">
|
||||
<div class="form-group col-md-4">
|
||||
<label>Betroffene Bestellungen</label>
|
||||
<input type="number" name="affected_orders" class="form-control" min="0"
|
||||
value="{{ old('affected_orders', 0) }}">
|
||||
</div>
|
||||
<div class="form-group col-md-4">
|
||||
<label>Betroffener Umsatz (€)</label>
|
||||
<input type="number" name="affected_revenue" class="form-control" min="0" step="0.01"
|
||||
value="{{ old('affected_revenue', '0.00') }}">
|
||||
</div>
|
||||
<div class="form-group col-md-4">
|
||||
<label>Ticket-Nummer</label>
|
||||
<input type="text" name="ticket_number" class="form-control"
|
||||
value="{{ old('ticket_number') }}" placeholder="z.B. PAYONE-12345">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label>Beschreibung</label>
|
||||
<textarea name="description" class="form-control" rows="3"
|
||||
placeholder="Was ist passiert?">{{ old('description') }}</textarea>
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button type="button" class="btn btn-secondary" data-dismiss="modal">Abbrechen</button>
|
||||
<button type="submit" class="btn btn-danger">
|
||||
<i class="ion ion-md-alert"></i> Incident anlegen
|
||||
</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -0,0 +1,71 @@
|
|||
<div class="table-responsive">
|
||||
<table class="table table-sm table-hover">
|
||||
<thead class="thead-light">
|
||||
<tr>
|
||||
<th>Schwere</th>
|
||||
<th>Titel</th>
|
||||
<th>Anbieter</th>
|
||||
<th>Typ</th>
|
||||
<th>Status</th>
|
||||
<th>Erkannt</th>
|
||||
<th>Dauer</th>
|
||||
@if(isset($showActions) && $showActions)
|
||||
<th></th>
|
||||
@endif
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@forelse($incidents as $incident)
|
||||
<tr>
|
||||
<td>
|
||||
<span class="badge badge-{{ $incident->severity_color }}">
|
||||
{{ $incident->severity_label }}
|
||||
</span>
|
||||
</td>
|
||||
<td>
|
||||
<a href="{{ route('admin.payment-dashboard.show', $incident) }}">
|
||||
{{ $incident->title }}
|
||||
</a>
|
||||
@if($incident->ticket_number)
|
||||
<span class="text-muted small ml-1">#{{ $incident->ticket_number }}</span>
|
||||
@endif
|
||||
</td>
|
||||
<td><span class="badge badge-secondary">{{ $incident->provider_label }}</span></td>
|
||||
<td>
|
||||
<i class="ion {{ $incident->type_icon }}"></i>
|
||||
{{ $incident->type_label }}
|
||||
</td>
|
||||
<td>
|
||||
<span class="badge badge-{{ $incident->status_color }}">
|
||||
{{ $incident->status_label }}
|
||||
</span>
|
||||
</td>
|
||||
<td class="text-nowrap">{{ $incident->detected_at->format('d.m.Y H:i') }}</td>
|
||||
<td class="text-nowrap">{{ $incident->duration }}</td>
|
||||
@if(isset($showActions) && $showActions)
|
||||
<td>
|
||||
<div class="d-flex gap-1">
|
||||
<form method="POST" action="{{ route('admin.payment-dashboard.status.update', $incident) }}" class="d-inline">
|
||||
@csrf
|
||||
@method('PATCH')
|
||||
<select name="status" class="custom-select custom-select-sm" onchange="this.form.submit()" style="width:auto">
|
||||
@foreach(['open' => 'Offen', 'in_progress' => 'In Bearb.', 'waiting_provider' => 'Wartet', 'resolved' => 'Gelöst', 'closed' => 'Geschl.'] as $value => $label)
|
||||
<option value="{{ $value }}" {{ $incident->status === $value ? 'selected' : '' }}>{{ $label }}</option>
|
||||
@endforeach
|
||||
</select>
|
||||
</form>
|
||||
<a href="{{ route('admin.payment-dashboard.show', $incident) }}" class="btn btn-sm btn-outline-secondary">
|
||||
<i class="ion ion-md-open"></i>
|
||||
</a>
|
||||
</div>
|
||||
</td>
|
||||
@endif
|
||||
</tr>
|
||||
@empty
|
||||
<tr>
|
||||
<td colspan="8" class="text-center text-muted py-3">Keine Incidents vorhanden.</td>
|
||||
</tr>
|
||||
@endforelse
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
|
|
@ -0,0 +1,64 @@
|
|||
<div class="row mb-4">
|
||||
<div class="col-sm-6 col-xl-2">
|
||||
<div class="card {{ $stats['critical_open'] > 0 ? 'border-danger' : '' }}">
|
||||
<div class="card-body text-center">
|
||||
<div class="text-muted small">Offene Incidents</div>
|
||||
<div class="display-4 font-weight-bold {{ $stats['open_incidents'] > 0 ? 'text-danger' : 'text-success' }}">
|
||||
{{ $stats['open_incidents'] }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-sm-6 col-xl-2">
|
||||
<div class="card">
|
||||
<div class="card-body text-center">
|
||||
<div class="text-muted small">In Bearbeitung</div>
|
||||
<div class="display-4 font-weight-bold {{ $stats['in_progress'] > 0 ? 'text-warning' : 'text-muted' }}">
|
||||
{{ $stats['in_progress'] }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-sm-6 col-xl-2">
|
||||
<div class="card">
|
||||
<div class="card-body text-center">
|
||||
<div class="text-muted small">PAYONE (30 Tage)</div>
|
||||
<div class="display-4 font-weight-bold text-info">
|
||||
{{ $stats['payone_incidents_30d'] }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-sm-6 col-xl-2">
|
||||
<div class="card">
|
||||
<div class="card-body text-center">
|
||||
<div class="text-muted small">Gelöst (Monat)</div>
|
||||
<div class="display-4 font-weight-bold text-success">
|
||||
{{ $stats['resolved_this_month'] }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-sm-6 col-xl-2">
|
||||
<div class="card">
|
||||
<div class="card-body text-center">
|
||||
<div class="text-muted small">Erfolgsrate Zahlung</div>
|
||||
<div class="display-4 font-weight-bold {{ $transactionStats['success_rate'] < 90 ? 'text-warning' : 'text-success' }}">
|
||||
{{ $transactionStats['success_rate'] }}%
|
||||
</div>
|
||||
<div class="text-muted" style="font-size:0.7rem">letzte {{ $transactionStats['days'] }} Tage</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-sm-6 col-xl-2">
|
||||
<div class="card {{ $transactionStats['failed'] > 0 ? 'border-warning' : '' }}">
|
||||
<div class="card-body text-center">
|
||||
<div class="text-muted small">Fehlgeschlagen</div>
|
||||
<div class="display-4 font-weight-bold {{ $transactionStats['failed'] > 0 ? 'text-danger' : 'text-success' }}">
|
||||
{{ $transactionStats['failed'] }}
|
||||
</div>
|
||||
<div class="text-muted" style="font-size:0.7rem">letzte {{ $transactionStats['days'] }} Tage</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
Loading…
Add table
Add a link
Reference in a new issue