CakeCannot установить Model- & gt; id в KeyValue Behavior :: beforeSave

Я пытаюсь реализовать поведение ключ / значение на основе https://github.com/josegonzalez/cakephp-keyvalue

Мое поведение будет вставлять новые строки в базу данных для каждого нового ключа из отправки формы, независимо от количества ключей, и обновлять существующие записи, если user_id и ключ найдены в таблице KeyValue. Я уже связал пользовательскую модель с моделью KeyValue, а также с поведением.

Если в базе данных нет записи user_id / key, она будет правильно вставлять новые записи. Однако я обнаружил, что если я пытаюсь обновить существующие пары ключ-значение одного и того же пользователя, первые два значения будут обновлены правильно, но последнее переданное значение приведет к новой записи.

После некоторого расследования я обнаружил, что в цикле сохранения в beforeSave()даже если я назначу идентификатор модели в beforeSave() с $Model->id перед возвратом истины, он не будет передан Model->save() учебный класс.

Я использую торт 2.5.4

Model->id в beforeSave не переходит на Model->save() в lib/Model/Model.php:# 1841

if ($count > 0) {
$cache = $this->_prepareUpdateFields(array_combine($fields, $values));

**pr($this->id); //this value is empty**

if (!empty($this->id)) {
$this->__safeUpdateMode = true;
try {
$success = (bool)$db->update($this, $fields, $values);
} catch (Exception $e) {
$this->__safeUpdateMode = false;
throw $e;
}
$this->__safeUpdateMode = false;
}

KeyValueBehavior:

public function beforeSave(Model $Model, $options = array()) {
extract($this->options[$Model->alias]);
$keys = array_keys($Model->data[$Model->alias]);
$data = $Model->data;

if (in_array($fields['key'], $keys) && in_array($fields['value'], $keys)) {
return true;
}

if (isset($data[$Model->alias]) && ! empty($data[$Model->alias])) {
$dataTemplate = array($Model->alias => array());

foreach ($data[$Model->alias] as $field => $value) {
if ($Model->hasField($field)) {
$dataTemplate[$Model->alias][$field] = $value;
unset($data[$Model->alias][$field]);
}
}

$index = 0;

foreach ($data[$Model->alias] as $key => $value) {
$index ++;
$insert = $dataTemplate;
$insert[$Model->alias][$fields['key']] = $key;

if ($uniqueKeys) {
$Model->deleteAll(reset($insert));
}

$insert[$Model->alias][$fields['value']] = $value;

//check existing key value
$belongsTo = reset($Model->belongsTo);
$existing = $Model->find('first', array(
'conditions' => array(
$belongsTo['foreignKey'] => $insert[$Model->alias][$belongsTo['foreignKey']],
$fields['key'] => $insert[$Model->alias][$fields['key']]
)
));$Model->create();
if(sizeof($existing) > 0){
$existingKV = reset($existing);
//pr($existingKV);
$Model->read(null, $existingKV['id']);
}if ($index == count($data[$Model->alias])) {
// Even if Model->id is set here, it will not be passed to Model->save()
$Model->id = $existingKV['id'];
$Model->data = $insert;
pr($Model); // Model->id is set here but not in Model->save()
return true;
} else {
pr($insert); //Updates correctly
if (false === $Model->save($insert)) {
return false;
}
}

}
}

UsersController:

public function test() {
if ($this->request->is('post')) {
$this->Userdetail->create();
$this->request->data['Userdetail']['user_id'] = $this->Auth->user('id');
if ($this->Userdetail->save($this->request->data)) {
$this->Session->setFlash(__('The Userdetail has been saved'));
//  $this->redirect(array('action' => 'index'));
} else {
$this->Session->setFlash(__('The Userdetail could not be saved. Please, try again.'));
}
}
$users = $this->Userdetail->User->find('list');
$this->set(compact('users'));
}

Тогда у меня есть три примера полей в моем View View / Users / test.ctp:

<?php
echo $this->Form->create('Userdetail');
echo $this->Form->input('field1');
echo $this->Form->input('field2');
echo $this->Form->input('field3');
echo $this->Form->end('submit');

Чтобы обойти это, я добавил еще один ключ с именем «id_holder» в модель в beforeSave()и отредактировал Model/Model.php, Но в конечном итоге я не хочу редактировать ядро ​​CakePHP.

Редактировать: по новому saveKeyValues() метод:

public function saveKeyValues(Model $Model, $data){
if($Model == null || $data == null){
return false;
}

if (isset($data[$Model->alias]) && ! empty($data[$Model->alias])) {
$dataTemplate = array($Model->alias => array());
foreach ($data[$Model->alias] as $field => $value) {
if ($Model->hasField($field)) {
$dataTemplate[$Model->alias][$field] = $value;
unset($data[$Model->alias][$field]);
}
}
}

$belongsTo = reset($Model->belongsTo);
$index = 0;

foreach ($data[$Model->alias] as $key => $value) {
$index++;

$insert = $dataTemplate;
$insert[$Model->alias][$this->options[$Model->alias]['fields']['key']] = $key;
$insert[$Model->alias][$this->options[$Model->alias]['fields']['value']] = $value;
$insert[$Model->alias][$belongsTo['foreignKey']] = $data[$belongsTo['foreignKey']];
//check existing key value
$existing = $Model->find('first', array(
'conditions' => array(
$belongsTo['foreignKey'] => $data[$belongsTo['foreignKey']],
$this->options[$Model->alias]['fields']['key'] => $key
)
));

//Reset for create/update
$Model->create();
if(sizeof($existing) > 0){
$existingKV = reset($existing);
$Model->read(null, $existingKV['id']);
}

if (false === $Model->save($insert)) {
return false;

}
if($index == count($data[$Model->alias])){
return true;
}
}
}

1

Решение

Задача ещё не решена.

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector