OpenXE/www/lib/versandarten/dhl.php
2024-09-28 23:16:51 +02:00

257 lines
13 KiB
PHP

<?php
/*
* SPDX-FileCopyrightText: 2022-2024 Andreas Palm
*
* SPDX-License-Identifier: LicenseRef-EGPL-3.1
*/
use Xentral\Carrier\Dhl\Data\Communication;
use Xentral\Carrier\Dhl\Data\Country;
use Xentral\Carrier\Dhl\Data\CreateShipmentOrderResponse;
use Xentral\Carrier\Dhl\Data\PackStation;
use Xentral\Carrier\Dhl\Data\Postfiliale;
use Xentral\Carrier\Dhl\Data\ReceiverNativeAddress;
use Xentral\Carrier\Dhl\Data\Shipment;
use Xentral\Carrier\Dhl\Data\ShipmentItem;
use Xentral\Carrier\Dhl\DhlApi;
use Xentral\Modules\ShippingMethod\Model\CreateShipmentResult;
use Xentral\Modules\ShippingMethod\Model\Product;
use Xentral\Modules\ShippingMethod\Model\ShipmentStatus;
require_once(dirname(__DIR__).'/class.versanddienstleister.php');
class Versandart_dhl extends Versanddienstleister{
public function GetName():string
{
return 'DHL';
}
public function AdditionalSettings(): array
{
return [
'user' => array('typ' => 'text', 'bezeichnung' => 'Benutzer:', 'info' => 'geschaeftskunden_api (Versenden/Intraship-Benutzername)'),
'signature' => array('typ' => 'text', 'bezeichnung' => 'Signature:', 'info' => 'Dhl_ep_test1 (Versenden/IntrashipPasswort)'),
'ekp' => array('typ' => 'text', 'bezeichnung' => 'EKP', 'info' => '5000000000 (gültige DHL Kundennummer)'),
'accountnumber' => array('typ' => 'text', 'bezeichnung' => 'Abrechnungsnummer Paket:'),
'accountnumber_int' => array('typ' => 'text', 'bezeichnung' => 'Abrechnungsnummer Paket International:'),
'accountnumber_euro' => array('typ' => 'text', 'bezeichnung' => 'Abrechnungsnummer Europaket:'),
'accountnumber_connect' => array('typ' => 'text', 'bezeichnung' => 'Abrechnungsnummer Paket Connect:'),
'accountnumber_wp' => array('typ' => 'text', 'bezeichnung' => 'Abrechnungsnummer Warenpost:'),
'accountnumber_wpint' => array('typ' => 'text', 'bezeichnung' => 'Abrechnungsnummer Warenpost International:'),
// 'intraship_retourenaccount' => array('typ' => 'text', 'bezeichnung' => 'Retouren Account:', 'info' => '14 Stellige DHL-Retoure Abrechnungsnummer'),
// 'intraship_retourenlabel' => array('typ' => 'checkbox', 'bezeichnung' => 'Vorauswahl Retourenlabel:', 'info' => 'Druckt Retourenlabel mit'),
'sender_name1' => array('typ' => 'text', 'bezeichnung' => 'Versender Firma:'),
'sender_street' => array('typ' => 'text', 'bezeichnung' => 'Versender Strasse:'),
'sender_streetnumber' => array('typ' => 'text', 'bezeichnung' => 'Versender Strasse Nr.:'),
'sender_zip' => array('typ' => 'text', 'bezeichnung' => 'Versender PLZ:'),
'sender_city' => array('typ' => 'text', 'bezeichnung' => 'Versender Stadt:'),
'sender_country' => array('typ' => 'text', 'bezeichnung' => 'Versender ISO Code:', 'info' => 'DE'),
'sender_email' => array('typ' => 'text', 'bezeichnung' => 'Versender E-Mail:'),
'sender_phone' => array('typ' => 'text', 'bezeichnung' => 'Versender Telefon:'),
'sender_web' => array('typ' => 'text', 'bezeichnung' => 'Versender Web:'),
'sender_contact_person' => array('typ' => 'text', 'bezeichnung' => 'Versender Ansprechpartner:'),
'cod_account_owner' => array('typ' => 'text', 'bezeichnung' => 'Nachnahme Kontoinhaber:'),
'cod_bank_name' => array('typ' => 'text', 'bezeichnung' => 'Nachnahme Bank Name:'),
'cod_account_iban' => array('typ' => 'text', 'bezeichnung' => 'Nachnahme IBAN:'),
'cod_account_bic' => array('typ' => 'text', 'bezeichnung' => 'Nachnahme BIC:'),
'cod_extra_fee' => array('typ' => 'text', 'bezeichnung' => 'Nachnahme Gebühr:', 'info' => 'z.B. 2,00 wird auf Rechnungsbetrag addiert, da DHL dies als extra Gebühr für sich behält'),
'weight' => array('typ' => 'text', 'bezeichnung' => 'Standard Gewicht:', 'info' => 'in KG'),
'length' => array('typ' => 'text', 'bezeichnung' => 'Standard Länge:', 'info' => 'in cm'),
'width' => array('typ' => 'text', 'bezeichnung' => 'Standard Breite:', 'info' => 'in cm'),
'height' => array('typ' => 'text', 'bezeichnung' => 'Standard Höhe:', 'info' => 'in cm'),
'product' => array('typ' => 'text', 'bezeichnung' => 'Standard Produkt:', 'info' => 'z.B. in DE: V01PAK oder AT: V86PARCEL'),
'use_premium' => array('typ' => 'checkbox', 'bezeichnung' => 'Premiumversand verwenden:'),
/*
'intraship_vorausverfuegung' => array('typ' => 'select', 'bezeichnung' => 'Vorausverf&uuml;gung: ', 'optionen' => array('-' => 'keine Vorausverf&uuml;gung', 'IMMEDIATE' => 'Sofortige R&uuml;cksendung an den Absender', 'AFTER_DEADLINE' => 'R&uuml;cksenden an den Absender nach Ablauf der Frist', 'ABANDONMENT' => 'Preisgabe des Pakets durch den Absender (entgeltfrei)')),
'sperrgut' => array('typ' => 'checkbox', 'bezeichnung' => 'Sperrgut:'),
'keineversicherung' => array('typ' => 'checkbox', 'bezeichnung' => 'Extra Versicherung ausschalten:', 'info' => 'Option muss von Hand im Paketmarkendialog gesetzt werden.'),
'leitcodierung' => array('typ' => 'checkbox', 'bezeichnung' => 'Leitcodierung aktivieren:'),
'use_shipping_article_from_order_on_export' => ['typ' => 'checkbox', 'bezeichnung' => 'Bei Export Porto aus Auftrag senden:'],
'autotracking' => array('typ' => 'checkbox', 'bezeichnung' => 'Tracking übernehmen:'),
'log' => array('typ' => 'checkbox', 'bezeichnung' => 'Logging')*/
];
}
public function CreateShipment(object $json, array $address): CreateShipmentResult
{
$shipment = new Shipment();
$shipment->ShipmentDetails->product = $json->product;
$shipment->ShipmentDetails->accountNumber = $this->GetAccountNumber($json->product);
$shipment->ShipmentDetails->SetShipmentDate(new DateTimeImmutable('today'));
$shipment->ShipmentDetails->ShipmentItem = new ShipmentItem();
$shipment->ShipmentDetails->ShipmentItem->weightInKG = $json->weight ?? 0;
$shipment->ShipmentDetails->ShipmentItem->lengthInCM = $json->length;
$shipment->ShipmentDetails->ShipmentItem->widthInCM = $json->width;
$shipment->ShipmentDetails->ShipmentItem->heightInCM = $json->height;
$shipment->Shipper->Name->name1 = $this->settings->sender_name1 ?? '';
$shipment->Shipper->Address->streetName = $this->settings->sender_street ?? '';
$shipment->Shipper->Address->streetNumber = $this->settings->sender_streetnumber;
$shipment->Shipper->Address->zip = $this->settings->sender_zip ?? '';
$shipment->Shipper->Address->city = $this->settings->sender_city ?? '';
$shipment->Shipper->Address->Origin = Country::Create($this->settings->sender_country ?? 'DE');
$shipment->Shipper->Communication = new Communication();
$shipment->Shipper->Communication->phone = $this->settings->sender_phone;
$shipment->Shipper->Communication->email = $this->settings->sender_email;
$shipment->Shipper->Communication->contactPerson = $this->settings->sender_contact_person;
$shipment->Receiver->name1 = $json->name;
switch ($json->addresstype) {
case 0:
$shipment->Receiver->Address = new ReceiverNativeAddress();
$shipment->Receiver->name1 = $json->company_name;
$shipment->Receiver->Address->name2 = join(
';',
array_filter(
[
$json->contact_name,
$json->company_division
],
fn(string $item) => !empty(trim($item))
)
);
$shipment->Receiver->Address->streetName = $json->street ?? '';
$shipment->Receiver->Address->streetNumber = $json->streetnumber;
$shipment->Receiver->Address->city = $json->city ?? '';
$shipment->Receiver->Address->zip = $json->zip ?? '';
$shipment->Receiver->Address->Origin = Country::Create($json->country ?? 'DE', $json->state);
if (isset($json->address2) && !empty($json->address2))
$shipment->Receiver->Address->addressAddition[] = $json->address2;
break;
case 1:
$shipment->Receiver->Packstation = new PackStation();
$shipment->Receiver->Packstation->postNumber = $json->postnumber;
$shipment->Receiver->Packstation->packstationNumber = $json->parcelstationNumber;
$shipment->Receiver->Packstation->city = $json->city ?? '';
$shipment->Receiver->Packstation->zip = $json->zip ?? '';
$shipment->Receiver->Packstation->Origin = Country::Create($json->country ?? 'DE', $json->state);
break;
case 2:
$shipment->Receiver->Postfiliale = new Postfiliale();
$shipment->Receiver->Postfiliale->postNumber = $json->postnumber;
$shipment->Receiver->Postfiliale->postfilialeNumber = $json->postofficeNumber;
$shipment->Receiver->Postfiliale->city = $json->city ?? '';
$shipment->Receiver->Postfiliale->zip = $json->zip ?? '';
$shipment->Receiver->Postfiliale->Origin = Country::Create($json->country ?? 'DE', $json->state);
break;
case 3:
$shipment->Receiver->Address = new ReceiverNativeAddress();
$shipment->Receiver->name1 = $json->name;
$shipment->Receiver->Address->name2 = $json->contact_name;
$shipment->Receiver->Address->streetName = $json->street ?? '';
$shipment->Receiver->Address->streetNumber = $json->streetnumber;
$shipment->Receiver->Address->city = $json->city ?? '';
$shipment->Receiver->Address->zip = $json->zip ?? '';
$shipment->Receiver->Address->Origin = Country::Create($json->country ?? 'DE', $json->state);
if (isset($json->address2) && !empty($json->address2))
$shipment->Receiver->Address->addressAddition[] = $json->address2;
break;
}
$shipment->Receiver->Communication = new Communication();
$shipment->Receiver->Communication->email = $json->email;
$shipment->Receiver->Communication->phone = $json->phone;
$api = new DhlApi($this->settings->user, $this->settings->signature);
$ret = new CreateShipmentResult();
$result = $api->CreateShipment($shipment);
if (!$result instanceof CreateShipmentOrderResponse) {
$ret->Errors[] = $result;
return $ret;
}
if ($result->Status->statusCode === 0) {
$ret->Success = true;
$ret->TrackingNumber = $result->CreationState->shipmentNumber;
$ret->TrackingUrl = sprintf('https://www.dhl.de/de/privatkunden/pakete-empfangen/verfolgen.html?piececode=%s', $ret->TrackingNumber);
if (isset($result->CreationState->LabelData->labelData))
$ret->Label = base64_decode($result->CreationState->LabelData->labelData);
if (isset($result->CreationState->LabelData->exportLabelData))
$ret->ExportDocuments = base64_decode($result->CreationState->LabelData->exportLabelData);
} else if (isset($result->CreationState)) {
if (is_array($result->CreationState->LabelData->Status->statusMessage))
$ret->Errors = $result->CreationState->LabelData->Status->statusMessage;
else
$ret->Errors[] = $result->CreationState->LabelData->Status->statusMessage;
} else {
$ret->Errors[] = $result->Status->statusText;
}
return $ret;
}
public function GetShippingProducts(): array
{
$result = [];
if ($this->settings->accountnumber) {
$result[] = Product::Create('V01PAK', 'DHL Paket')
->WithLength(15, 120)
->WithWidth(11, 60)
->WithHeight(1, 60)
->WithWeight(0.01, 31.5);
}
if ($this->settings->accountnumber_int) {
$result[] = Product::Create('V53WPAK', 'DHL Paket International')
->WithLength(15, 120)
->WithWidth(11, 60)
->WithHeight(1, 60)
->WithWeight(0.01, 31.5)
->WithServices([Product::SERVICE_PREMIUM]);
}
if ($this->settings->accountnumber_euro) {
$result[] = Product::Create('V54EPAK', 'DHL Europaket')
->WithLength(15, 120)
->WithWidth(11, 60)
->WithHeight(3.5, 60)
->WithWeight(0.01, 31.5);
}
if ($this->settings->accountnumber_connect) {
$result[] = Product::Create('V55PAK', 'DHL Paket Connect')
->WithLength(15, 120)
->WithWidth(11, 60)
->WithHeight(3.5, 60)
->WithWeight(0.01, 31.5);
}
if ($this->settings->accountnumber_wp) {
$result[] = Product::Create('V62WP', 'DHL Warenpost')
->WithLength(10, 35)
->WithWidth(7, 25)
->WithHeight(0.1, 5)
->WithWeight(0.01, 1);
}
if ($this->settings->accountnumber_wpint) {
$result[] = Product::Create('V66WPI', 'DHL Warenpost International')
->WithLength(10, 35)
->WithWidth(7, 25)
->WithHeight(0.1, 10)
->WithWeight(0.01, 1)
->WithServices([Product::SERVICE_PREMIUM]);
}
return $result;
}
private function GetAccountNumber(string $product):?string {
switch ($product) {
case 'V01PAK': return $this->settings->accountnumber;
case 'V53WPAK': return $this->settings->accountnumber_int;
case 'V54EPAK': return $this->settings->accountnumber_euro;
case 'V55PAK': return $this->settings->accountnumber_connect;
case 'V62WP': return $this->settings->accountnumber_wp;
case 'V66WPI': return $this->settings->accountnumber_wpint;
}
return null;
}
public function GetShipmentStatus(string $tracking): ShipmentStatus|null
{
return null;
}
}