Мне нужно выполнить команду upsert в yiimongodbsuite. Я пытался
$model = new Murls(); $model->userid=$userid; $model->title=$title; $model->edits[0] = new Medithtml(); $model->edits[0]->path= $htm; $model->edits[0]->html=$path; $model->edits[0]->ci=$ci; $model->update(array('_id'=>$rec->_id ),array('userid', 'title','edits' ), true );
Но это показывает ошибку.
Модель Мурлса определяется следующим образом
class Murls extends EMongoDocument { public $userid; public $title; public $edits; public static function model($className=__CLASS__) { return parent::model($className); } // This method is required! public function getCollectionName() { return 'murls'; } public function attributeLabels() { return array( 'html'=>'Html', ); } public function embeddedDocuments() { return array( // property name => embedded document class name 'edits'=>'Medithtml', ); } public function behaviors(){ return array( 'embeddedArrays' => array( 'class' => 'ext.YiiMongoDbSuite.extra.EEmbeddedArraysBehavior', 'arrayPropertyName' => 'edits', // name of property, that will be used as an array 'arrayDocClassName' => 'Medithtml' // class name of embedded documents in array ), ); } }
и модель Medithtml as
class Medithtml extends EMongoEmbeddedDocument{ public $html; public $path; public $ci; public static function model($className=__CLASS__) { return parent::model($className); } }
Я должен достигнуть того, что запись с $title
может иметь n число $html
, $path
и $ci
. Любая помощь будет оценена. Я ищу, чтобы хранить данные, подобные этому
array ( '_id' => MongoId::__set_state(array( '$id' => '51ee1956d39c2c7e078d80da', )), 'userid' => '12', 'title' => 'Mongo', 'edits' => array ( 0 => array ( 'html' => 'html>body>div:nth-child(2)>a>div>a>div', 'path' => 'ssssss', 'ci' => '1', ), 1 => array ( 'html' => 'html>body>div:nth-child(2)>a>div:nth-child(3)>a>h2', 'path' => '/assets/img/demo/demo-avatar9604.jpg', 'ci' => '2', ), 2 => array ( 'html' => ' html>body>div:nth-child(2)>a>div:nth-child(3)>a>center:nth-child(16)>a>h1', 'path' => '333', 'ci' => '3', ), ), )
Только массив комментариев будет обновлен, если существует запись с определенной комбинацией 'title'
и 'userid'
Если она не существует, будет добавлена новая запись
Вы наследуете от неправильного класса. Чтобы сохранить документ, вы должны наследовать EMongoDocument
не EMongoEmbeddedDocument
. Эти классы схожи, но имеют разные цели.
EMongoEmbeddedDocument
для встроенных документов, он должен использоваться только для встроенных документов EMongoDocument
выходит из EMongoEmbeddedDocument
с помощью методов фактического сохранения данных в db. Для массива комментариев у вас есть два варианта:
По умолчанию save
/ insert
/ update
сохраняет все атрибуты. Для частичных обновлений используйте комбинацию $attributes
и установите $modify
для true. Предупреждение . Передача массива атрибутов без $modify
сохраняет только прошедшие атрибуты, отбрасывая остальную часть документа.
public function save($runValidation = true, $attributes = null) ... public function insert(array $attributes = null) ... public function update(array $attributes = null, $modify = false) ...
Так что в вашем случае вы можете обновить:
$model->update(array('comments'), true);
Или, если вам все овервердировать весь документ, просто сохраните:
$model->save();
Примечание: для составного pk ovverride primaryKey()
:
public function primaryKey() { return array('title', 'userid'); }
Хорошо, что stackoverflow имеет сквозную автосохранение черт 🙂
Наконец, я получил решение таким образом:
$rec = $model->find($criteria) ; if($rec){ foreach($rec->edits as $editarray){ $var[]=$editarray; } $edits_new= new Medithtml(); $edits_new['html']=$htm; $edits_new['ci']=$ci; $edits_new['path']=$path; $var[]=$edits_new; $rec->edits=$var; $rec->userid=$userid; $rec->title=$title; $rec->update(array('edits' ), true); }