27-05-2026 Update DHL Modul v2.0

This commit is contained in:
Kevin 2026-05-27 13:40:38 +00:00
parent 53bdba33cd
commit 036595be94
41 changed files with 3346 additions and 310 deletions

View file

@ -109,9 +109,148 @@ $(document).ready(function() {
return;
}
if ($('#dhl-preflight-confirmed').val() !== '1') {
validateDhlAddress(formData, submitBtn, function() {
$('#dhl-preflight-confirmed').val('1');
submitBtn.prop('disabled', false).html('<i class="fas fa-shipping-fast"></i> Sendung jetzt erstellen');
});
return;
}
validateDhlAddress(formData, submitBtn, function() {
submitDhlShipment(form, formData, submitBtn);
});
});
function validateDhlAddress(formData, submitBtn, onSuccess) {
submitBtn.prop('disabled', true).html('<i class="fas fa-spinner fa-spin"></i> Prüfe Sendung...');
$.ajax({
url: '{{ route('admin.dhl.validate-address') }}',
method: 'POST',
data: formData,
success: function(response) {
renderDhlPreflightStatus(response);
onSuccess();
},
error: function(xhr) {
var response = xhr.responseJSON || {};
renderDhlPreflightStatus(response);
resetDhlPreflight(true);
}
});
}
function renderDhlPreflightStatus(response) {
var status = response.status || 'error';
var product = (response.preflight && response.preflight.product) ? response.preflight.product : {};
var address = (response.preflight && response.preflight.address) ? response.preflight.address : {};
var normalized = address.normalized || {};
var errors = response.errors || [];
var warnings = response.warnings || [];
var statusClass = status === 'valid' ? 'success' : (status === 'warning' ? 'warning' : 'danger');
var statusIcon = status === 'valid' ? 'check-circle' : (status === 'warning' ? 'exclamation-triangle' : 'times-circle');
var productScope = product.scope_label || 'Nicht geprüft';
var productCode = product.code || $('#modal-product-code').val() || '-';
var countryLabel = product.country_label || $('#shipping_country option:selected').text().trim() || '-';
var validationBadgeClass = address.validation_available ? 'info' : 'warning';
var validationBadgeText = address.validation_available ? 'Formale DACH-Prüfung' : 'Basisprüfung';
var validationMessage = address.validation_message || 'Adressvalidierung wurde nicht eindeutig bestimmt.';
var listHtml = '';
if (errors.length) {
listHtml += '<div class="alert alert-danger mb-2"><strong>Fehler:</strong><ul class="mb-0 pl-3">';
errors.forEach(function(error) {
listHtml += '<li>' + escapeHtml(error) + '</li>';
});
listHtml += '</ul></div>';
}
if (warnings.length) {
listHtml += '<div class="alert alert-warning mb-2"><strong>Hinweise:</strong><ul class="mb-0 pl-3">';
warnings.forEach(function(warning) {
listHtml += '<li>' + escapeHtml(warning) + '</li>';
});
listHtml += '</ul></div>';
}
if (!errors.length && !warnings.length) {
listHtml = '<div class="alert alert-success mb-2">Alle Vorabprüfungen sind erfolgreich.</div>';
}
$('#dhl-preflight-status')
.removeClass('border-secondary border-success border-warning border-danger')
.addClass('border-' + statusClass)
.html(`
<div class="card-header d-flex align-items-center">
<i class="fas fa-${statusIcon} text-${statusClass} mr-2"></i>
<strong>Vorabprüfung: ${escapeHtml(response.message || 'Prüfung abgeschlossen')}</strong>
</div>
<div class="card-body">
<div class="row mb-3">
<div class="col-md-4">
<small class="text-muted d-block">Produktcode</small>
<strong>${escapeHtml(productCode)}</strong>
</div>
<div class="col-md-4">
<small class="text-muted d-block">Sendungsart</small>
<strong>${escapeHtml(productScope)}</strong>
</div>
<div class="col-md-4">
<small class="text-muted d-block">Zielland</small>
<strong>${escapeHtml(countryLabel)}</strong>
</div>
</div>
<div class="mb-3">
<small class="text-muted d-block">Lieferadresse</small>
<strong>${escapeHtml([normalized.street, normalized.house_number].filter(Boolean).join(' '))}</strong>,
${escapeHtml([normalized.postal_code, normalized.city].filter(Boolean).join(' '))}
</div>
<div class="mb-3">
<small class="text-muted d-block">Adressvalidierung</small>
<span class="badge badge-${validationBadgeClass} mr-2">${escapeHtml(validationBadgeText)}</span>
<span>${escapeHtml(validationMessage)}</span>
</div>
${listHtml}
${response.can_create_label ? '<small class="text-muted">Prüfung bestätigt. Klicken Sie erneut auf „Sendung jetzt erstellen“, um das Label zu erzeugen.</small>' : ''}
</div>
`);
}
function resetDhlPreflight(keepStatus) {
$('#dhl-preflight-confirmed').val('0');
$('#create-shipment-btn').prop('disabled', false).html('<i class="fas fa-clipboard-check"></i> Vorabprüfung durchführen');
if (keepStatus) {
return;
}
$('#dhl-preflight-status')
.removeClass('border-success border-warning border-danger')
.addClass('border-secondary')
.html(`
<div class="card-header d-flex align-items-center">
<i class="fas fa-clipboard-check text-secondary mr-2"></i>
<strong>Vorabprüfung vor Labelerstellung</strong>
</div>
<div class="card-body">
<p class="text-muted mb-0">
Formular geändert. Bitte führen Sie die Vorabprüfung erneut aus, bevor das Label erstellt wird.
</p>
</div>
`);
}
function escapeHtml(value) {
return $('<div>').text(value || '').html();
}
function submitDhlShipment(form, formData, submitBtn) {
// Disable submit button
submitBtn.prop('disabled', true).html('<i class="fas fa-spinner fa-spin"></i> Wird erstellt...');
$.ajax({
url: form.attr('action'),
method: 'POST',
@ -119,14 +258,14 @@ $(document).ready(function() {
success: function(response) {
if (response.success) {
console.log(response);
// Show success message
if (typeof showAlert === 'function') {
showAlert('success', response.message);
} else {
alert(response.message);
}
// Switch to info mode instead of closing modal
setTimeout(function() {
// Show loading indicator
@ -140,7 +279,7 @@ $(document).ready(function() {
</div>
`;
$('#modals-load-content .modal-dialog').html(loadingHtml);
// Reload modal in info mode to show the created shipment
$.post('{{ route('modal_load') }}', {
action: 'create-dhl-shipment',
@ -148,7 +287,7 @@ $(document).ready(function() {
_token: '{{ csrf_token() }}'
}).done(function(response) {
$('#modals-load-content .modal-dialog').html(response.html);
// Show success message in the new modal content
setTimeout(function() {
if (typeof showAlert === 'function') {
@ -160,30 +299,60 @@ $(document).ready(function() {
});
}, 1000); // Wait 1 seconds to show success message
} else {
alert(response.message || 'Fehler beim Erstellen der Sendung.');
submitBtn.prop('disabled', false).html('<i class="fas fa-shipping-fast"></i> Sendung erstellen');
renderDhlCreationErrorStatus(response);
resetDhlPreflight(true);
}
},
error: function(xhr) {
var errorMessage = 'Fehler beim Erstellen der Sendung.';
var response = xhr.responseJSON || {
message: 'Fehler beim Erstellen der Sendung.'
};
if (xhr.responseJSON && xhr.responseJSON.message) {
errorMessage = xhr.responseJSON.message;
response.message = xhr.responseJSON.message;
} else if (xhr.responseText) {
try {
var errorData = JSON.parse(xhr.responseText);
if (errorData.errors) {
errorMessage = Object.values(errorData.errors).flat().join(', ');
response.errors = Object.values(errorData.errors).flat();
}
} catch (e) {
// Ignore JSON parse errors
}
}
alert(errorMessage);
submitBtn.prop('disabled', false).html('<i class="fas fa-shipping-fast"></i> Sendung erstellen');
renderDhlCreationErrorStatus(response);
resetDhlPreflight(true);
}
});
});
}
function renderDhlCreationErrorStatus(response) {
var errors = response.errors || [response.message || 'DHL hat die Labelerstellung abgelehnt.'];
renderDhlPreflightStatus({
status: 'error',
can_create_label: false,
message: 'DHL hat die Adresse bei der Labelerstellung abgelehnt.',
errors: errors,
warnings: [],
preflight: {
product: {
code: $('#modal-product-code').val(),
scope_label: $('#modal-product-code option:selected').text().trim()
},
address: {
validation_available: true,
validation_message: 'DHL-Leitcodierung über mustEncode wurde bei der Labelerstellung geprüft.',
normalized: {
street: $('#shipping_address').val(),
house_number: $('#shipping_houseNumber').val(),
postal_code: $('#shipping_zipcode').val(),
city: $('#shipping_city').val()
}
}
}
});
}
// Enhanced form validation
function validateForm() {
@ -216,6 +385,12 @@ $(document).ready(function() {
isValid = false;
}
});
var reference = $('#modal-reference').val();
if (reference && reference.length > 35) {
$('#modal-reference').addClass('is-invalid').after('<div class="invalid-feedback">Referenz darf maximal 35 Zeichen lang sein.</div>');
isValid = false;
}
return isValid;
}
@ -237,6 +412,23 @@ $(document).ready(function() {
}
}
});
var dhlProductSuggestions = @json($productSuggestions ?? []);
$('#shipping_country').on('change', function() {
var countryCode = $(this).find(':selected').data('country-code');
var suggestedProduct = dhlProductSuggestions[countryCode];
if (suggestedProduct && $('#modal-product-code option[value="' + suggestedProduct + '"]').length) {
$('#modal-product-code').val(suggestedProduct);
}
});
$('#modal-create-shipment-form').on('input change', 'input, select', function() {
if ($(this).attr('id') !== 'dhl-preflight-confirmed') {
resetDhlPreflight();
}
});
// Real-time required field validation
$('input[required], select[required]').on('blur', function() {