-
-
Notifications
You must be signed in to change notification settings - Fork 2.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Order][OrderItem] Immutable product/variant names #8874
Conversation
It currently covers product + variant information. It would make sense to me also to write the underlying product option values with the variant. For my project they say way more than the variant name / code, as we have 1000s of variants per products and they just have something generated. The underlying naming says way more to the client and is also printed on invoices. Would be great to have that also added. The basics now already implemented are also a must, so it's great to see it moving on :) |
Thanks @GSadee! |
@johnrisby no problem and of course I hope you don't mind that I continue your work 😃 |
Not at all @GSadee, it's great. That's the whole point! |
$this->addSql('ALTER TABLE sylius_order_item ADD immutable_product_name VARCHAR(255), ADD immutable_product_code VARCHAR(255), ADD immutable_variant_name VARCHAR(255), ADD immutable_variant_code VARCHAR(255)'); | ||
|
||
$this->addSql('UPDATE sylius_order_item | ||
INNER JOIN sylius_order AS o ON sylius_order_item.order_id = o.id |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It would much easier to follow the SQL logic if we would use some more appropriate names for aliases rather than abbreviate the table name
INNER JOIN sylius_product_variant AS pv ON sylius_order_item.variant_id = pv.id | ||
INNER JOIN sylius_product_variant_translation AS pt ON pt.translatable_id = pv.id | ||
INNER JOIN sylius_order AS ol ON pt.locale = ol.locale_code | ||
SET sylius_order_item.immutable_variant_name = pt.name, sylius_order_item.immutable_variant_code = pv.code |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is it really worthy to add another SQL statement?
return 1 === count($rows); | ||
foreach ($rows as $row) { | ||
$field = $this->tableAccessor->getFieldFromRow($table, $row, 'item'); | ||
$name = $field->find('css', '.sylius-product-name'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't we assert that the field would exist?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not in this case, it would change the behaviour of this method.
@@ -6,7 +6,7 @@ | |||
{% set taxAdjustment = constant('Sylius\\Component\\Core\\Model\\AdjustmentInterface::TAX_ADJUSTMENT') %} | |||
|
|||
{% set variant = item.variant %} | |||
{% set product = variant.product %} | |||
{% set product = item.variant.product %} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What's the difference?
<a href="{{ path('sylius_admin_product_update', {'id': product.id}) }}" class="sylius-product-name" title="{{ product.name }}">{{ product.name }}</a> | ||
<span class="sub header sylius-product-variant-code" title="{{ variant.code }}"> | ||
{{ variant.code }} | ||
<div class="sylius-product-name" title="{{ item.immutableProductName }}">{{ item.immutableProductName }}</div> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we need to add immutable
prefix? It is set to order item, so it shouldn't change anyway.
Just thinking
@@ -17,6 +17,11 @@ | |||
http://doctrine-project.org/schemas/orm/doctrine-mapping.xsd"> | |||
|
|||
<mapped-superclass name="Sylius\Component\Core\Model\OrderItem" table="sylius_order_item"> | |||
<field name="immutableProductName" column="immutable_product_name" type="string" nullable="true"/> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure if the product name on order item should be nullable. It is pretty important data
/** | ||
* {@inheritdoc} | ||
*/ | ||
public function setImmutableProductCode(?string $immutableProductCode): void |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe we could skip this new setter?
2609a6a
to
61f2419
Compare
INNER JOIN sylius_product AS p ON pv.product_id = p.id | ||
INNER JOIN sylius_product_translation AS pt ON pt.translatable_id = p.id | ||
INNER JOIN sylius_order AS ol ON pt.locale = ol.locale_code | ||
SET sylius_order_item.product_name = pt.name |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Doubled space after =
sign 🎉
INNER JOIN sylius_product_variant AS pv ON sylius_order_item.variant_id = pv.id | ||
INNER JOIN sylius_product_variant_translation AS pvt ON pvt.translatable_id = pv.id | ||
INNER JOIN sylius_order AS ol ON pvt.locale = ol.locale_code | ||
SET sylius_order_item.variant_name = pvt.name |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same here
INNER JOIN sylius_product_variant AS pv ON sylius_order_item.variant_id = pv.id | ||
INNER JOIN sylius_product AS p ON pv.product_id = p.id | ||
INNER JOIN sylius_product_translation AS pt ON pt.translatable_id = p.id | ||
INNER JOIN sylius_order AS ol ON pt.locale = ol.locale_code |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we need to join sylius_order
for the second time? Isn't WHERE
enough then?
/** | ||
* {@inheritdoc} | ||
*/ | ||
public function setVariant(?ProductVariantInterface $variant): void |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, what if a product name changes after the product was added to the cart but before the checkout was completed?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good point 👍 What is your suggestion? Should I set immutable names on checkout complete
transition?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've created OrderImmutableNamesSetter
which is called on checkout complete
transition.
$this->addSql('ALTER TABLE sylius_order_item ADD product_name VARCHAR(255), ADD variant_name VARCHAR(255)'); | ||
|
||
$this->addSql('UPDATE sylius_order_item | ||
INNER JOIN sylius_order AS o ON sylius_order_item.order_id = o.id |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we not abbreviate rest of table aliases. It is not easy to understand what happened here
620a8fe
to
3966d36
Compare
/** | ||
* @param OrderInterface $order | ||
*/ | ||
public function setNames(OrderInterface $order): void; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This can be changed later (up to v1.1.0 release), so it's not a big deal, only this interface name looks weird.
OrderImmutableNamesSetterInterface::setNames
-> OrderItemProductNamesSetterInterface::__invoke
/ OrderFinalizer::__invoke
/ something else?
8005059
to
b3be998
Compare
@@ -63,3 +63,7 @@ winzou_state_machine: | |||
on: ["complete"] | |||
do: ["@sylius.state_resolver.order_shipping", "resolve"] | |||
args: ["object"] | |||
sylius_set_order_immutable_names: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should move it to the main order state machine. This is not really specific to checkout, it should happen whenver we create a new order (cart -> new transition).
b3be998
to
bb52a56
Compare
Thank you John & Grzesiu, nice work guys! /cc @johnrisby |
Great stuff. Sorry I've not contributed more to this recently but I've got a lot on. Thanks for picking up the baton Grzesiu! |
It replaces a PR (#8667) created by @johnrisby using his squashed commits.