创建方法直接在实体中生成带有前缀和自动递增的默认值


create method to generate default value with prefix and auto-increlmentation directly in entity

在我的Symfony项目我有这个实体命名为Order.php:

<?php
namespace myApp'EntityBundle'Entity;
use Doctrine'ORM'Mapping as ORM;
use Symfony'Component'Validator'Constraints as Assert;
use Datetime;

/**
 *
 * @ORM'Table(name="`order`")
 * @ORM'Entity(repositoryClass="myApp'EntityBundle'Repository'OrderRepository")
 *
 */
class Order
{
    /**
     * @var integer
     *
     * @ORM'Column(name="order_id", type="integer", nullable=false)
     * @ORM'Id
     * @ORM'GeneratedValue(strategy="IDENTITY")
     */
    protected $id;
    /**
     * Command name ref for right accounting
     *
     * @var string
     *
     * @Assert'Type(
     *     type="string",
     *     message="The value {{ value }} is not a valid {{ type }}."
     * )
     * @Assert'NotNull()
     * @Assert'NotBlank()
     * @ORM'Column(name="order_name", type="string", length=255, nullable=true, unique=true)
     */
    protected $orderName;
    // etc other associations, object and getters setters...
    /**
     * Constructor
     */
    public function __construct()
    {
        $this->generateOrderName();
    }
    /**
     * generate order_name with base ref
     *
     * @return Order
     */
    public function generateOrderName()
    {
        // trying to make the good practice for generated orderName value
        //$now = new Datetime();
        //$year = $now->format("Y");
        //$month = $now->format("m");
        //$orderNameCommon = $year."_".$month."_";
        $this->setOrderName();
        return $this;
    }
    /**
     * Set orderName
     *
     * @param string $orderName
     *
     * @return Order
     */
    public function setOrderName($orderName)
    {
        $this->orderName = $orderName;
        return $this;
    }
    /**
     * Get orderName
     *
     * @return string
     */
    public function getOrderName()
    {
        return $this->orderName;
    }
}

目的是生成如下的orderName: '2016_09_00001',这意味着我按日期Year_Month_orderNumber注册了订单。

我必须注意orderName必须是唯一的,例如,如果我已经有一个名为"2016_09_00001"的订单,我必须像这样注册orderName"2016_09_00002"。比如自动递增。

如你所见,我直接在实体类Order: 中编写了这段代码
/**
 * Constructor
 */
public function __construct()
{
    // call the order name generation function
    $this->generateOrderName();
}
/**
 * generate order_name with base ref
 *
 * @return Order
 */
public function generateOrderName()
{
    $now = new Datetime();
    $year = $now->format("Y");
    $month = $now->format("m");
    $prefix = $year."_".$month."_";
    // That I had planned:
    // to create a prefix with Datetime argument, year and month
    // Then check all order in database with this prefix
    // Finally count the results and add +1 on the final value
    $this->setOrderName();
    return $this;
}
如您所见,我在构造函数中调用了generateOrderName()函数,然后我想使这个过程:

我已经计划好了:

  1. 用Datetime参数,年和月创建前缀

  2. 然后用这个前缀检查数据库中的所有订单

  3. 最后计算结果并在最终值上加+1

直接在实体中正确地做到这一点的最佳方法是什么?我认为在实体类本身中有一个存储库dql查询调用不是一件好事。

我创建了这个,例如:

public function searchOrderName($prefix)
{
    return
        $this->getEntityManager()
             ->createQuery(
              "SELECT o.orderName FROM EntityBundle:Order o
               WHERE o.orderName
               LIKE :prefix
               ORDER BY o.id ASC"
            )
             ->setParameter("prefix", $prefix.'%')
             ->getResult();
}

我如何继续在实体中创建generateOrderName()函数以使生成的过程我想直接在实体类中?

您将需要一个服务。您无法从您的实体访问DB。所以创建OrderFactory,注入OrderRepository,你将很容易达到你的目标