-
Notifications
You must be signed in to change notification settings - Fork 10.7k
[Migrator]: Add COGS support even if the feature is disabled #60862
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
Conversation
Testing GuidelinesHi @roccotripaldi , Apart from reviewing the code changes, please make sure to review the testing instructions (Guide) and verify that relevant tests (E2E, Unit, Integration, etc.) have been added or updated as needed. Reminder: PR reviewers are required to document testing performed. This includes:
|
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.
Pull Request Overview
This PR adds support for migrating Cost of Goods Sold (COGS) data from Shopify to WooCommerce, ensuring COGS values are preserved during migration even when the COGS feature is disabled in WooCommerce.
- Extends Shopify GraphQL query to fetch
unitCostdata for inventory items - Adds COGS mapping logic for both simple and variable products in the Shopify mapper
- Implements COGS value storage using both feature API (when enabled) and direct meta data approach (when disabled)
Reviewed Changes
Copilot reviewed 4 out of 4 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
| ShopifyFetcher.php | Adds unitCost fields to GraphQL query for fetching COGS data from Shopify |
| ShopifyMapper.php | Maps Shopify unitCost data to cost_of_goods field for simple and variable products |
| WooCommerceProductImporter.php | Handles COGS import with feature detection and fallback meta storage |
| changelog/add-cogs-support | Adds changelog entry for the new COGS migration functionality |
Comments suppressed due to low confidence (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php:537
- The docblock comment line
@param array $attributes_data Standardized attribute data from mapper.appears to be orphaned after the removal and doesn't match any actual parameter. This should be removed or corrected.
private function handle_variable_product( WC_Product_Variable $product, array $product_data ): void {
Tip: Customize your code reviews with copilot-instructions.md. Create the file or learn how to get started.
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
Outdated
Show resolved
Hide resolved
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
Show resolved
Hide resolved
Test using WordPress PlaygroundThe changes in this pull request can be previewed and tested using a WordPress Playground instance. Test this pull request with WordPress Playground. Note that this URL is valid for 30 days from when this comment was last updated. You can update it by closing/reopening the PR or pushing a new commit. |
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.
Nice, Naman! I set up a dev store on Shopify, where I created a simple product and a variable product. I set the "cost per item" for the simple product and all the variants.
I migrated them with COGS disabled. And when I enabled COGs, the costs of goods values were present and correct.
I repeated the migration with COGS enabled, and same deal, the values were present and correct.
Great work - send it!
| On Shopify | On Woo |
|---|---|
![]() |
![]() |
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
Show resolved
Hide resolved
plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyMapper.php
Show resolved
Hide resolved
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
Show resolved
Hide resolved
e92aefa to
ba9611f
Compare
ba9611f to
dbe2476
Compare
dbe2476 to
a36bb2b
Compare
|
Note Other AI code review bot(s) detectedCodeRabbit has detected other AI code review bot(s) in this pull request and will avoid duplicating their findings in the review comments. This may lead to a less comprehensive review. 📝 WalkthroughWalkthroughFetches Shopify variant unitCost, maps it into a new cost_of_goods field, and applies COGS during import by using the feature-aware API when available or falling back to writing Changes
Sequence Diagram(s)sequenceDiagram
autonumber
participant Shopify as Shopify API
participant Fetcher as ShopifyFetcher
participant Mapper as ShopifyMapper
participant Importer as WooCommerceProductImporter
participant Feature as FeaturesUtil
participant Product as WC_Product
participant Meta as Post Meta
Shopify->>Fetcher: GraphQL products (variants.unitCost)
Fetcher-->>Mapper: Product payloads (unitCost included)
Mapper-->>Importer: Mapped data (includes cost_of_goods when available)
Importer->>Feature: is_enabled('cost_of_goods_sold')?
alt Feature enabled
Importer->>Product: set_cogs_value((float) cost_of_goods)
else Feature disabled
Importer->>Meta: update_post_meta(_cogs_total_value, cost_of_goods)
end
opt Variations
Importer->>Product: save variation
Importer->>Meta: update variation _cogs_total_value if provided
end
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
Pre-merge checks and finishing touches✅ Passed checks (3 passed)
✨ Finishing touches
🧪 Generate unit tests
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
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.
Actionable comments posted: 2
♻️ Duplicate comments (2)
plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyMapper.php (1)
452-456: Guard for missing amount; preserve zero; cast to float.Current check can read a missing property and drops valid zero values.
- if ( property_exists( $variant_node, 'inventoryItem' ) && is_object( $variant_node->inventoryItem ) && - property_exists( $variant_node->inventoryItem, 'unitCost' ) && is_object( $variant_node->inventoryItem->unitCost ) - ) { - $simple_data['cost_of_goods'] = $variant_node->inventoryItem->unitCost->amount; - } + if ( + property_exists( $variant_node, 'inventoryItem' ) + && is_object( $variant_node->inventoryItem ) + && property_exists( $variant_node->inventoryItem, 'unitCost' ) + && is_object( $variant_node->inventoryItem->unitCost ) + && isset( $variant_node->inventoryItem->unitCost->amount ) + && is_numeric( $variant_node->inventoryItem->unitCost->amount ) + ) { + $simple_data['cost_of_goods'] = (float) $variant_node->inventoryItem->unitCost->amount; + }plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (1)
816-818: Variation COGS should mirror feature-aware handling and keep zero values.Currently always writes post meta after save and skips 0.0. Align with the simple-product logic.
- if ( ! empty( $var_data['cost_of_goods'] ) ) { - update_post_meta( $saved_variation_id, '_cogs_total_value', (float) $var_data['cost_of_goods'] ); - } + if ( array_key_exists( 'cost_of_goods', $var_data ) ) { + $cogs = (float) $var_data['cost_of_goods']; + if ( FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ) ) { + $variation->set_cogs_value( $cogs ); + $variation->save(); // ensure persisted when feature enabled + } else { + update_post_meta( $saved_variation_id, '_cogs_total_value', $cogs ); + } + }
🧹 Nitpick comments (5)
plugins/woocommerce/changelog/add-cogs-support (1)
4-4: Clarify and standardize wording (“COGS”, mention migration).Suggest tightening the entry and using “COGS” consistently.
-Added cogs support even if the feature is disabled +Added COGS migration support even if the feature is disabled.plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyMapper.php (2)
543-547: Same fix for variations: check amount, allow 0, cast.Mirrors the simple path.
- if ( property_exists( $variant_node, 'inventoryItem' ) && is_object( $variant_node->inventoryItem ) && - property_exists( $variant_node->inventoryItem, 'unitCost' ) && is_object( $variant_node->inventoryItem->unitCost ) - ) { - $variation_data['cost_of_goods'] = $variant_node->inventoryItem->unitCost->amount; - } + if ( + property_exists( $variant_node, 'inventoryItem' ) + && is_object( $variant_node->inventoryItem ) + && property_exists( $variant_node->inventoryItem, 'unitCost' ) + && is_object( $variant_node->inventoryItem->unitCost ) + && isset( $variant_node->inventoryItem->unitCost->amount ) + && is_numeric( $variant_node->inventoryItem->unitCost->amount ) + ) { + $variation_data['cost_of_goods'] = (float) $variant_node->inventoryItem->unitCost->amount; + }
452-456: Currency is fetched upstream but ignored here; confirm strategy.Shopify returns unitCost.amount + currencyCode. If store currency differs, migrating raw amounts can be wrong. Either convert to the WooCommerce store currency during mapping/import, or persist the currency alongside the amount and reconcile later.
Would you like a small helper that converts MoneyV2 to store currency (with fallback to storing the currency separately)?
Also applies to: 543-547
plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyFetcher.php (1)
92-95: We fetch currencyCode but don’t use it.Keep only needed fields or wire currency through the mapper/importer.
If we keep it, please add a follow-up to handle conversion or storage; otherwise remove currencyCode from the query to reduce payload.
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (1)
493-531: Add tests for COGS import paths (enabled/disabled, simple/variation, zero values).Please cover:
- Simple product: feature disabled → meta persisted pre-save; enabled → set_cogs_value called.
- Variation: both branches; zero amounts retained.
I can scaffold PHPUnit tests for the importer and a CLI E2E exercising wp-cli flows; want me to push a test skeleton?
Also applies to: 694-828
📜 Review details
Configuration used: Path: .coderabbit.yml
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (4)
plugins/woocommerce/changelog/add-cogs-support(1 hunks)plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php(5 hunks)plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyFetcher.php(1 hunks)plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyMapper.php(2 hunks)
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{php,js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/code-quality.mdc)
**/*.{php,js,jsx,ts,tsx}: Guard against unexpected inputs
Sanitize and validate any potentially dangerous inputs
Ensure code is backwards compatible
Write code that is readable and intuitive
Ensure code has unit or E2E tests where applicable
Files:
plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyMapper.phpplugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.phpplugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyFetcher.php
**/*.{php,js,ts,jsx,tsx}
⚙️ CodeRabbit configuration file
**/*.{php,js,ts,jsx,tsx}: Don't trust that extension developers will follow the best practices, make sure the code:
- Guards against unexpected inputs.
- Sanitizes and validates any potentially dangerous inputs.
- Is backwards compatible.
- Is readable and intuitive.
- Has unit or E2E tests where applicable.
Files:
plugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyMapper.phpplugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.phpplugins/woocommerce/src/Internal/CLI/Migrator/Platforms/Shopify/ShopifyFetcher.php
🧠 Learnings (3)
📚 Learning: 2025-08-29T14:38:18.023Z
Learnt from: Aljullu
PR: woocommerce/woocommerce#60641
File: plugins/woocommerce/client/blocks/tests/e2e/tests/add-to-cart-with-options/add-to-cart-with-options.block_theme.spec.ts:410-480
Timestamp: 2025-08-29T14:38:18.023Z
Learning: The "sold individually" variation functionality (where the Product Quantity block should hide when a variation is sold individually) mentioned in issue #59443 objectives is not implemented in PR #60641 and will be addressed in a future PR.
Applied to files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
📚 Learning: 2025-08-29T10:13:44.287Z
Learnt from: Aljullu
PR: woocommerce/woocommerce#60667
File: plugins/woocommerce/src/Blocks/BlockTypes/AddToCartForm.php:122-125
Timestamp: 2025-08-29T10:13:44.287Z
Learning: In WooCommerce, the ProductType class in plugins/woocommerce/src/Enums/ProductType.php contains string constants (not a PHP backed enum), so ProductType::VARIATION directly returns the string 'variation' and can be passed directly to methods like WC_Product::is_type() without needing ->value.
Applied to files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
📚 Learning: 2025-09-08T15:12:20.201Z
Learnt from: Aljullu
PR: woocommerce/woocommerce#60767
File: plugins/woocommerce/client/blocks/assets/js/blocks/add-to-cart-with-options/grouped-product-selector/frontend.ts:121-126
Timestamp: 2025-09-08T15:12:20.201Z
Learning: In WooCommerce, 'variation' is the product type used for variable products' children, while 'variable' is the type of the parent product. These are two distinct product types in the WooCommerce system.
Applied to files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
🧬 Code graph analysis (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (2)
plugins/woocommerce/src/Utilities/FeaturesUtil.php (1)
FeaturesUtil(14-102)plugins/woocommerce/includes/abstracts/abstract-wc-product.php (1)
set_cogs_value(2347-2352)
🔇 Additional comments (3)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (3)
18-18: Importing FeaturesUtil is appropriate.
588-589: Docblock nit is fine.
522-530: Resolved — _cogs_total_value is the per‑unit COGS meta (no change required). Verified: the product data store persists the product COGS to _cogs_total_value, get_cogs_total_value() is used as the per‑unit cost in order/item calculations, and the importer writes that meta (via set_cogs_value or set_cogs_value_direct) when importing.
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
Outdated
Show resolved
Hide resolved
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
Show resolved
Hide resolved
…ProductImporter.php Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
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.
Actionable comments posted: 1
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (1)
122-122: Fix fatal: find_existing_product is called with 2 args but accepts 1.This will throw at runtime. Drop the unused
$source_dataargument.- $existing_product_id = $this->find_existing_product( $product_data, $source_data ); + $existing_product_id = $this->find_existing_product( $product_data );
♻️ Duplicate comments (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (1)
815-817: Variation COGS: don’t drop 0.0; align with feature detection used for simple products.
! empty(...)skips valid zero and ignores the feature‑enabled path. Apply the same logic as simple products. This also addresses past feedback.- if ( ! empty( $var_data['cost_of_goods'] ) ) { - update_post_meta( $saved_variation_id, '_cogs_total_value', (float) $var_data['cost_of_goods'] ); - } + if ( array_key_exists( 'cost_of_goods', $var_data ) ) { + $raw_cogs = $var_data['cost_of_goods']; + if ( is_numeric( $raw_cogs ) ) { + $cogs = (float) $raw_cogs; + if ( FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ) ) { + $variation->set_cogs_value( $cogs ); + $variation->save(); + } else { + update_post_meta( $saved_variation_id, '_cogs_total_value', $cogs ); + } + } + }
🧹 Nitpick comments (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (1)
587-587: Doc nit: clarify parameter meaning.Minor: tighten the description to reflect taxonomy/term creation and mapping.
- * @param array $attributes_data Standardized attribute data from mapper. + * @param array $attributes_data Standardized attribute data from the mapper (names/options); creates taxonomies/terms and updates current mapping.
📜 Review details
Configuration used: Path: .coderabbit.yml
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php(5 hunks)
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{php,js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/code-quality.mdc)
**/*.{php,js,jsx,ts,tsx}: Guard against unexpected inputs
Sanitize and validate any potentially dangerous inputs
Ensure code is backwards compatible
Write code that is readable and intuitive
Ensure code has unit or E2E tests where applicable
Files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
**/*.{php,js,ts,jsx,tsx}
⚙️ CodeRabbit configuration file
**/*.{php,js,ts,jsx,tsx}: Don't trust that extension developers will follow the best practices, make sure the code:
- Guards against unexpected inputs.
- Sanitizes and validates any potentially dangerous inputs.
- Is backwards compatible.
- Is readable and intuitive.
- Has unit or E2E tests where applicable.
Files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
🧠 Learnings (3)
📚 Learning: 2025-08-29T14:38:18.023Z
Learnt from: Aljullu
PR: woocommerce/woocommerce#60641
File: plugins/woocommerce/client/blocks/tests/e2e/tests/add-to-cart-with-options/add-to-cart-with-options.block_theme.spec.ts:410-480
Timestamp: 2025-08-29T14:38:18.023Z
Learning: The "sold individually" variation functionality (where the Product Quantity block should hide when a variation is sold individually) mentioned in issue #59443 objectives is not implemented in PR #60641 and will be addressed in a future PR.
Applied to files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
📚 Learning: 2025-08-29T10:13:44.287Z
Learnt from: Aljullu
PR: woocommerce/woocommerce#60667
File: plugins/woocommerce/src/Blocks/BlockTypes/AddToCartForm.php:122-125
Timestamp: 2025-08-29T10:13:44.287Z
Learning: In WooCommerce, the ProductType class in plugins/woocommerce/src/Enums/ProductType.php contains string constants (not a PHP backed enum), so ProductType::VARIATION directly returns the string 'variation' and can be passed directly to methods like WC_Product::is_type() without needing ->value.
Applied to files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
📚 Learning: 2025-09-08T15:12:20.201Z
Learnt from: Aljullu
PR: woocommerce/woocommerce#60767
File: plugins/woocommerce/client/blocks/assets/js/blocks/add-to-cart-with-options/grouped-product-selector/frontend.ts:121-126
Timestamp: 2025-09-08T15:12:20.201Z
Learning: In WooCommerce, 'variation' is the product type used for variable products' children, while 'variable' is the type of the parent product. These are two distinct product types in the WooCommerce system.
Applied to files:
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
🧬 Code graph analysis (1)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (3)
plugins/woocommerce/src/Utilities/FeaturesUtil.php (1)
FeaturesUtil(14-102)plugins/woocommerce/includes/abstracts/abstract-wc-product.php (1)
set_cogs_value(2347-2352)plugins/woocommerce/includes/abstracts/abstract-wc-data.php (1)
update_meta_data(463-504)
🔇 Additional comments (2)
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (2)
18-18: Good: feature flag import wired.Importing FeaturesUtil here is correct for feature detection.
1235-1243: Good: meta API ensures persistence pre‑save.Switching to
$product->update_meta_data()makes this work for unsaved products and matches WC data patterns.
|
|
||
| if ( array_key_exists( 'cost_of_goods', $product_data ) ) { | ||
| $cogs_is_enabled = FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ); | ||
| if ( $cogs_is_enabled ) { | ||
| $product->set_cogs_value( (float) $product_data['cost_of_goods'] ); | ||
| } else { | ||
| $this->set_cogs_value_direct( $product, (float) $product_data['cost_of_goods'] ); | ||
| } | ||
| } |
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.
💡 Verification agent
🧩 Analysis chain
Guard against non‑numeric COGS; don’t coerce invalid input to 0.0.
array_key_exists correctly preserves 0.0. Add an is_numeric check to avoid persisting accidental 0.0 from non‑numeric strings.
- if ( array_key_exists( 'cost_of_goods', $product_data ) ) {
- $cogs_is_enabled = FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' );
- if ( $cogs_is_enabled ) {
- $product->set_cogs_value( (float) $product_data['cost_of_goods'] );
- } else {
- $this->set_cogs_value_direct( $product, (float) $product_data['cost_of_goods'] );
- }
- }
+ if ( array_key_exists( 'cost_of_goods', $product_data ) ) {
+ $raw_cogs = $product_data['cost_of_goods'];
+ if ( is_numeric( $raw_cogs ) ) {
+ $cogs = (float) $raw_cogs;
+ if ( FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ) ) {
+ $product->set_cogs_value( $cogs );
+ } else {
+ $this->set_cogs_value_direct( $product, $cogs );
+ }
+ }
+ }To verify coverage for enabled/disabled and zero values:
🏁 Script executed:
#!/bin/bash
# Look for tests covering COGS migration scenarios (enabled/disabled, zero)
rg -n -C2 -S 'cost_of_goods|_cogs_total_value|set_cogs_value' --type=php plugins/woocommerceLength of output: 128005
Guard against non‑numeric COGS; preserve explicit zeros.
Persist only when cost_of_goods is numeric — avoid coercing non‑numeric strings to 0.0. Fix in plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php (≈lines 522–529). Also address the variation branch at ≈815–816 where !empty(...) will drop '0'.
- if ( array_key_exists( 'cost_of_goods', $product_data ) ) {
- $cogs_is_enabled = FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' );
- if ( $cogs_is_enabled ) {
- $product->set_cogs_value( (float) $product_data['cost_of_goods'] );
- } else {
- $this->set_cogs_value_direct( $product, (float) $product_data['cost_of_goods'] );
- }
- }
+ if ( array_key_exists( 'cost_of_goods', $product_data ) ) {
+ $raw_cogs = $product_data['cost_of_goods'];
+ if ( is_numeric( $raw_cogs ) ) {
+ $cogs = (float) $raw_cogs;
+ if ( FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ) ) {
+ $product->set_cogs_value( $cogs );
+ } else {
+ $this->set_cogs_value_direct( $product, $cogs );
+ }
+ }
+ }📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| if ( array_key_exists( 'cost_of_goods', $product_data ) ) { | |
| $cogs_is_enabled = FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ); | |
| if ( $cogs_is_enabled ) { | |
| $product->set_cogs_value( (float) $product_data['cost_of_goods'] ); | |
| } else { | |
| $this->set_cogs_value_direct( $product, (float) $product_data['cost_of_goods'] ); | |
| } | |
| } | |
| if ( array_key_exists( 'cost_of_goods', $product_data ) ) { | |
| $raw_cogs = $product_data['cost_of_goods']; | |
| if ( is_numeric( $raw_cogs ) ) { | |
| $cogs = (float) $raw_cogs; | |
| if ( FeaturesUtil::feature_is_enabled( 'cost_of_goods_sold' ) ) { | |
| $product->set_cogs_value( $cogs ); | |
| } else { | |
| $this->set_cogs_value_direct( $product, $cogs ); | |
| } | |
| } | |
| } |
🤖 Prompt for AI Agents
In
plugins/woocommerce/src/Internal/CLI/Migrator/Core/WooCommerceProductImporter.php
around lines 521–529, ensure cost_of_goods is persisted only when it is numeric
while preserving explicit zeros: replace the current array_key_exists + cast
logic with a numeric guard (use is_numeric on the raw value) and then set the
COGS using the existing feature branch; likewise, update the variation branch
around lines ~815–816 to stop using !empty(...) (which drops "0") and instead
check presence with array_key_exists and validate with is_numeric before
assigning so "0" or "0.0" are preserved and non‑numeric strings are ignored.


Submission Review Guidelines:
Changes proposed in this Pull Request:
This PR add the support for COGS. The cogs value should migrate from Shopify even if the feature is disabled.
How to test the changes in this Pull Request:
Using the WooCommerce Testing Instructions Guide, include your detailed testing instructions:
wp wc migrate products --product-type="Cycling Jersey" --status=active- Variablewp wc migrate products --product-type="Cap" --status=active- SimpleTesting that has already taken place:
Changelog entry
Changelog Entry Details
Significance
Type
Message
Changelog Entry Comment
Comment