选择一个未加载的实体

时间:2015-09-21 11:50:23

标签: php symfony

我正在使用twig for循环来显示元素列表。这些元素来自API的解码json数组。

我的用户与这些元素之间存在OneToMany关系。

用户需要选择其中一个元素,这些元素将通过addElement()函数添加到用户。

我尝试在循环中使用Symfony2表单,但它只显示在第一个元素上。我也尝试使用链接到控制器函数,但由于我的数据库中没有这些元素,所以我收到了这个错误:

"Unable to guess how to get a Doctrine instance from the request information."

以下是我展示元素的方式:

{% block itinerary %}
    {% for element in elements %}

<aside class="flights-results__by-price col-md-3">
  <span class="flights-results__price">{{ element.price ? element.price : 'Unknown' }}</span>
  <a href="{{ path('selectLeg', {'element': element}) }}">Delete</a>
</aside>

    {% endfor %}
{% endblock itinerary %}

这是我创建和填充元素的函数:

  public function getAvailabilities($availabilities, $planes,     $airports)
{
    $reservations = array();
    foreach ($availabilities as $ar)
    {
        $leg = new Leg();
        $leg->getId();
        foreach($ar as $a)
        {
            $leg = $this->fillLeg($leg, $a);
            foreach($a->availabilities as $aleg)
            {
                $leg->setAirplaneType($this->findPlane($planes, $aleg->airplane_type_id));
                $leg->setAirportStart($this->findAirport($airports, $a->lfi_from));
                $leg->setAirportEnd($this->findAirport($airports, $a->lfi_to));
                $leg->setDurationLeg($aleg->duration);
                $leg->setEndHour($aleg->datetime_to);
            }
            $startdate = $a->datetime;
        }
        $reservations[] = $leg;
    }
    return $reservations;
}

这是我转储($ elements)时的结果:

FlightController.php on line 55:
array:4 [▼
  0 => {#953 ▼
    +"3e1f975601f59090decc8f2d5ced72010162e48e": {#954 ▼
  +"lfi_from": "FR58957"
  +"lfi_to": "FR45300"
  +"datetime": "2015-09-10 20:00:00"
  +"nb_pax": "4"
  +"availabilities": array:1 [▼
    0 => {#955 ▶}
  ]
}
  }
  1 => {#956 ▼
+"3e1f975601f59090decc8f2d5ced72010162e48e": {#957 ▼
  +"lfi_from": "FR45300"
  +"lfi_to": "AG00060"
  +"datetime": "2015-09-10 23:00:00"
  +"nb_pax": "4"
  +"availabilities": array:1 [▼
    0 => {#958 ▶}
  ]
}
}
2 => {#959 ▼
+"3e1f975601f59090decc8f2d5ced72010162e48e": {#960 ▼
  +"lfi_from": "FR45300"
  +"lfi_to": "AG00060"
  +"datetime": "2015-11-30 23:00:00"
  +"nb_pax": "4"
  +"availabilities": array:1 [▼
    0 => {#961 ▶}
  ]
}
}
3 => {#962 ▼
+"3e1f975601f59090decc8f2d5ced72010162e48e": {#963 ▼
  +"lfi_from": "FR45300"
  +"lfi_to": "OLOLOL"
  +"datetime": "2015-09-18 23:00:00"
  +"nb_pax": "2"
  +"availabilities": array:1 [▼
    0 => {#964 ▶}
  ]
 }
}
]

主要问题是API会返回数千个结果。出于显而易见的原因,我无法坚持下去。

我想最简单的问题是“将实体上的数据发送到控制器中的另一个函数,而不保留此实体的最佳方法是什么?”。到目前为止,我一直使用持久化元素,id为标识符,但我发现当我们处理非持久化实体时它会变得更加棘手。

1 个答案:

答案 0 :(得分:0)

如果您的User与这些Elements之间存在 OneToMany 关系,则表示元素会以某种方式保留。那你为什么不能使用元素的id

如果您坚持使用它,您可能需要在控制器代码中的某处添加 ParamConverter

/**
  * @Route("/selectLeg/{element}")
  * @ParamConverter("element", class="YourBundle:Element", options={"mapping": {"name": "element.whatever_param"}})
  * @Template()
  */
public function selectLegAction(Element $element)

事实是,如果Symfony2不了解您的Element实体,您将无法addElement() User。{/ p>

我猜您在前端获取元素列表,然后尝试更新User对象。在这种情况下,我会在Twig中对你的元素进行json_encode(如果我理解的话,它毕竟是一个简单的数组):

<a href="{{ path('selectLeg', {'legAsJSONString': element|json_encode}) }}">Select this leg</a>

并在您的控制器中创建一个新的Element

/**
  * @Route("/selectLeg/{legAsJSONString}")
  */
public function selectLegAction($legAsJSONString) {

  $e = json_decode($legAsJSONString);

  $leg = new Leg();
  $leg->setWhateverParameter($e->parameter_in_the_array);
  // more parameters here
  $em->persist($leg)->flush();

  /// Now here you have $leg->getId(); if  ever you need it

}

编辑:改编自您的评论。如果您不需要在用户选择特定元素之前保留元素(支线),则在 GET 参数,路径参数或数据中以字符串形式发送元素一个 POST 请求(更清洁的解决方案)。您不需要id,因为您可以将请求中的完整对象作为JSON字符串传递。

$leg->getId();中删除无用的getAvailabilities(),它实际上并没有做任何事情,而且无论如何都不存在。

如果我忽略了这一点并且$leg对象过于复杂,因此无法在JSON中进行序列化,那么需要保留它,因为两个后续请求需要具有访问权限它。