Browse Source

Changed elasticsearch AR primary key handling

now supports mapped primary key when _id is part of source with an
alias.
tags/2.0.0-beta
Carsten Brandt 11 years ago
parent
commit
a7b852fcc3
  1. 34
      extensions/yii/elasticsearch/ActiveQuery.php
  2. 77
      extensions/yii/elasticsearch/ActiveRecord.php
  3. 1
      extensions/yii/elasticsearch/CHANGELOG.md
  4. 12
      extensions/yii/elasticsearch/QueryBuilder.php
  5. 13
      extensions/yii/elasticsearch/README.md
  6. 8
      extensions/yii/gii/generators/crud/Generator.php
  7. 2
      extensions/yii/gii/generators/crud/templates/controller.php
  8. 2
      framework/yii/data/ActiveDataProvider.php
  9. 4
      framework/yii/db/BaseActiveRecord.php
  10. 2
      framework/yii/validators/UniqueValidator.php
  11. 31
      tests/unit/data/ar/elasticsearch/Customer.php
  12. 27
      tests/unit/data/ar/elasticsearch/Item.php
  13. 38
      tests/unit/data/ar/elasticsearch/Order.php
  14. 25
      tests/unit/data/ar/elasticsearch/OrderItem.php
  15. 70
      tests/unit/extensions/elasticsearch/ActiveRecordTest.php
  16. 3
      tests/unit/framework/ar/ActiveRecordTestTrait.php

34
extensions/yii/elasticsearch/ActiveQuery.php

@ -90,16 +90,26 @@ class ActiveQuery extends Query implements ActiveQueryInterface
}
unset($row);
}
/** @var ActiveRecord $modelClass */
$modelClass = $this->modelClass;
$pk = $modelClass::primaryKey();
if ($this->asArray && $this->indexBy) {
foreach ($result['hits']['hits'] as &$row) {
$row['_source'][ActiveRecord::PRIMARY_KEY_NAME] = $row['_id'];
if ($pk === '_id') {
$row['_source']['_id'] = $row['_id'];
}
$row['_source']['_score'] = $row['_score'];
$row = $row['_source'];
}
unset($row);
}
$models = $this->createModels($result['hits']['hits']);
if ($this->asArray && !$this->indexBy) {
foreach($models as $key => $model) {
$model['_source'][ActiveRecord::PRIMARY_KEY_NAME] = $model['_id'];
if ($pk === '_id') {
$model['_source']['_id'] = $model['_id'];
}
$model['_source']['_score'] = $model['_score'];
$models[$key] = $model['_source'];
}
}
@ -123,8 +133,14 @@ class ActiveQuery extends Query implements ActiveQueryInterface
return null;
}
if ($this->asArray) {
/** @var ActiveRecord $modelClass */
$modelClass = $this->modelClass;
$model = $result['_source'];
$model[ActiveRecord::PRIMARY_KEY_NAME] = $result['_id'];
$pk = $modelClass::primaryKey();
if ($pk === '_id') {
$model['_id'] = $result['_id'];
}
$model['_score'] = $result['_score'];
} else {
/** @var ActiveRecord $class */
$class = $this->modelClass;
@ -147,8 +163,14 @@ class ActiveQuery extends Query implements ActiveQueryInterface
if (!empty($result['hits']['hits'])) {
$models = $this->createModels($result['hits']['hits']);
if ($this->asArray) {
/** @var ActiveRecord $modelClass */
$modelClass = $this->modelClass;
$pk = $modelClass::primaryKey();
foreach($models as $key => $model) {
$model['_source'][ActiveRecord::PRIMARY_KEY_NAME] = $model['_id'];
if ($pk === '_id') {
$model['_source']['_id'] = $model['_id'];
}
$model['_source']['_score'] = $model['_score'];
$models[$key] = $model['_source'];
}
}
@ -167,7 +189,7 @@ class ActiveQuery extends Query implements ActiveQueryInterface
{
$record = parent::one($db);
if ($record !== false) {
if ($field == ActiveRecord::PRIMARY_KEY_NAME) {
if ($field == '_id') {
return $record['_id'];
} elseif (isset($record['_source'][$field])) {
return $record['_source'][$field];
@ -181,7 +203,7 @@ class ActiveQuery extends Query implements ActiveQueryInterface
*/
public function column($field, $db = null)
{
if ($field == ActiveRecord::PRIMARY_KEY_NAME) {
if ($field == '_id') {
$command = $this->createCommand($db);
$command->queryParts['fields'] = [];
$result = $command->search();

77
extensions/yii/elasticsearch/ActiveRecord.php

@ -47,6 +47,7 @@ class ActiveRecord extends BaseActiveRecord
const PRIMARY_KEY_NAME = 'id';
private $_id;
private $_score;
private $_version;
/**
@ -155,9 +156,12 @@ class ActiveRecord extends BaseActiveRecord
// TODO implement copy and move as pk change is not possible
public function getId()
/**
* @return float returns the score of this record when it was retrieved via a [[find()]] query.
*/
public function getScore()
{
return $this->_id;
return $this->_score;
}
/**
@ -165,10 +169,11 @@ class ActiveRecord extends BaseActiveRecord
* @param mixed $value
* @throws \yii\base\InvalidCallException when record is not new
*/
public function setId($value)
public function setPrimaryKey($value)
{
if ($this->isNewRecord) {
$this->_id = $value;
$pk = static::primaryKey();
if ($this->getIsNewRecord() || $pk != '_id') {
$this->$pk = $value;
} else {
throw new InvalidCallException('Changing the primaryKey of an already saved record is not allowed.');
}
@ -179,10 +184,11 @@ class ActiveRecord extends BaseActiveRecord
*/
public function getPrimaryKey($asArray = false)
{
$pk = static::primaryKey();
if ($asArray) {
return [ActiveRecord::PRIMARY_KEY_NAME => $this->_id];
return [$pk => $this->$pk];
} else {
return $this->_id;
return $this->$pk;
}
}
@ -191,11 +197,18 @@ class ActiveRecord extends BaseActiveRecord
*/
public function getOldPrimaryKey($asArray = false)
{
$id = $this->isNewRecord ? null : $this->_id;
$pk = static::primaryKey();
if ($this->getIsNewRecord()) {
$id = null;
} elseif ($pk == '_id') {
$id = $this->_id;
} else {
$id = $this->getOldAttribute($pk);
}
if ($asArray) {
return [ActiveRecord::PRIMARY_KEY_NAME => $id];
return [$pk => $id];
} else {
return $this->_id;
return $id;
}
}
@ -204,11 +217,11 @@ class ActiveRecord extends BaseActiveRecord
*
* The primaryKey for elasticsearch documents is always `primaryKey`. It can not be changed.
*
* @return string[] the primary keys of this record.
* @return string the primary key of this record.
*/
public static function primaryKey()
{
return [ActiveRecord::PRIMARY_KEY_NAME];
return '_id';
}
/**
@ -246,8 +259,11 @@ class ActiveRecord extends BaseActiveRecord
*/
public static function create($row)
{
$row['_source'][ActiveRecord::PRIMARY_KEY_NAME] = $row['_id'];
$record = parent::create($row['_source']);
$pk = static::primaryKey();
$record->$pk = $row['_id'];
$record->_score = isset($row['_score']) ? $row['_score'] : null;
$record->_version = isset($row['_version']) ? $row['_version'] : null; // TODO version should always be available...
return $record;
}
@ -317,11 +333,13 @@ class ActiveRecord extends BaseActiveRecord
$options
);
if (!$response['ok']) {
if (!isset($response['ok'])) {
return false;
}
$this->_id = $response['_id'];
$pk = static::primaryKey();
$values[$pk] = $this->$pk = $response['_id'];
$this->_version = $response['_version'];
$this->_score = null;
$this->setOldAttributes($values);
$this->afterSave(true);
return true;
@ -344,10 +362,11 @@ class ActiveRecord extends BaseActiveRecord
*/
public static function updateAll($attributes, $condition = [])
{
if (count($condition) == 1 && isset($condition[ActiveRecord::PRIMARY_KEY_NAME])) {
$primaryKeys = (array) $condition[ActiveRecord::PRIMARY_KEY_NAME];
$pkName = static::primaryKey();
if (count($condition) == 1 && isset($condition[$pkName])) {
$primaryKeys = (array) $condition[$pkName];
} else {
$primaryKeys = static::find()->where($condition)->column(ActiveRecord::PRIMARY_KEY_NAME);
$primaryKeys = static::find()->where($condition)->column($pkName); // TODO check whether this works with default pk _id
}
if (empty($primaryKeys)) {
return 0;
@ -371,11 +390,17 @@ class ActiveRecord extends BaseActiveRecord
$url = [static::index(), static::type(), '_bulk'];
$response = static::getDb()->post($url, [], $bulk);
$n=0;
$errors = [];
foreach($response['items'] as $item) {
if ($item['update']['ok']) {
if (isset($item['update']['error'])) {
$errors[] = $item['update'];
} elseif ($item['update']['ok']) {
$n++;
}
}
if (!empty($errors)) {
throw new Exception(__METHOD__ . ' failed updating records.', $errors);
}
return $n;
}
@ -395,10 +420,11 @@ class ActiveRecord extends BaseActiveRecord
*/
public static function updateAllCounters($counters, $condition = [])
{
if (count($condition) == 1 && isset($condition[ActiveRecord::PRIMARY_KEY_NAME])) {
$primaryKeys = (array) $condition[ActiveRecord::PRIMARY_KEY_NAME];
$pkName = static::primaryKey();
if (count($condition) == 1 && isset($condition[$pkName])) {
$primaryKeys = (array) $condition[$pkName];
} else {
$primaryKeys = static::find()->where($condition)->column(ActiveRecord::PRIMARY_KEY_NAME);
$primaryKeys = static::find()->where($condition)->column($pkName); // TODO check whether this works with default pk _id
}
if (empty($primaryKeys) || empty($counters)) {
return 0;
@ -452,10 +478,11 @@ class ActiveRecord extends BaseActiveRecord
*/
public static function deleteAll($condition = [])
{
if (count($condition) == 1 && isset($condition[ActiveRecord::PRIMARY_KEY_NAME])) {
$primaryKeys = (array) $condition[ActiveRecord::PRIMARY_KEY_NAME];
$pkName = static::primaryKey();
if (count($condition) == 1 && isset($condition[$pkName])) {
$primaryKeys = (array) $condition[$pkName];
} else {
$primaryKeys = static::find()->where($condition)->column(ActiveRecord::PRIMARY_KEY_NAME);
$primaryKeys = static::find()->where($condition)->column($pkName); // TODO check whether this works with default pk _id
}
if (empty($primaryKeys)) {
return 0;

1
extensions/yii/elasticsearch/CHANGELOG.md

@ -5,6 +5,7 @@ Yii Framework 2 elasticsearch extension Change Log
----------------------------
- Enh #1382: Added a debug toolbar panel for elasticsearch (cebe)
- Chg: Changed handling of ActiveRecord primary keys (cebe)
2.0.0 alpha, December 1, 2013
-----------------------------

12
extensions/yii/elasticsearch/QueryBuilder.php

@ -114,7 +114,7 @@ class QueryBuilder extends \yii\base\Object
} else {
$column = $name;
}
if ($column == ActiveRecord::PRIMARY_KEY_NAME) {
if ($column == '_id') {
$column = '_uid';
}
@ -176,7 +176,7 @@ class QueryBuilder extends \yii\base\Object
{
$parts = [];
foreach($condition as $attribute => $value) {
if ($attribute == ActiveRecord::PRIMARY_KEY_NAME) {
if ($attribute == '_id') {
if ($value == null) { // there is no null pk
$parts[] = ['script' => ['script' => '0==1']];
} else {
@ -235,8 +235,8 @@ class QueryBuilder extends \yii\base\Object
}
list($column, $value1, $value2) = $operands;
if ($column == ActiveRecord::PRIMARY_KEY_NAME) {
throw new NotSupportedException('Between condition is not supported for primaryKey.');
if ($column == '_id') {
throw new NotSupportedException('Between condition is not supported for the _id field.');
}
$filter = ['range' => [$column => ['gte' => $value1, 'lte' => $value2]]];
if ($operator == 'not between') {
@ -274,7 +274,7 @@ class QueryBuilder extends \yii\base\Object
unset($values[$i]);
}
}
if ($column == ActiveRecord::PRIMARY_KEY_NAME) {
if ($column == '_id') {
if (empty($values) && $canBeNull) { // there is no null pk
$filter = ['script' => ['script' => '0==1']];
} else {
@ -306,6 +306,6 @@ class QueryBuilder extends \yii\base\Object
private function buildLikeCondition($operator, $operands)
{
throw new NotSupportedException('like conditions is not supported by elasticsearch.');
throw new NotSupportedException('like conditions are not supported by elasticsearch.');
}
}

13
extensions/yii/elasticsearch/README.md

@ -55,8 +55,10 @@ For general information on how to use yii's ActiveRecord please refer to the [gu
For defining an elasticsearch ActiveRecord class your record class needs to extend from `yii\elasticsearch\ActiveRecord` and
implement at least the `attributes()` method to define the attributes of the record.
The primary key (the `_id` field in elasticsearch terms) is represented by `getId()` and `setId()` and can not be changed.
The primary key is not part of the attributes.
The handling of primary keys is different in elasticsearch as the primary key (the `_id` field in elasticsearch terms)
is not part of the attributes by default. However it is possible to define a [mapping](TODO link to ES docs)
for the `_id` field to be part of the attributes. See [...TODO...] on how to do this.
The `_id` field of a document/record can be accessed using [[ActiveRecord::getPrimaryKey()]] and [[ActiveRecord::setPrimaryKey()]].
primary key can be defined via [[primaryKey()]] which defaults to `id` if not specified.
The primaryKey needs to be part of the attributes so make sure you have an `id` attribute defined if you do
@ -152,10 +154,11 @@ Using the elasticsearch DebugPanel
----------------------------------
The yii2 elasticsearch extensions provides a `DebugPanel` that can be integrated with the yii debug module
an shows the executed elasticsearch queries. It also allows to run these queries on different cluster nodes
an view the results.
and shows the executed elasticsearch queries. It also allows to run these queries
and view the results.
Add the following to you application config to enable it:
Add the following to you application config to enable it (if you already have the debug module
enabled, it is sufficient to just add the panels configuration):
```php
// ...

8
extensions/yii/gii/generators/crud/Generator.php

@ -176,7 +176,7 @@ class Generator extends \yii\gii\Generator
/** @var \yii\db\ActiveRecord $class */
$class = $this->modelClass;
$pk = $class::primaryKey();
return $pk[0];
return is_array($pk) ? $pk[0] : $pk;
}
/**
@ -363,7 +363,7 @@ class Generator extends \yii\gii\Generator
{
/** @var ActiveRecord $class */
$class = $this->modelClass;
$pks = $class::primaryKey();
$pks = (array) $class::primaryKey();
if (count($pks) === 1) {
return "'id' => \$model->{$pks[0]}";
} else {
@ -379,7 +379,7 @@ class Generator extends \yii\gii\Generator
{
/** @var ActiveRecord $class */
$class = $this->modelClass;
$pks = $class::primaryKey();
$pks = (array) $class::primaryKey();
if (count($pks) === 1) {
return '$id';
} else {
@ -391,7 +391,7 @@ class Generator extends \yii\gii\Generator
{
/** @var ActiveRecord $class */
$class = $this->modelClass;
$pks = $class::primaryKey();
$pks = (array) $class::primaryKey();
if (($table = $this->getTableSchema()) === false) {
$params = [];
foreach ($pks as $pk) {

2
extensions/yii/gii/generators/crud/templates/controller.php

@ -19,7 +19,7 @@ if ($modelClass === $searchModelClass) {
/** @var ActiveRecordInterface $class */
$class = $generator->modelClass;
$pks = $class::primaryKey();
$pks = (array) $class::primaryKey();
$urlParams = $generator->generateUrlParams();
$actionParams = $generator->generateActionParams();
$actionParamComments = $generator->generateActionParamComments();

2
framework/yii/data/ActiveDataProvider.php

@ -128,7 +128,7 @@ class ActiveDataProvider extends BaseDataProvider
} elseif ($this->query instanceof ActiveQueryInterface) {
/** @var \yii\db\ActiveRecord $class */
$class = $this->query->modelClass;
$pks = $class::primaryKey();
$pks = (array) $class::primaryKey();
if (count($pks) === 1) {
$pk = $pks[0];
foreach ($models as $model) {

4
framework/yii/db/BaseActiveRecord.php

@ -924,7 +924,7 @@ abstract class BaseActiveRecord extends Model implements ActiveRecordInterface
*/
public function equals($record)
{
if ($this->isNewRecord || $record->isNewRecord) {
if ($this->getIsNewRecord() || $record->getIsNewRecord()) {
return false;
}
return get_class($this) === get_class($record) && $this->getPrimaryKey() === $record->getPrimaryKey();
@ -1273,7 +1273,7 @@ abstract class BaseActiveRecord extends Model implements ActiveRecordInterface
*/
public static function isPrimaryKey($keys)
{
$pks = static::primaryKey();
$pks = (array) static::primaryKey();
if (count($keys) === count($pks)) {
return count(array_intersect($keys, $pks)) === count($pks);
} else {

2
framework/yii/validators/UniqueValidator.php

@ -101,7 +101,7 @@ class UniqueValidator extends Validator
$n = count($objects);
if ($n === 1) {
$keys = array_keys($params);
$pks = $targetClass::primaryKey();
$pks = (array) $targetClass::primaryKey();
sort($keys);
sort($pks);
if ($keys === $pks) {

31
tests/unit/data/ar/elasticsearch/Customer.php

@ -1,6 +1,7 @@
<?php
namespace yiiunit\data\ar\elasticsearch;
use yii\elasticsearch\Command;
use yiiunit\extensions\elasticsearch\ActiveRecordTest;
/**
@ -19,14 +20,19 @@ class Customer extends ActiveRecord
public $status2;
public static function primaryKey()
{
return 'id';
}
public function attributes()
{
return ['name', 'email', 'address', 'status'];
return ['id', 'name', 'email', 'address', 'status'];
}
public function getOrders()
{
return $this->hasMany(Order::className(), array('customer_id' => ActiveRecord::PRIMARY_KEY_NAME))->orderBy('create_time');
return $this->hasMany(Order::className(), array('customer_id' => 'id'))->orderBy('create_time');
}
public static function active($query)
@ -40,4 +46,25 @@ class Customer extends ActiveRecord
ActiveRecordTest::$afterSaveNewRecord = $this->isNewRecord;
parent::afterSave($insert);
}
/**
* sets up the index for this record
* @param Command $command
*/
public static function setUpMapping($command, $statusIsBoolean = false)
{
$command->deleteMapping(static::index(), static::type());
$command->setMapping(static::index(), static::type(), [
static::type() => [
"_id" => ["path" => "id", "index" => "not_analyzed", "store" => "yes"],
"properties" => [
"name" => ["type" => "string", "index" => "not_analyzed"],
"email" => ["type" => "string", "index" => "not_analyzed"],
"address" => ["type" => "string", "index" => "analyzed"],
"status" => $statusIsBoolean ? ["type" => "boolean"] : ["type" => "integer"],
]
]
]);
}
}

27
tests/unit/data/ar/elasticsearch/Item.php

@ -1,6 +1,7 @@
<?php
namespace yiiunit\data\ar\elasticsearch;
use yii\elasticsearch\Command;
/**
* Class Item
@ -11,8 +12,32 @@ namespace yiiunit\data\ar\elasticsearch;
*/
class Item extends ActiveRecord
{
public static function primaryKey()
{
return 'id';
}
public function attributes()
{
return ['name', 'category_id'];
return ['id', 'name', 'category_id'];
}
/**
* sets up the index for this record
* @param Command $command
*/
public static function setUpMapping($command)
{
$command->deleteMapping(static::index(), static::type());
$command->setMapping(static::index(), static::type(), [
static::type() => [
"_id" => ["path" => "id", "index" => "not_analyzed", "store" => "yes"],
"properties" => [
"name" => ["type" => "string", "index" => "not_analyzed"],
"category_id" => ["type" => "integer"],
]
]
]);
}
}

38
tests/unit/data/ar/elasticsearch/Order.php

@ -1,6 +1,7 @@
<?php
namespace yiiunit\data\ar\elasticsearch;
use yii\elasticsearch\Command;
/**
* Class Order
@ -12,24 +13,29 @@ namespace yiiunit\data\ar\elasticsearch;
*/
class Order extends ActiveRecord
{
public static function primaryKey()
{
return 'id';
}
public function attributes()
{
return ['customer_id', 'create_time', 'total'];
return ['id', 'customer_id', 'create_time', 'total'];
}
public function getCustomer()
{
return $this->hasOne(Customer::className(), [ActiveRecord::PRIMARY_KEY_NAME => 'customer_id']);
return $this->hasOne(Customer::className(), ['id' => 'customer_id']);
}
public function getOrderItems()
{
return $this->hasMany(OrderItem::className(), ['order_id' => ActiveRecord::PRIMARY_KEY_NAME]);
return $this->hasMany(OrderItem::className(), ['order_id' => 'id']);
}
public function getItems()
{
return $this->hasMany(Item::className(), [ActiveRecord::PRIMARY_KEY_NAME => 'item_id'])
return $this->hasMany(Item::className(), ['id' => 'item_id'])
->via('orderItems')->orderBy('id');
}
@ -51,8 +57,8 @@ class Order extends ActiveRecord
// public function getBooks()
// {
// return $this->hasMany('Item', [ActiveRecord::PRIMARY_KEY_NAME => 'item_id'])
// ->viaTable('tbl_order_item', ['order_id' => ActiveRecord::PRIMARY_KEY_NAME])
// return $this->hasMany('Item', ['id' => 'item_id'])
// ->viaTable('tbl_order_item', ['order_id' => 'id'])
// ->where(['category_id' => 1]);
// }
@ -65,4 +71,24 @@ class Order extends ActiveRecord
return false;
}
}
/**
* sets up the index for this record
* @param Command $command
*/
public static function setUpMapping($command)
{
$command->deleteMapping(static::index(), static::type());
$command->setMapping(static::index(), static::type(), [
static::type() => [
"_id" => ["path" => "id", "index" => "not_analyzed", "store" => "yes"],
"properties" => [
"customer_id" => ["type" => "integer"],
// "create_time" => ["type" => "string", "index" => "not_analyzed"],
"total" => ["type" => "integer"],
]
]
]);
}
}

25
tests/unit/data/ar/elasticsearch/OrderItem.php

@ -1,6 +1,7 @@
<?php
namespace yiiunit\data\ar\elasticsearch;
use yii\elasticsearch\Command;
/**
* Class OrderItem
@ -19,11 +20,31 @@ class OrderItem extends ActiveRecord
public function getOrder()
{
return $this->hasOne(Order::className(), [ActiveRecord::PRIMARY_KEY_NAME => 'order_id']);
return $this->hasOne(Order::className(), ['id' => 'order_id']);
}
public function getItem()
{
return $this->hasOne(Item::className(), [ActiveRecord::PRIMARY_KEY_NAME => 'item_id']);
return $this->hasOne(Item::className(), ['id' => 'item_id']);
}
/**
* sets up the index for this record
* @param Command $command
*/
public static function setUpMapping($command)
{
$command->deleteMapping(static::index(), static::type());
$command->setMapping(static::index(), static::type(), [
static::type() => [
"properties" => [
"order_id" => ["type" => "integer"],
"item_id" => ["type" => "integer"],
"quantity" => ["type" => "integer"],
"subtotal" => ["type" => "integer"],
]
]
]);
}
}

70
tests/unit/extensions/elasticsearch/ActiveRecordTest.php

@ -48,17 +48,11 @@ class ActiveRecordTest extends ElasticSearchTestCase
$db->createCommand()->deleteIndex('yiitest');
}
$db->post(['yiitest'], [], Json::encode([
'mappings' => [
"item" => [
"_source" => [ "enabled" => true ],
"properties" => [
// allow proper sorting by name
"name" => ["type" => "string", "index" => "not_analyzed"],
]
]
],
]));
$command = $db->createCommand();
Customer::setUpMapping($command);
Item::setUpMapping($command);
Order::setUpMapping($command);
OrderItem::setUpMapping($command);
$customer = new Customer();
$customer->id = 1;
@ -132,6 +126,20 @@ class ActiveRecordTest extends ElasticSearchTestCase
$db->createCommand()->flushIndex('yiitest');
}
public function testFindAsArray()
{
// asArray
$customer = $this->callCustomerFind()->where(['id' => 2])->asArray()->one();
$this->assertEquals([
'id' => 2,
'email' => 'user2@example.com',
'name' => 'user2',
'address' => 'address2',
'status' => 1,
'_score' => 1.0
], $customer);
}
public function testSearch()
{
$customers = $this->callCustomerFind()->search()['hits'];
@ -243,8 +251,8 @@ class ActiveRecordTest extends ElasticSearchTestCase
public function testInsertNoPk()
{
$this->assertEquals([ActiveRecord::PRIMARY_KEY_NAME], Customer::primaryKey());
$pkName = ActiveRecord::PRIMARY_KEY_NAME;
$this->assertEquals('id', Customer::primaryKey());
$pkName = 'id';
$customer = new Customer;
$customer->email = 'user4@example.com';
@ -257,6 +265,7 @@ class ActiveRecordTest extends ElasticSearchTestCase
$this->assertTrue($customer->isNewRecord);
$customer->save();
$this->afterSave();
$this->assertNotNull($customer->primaryKey);
$this->assertNotNull($customer->oldPrimaryKey);
@ -268,7 +277,7 @@ class ActiveRecordTest extends ElasticSearchTestCase
public function testInsertPk()
{
$pkName = ActiveRecord::PRIMARY_KEY_NAME;
$pkName = 'id';
$customer = new Customer;
$customer->$pkName = 5;
@ -288,17 +297,26 @@ class ActiveRecordTest extends ElasticSearchTestCase
public function testUpdatePk()
{
$pkName = ActiveRecord::PRIMARY_KEY_NAME;
$pkName = 'id';
$pk = [$pkName => 2];
$orderItem = Order::find($pk);
$orderItem = Order::find([$pkName => 2]);
$this->assertEquals(2, $orderItem->primaryKey);
$this->assertEquals(2, $orderItem->oldPrimaryKey);
$this->assertEquals(2, $orderItem->$pkName);
$this->setExpectedException('yii\base\InvalidCallException');
// $this->setExpectedException('yii\base\InvalidCallException');
$orderItem->$pkName = 13;
$this->assertEquals(13, $orderItem->primaryKey);
$this->assertEquals(2, $orderItem->oldPrimaryKey);
$this->assertEquals(13, $orderItem->$pkName);
$orderItem->save();
$this->afterSave();
$this->assertEquals(13, $orderItem->primaryKey);
$this->assertEquals(13, $orderItem->oldPrimaryKey);
$this->assertEquals(13, $orderItem->$pkName);
$this->assertNull(Order::find([$pkName => 2]));
$this->assertNotNull(Order::find([$pkName => 13]));
}
public function testFindLazyVia2()
@ -306,7 +324,7 @@ class ActiveRecordTest extends ElasticSearchTestCase
/** @var TestCase|ActiveRecordTestTrait $this */
/** @var Order $order */
$orderClass = $this->getOrderClass();
$pkName = ActiveRecord::PRIMARY_KEY_NAME;
$pkName = 'id';
$order = new $orderClass();
$order->$pkName = 100;
@ -320,18 +338,8 @@ class ActiveRecordTest extends ElasticSearchTestCase
public function testBooleanAttribute()
{
$db = $this->getConnection();
$db->createCommand()->deleteIndex('yiitest');
$db->post(['yiitest'], [], Json::encode([
'mappings' => [
"customer" => [
"_source" => [ "enabled" => true ],
"properties" => [
// this is for the boolean test
"status" => ["type" => "boolean"],
]
]
],
]));
Customer::setUpMapping($db->createCommand(), true);
Customer::deleteAll();
$customerClass = $this->getCustomerClass();
$customer = new $customerClass();

3
tests/unit/framework/ar/ActiveRecordTestTrait.php

@ -145,7 +145,10 @@ trait ActiveRecordTestTrait
// scope
$this->assertEquals(2, count($this->callCustomerFind()->active()->all()));
$this->assertEquals(2, $this->callCustomerFind()->active()->count());
}
public function testFindAsArray()
{
// asArray
$customer = $this->callCustomerFind()->where(['id' => 2])->asArray()->one();
$this->assertEquals([

Loading…
Cancel
Save