ActiveDocument is an ORM for Yii, providing Active Record functionality for document-based storage engines. This library is functionally similar to Yii's own SQL-based Active Record class, CActiveRecord.
- Memory - temporary storage using PHP memory. Good for nested documents, and testing.
- Riak - via the Yii ext, Riiak (currently packaged in with ActiveDocument)
- MongoDB - via PHP PECL extension
- CouchDB
- Redis
- SQL - may possibly add support for SQL, if only as a CActiveRecord wrapper (to enable seamlessly changing storage driver)
- Yii 1.1+ (Yii 1.1.7+ recommended, lower releases should be compatible, but are untested)
- PHP 5.3+ (ActiveDocument library is namespaced, which is a PHP 5.3 feature)
Clone this repository to your protected/extensions/ directory, to use the latest available code
hg clone https://bitbucket.org/intel352/activedocument
This quick example uses the Memory driver
###protected/config/main.php:###
// ...
'components' => array(
// ...
'conn'=>array(
'class' => '\ext\activedocument\Connection',
'driver' => 'memory',
),
// ...
),
// ...
###protected/models/Config.php:###
<?php
/**
* NOTE:
* An important difference in ActiveDocument from CActiveRecord, is that you are no longer required to specify a
* model() method within every model class that you create. ActiveDocument makes use of a PHP 5.3 feature, Late
* Static Binding, to achieve the same purpose as CActiveRecord::model() with less redundancy.
*
* @property ConfigSetting[] $options Not needed for ActiveDocument, this exists as helper phpdoc for IDE users
*/
class Config extends \ext\activedocument\Document {
/**
* This phpdoc notation is detected by ActiveDocument. Only partially supported at this time.
* @var string
*/
public $name;
/**
* Relations function similar to CActiveRecord, see below for an example.
*
* @return array
*/
public function relations() {
return array(
/**
* For CActiveRecord, a relation requires 3 values specified (type, model, foreign key).
* ActiveDocument instead requires 2 values (type, model). A foreign key is no longer needed, as related
* documents have their primary key stored into the parent document.
*
* If you specify the named parameter, 'nested', as true, the related document[s] will have copies
* stored directly into this model. So in this specific example, if 4 ConfigSetting instances were saved
* to the 'options' relation, a copy of each would be stored within the Config instance in the data
* engine.
*/
'options'=>array(self::HAS_MANY, 'ConfigSetting', 'nested'=>true),
);
}
}
###protected/models/ConfigSetting.php:###
<?php
/**
* ConfigSetting
*/
class ConfigSetting extends \ext\activedocument\Document {
/**
* @var string Setting name
*/
public $name;
/**
* @var mixed
*/
public $value;
/**
* If you do not specify which attribute carries your primary key value, then the default of '_pk' will be used.
* If the default '_pk' is used, a primary key may be generated for you, based on the behavior of your selected
* driver and storage engine.
*
* You can specify a composite key, by returning an array of attribute names.
*
* @return string|array
*/
public function primaryKey() {
return 'name';
}
}
###protected/controllers/TestController.php:###
<?php
class TestController extends Controller {
public function actionIndex() {
$config = new Config;
$config->name = 'Test Config';
$cs = new ConfigSetting;
$cs->name = 'config1';
$cs->value = 'config1value';
$cs2 = new ConfigSetting;
$cs2->name = 'config2';
$cs2->value = 'config2value';
/**
* Helper method to add one or more related documents.
* Other ways to add related documents:
* - $config->addRelated('options', array($cs, $cs2));
* - $config->options = array($cs, $cs2);
*/
$config->addRelated('options', $cs);
$config->addRelated('options', $cs2);
$config->save();
/**
* $config->primaryKey triggers magic call to Document::getPrimaryKey()
*/
$pk = $config->primaryKey;
/**
* Perform a fresh lookup of the new config instance
*/
$config = Config::model()->findByPk($pk);
/**
* Loop and print the related values
*/
foreach($config->options as $option) {
echo 'Option "'.$option->name.'": "'.$option->value.'"<br />';
}
}
}