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

@ -45,6 +45,8 @@ class DhlModalService
'shippingAddress' => null,
'availableCountries' => $this->getAvailableCountries(),
'productCodes' => $this->getAvailableProductCodes(),
'productSuggestions' => (new DhlProductResolver)->getProductSuggestionsByCountry(),
'selectedProductCode' => null,
'errors' => [],
'warnings' => [],
'existingShipments' => [],
@ -89,6 +91,7 @@ class DhlModalService
// Process and validate shipping address
$result['shippingAddress'] = $this->processShippingAddress($order);
$result['selectedProductCode'] = $this->getSuggestedProductCode($result['shippingAddress']);
// Validate address completeness
$addressValidation = $this->validateAddress($result['shippingAddress']);
@ -111,7 +114,7 @@ class DhlModalService
'error' => $e->getMessage(),
]);
$result['errors'][] = 'Fehler beim Laden der Bestelldaten: ' . $e->getMessage();
$result['errors'][] = 'Fehler beim Laden der Bestelldaten: '.$e->getMessage();
}
return $result;
@ -125,7 +128,7 @@ class DhlModalService
private function loadOrder($id): ?ShoppingOrder
{
return ShoppingOrder::with([
'shopping_order_items',
'shopping_order_items.product',
'shopping_user',
'dhlShipments', // Include DHL shipments
])->find($id);
@ -170,38 +173,7 @@ class DhlModalService
*/
private function calculateOrderWeight(ShoppingOrder $order): float
{
return $order->weight / 1000; // from grams to kg
/*
// Default fallback weight
$defaultWeight = 1.0;
if (!$order->shopping_order_items || $order->shopping_order_items->isEmpty()) {
return $defaultWeight;
}
// If order has a weight field (in grams), convert to kg
if ($order->weight && $order->weight > 0) {
return round($order->weight / 100, 1); // Convert grams to kg
}
// Calculate from items if available
$totalWeight = 0;
foreach ($order->shopping_order_items as $item) {
if ($item->weight && $item->weight > 0) {
$totalWeight += ($item->weight * $item->quantity);
}
}
if ($totalWeight > 0) {
return round($totalWeight / 100, 1); // Convert grams to kg
}
// Estimate based on item count if no weight data
$itemCount = $order->shopping_order_items->sum('quantity');
$estimatedWeight = max($itemCount * 0.5, $defaultWeight); // Estimate 0.5kg per item
return round($estimatedWeight, 1);
*/
return (new DhlShipmentWeightCalculator)->calculate($order);
}
/**
@ -287,50 +259,12 @@ class DhlModalService
*/
private function validateAddress(array $address): array
{
$errors = [];
$warnings = [];
// Required fields
$requiredFields = [
'firstname' => 'Vorname',
'lastname' => 'Nachname',
'address' => 'Straße',
'zipcode' => 'Postleitzahl',
'city' => 'Stadt',
];
foreach ($requiredFields as $field => $label) {
if (empty(trim($address[$field]))) {
$errors[] = "{$label} ist erforderlich.";
}
}
// Name validation
if (empty(trim($address['firstname'])) && empty(trim($address['lastname'])) && empty(trim($address['company']))) {
$errors[] = 'Entweder Name oder Firmenname muss angegeben werden.';
}
// Street number validation
if (! empty($address['address']) && empty($address['houseNumber'])) {
$warnings[] = 'Hausnummer konnte nicht automatisch erkannt werden. Bitte prüfen Sie die Adressangaben.';
}
// Postal code format validation for Germany
if (! empty($address['zipcode']) && $address['country'] && $address['country']->code === 'DE') {
if (! preg_match('/^\d{5}$/', $address['zipcode'])) {
$warnings[] = 'Deutsche Postleitzahl sollte 5 Ziffern haben.';
}
}
// Country validation
if (! $address['country']) {
$errors[] = 'Land konnte nicht ermittelt werden.';
}
$result = (new DhlAddressValidator)->validate($address);
return [
'valid' => empty($errors),
'errors' => $errors,
'warnings' => $warnings,
'valid' => $result['can_create_label'],
'errors' => $result['errors'],
'warnings' => $result['warnings'],
];
}
@ -386,8 +320,8 @@ class DhlModalService
$productCodes['V53PAK'] = 'DHL Paket International';
}
if (! empty($accountNumbers['V62WP'])) {
$productCodes['V62WP'] = 'DHL Warenpost National';
if (! empty($accountNumbers['V62KP'])) {
$productCodes['V62KP'] = 'DHL Kleinpaket';
}
if (! empty($accountNumbers['V07PAK'])) {
@ -399,13 +333,27 @@ class DhlModalService
$productCodes = [
'V01PAK' => 'DHL Paket National',
'V53PAK' => 'DHL Paket International',
'V62WP' => 'DHL Warenpost National',
'V62KP' => 'DHL Kleinpaket',
];
}
return $productCodes;
}
private function getSuggestedProductCode(array $shippingAddress): string
{
$countryCode = $shippingAddress['country']?->code;
if (! $countryCode) {
return 'V01PAK';
}
try {
return (new DhlProductResolver)->resolveProductCode($countryCode, null, 'V01PAK');
} catch (\InvalidArgumentException) {
return 'V01PAK';
}
}
/**
* Validate shipment parameters before API call
*
@ -431,23 +379,35 @@ class DhlModalService
$errors[] = 'Ungültiger Produktcode ausgewählt.';
}
// Address validation
$requiredAddressFields = [
'shipping_firstname' => 'Vorname',
'shipping_lastname' => 'Nachname',
'shipping_address' => 'Straße',
'shipping_houseNumber' => 'Hausnummer',
'shipping_zipcode' => 'Postleitzahl',
'shipping_city' => 'Stadt',
'shipping_country_id' => 'Land',
];
foreach ($requiredAddressFields as $field => $label) {
if (empty(trim($shipmentData[$field] ?? ''))) {
$errors[] = "{$label} ist erforderlich.";
if (! empty($shipmentData['shipping_country_id']) && $productCode) {
$country = Country::find($shipmentData['shipping_country_id']);
if ($country) {
try {
(new DhlProductResolver)->resolveProductCode($country->code, $productCode);
} catch (\InvalidArgumentException $e) {
$errors[] = $e->getMessage();
}
}
}
if ($productCode) {
try {
(new DhlShipmentWeightCalculator)->assertWithinProductLimit($weight, $productCode);
} catch (\InvalidArgumentException $e) {
$errors[] = $e->getMessage();
}
}
$country = null;
if (! empty($shipmentData['shipping_country_id'])) {
$country = Country::find($shipmentData['shipping_country_id']);
}
$addressValidation = (new DhlAddressValidator)->validate(array_merge($shipmentData, [
'shipping_country_code' => $country?->code,
]));
$errors = array_merge($errors, $addressValidation['errors']);
$warnings = array_merge($warnings, $addressValidation['warnings']);
return [
'valid' => empty($errors),
'errors' => $errors,