View source
<?php
namespace Drupal\Tests\commerce_shipping\Kernel;
use Drupal\commerce_order\Entity\Order;
use Drupal\commerce_order\Entity\OrderItem;
use Drupal\commerce_price\Price;
use Drupal\commerce_promotion\Entity\Coupon;
use Drupal\commerce_promotion\Entity\Promotion;
use Drupal\commerce_shipping\Entity\Shipment;
use Drupal\commerce_shipping\Entity\ShippingMethod;
use Drupal\commerce_shipping\ShipmentItem;
use Drupal\language\Entity\ConfigurableLanguage;
use Drupal\physical\Weight;
class ShipmentManagerTest extends ShippingKernelTestBase {
protected $shipmentManager;
protected $order;
protected $shipment;
protected $shippingMethods = [];
public static $modules = [
'commerce_promotion',
'language',
'content_translation',
];
protected function setUp() : void {
parent::setUp();
$this
->installEntitySchema('commerce_promotion');
$this
->installEntitySchema('commerce_promotion_coupon');
$this
->installSchema('commerce_promotion', [
'commerce_promotion_usage',
]);
ConfigurableLanguage::createFromLangcode('fr')
->save();
$this->container
->get('content_translation.manager')
->setEnabled('commerce_shipping_method', 'commerce_shipping_method', TRUE);
$this->shipmentManager = $this->container
->get('commerce_shipping.shipment_manager');
$order_item = OrderItem::create([
'type' => 'test',
'quantity' => 1,
'unit_price' => new Price('12.00', 'USD'),
]);
$order_item
->save();
$order = Order::create([
'type' => 'default',
'order_number' => '6',
'store_id' => $this->store
->id(),
'state' => 'completed',
'order_items' => [
$order_item,
],
]);
$order
->save();
$this->order = $order;
$shipping_method = ShippingMethod::create([
'stores' => $this->store
->id(),
'name' => 'Example',
'plugin' => [
'target_plugin_id' => 'flat_rate',
'target_plugin_configuration' => [
'rate_label' => 'Standard shipping',
'rate_amount' => [
'number' => '5',
'currency_code' => 'USD',
],
],
],
'status' => TRUE,
'weight' => 1,
]);
$shipping_method
->save();
$this->shippingMethods[] = $shipping_method;
$another_shipping_method = ShippingMethod::create([
'stores' => $this->store
->id(),
'name' => 'Another shipping method',
'plugin' => [
'target_plugin_id' => 'flat_rate',
'target_plugin_configuration' => [
'rate_label' => 'Overnight shipping',
'rate_amount' => [
'number' => '20',
'currency_code' => 'USD',
],
],
],
'status' => TRUE,
'weight' => 0,
]);
$another_shipping_method
->addTranslation('fr', [
'name' => 'Another shipping method (FR)',
'plugin' => [
'target_plugin_id' => 'flat_rate',
'target_plugin_configuration' => [
'rate_label' => 'Le overnight shipping',
'rate_amount' => [
'number' => '22',
'currency_code' => 'USD',
],
],
],
]);
$another_shipping_method
->save();
$this->shippingMethods[] = $another_shipping_method;
$bad_shipping_method = ShippingMethod::create([
'stores' => $this->store
->id(),
'name' => $this
->randomString(),
'status' => TRUE,
'plugin' => [
'target_plugin_id' => 'exception_thrower',
'target_plugin_configuration' => [],
],
]);
$bad_shipping_method
->save();
$shipment = Shipment::create([
'type' => 'default',
'order_id' => $order
->id(),
'title' => 'Shipment',
'tracking_code' => 'ABC123',
'items' => [
new ShipmentItem([
'order_item_id' => 1,
'title' => 'T-shirt (red, large)',
'quantity' => 2,
'weight' => new Weight('40', 'kg'),
'declared_value' => new Price('30', 'USD'),
]),
],
'amount' => new Price('5', 'USD'),
'state' => 'draft',
]);
$shipment
->save();
$this->shipment = $this
->reloadEntity($shipment);
}
public function testApplyRate() {
$rates = $this->shipmentManager
->calculateRates($this->shipment);
$this
->assertCount(2, $rates);
$second_rate = end($rates);
$this->shipmentManager
->applyRate($this->shipment, $second_rate);
$this
->assertEquals($second_rate
->getShippingMethodId(), $this->shipment
->getShippingMethodId());
$this
->assertEquals($second_rate
->getService()
->getId(), $this->shipment
->getShippingService());
$this
->assertEquals($second_rate
->getOriginalAmount(), $this->shipment
->getOriginalAmount());
$this
->assertEquals($second_rate
->getAmount(), $this->shipment
->getAmount());
}
public function testCalculateRates() {
$this->container
->get('language.default')
->set(ConfigurableLanguage::createFromLangcode('fr'));
$rates = $this->shipmentManager
->calculateRates($this->shipment);
$this
->assertCount(2, $rates);
$first_rate = reset($rates);
$second_rate = end($rates);
$this
->assertArrayHasKey($first_rate
->getId(), $rates);
$this
->assertEquals('2', $first_rate
->getShippingMethodId());
$this
->assertEquals('default', $first_rate
->getService()
->getId());
$this
->assertEquals('Le overnight shipping', $first_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('22.00', 'USD'), $first_rate
->getOriginalAmount());
$this
->assertEquals(new Price('22.00', 'USD'), $first_rate
->getAmount());
$this
->assertArrayHasKey($second_rate
->getId(), $rates);
$this
->assertEquals('1', $second_rate
->getShippingMethodId());
$this
->assertEquals('default', $second_rate
->getService()
->getId());
$this
->assertEquals('Standard shipping', $second_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('5.00', 'USD'), $second_rate
->getOriginalAmount());
$this
->assertEquals(new Price('5.00', 'USD'), $second_rate
->getAmount());
$this->shipment
->setData('alter_rate', TRUE);
$rates = $this->shipmentManager
->calculateRates($this->shipment);
$this
->assertCount(2, $rates);
$first_rate = reset($rates);
$second_rate = end($rates);
$this
->assertArrayHasKey($first_rate
->getId(), $rates);
$this
->assertEquals('2', $first_rate
->getShippingMethodId());
$this
->assertEquals('default', $first_rate
->getService()
->getId());
$this
->assertEquals('Le overnight shipping', $first_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('22.00', 'USD'), $first_rate
->getOriginalAmount());
$this
->assertEquals(new Price('44.00', 'USD'), $first_rate
->getAmount());
$this
->assertArrayHasKey($second_rate
->getId(), $rates);
$this
->assertEquals('1', $second_rate
->getShippingMethodId());
$this
->assertEquals('default', $second_rate
->getService()
->getId());
$this
->assertEquals('Standard shipping', $second_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('5.00', 'USD'), $second_rate
->getOriginalAmount());
$this
->assertEquals(new Price('10.00', 'USD'), $second_rate
->getAmount());
}
public function testPromotions() {
$first_promotion = Promotion::create([
'name' => 'Promotion 1',
'order_types' => [
$this->order
->bundle(),
],
'stores' => [
$this->store
->id(),
],
'offer' => [
'target_plugin_id' => 'shipment_fixed_amount_off',
'target_plugin_configuration' => [
'display_inclusive' => TRUE,
'filter' => 'include',
'shipping_methods' => [
[
'shipping_method' => $this->shippingMethods[0]
->uuid(),
],
],
'amount' => [
'number' => '1.00',
'currency_code' => 'USD',
],
],
],
'status' => TRUE,
]);
$first_promotion
->save();
$second_promotion = Promotion::create([
'name' => 'Promotion 1',
'order_types' => [
$this->order
->bundle(),
],
'stores' => [
$this->store
->id(),
],
'offer' => [
'target_plugin_id' => 'shipment_percentage_off',
'target_plugin_configuration' => [
'display_inclusive' => TRUE,
'filter' => 'include',
'shipping_methods' => [
[
'shipping_method' => $this->shippingMethods[1]
->uuid(),
],
],
'percentage' => '0.5',
],
],
'status' => TRUE,
]);
$second_promotion
->save();
$coupon = Coupon::create([
'promotion_id' => $second_promotion
->id(),
'code' => '50% off shipping',
'status' => TRUE,
]);
$coupon
->save();
$this->order
->set('coupons', [
$coupon,
]);
$this->order
->setRefreshState(Order::REFRESH_SKIP);
$this->order
->save();
$rates = $this->shipmentManager
->calculateRates($this->shipment);
$this
->assertCount(2, $rates);
$first_rate = reset($rates);
$second_rate = end($rates);
$this
->assertArrayHasKey($first_rate
->getId(), $rates);
$this
->assertEquals('2', $first_rate
->getShippingMethodId());
$this
->assertEquals('default', $first_rate
->getService()
->getId());
$this
->assertEquals('Overnight shipping', $first_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('20.00', 'USD'), $first_rate
->getOriginalAmount());
$this
->assertEquals(new Price('10.00', 'USD'), $first_rate
->getAmount());
$this
->assertArrayHasKey($second_rate
->getId(), $rates);
$this
->assertEquals('1', $second_rate
->getShippingMethodId());
$this
->assertEquals('default', $second_rate
->getService()
->getId());
$this
->assertEquals('Standard shipping', $second_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('5.00', 'USD'), $second_rate
->getOriginalAmount());
$this
->assertEquals(new Price('4.00', 'USD'), $second_rate
->getAmount());
$second_promotion
->set('offer', [
'target_plugin_id' => 'combination_offer',
'target_plugin_configuration' => [
'offers' => [
[
'target_plugin_id' => 'shipment_percentage_off',
'target_plugin_configuration' => [
'display_inclusive' => TRUE,
'filter' => 'include',
'shipping_methods' => [
[
'shipping_method' => $this->shippingMethods[1]
->uuid(),
],
],
'percentage' => '0.2',
],
],
],
],
]);
$second_promotion
->save();
$rates = $this->shipmentManager
->calculateRates($this->shipment);
$this
->assertCount(2, $rates);
$first_rate = reset($rates);
$this
->assertArrayHasKey($first_rate
->getId(), $rates);
$this
->assertEquals('2', $first_rate
->getShippingMethodId());
$this
->assertEquals('default', $first_rate
->getService()
->getId());
$this
->assertEquals('Overnight shipping', $first_rate
->getService()
->getLabel());
$this
->assertEquals(new Price('20.00', 'USD'), $first_rate
->getOriginalAmount());
$this
->assertEquals(new Price('16.00', 'USD'), $first_rate
->getAmount());
}
public function testSelectDefaultRate() {
$rates = $this->shipmentManager
->calculateRates($this->shipment);
$default_rate = $this->shipmentManager
->selectDefaultRate($this->shipment, $rates);
$this
->assertEquals('2--default', $default_rate
->getId());
$this->shipment
->setShippingMethodId('1');
$this->shipment
->setShippingService('default');
$default_rate = $this->shipmentManager
->selectDefaultRate($this->shipment, $rates);
$this
->assertEquals('1--default', $default_rate
->getId());
}
}