Skip to content

Simplificando o participante Shopping\Cart #4

@lcobucci

Description

@lcobucci

O participante Shopping\Cart está gerenciando tanto os produtos quanto as quantidades dos produtos, acredito que isso poderia ser simplificado com a adição de um outro participante, o Shopping\CartItem:

namespace PHPBr\Shopping;

class CartItem
{
    /**
     * @var \PHPBr\Shopping\Product
     */
    private $product;

    /**
     * @var int
     */
    private $quantity;

    /**
     * @param \PHPBr\Shopping\Product $product
     */
    public function __construct(Product $product)
    {
        $this->product = $product;
        $this->quantity = 0;
    }

    /**
     * @return \PHPBr\Shopping\Product
     */
    public function getProduct()
    {
        return $this->product;
    }

    /**
     * @return int
     */
    public function getQuantity()
    {
        return $this->quantity;
    }

    /**
     * @return boolean
     */
    public function isEmpty() // dá pra pensar em um nome melhor pra isso...
    {
        return $this->quantity <= 0;
    }

    /**
     * @param int $quantity
     */
    public function append($quantity)
    {
        $this->quantity += $quantity * 1;
    }

    /**
     * @param int $quantity
     */
    public function remove($quantity)
    {
        $this->quantity -= $quantity * 1;
    }
}

O uso dele seria apenas pelo Shopping\Cart, desta forma (apenas com os métodos referentes à esta proposta):

namespace PHPBr\Shopping;

class Cart implements \Countable, \IteratorAggregate, \Serializable
{
    /**
     * @var \PHPBr\Shopping\CartItem[]
     */
    private $items = [];

    /**
     * @param \PHPBr\Shopping\Product $product
     * @param int $quantity
     */
    public function addItem(Product $product, $quantity)
    {
        $id = $product->getId();

        if (!isset($this->items[$id])) {
            $this->items[$id] = new CartItem($product);
        }

        $this->items[$id]->append($quantity);
    }

    /**
     * @return int
     * @see \Countable::count()
     */
    public function count()
    {
        return count($this->items);
    }

    /**
     * @return \Iterator<\PHPBr\Shopping\Product>
     * @see \IteratorAggregate::getIterator()
     */
    public function getIterator()
    {
        foreach ($this->items as $item) {
            yield $item->getQuantity() => $item->getProduct();
        }
    }

    /**
     * @param \PHPBr\Shopping\Product $product
     * @param int $quantity
     */
    public function removeItem(Product $product, $quantity = 0)
    {
        $id = $product->getId();

        if (!isset($this->items[$id])) {
            throw new \DomainException('Can\'t remove. Product not found.');
            return;
        }

        if ($quantity > 0) {
            $this->items[$id]->remove($quantity);
        }

        if ($this->items[$id]->isEmpty() || $quantity <= 0) {
            unset($this->items[$id]);
        }
    }

    /**
     * @return string
     * @see \Serializable::serialize()
     */
    public function serialize() { /* ... */ }

    /**
     * @see \Serializable::unserialize()
     */
    public function unserialize($serialized) { /* ... */ }
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions