Magento 2: Thay đổi giá sản phẩm trong Bộ điều khiển hiện không hoạt động!


9

Tôi đã cố gắng thay đổi Giá của các sản phẩm của mình như thế này:

Trình điều khiển.php:

[BIÊN TẬP]

   <?php

namespace MassiveArt\ShoppingCart\Controller\Index;

use Magento\Catalog\Model\ProductFactory;
use Magento\Checkout\Model\Cart;
use Magento\Framework\App\Action\Action;
use Magento\Framework\App\Action\Context;
use Magento\Framework\Controller\Result\JsonFactory;
use Magento\Framework\Data\Form\FormKey;

class Index extends Action
{
    /**
     * @var FormKey
     */
    protected $formKey;

    /**
     * @var Session
     */
    protected $checkoutSession;

    /**
     * @var Cart
     */
    protected $cart;

    /**
     * @var ProductFactory
     */
    protected $productFactory;

    /**
     * Constructor.
     *
     * @param Context                         $context
     * @param \Magento\Checkout\Model\Session $checkoutSession
     * @param \Magento\Customer\Model\Session $customerSession
     * @param JsonFactory                     $resultJsonFactory
     * @param FormKey                         $formKey
     * @param Cart                            $cart
     * @param ProductFactory                  $productFactory
     */
    public function __construct(
        Context $context,
        \Magento\Checkout\Model\Session $checkoutSession,
        \Magento\Customer\Model\Session $customerSession,
        JsonFactory $resultJsonFactory,
        FormKey $formKey,
        Cart $cart,
        ProductFactory $productFactory
    ) {
        $this->checkoutSession = $checkoutSession;
        $this->customerSession = $customerSession;
        $this->formKey = $formKey;
        $this->resultJsonFactory = $resultJsonFactory;
        $this->cart = $cart;
        $this->productFactory = $productFactory;
        parent::__construct($context);
    }

    public function execute()
    {
        try {

            // Set result data and pass back
            $result = $this->resultJsonFactory->create();


            $allItems = $this->checkoutSession->getQuote()->getAllVisibleItems();
            foreach ($allItems as $item) {
                $item = ( $item->getParentItem() ? $item->getParentItem() : $item );
                $price = 100; //set your price here
                $item->setCustomPrice($price);
                $item->setOriginalCustomPrice($price);
                $item->setSubtotal($price);
                $item->getProduct()->setIsSuperMode(true);
            }
            $this->checkoutSession->setTotalsCollectedFlag(false);
            $this->checkoutSession->getQuote()->save();
            $this->checkoutSession->getQuote()->setTotalsCollectedFlag(false);
            $this->setTotalsCollectedFlag(false);

            $result->setData(['message' => __("Products added succesfully")]);

            return $result;
        } catch (\Exception $e) {
            $result->setData(['error' => __($e->getMessage())]);
            return $result;
        }
    }
}

(EDIT) Với mã mới, giá thay đổi, nhưng tổng phụ thì không! Như bạn có thể thấy ở đây: nhập mô tả hình ảnh ở đây

Cảm ơn trước!


Xin chào, bạn có thể giải thích? bạn sử dụng bộ điều khiển nào, và nhiệm vụ của bạn là gì? Bạn có muốn thay đổi giá khi khách hàng thêm sản phẩm vào giỏ hàng không?
Sony

Xin chào Sony, không tôi muốn thay đổi giá, nếu một nút được nhấp, không phải nếu một sản phẩm được thêm vào giỏ hàng. Bây giờ tôi chỉ muốn thay đổi giá của tất cả các sản phẩm thành 100 đô la để thử nghiệm. Tôi sẽ cập nhật câu hỏi của mình để cho bạn biết thêm một số mã
Felix Schönherr

Xin lỗi, tôi sợ không hiểu những gì bạn đang cố gắng. Khi tôi nhìn vào mã của bạn, bạn có vẻ muốn thay đổi giá của các mặt hàng trong giỏ hàng của bạn. Thật vậy, bạn đang gọi quotetừ checkoutSession. Tôi la một chut Nhâm lân.
Sony

Có, tôi muốn thay đổi giá của các mặt hàng trong giỏ hàng của tôi. Tôi đã thử một số thứ khác để đạt được điều này và cái cuối cùng tôi đã thử là mã hiện tại có trích dẫn.
Felix Schönherr

Thay đổi giá sẽ không hoạt động bằng bộ điều khiển bạn cần sử dụng plugin hoặc trình quan sát cho điều đó.
Aasim Goriya

Câu trả lời:


5

Tôi hiểu rồi, tôi nghĩ bạn đang đi đúng hướng, nhưng tôi nghĩ bạn phải lưu lại trích dẫn. Nếu bạn xem lớp này: \Magento\Checkout\Controller\Cart\Add bạn có thể thấy ở Dòng 114:

$this->cart->addProduct($product, $params);
            if (!empty($related)) {
                $this->cart->addProductsByIds(explode(',', $related));
            }

            $this->cart->save();

Tôi thay đổi giá từ sự kiện được gọi ở cuối addProduct()phương thức và Magento lưu giỏ hàng vào cuối. Vì vậy, trong trường hợp của bạn, bạn phải lưu báo giá trong bộ điều khiển của bạn.


Ok, Giá được thay đổi ngay bây giờ (nhìn vào Câu hỏi cập nhật của tôi), nhưng tổng số phụ sẽ không thay đổi, có ý tưởng nào không?
Felix Schönherr

Ngoài ra, nếu sau đó bạn nhấp vào thanh toán, giá sẽ lại như cũ
Felix Schönherr

Tôi nghĩ rằng bạn phải xem Mô hình trích dẫn, đặc biệt là phương thức collTotals (). Bạn phải đặt cờ $ this-> setTotalsCollectedFlag (false) yêu cầu Magento tính toán lại.
Sony

Thật không may, điều này không làm việc cho tôi :(
Felix Schönherr

Đã thử nó theo nhiều cách khác nhau và nó không bao giờ hoạt động.
Felix Schönherr

3

Tôi đã làm một đoạn cho phép bạn thay đổi giá. Trên thực tế, nó thay đổi giá sau khi bạn thêm sản phẩm vào giỏ hàng của bạn. Nói cách khác, nó thay đổi giá của các mặt hàng của bạn trong báo giá của bạn. https://gist.github.com/0-Sony/d9d2ea792b5533bfeaff28827e6f207a

Hy vọng nó giúp.


Xin lỗi, nó không có ích gì, tôi không thể sử dụng một người quan sát, tôi cần sử dụng bộ điều khiển của mình
Felix Schönherr

3

Bạn muốn cập nhật tổng hàng và không phải tổng phụ, sử dụng phương thức $item->setRowTotal()hoặc $item->setBaseRowTotal(). Ngoài ra, nó có thể giúp thêm $item->save()trước khi kết thúc vòng lặp.

Tổng phụ là tổng phụ đơn hàng / giỏ hàng.


Thật không may điều này không thay đổi gì. Nhưng cảm ơn câu trả lời của bạn
Felix Schönherr

3

@ felix, Bạn cần đặt setSubtotal()báo giá. Đặt Tổng phụ bên ngoài f or loop.

$subTotal = $cart->getQuote()->setSubtotal($price);
$this->checkoutSession->getQuote()->save();

như thế này

foreach ($allItems as $item) {
                $item = ( $item->getParentItem() ? $item->getParentItem() : $item );
                $price = 100; //set your price here
                $item->setCustomPrice($price);
                $item->setOriginalCustomPrice($price);
                $item->getProduct()->setIsSuperMode(true);
            }
            $subtotalprice=100;
            $subTotal = $cart->getQuote()->setSubtotal($subtotalprice);
            $this->checkoutSession->setTotalsCollectedFlag(false);
            $this->checkoutSession->getQuote()->save();

Lưu ý: Mã đã kiểm tra


Có thể làm việc cho bạn, nhưng không phải cho tôi.
Felix Schönherr

Bạn đã thử này ($ SUBTOTAL = $ cart-> getQuote () -> setSubtotal ($ subtotalprice);) bên ngoài này cho vòng lặp
Arunprabakaran M

vâng, tôi đã làm điều này chính xác như bạn đã nói
Felix Schönherr

setSubtotal chỉ không hoạt động. chính xác? phương pháp thiết lập khác hoạt động tốt như setprice? chính xác?
Arunprabakaran M

Đúng rồi ....
Felix Schönherr

3

Đối với giá giỏ hàng Upadate, bạn phải sử dụng Mô hình giỏ hàng thay vì phiên thanh toán. Tải mục từ giỏ hàng và cập nhật nó.

<?php 
$items = $this->cart->getQuote()->getAllItems(); //Magento\Checkout\Model\Cart $cart
foreach($items as $item) {

    $item = $this->cart->getQuote()->getItemById($item->getId());
    if (!$item) {
      continue;
    }

    $price = 100;
    $item->setCustomPrice($price);
    $item->setOriginalCustomPrice($price);
    $item->getProduct()->setIsSuperMode(true);
    $item->save();           
}
$this->cart->save();
?>

Trên thực tế, nó không hoạt động, xin lỗi
Felix Schönherr

Đó là mã làm việc của tôi, tôi đang tạo Trích dẫn theo giá tùy chỉnh của API. Nó phải Work.may là bất kỳ mô-đun nào xung đột với phía bạn
Ketan Borada

0

Hãy thử mã dưới đây:

bạn cần sửa đổi process()chức năng cho yêu cầu của bạn.

nhà cung cấp / magento / module-sales-rule / Model / Validator.php

/**
     * Quote item discount calculation process
     *
     * @param AbstractItem $item
     * @return $this
     */
    public function process(AbstractItem $item)
    {
        $item->setDiscountAmount(0);
        $item->setBaseDiscountAmount(0);
        $item->setDiscountPercent(0);
        $itemPrice = $this->getItemPrice($item);
        if ($itemPrice < 0) {
            return $this;
        }

        $appliedRuleIds = $this->rulesApplier->applyRules(
            $item,
            $this->_getRules($item->getAddress()),
            $this->_skipActionsValidation,
            $this->getCouponCode()
        );
        $this->rulesApplier->setAppliedRuleIds($item, $appliedRuleIds);
        /*Your custom code START here*/
        $item = ( $item->getParentItem() ? $item->getParentItem() : $item );
        $price = 499; //set your price here
        $item->setCustomPrice($price);
        $item->setOriginalCustomPrice($price);
        $item->getProduct()->setIsSuperMode(true);
        //echo "sku: ".$item->getSku()."=== Name: ".$item->getName();die;
        /* Your custom code END here */
        return $this;
    }

LƯU Ý: Không sửa đổi các tệp lõi magento. Tạo plugin cho việc này.

Tôi mong nó sẽ có ích...!!!


Nhưng nếu tôi tạo một plugin cho cái này và một phần mở rộng khác, chạy trên cùng một cửa hàng, thì cũng tạo một plugin của Validator.php, chỉ có một cái sẽ hoạt động. thật?
Felix Schönherr

@felix: Không, bạn chỉ cần tạo plugin cho chức năng xử lý của tệp validator.php. nó sẽ chạy cho tất cả các cửa hàng của bạn. Trước tiên, bạn chỉ cần thay đổi tệp lõi và kiểm tra xem yêu cầu của bạn có được thực hiện hay không? Nếu tất cả đều ổn với sửa đổi này thì sau khi bạn tạo plugin cho việc này.
Balwant Singh

Ok, sẽ thử điều này vào ngày mai và sau đó sẽ trả lời bạn.
Felix Schönherr

Điều này chỉ thay đổi Giá trong bản tóm tắt của giỏ hàng, nhưng giá của các sản phẩm vẫn giữ nguyên
Felix Schönherr
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.