Skip to content

Commit

Permalink
Merge pull request #1502 from dpfaffenbauer/issue/1501
Browse files Browse the repository at this point in the history
[Product] fix cloning of ProductUnitDefinitions and add test for it.
  • Loading branch information
dpfaffenbauer authored Oct 19, 2020
2 parents 36fcae9 + 0c51e19 commit b3d0641
Show file tree
Hide file tree
Showing 7 changed files with 261 additions and 14 deletions.
23 changes: 23 additions & 0 deletions features/product/clone_units_and_qpr.feature
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
@product
Feature: Adding a new product with a simple quantity price rule

Background:
Given the site operates on a store in "Austria"
And the site has a currency "Euro" with iso "EUR"
And I am in country "Austria"
And the site has a product "Shoe" priced at 10000
And the site has a product-unit "Pieces"
And the site has a product-unit "Carton"
And the site has a product-unit "Palette"
And the product has the default unit "Pieces"
And the product has and additional unit "Carton" with conversion rate "24"
And the product has and additional unit "Palette" with conversion rate "200"

Scenario: Add a quantity price rule with no conditions
Given adding a quantity price rule to product "Shoe" named "default-product-quantity-price-rule" and with calculation-behaviour "volume"
And the quantity price rule is active
And the quantity price rule has a range starting from 0 with behaviour percentage-decrease of 10% for unit "Pieces"
And the quantity price rule has a range starting from 0 with behaviour percentage-decrease of 10% for unit "Carton"
And the quantity price rule has a range starting from 0 with behaviour percentage-decrease of 10% for unit "Palette"
And the product has a variant "Shoe Red"
And I copy the products unit-definitions and quantity-price-rules to all variants
42 changes: 41 additions & 1 deletion src/CoreShop/Behat/Context/Setup/ProductContext.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@
use CoreShop\Component\Core\Model\ProductStoreValuesInterface;
use CoreShop\Component\Core\Model\ProductUnitDefinitionPriceInterface;
use CoreShop\Component\Core\Model\StoreInterface;
use CoreShop\Component\Core\Product\Cloner\ProductQuantityPriceRulesCloner;
use CoreShop\Component\Core\Product\Cloner\ProductUnitDefinitionsCloner;
use CoreShop\Component\Product\Model\ManufacturerInterface;
use CoreShop\Component\Product\Model\ProductUnitDefinitionInterface;
use CoreShop\Component\Product\Model\ProductUnitDefinitionsInterface;
Expand All @@ -31,6 +33,7 @@
use Pimcore\Model\DataObject\Folder;
use Pimcore\Model\DataObject\Service;
use Pimcore\Tool;
use Webmozart\Assert\Assert;

final class ProductContext implements Context
{
Expand Down Expand Up @@ -59,25 +62,41 @@ final class ProductContext implements Context
*/
private $productUnitDefinitionPriceFactory;

/**
* @var ProductUnitDefinitionsCloner
*/
private $unitDefinitionsCloner;

/**
* @var ProductQuantityPriceRulesCloner
*/
private $quantityPriceRulesCloner;

/**
* @param SharedStorageInterface $sharedStorage
* @param FactoryInterface $productFactory
* @param FactoryInterface $productUnitDefinitions
* @param FactoryInterface $productUnitDefinition
* @param FactoryInterface $productUnitDefinitionPriceFactory
* @param ProductUnitDefinitionsCloner $unitDefinitionsCloner
* @param ProductQuantityPriceRulesCloner $quantityPriceRulesCloner
*/
public function __construct(
SharedStorageInterface $sharedStorage,
FactoryInterface $productFactory,
FactoryInterface $productUnitDefinitions,
FactoryInterface $productUnitDefinition,
FactoryInterface $productUnitDefinitionPriceFactory
FactoryInterface $productUnitDefinitionPriceFactory,
ProductUnitDefinitionsCloner $unitDefinitionsCloner,
ProductQuantityPriceRulesCloner $quantityPriceRulesCloner
) {
$this->sharedStorage = $sharedStorage;
$this->productFactory = $productFactory;
$this->productUnitDefinitions = $productUnitDefinitions;
$this->productUnitDefinition = $productUnitDefinition;
$this->productUnitDefinitionPriceFactory = $productUnitDefinitionPriceFactory;
$this->unitDefinitionsCloner = $unitDefinitionsCloner;
$this->quantityPriceRulesCloner = $quantityPriceRulesCloner;
}

/**
Expand Down Expand Up @@ -398,6 +417,27 @@ public function iCopyTheProduct(ProductInterface $product)

$this->sharedStorage->set('copied-object', $newObject);
}
/**
* @Given /^I copy the (products) unit-definitions and quantity-price-rules to all variants$/
*/
public function iCopyTheUnitDefinitionsAndQuantityPriceRulesToAllVariants(ProductInterface $product)
{
/**
* @var Concrete $product
*/
Assert::isInstanceOf($product, Concrete::class);

foreach ($product->getChildren([AbstractObject::OBJECT_TYPE_VARIANT], true) as $variant) {

if (!$variant instanceof ProductInterface) {
continue;
}

$this->unitDefinitionsCloner->clone($variant, $product, false);
$this->quantityPriceRulesCloner->clone($variant, $product, false);
$variant->save();
}
}

private function getOrCreateUnitDefinitions(ProductUnitDefinitionsInterface $definitions = null)
{
Expand Down
178 changes: 169 additions & 9 deletions src/CoreShop/Behat/Context/Setup/ProductQuantityPriceRuleContext.php
Original file line number Diff line number Diff line change
Expand Up @@ -31,12 +31,15 @@
use CoreShop\Component\Core\Model\ProductInterface;
use CoreShop\Component\Core\Model\QuantityRangeInterface;
use CoreShop\Component\Core\Model\StoreInterface;
use CoreShop\Component\Core\Repository\ProductRepositoryInterface;
use CoreShop\Component\Customer\Model\CustomerGroupInterface;
use CoreShop\Component\Product\Model\ProductUnitInterface;
use CoreShop\Component\ProductQuantityPriceRules\Model\ProductQuantityPriceRuleInterface;
use CoreShop\Component\Resource\Factory\FactoryInterface;
use CoreShop\Component\Rule\Model\ConditionInterface;
use CoreShop\Component\ProductQuantityPriceRules\Model\ProductQuantityPriceRuleInterface;
use Doctrine\Common\Persistence\ObjectManager;
use Symfony\Component\Form\FormFactoryInterface;
use Webmozart\Assert\Assert;

final class ProductQuantityPriceRuleContext implements Context
{
Expand Down Expand Up @@ -73,27 +76,35 @@ final class ProductQuantityPriceRuleContext implements Context
private $productQuantityPriceRuleFactory;

/**
* @param SharedStorageInterface $sharedStorage
* @param ObjectManager $objectManager
* @param FactoryInterface $rangeFactory
* @param FormFactoryInterface $formFactory
* @param FormTypeRegistryInterface $conditionFormTypeRegistry
* @param FactoryInterface $productQuantityPriceRuleFactory
* @var ProductRepositoryInterface
*/
private $productRepository;

/**
* @param SharedStorageInterface $sharedStorage
* @param ObjectManager $objectManager
* @param FactoryInterface $rangeFactory
* @param FormFactoryInterface $formFactory
* @param FormTypeRegistryInterface $conditionFormTypeRegistry
* @param FactoryInterface $productQuantityPriceRuleFactory
* @param ProductRepositoryInterface $productRepository
*/
public function __construct(
SharedStorageInterface $sharedStorage,
ObjectManager $objectManager,
FactoryInterface $rangeFactory,
FormFactoryInterface $formFactory,
FormTypeRegistryInterface $conditionFormTypeRegistry,
FactoryInterface $productQuantityPriceRuleFactory
FactoryInterface $productQuantityPriceRuleFactory,
ProductRepositoryInterface $productRepository
) {
$this->sharedStorage = $sharedStorage;
$this->objectManager = $objectManager;
$this->rangeFactory = $rangeFactory;
$this->formFactory = $formFactory;
$this->conditionFormTypeRegistry = $conditionFormTypeRegistry;
$this->productQuantityPriceRuleFactory = $productQuantityPriceRuleFactory;
$this->productRepository = $productRepository;
}

/**
Expand Down Expand Up @@ -221,8 +232,141 @@ public function theProductQuantityPriceRuleHasRangeAmountIncrease(
* @Given /^the (quantity price rule "[^"]+") has a range starting from ([^"]+) with behaviour fixed of ([^"]+) in (currency "[^"]+")$/
* @Given /^the (quantity price rule) has a range starting from ([^"]+) with behaviour fixed of ([^"]+) in (currency "[^"]+")$/
*/
public function theProductQuantityPriceRuleHasRangeFixed(ProductQuantityPriceRuleInterface $rule, int $from, $amount, CurrencyInterface $currency)
public function theProductQuantityPriceRuleHasRangeFixed(
ProductQuantityPriceRuleInterface $rule,
int $from,
$amount,
CurrencyInterface $currency
)
{
/**
* @var QuantityRangeInterface $range
*/
$range = $this->rangeFactory->createNew();
$range->setPricingBehaviour('fixed');
$range->setAmount($amount);
$range->setRangeStartingFrom($from);
$range->setCurrency($currency);

$this->addRange($rule, $range);
}

/**
* @Given /^the (quantity price rule "[^"]+") has a range starting from ([^"]+) with behaviour percentage-decrease of ([^"]+)% for (unit "[^"]+")$/
* @Given /^the (quantity price rule) has a range starting from ([^"]+) with behaviour percentage-decrease of ([^"]+)% for (unit "[^"]+")$/
*/
public function theProductQuantityPriceRuleHasRangePercentageDecreaseForUnit(
ProductQuantityPriceRuleInterface $rule,
int $from,
$percentage,
ProductUnitInterface $unit
)
{
$unitDefinition = $this->getUnitDefinitionFromProduct($rule->getProduct(), $unit);

/**
* @var QuantityRangeInterface $range
*/
$range = $this->rangeFactory->createNew();
$range->setPricingBehaviour('percentage_decrease');
$range->setPercentage($percentage);
$range->setRangeStartingFrom($from);
$range->setUnitDefinition($unitDefinition);

$this->addRange($rule, $range);
}

/**
* @Given /^the (quantity price rule "[^"]+") has a range starting from to ([^"]+) with behaviour percentage-increase of ([^"]+)% (unit "[^"]+")$/
* @Given /^the (quantity price rule) has a range starting from ([^"]+) with behaviour percentage-increase of ([^"]+)% (unit "[^"]+")$/
*/
public function theProductQuantityPriceRuleHasRangePercentageIncreaseForUnit(
ProductQuantityPriceRuleInterface $rule,
int $from,
$percentage,
ProductUnitInterface $unit
)
{
$unitDefinition = $this->getUnitDefinitionFromProduct($rule->getProduct(), $unit);

/**
* @var QuantityRangeInterface $range
*/
$range = $this->rangeFactory->createNew();
$range->setPricingBehaviour('percentage_increase');
$range->setPercentage($percentage);
$range->setRangeStartingFrom($from);
$range->setUnitDefinition($unitDefinition);

$this->addRange($rule, $range);
}

/**
* @Given /^the (quantity price rule "[^"]+") has a range starting from ([^"]+) with behaviour amount-decrease of ([^"]+) in (currency "[^"]+") (unit "[^"]+")$/
* @Given /^the (quantity price rule) has a range starting from ([^"]+) with behaviour amount-decrease of ([^"]+) in (currency "[^"]+") (unit "[^"]+")$/
*/
public function theProductQuantityPriceRuleHasRangeAmountDecreaseForUnit(
ProductQuantityPriceRuleInterface $rule,
int $from,
$amount,
CurrencyInterface $currency,
ProductUnitInterface $unit
) {
$unitDefinition = $this->getUnitDefinitionFromProduct($rule->getProduct(), $unit);

/**
* @var QuantityRangeInterface $range
*/
$range = $this->rangeFactory->createNew();
$range->setPricingBehaviour('amount_decrease');
$range->setAmount($amount);
$range->setRangeStartingFrom($from);
$range->setCurrency($currency);
$range->setUnitDefinition($unitDefinition);

$this->addRange($rule, $range);
}

/**
* @Given /^the (quantity price rule "[^"]+") has a range starting from ([^"]+) with behaviour amount-increase of ([^"]+) in (currency "[^"]+") (unit "[^"]+")$/
* @Given /^the (quantity price rule) has a range starting from ([^"]+) with behaviour amount-increase of ([^"]+) in (currency "[^"]+") (unit "[^"]+")$/
*/
public function theProductQuantityPriceRuleHasRangeAmountIncreaseForUnit(
ProductQuantityPriceRuleInterface $rule,
int $from,
$amount,
CurrencyInterface $currency,
ProductUnitInterface $unit
) {
$unitDefinition = $this->getUnitDefinitionFromProduct($rule->getProduct(), $unit);

/**
* @var QuantityRangeInterface $range
*/
$range = $this->rangeFactory->createNew();
$range->setPricingBehaviour('amount_increase');
$range->setAmount($amount);
$range->setRangeStartingFrom($from);
$range->setCurrency($currency);
$range->setUnitDefinition($unitDefinition);

$this->addRange($rule, $range);
}

/**
* @Given /^the (quantity price rule "[^"]+") has a range starting from ([^"]+) with behaviour fixed of ([^"]+) in (currency "[^"]+") (unit "[^"]+")$/
* @Given /^the (quantity price rule) has a range starting from ([^"]+) with behaviour fixed of ([^"]+) in (currency "[^"]+") (unit "[^"]+")$/
*/
public function theProductQuantityPriceRuleHasRangeFixedForUnit(
ProductQuantityPriceRuleInterface $rule,
int $from,
$amount,
CurrencyInterface $currency,
ProductUnitInterface $unit
)
{
$unitDefinition = $this->getUnitDefinitionFromProduct($rule->getProduct(), $unit);

/**
* @var QuantityRangeInterface $range
*/
Expand All @@ -231,6 +375,7 @@ public function theProductQuantityPriceRuleHasRangeFixed(ProductQuantityPriceRul
$range->setAmount($amount);
$range->setRangeStartingFrom($from);
$range->setCurrency($currency);
$range->setUnitDefinition($unitDefinition);

$this->addRange($rule, $range);
}
Expand Down Expand Up @@ -412,6 +557,21 @@ public function theProductQuantityPriceRuleHasANestedConditionWithStoreAndCountr
]));
}

private function getUnitDefinitionFromProduct(int $productId, ProductUnitInterface $unit)
{
$product = $this->productRepository->find($productId);

Assert::isInstanceOf($product, ProductInterface::class);

foreach ($product->getUnitDefinitions()->getUnitDefinitions() as $unitDefinition) {
if ($unitDefinition->getUnit()->getName() === $unit->getName()) {
return $unitDefinition;
}
}

throw new \Exception(sprintf('Unit %s in product %s (%s) not found', $unit->getName(), $product->getName(), $product->getId()));
}

/**
* @param ProductQuantityPriceRuleInterface $rule
* @param ConditionInterface $condition
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ services:
- '@coreshop.factory.product_unit_definitions'
- '@coreshop.factory.product_unit_definition'
- '@coreshop.factory.product_unit_definition_price'
- '@CoreShop\Component\Core\Product\Cloner\ProductUnitDefinitionsCloner'
- '@CoreShop\Component\Core\Product\Cloner\ProductQuantityPriceRulesCloner'
tags:
- { name: fob.context_service }

Expand Down Expand Up @@ -321,6 +323,7 @@ services:
- '@form.factory'
- '@coreshop.form_registry.product_quantity_price_rules.conditions'
- '@coreshop.factory.product_quantity_price_rule'
- '@coreshop.repository.product'
tags:
- { name: fob.context_service }

Expand Down
3 changes: 3 additions & 0 deletions src/CoreShop/Behat/Resources/config/suites/domain/product.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ default:
- coreshop.behat.context.transform.tax_rule_group
- coreshop.behat.context.transform.product_unit
- coreshop.behat.context.transform.cart
- coreshop.behat.context.transform.product_quantity_price_rule

- coreshop.behat.context.setup.product
- coreshop.behat.context.setup.product_price_rule
Expand All @@ -39,6 +40,7 @@ default:
- coreshop.behat.context.setup.product_unit
- coreshop.behat.context.setup.pimcore_class
- coreshop.behat.context.setup.cart
- coreshop.behat.context.setup.product_quantity_price_rule

- coreshop.behat.context.domain.product
- coreshop.behat.context.domain.product_price_rule
Expand All @@ -48,5 +50,6 @@ default:
- coreshop.behat.context.domain.category
- coreshop.behat.context.domain.link_generator
- coreshop.behat.context.domain.product_unit
- coreshop.behat.context.domain.product_quantity_price_rule
filters:
tags: "@product"
Loading

0 comments on commit b3d0641

Please sign in to comment.