Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 3 additions & 2 deletions src/import/basic/Importer.php
Original file line number Diff line number Diff line change
Expand Up @@ -47,13 +47,14 @@ protected function safeRun()
foreach ($this->_models as $model) {
$model->load();
$model->validate();
$model->save(false);
}

Yii::$app->db->transaction(function () {
/*Yii::$app->db->transaction(function () {
foreach ($this->_models as $model) {
$model->save(false);
}
});
});*/

$this->trigger(self::EVENT_RUN);
}
Expand Down
123 changes: 78 additions & 45 deletions src/import/basic/Model.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,16 @@

namespace arogachev\excel\import\basic;

use arogachev\excel\components\Model as BaseModel;
use arogachev\excel\import\DI;
use arogachev\excel\import\exceptions\RowException;
use PHPExcel_Worksheet_Row;
use yii\base\Component;

/**
* @property StandardModel $standardModel
* @property \yii\db\ActiveRecord $instance
*/
class Model extends BaseModel
class Model extends Component
{
const EVENT_INIT = 'init';

Expand All @@ -21,18 +21,27 @@ class Model extends BaseModel
public $row;

/**
* @inheritdoc
* @var StandardModel
*/
protected $_standardModel;

/**
* @var Attribute[]
*/
protected static $attributeClassName = 'arogachev\excel\import\basic\Attribute';
protected $_attributes = [];

/**
* @var \yii\db\ActiveRecord
*/
protected $_instance;


/**
* @inheritdoc
*/
public function init()
{
parent::init();

$this->initAttributes();
$this->trigger(self::EVENT_INIT);
}

Expand All @@ -50,6 +59,14 @@ protected function initAttributes()
}
}

/**
* @param array $config
*/
protected function initAttribute($config)
{
$this->_attributes[] = new Attribute($config);
}

public function load()
{
$this->loadExisting();
Expand All @@ -58,58 +75,42 @@ public function load()

protected function loadExisting()
{
if ($this->isPkEmpty()) {
$pk = [];
foreach ($this->_attributes as $attribute) {
//if (in_array($attribute->standardAttribute->name, $this->_instance->primaryKey())) {
if (in_array($attribute->standardAttribute->name, $attribute->standardAttribute->primaryKey())) {
$pk[$attribute->standardAttribute->name] = $attribute->value;
}
}

if (!$pk) {
return;
}

/* @var $modelClass \yii\db\ActiveRecord */
$modelClass = $this->_standardModel->className;
$model = $modelClass::findOne($this->getPkValues());
if ($model) {
$this->_instance = $model;
if (count($pk) == 1 && !reset($pk)) {
return;
}
}

/**
* @return Attribute[]
*/
protected function getPk()
{
$attributes = [];
foreach ($this->_attributes as $attribute) {
if (in_array($attribute->standardAttribute->name, $this->_instance->primaryKey())) {
$attributes[] = $attribute;
foreach ($pk as $value) {
if (!$value) {
throw new RowException($this->row, 'For updated model all primary key attributes must be specified.');
}
}

return $attributes;
}
/* @var $modelClass \yii\db\ActiveRecord */
$modelClass = $this->_standardModel->className;
$model = $modelClass::find()->where($pk)->andWhere($this->_standardModel->where)->one();

/**
* @return array
*/
protected function getPkValues()
{
$values = [];
foreach ($this->getPk() as $attribute) {
$values[$attribute->standardAttribute->name] = $attribute->value;
if (!$model) {
//throw new RowException($this->row, 'Model for update not found.');
$model = new $modelClass();
}

return $values;
}

/**
* @return boolean
*/
protected function isPkEmpty()
{
foreach ($this->getPkValues() as $value) {
if ($value) {
return false;
}
foreach ($this->_standardModel->extendAttributesConfig as $name => $value) {
$model->{$name} = $value;
}

return true;
$this->_instance = $model;
}

protected function assignMassively()
Expand Down Expand Up @@ -139,4 +140,36 @@ public function save($runValidation = true)

$this->_instance->save(false);
}

/**
* @return StandardModel
*/
public function getStandardModel()
{
return $this->_standardModel;
}

/**
* @param StandardModel $value
*/
public function setStandardModel($value)
{
$this->_standardModel = $value;
}

/**
* @return \yii\db\ActiveRecord
*/
public function getInstance()
{
return $this->_instance;
}

/**
* @param \yii\db\ActiveRecord $value
*/
public function setInstance($value)
{
$this->_instance = $value;
}
}
114 changes: 109 additions & 5 deletions src/import/basic/StandardAttribute.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,26 +2,69 @@

namespace arogachev\excel\import\basic;

use arogachev\excel\components\StandardAttribute as BaseStandardAttribute;
use arogachev\excel\exceptions\StandardAttributeException;
use arogachev\excel\import\exceptions\StandardAttributeException;
use yii\base\Object;
use yii\helpers\ArrayHelper;

/**
* @property StandardModel $standardModel
* @property string $column
*/
class StandardAttribute extends BaseStandardAttribute
class StandardAttribute extends Object
{
/**
* @var string
*/
public $name;

/**
* @var string
*/
public $label;

/**
* @var array|callable
*/
public $valueReplacement;

/**
* @var StandardModel
*/
protected $_standardModel;

/**
* @var string
*/
protected $_column;


/**
* @inheritdoc
*/
protected function validateName()
public function init()
{
parent::validateName();
$this->validateName();

if ($this->_standardModel->extendStandardAttributes && !$this->label) {
$this->label = $this->_standardModel->instance->getAttributeLabel($this->name);
}

$this->validateLabel();
$this->validateValueReplacement();
}

/**
* @throws StandardAttributeException
*/
protected function validateName()
{
$standardModel = $this->_standardModel;
$model = $standardModel->instance;

if (!$this->name) {
throw new StandardAttributeException($this, 'Name is required.');
}

if (!in_array($this->name, $model->attributes())) {
throw new StandardAttributeException($this, 'Attribute not exist.');
}
Expand All @@ -38,4 +81,65 @@ protected function validateName()
throw new StandardAttributeException($this, 'Attribute is not allowed for import.');
}
}

/**
* @throws StandardAttributeException
*/
protected function validateLabel()
{
if ($this->standardModel->useAttributeLabels && !$this->label) {
throw new StandardAttributeException($this, 'Label not specified.');
}
}

/**
* @throws StandardAttributeException
*/
protected function validateValueReplacement()
{
if (!$this->valueReplacement || !is_array($this->valueReplacement)) {
return;
}

if ($this->valueReplacement != array_unique($this->valueReplacement)) {
throw new StandardAttributeException($this, 'Value replacement list contains duplicate labels / values.');
}
}

/**
* @return StandardModel
*/
public function getStandardModel()
{
return $this->_standardModel;
}

/**
* @param StandardModel $value
*/
public function setStandardModel($value)
{
$this->_standardModel = $value;
}

/**
* @return string
*/
public function getColumn()
{
return $this->_column;
}

/**
* @param string $value
*/
public function setColumn($value)
{
$this->_column = $value;
}

public function primaryKey()
{
return $this->_standardModel->primaryKey();
}
}
Loading