douwen7516 2016-10-28 07:20
浏览 22
已采纳

超薄支付控制器

I followed a serie on creating a shopping cart on codecourse - and it was just what I was looking for.

In the series the payment happens on creating the order - but now my client says that they don't want the payment on creating order - first when they have processed the order - they want to send an email with payment or an link to a payment site.

I thought no big deal - just move the BraintreePayment par out of the create class - create a new class called payment and thats that - but no - so now I am stuck.

I am using swiftmailer to send the mail with the link and that works fine - but the payment part fails.

I am new to this MVC / Slim thing - so please can someone help me in the right direction.

The error it throws say:

Type: TypeError Message: Argument 1 passed to Cart\Events\OrderWasCreated::__construct() must be an instance of Cart\Models\Order, integer given, called in /Applications/AMPPS/www/testshop.dev/cart/app/Controllers/OrderController.php on line 160 File: /Applications/AMPPS/www/testshop.dev/cart/app/Events/OrderWasCreated.php Line: 17

My ordercontroller with the payment class - looks like this:

<?php

namespace Cart\Controllers;

use Slim\Router;
use Slim\Views\Twig;
use Cart\Basket\Basket;
use Cart\Models\Order;
use Cart\Models\Product;
use Cart\Models\Address;
use Cart\Models\Delivery;
use Cart\Models\Customer;
use Cart\Controllers\MailController;
use Cart\Validation\Contracts\ValidatorInterface;
use Cart\Validation\Forms\OrderForm;
use Psr\Http\Message\ResponseInterface as Response;
use Psr\Http\Message\ServerRequestInterface as Request;
use Braintree_transaction;

class OrderController
{
    protected $basket;

    protected $mailcontroller;

    protected $router;

    protected $validator;

    public function __construct(Basket $basket, Mailcontroller $mailcontroller, Router $router, ValidatorInterface $validator)
    {
        $this->basket = $basket;
        $this->mailcontroller = $mailcontroller;
        $this->router = $router;
        $this->validator = $validator;

    }

    public function index(Request $request, Response $response, Twig $view)
    {

        $this->basket->refresh();

        if (!$this->basket->subTotal()) {
            return $response->withRedirect($this->router->pathFor('cart.index'));
        }

        return $view->render($response, 'order/index.twig');
    }

    public function show($hash, Request $request, Response $response, twig $view, Order $order)
    {
        $order = $order->with('address', 'products')->where('hash', $hash)->first();

        $this->mailcontroller->mailLisbeth($hash);

        if (!$order) {
            return $response->withRedirect($this->router->pathFor('home'));
        }

        return $view->render($response, 'order/show.twig', [
            'order' => $order,
        ]);
    }

    public function create(Request $request, Response $response, Customer $customer, Address $address, Delivery $delivery, Order $order)
    {
        $this->basket->refresh();

        $validation = $this->validator->validate($request, OrderForm::rules());

        if (!$this->basket->subTotal()) {
            return $response->withRedirect($this->router->pathFor('cart.index'));
        }

        if ($validation->fails()) {
            return $response->withRedirect($this->router->pathFor('order.index'));
        }

        $hash = bin2hex(random_bytes(32));

        $customer = $customer->firstOrCreate([
            'email' => $request->getParam('email'),
            'name' => $request->getParam('name'),
        ]);

        $delivery = $delivery->firstOrCreate([
            'delivery'     => $request->getParam('delivery'),
            'deliverydate' => $request->getParam('deliverydate'),
            'deliverytime' => $request->getParam('deliverytime'),
        ]);

        $address  = $address->firstOrCreate([
            'address1'     => $request->getParam('address1'),
            'address2'     => $request->getParam('address2'),
            'city'         => $request->getParam('city'),
            'postal_code'  => $request->getParam('postal_code'),
        ]);

        $order = $customer->orders()->create([
            'hash' => $hash,
            'accepted' => "2",
            'paid' => false,
            'total' => $this->basket->subTotal() + 150,
        ]);

        $address->order()->save($order);

        $delivery->order()->save($order);

        $allItems = $this->basket->all();

        $order->products()->saveMany(
            $allItems,
            $this->getQuantities($allItems)
        );

        $event = new \Cart\Events\OrderWasCreated($order, $this->basket);

        $event->attach([
            // new \Cart\Handlers\MarkOrderPaid,
            // new \Cart\Handlers\RecordSuccessfulPayment($result->transaction->id),
            new \Cart\Handlers\UpdateStock,
            new \Cart\Handlers\Emptybasket,
        ]);

        $event->dispatch();

        return $view->render($response, 'order/show.twig', [
            'order' => $order,
        ]);

    }

    //
    public function payment($slug, Request $request, Response $response, twig $view, Customer $customer, Address $address, Delivery $delivery, Order $order)
    {
        $order = $order->with('address', 'products')->where('id', $slug)->first();

        // var_dump($order);
        // die();

        // if (!$request->getParam('payment_method_nonce')) {
        //     return $response->withRedirect($this->router->pathFor('order.index'));
        // }

        $order = $customer->orders()->update([
            'paid' => true,
        ]);

        $result = Braintree_Transaction::sale([
            'amount' => $this->basket->subTotal() + 150,
            'paymentMethodNonce' => $request->getParam('payment_method_nonce'),
            'options' => [
                'submitForSettlement' => true,
            ]
        ]);


        $event = new \Cart\Events\OrderWasCreated($order, $this->basket);

        if (!$result->success) {
            $event->attach(new \Cart\Handlers\RecordFailedPayment);
            $event->dispatch();

            return $response->withRedirect($this->router->pathFor('order.index'));
        }

        $event->attach([
            new \Cart\Handlers\MarkOrderPaid,
            new \Cart\Handlers\RecordSuccessfulPayment($result->transaction->id),
            // new \Cart\Handlers\UpdateStock,
            // new \Cart\Handlers\Emptybasket,
        ]);
    }

    protected function getQuantities($items)
    {
        $quantities = [];

        foreach ($items as $item) {
            $quantities[] = ['quantity' => $item->quantity];
        }

        return $quantities;
    }
}
  • 写回答

1条回答 默认 最新

  • douji8347 2016-10-31 17:23
    关注

    The error occures on line 160:

    $event = new \Cart\Events\OrderWasCreated($order, $this->basket);
    

    because you invoke Cart\Events\OrderWasCreated constructor, which requires instance of Cart\Models\Order class as first argument. Instead your first argument ($order) is integer.

    Now latest assignment of $order is on line 147:

    $order = $customer->orders()->update([
        'paid' => true,
    ]);
    

    I'll have a guess and say that this is an operation that returns integer as result (be that a simple 1/0 success/fauilure or the id of the order being updated). Are you sure that you need that? Asking because:

    • You are assigning $order a value on line 138:

      $order = $order->with('address', 'products')->where('id', $slug)->first();

    • And you're passing $order as an argument to the OrderController::payment.

    So, my guess is: you want to remove lines 138 and 147.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥100 求三轴之间相互配合画圆以及直线的算法
  • ¥100 c语言,请帮蒟蒻写一个题的范例作参考
  • ¥15 名为“Product”的列已属于此 DataTable
  • ¥15 安卓adb backup备份应用数据失败
  • ¥15 eclipse运行项目时遇到的问题
  • ¥15 关于#c##的问题:最近需要用CAT工具Trados进行一些开发
  • ¥15 南大pa1 小游戏没有界面,并且报了如下错误,尝试过换显卡驱动,但是好像不行
  • ¥15 自己瞎改改,结果现在又运行不了了
  • ¥15 链式存储应该如何解决
  • ¥15 没有证书,nginx怎么反向代理到只能接受https的公网网站