Как заполнить параметры в элементе управления формой из третьей таблицы в "edit.ctp" в CakePHP 3. X?
у меня есть три таблицы (локали ,маршруты и расписания):
Локальная Таблица:
id | nombreLocal
--------------------------
1 Local Uno
2 Local Dos
3 Local Tres
Таблица Пути:
id | id_local_origen | id_local_destino
--------------------------------------------------
1 1 2
2 2 3
Таблица Расписаний:
id | id_rutas
---------------------
1 1
2 2
у меня есть следующие ассоциации:
в локальной таблице:
$this->hasMany('Rutas', [
'foreignKey' => 'id_local_origen'
]);
$this->hasMany('Rutas', [
'foreignKey' => 'id_local_destino'
]);
в таблице пути:
$this->belongsTo('Origen', [
'foreignKey' => 'id_local_origen',
'className' => 'Locales',
'joinType' => 'INNER'
]);
$this->belongsTo('Destino', [
'foreignKey' => 'id_local_destino',
'className' => 'Locales',
'joinType' => 'INNER'
]);
$this->hasMany('Programaciones', [
'foreignKey' => 'id_rutas'
]);
в таблице расписания:
$this->belongsTo('Rutas', [
'foreignKey' => 'id_rutas',
'joinType' => 'INNER'
]);
Мне нужно решить
в edit. ctp расписаний должно что-то выйти так:
в обработчике расписания у меня есть следующее в действии Edit:
public function edit($id = null)
{
$programacione = $this->Programaciones->get($id, [
'contain' => []
]);
if ($this->request->is(['patch', 'post', 'put'])) {
$programacione = $this->Programaciones->patchEntity($programacione, $this->request->getData());
if ($this->Programaciones->save($programacione)) {
$this->Flash->success(__('The programacione has been saved.'));
return $this->redirect(['action' => 'index']);
}
$this->Flash->error(__('The programacione could not be saved. Please, try again.'));
}
$this->set(compact('programacione'));
// Enviando rutas
$tabla_rutas = TableRegistry::get('Rutas');
$query = $tabla_rutas->find('list', [
'keyField' => 'id_rutas',
'valueField' => ['id_local_origen','id_local_destino']
]);
$rutas = $query->toArray();
$this->set(compact('rutas', $rutas));
debug($rutas);
}
в debug я получаю это:
[
(int) 1 => '1;2',
(int) 2 => '2;3'
]
1 answers
Для этого случая мы можем объявить virtual property
в Entity.
Для этого мы добавляем функцию _getRutaName()
внутри класса Path
Ruta.php
public function _getRutaName()
{
$rutaName = '';
if (
!empty($this->_properties['origen']->nombreLocal) &&
!empty($this->_properties['destino']->nombreLocal)
) {
$rutaName = $this->_properties['origen']->nombreLocal . ' - ' .
$this->_properties['destino']->nombreLocal;
}
return $rutaName;
}
В Table Мы должны сказать вам, что ваш displayField является новым виртуальным свойством, которое мы только что объявили, следуя соглашениям CakePHP, это будет имя с "underscore"
В RutasTable.php
$this->setDisplayField('ruta_name');
И, наконец, в контроллере мы вызываем массив, который мы развернем в наше представление важно чтобы с помощью магии query builder CakePHP мы вызывали contain с источником и целью, чтобы они существовали в $this->_properties
в Entity.
Параметрам find
мы передадим в качестве аргументов 'keyField' => 'id'
с идентификатором пути для сохранения и с 'valueField' => 'ruta_name'
с нашим новым virtualField
ProgramacionesController.php
public function edit($id = null)
{
$programacione = $this->Programaciones->get($id, [
'contain' => []
]);
if ($this->request->is(['patch', 'post', 'put'])) {
$programacione = $this->Programaciones->patchEntity($programacione, $this->request->getData());
if ($this->Programaciones->save($programacione)) {
$this->Flash->success(__('The programacione has been saved.'));
return $this->redirect(['action' => 'index']);
}
$this->Flash->error(__('The programacione could not be saved. Please, try again.'));
}
$query = $this->Programaciones->Rutas->find('list', [
'keyField' => 'id',
'valueField' => 'ruta_name'
])->contain(['Origen', 'Destino']);
$rutas = $query->toArray();
$this->set(compact('programacione', 'rutas'));
}
Наконец, в представлении мы обычно называем, как мы делали раньше с магия FormHelper CakePHP, я предлагаю удалить параметр 'empty' => true
, так как если он будет выбран, он добавит как id
0, что приведет к неожиданным результатам
<?= $this->Form->control('id_rutas', ['options' => $rutas, 'empty' => true]) ?>
Это приведет к чему-то похожему на это:
<div class="input select"><label for="id-rutas">Id Rutas</label>
<select name="id_rutas" id="id-rutas">
<option value=""></option>
<option value="1" selected="selected">Local uno - Local dos</option>
<option value="2">Local dos - Local tres</option>
</select>
</div>