yii2tech / ar-softdelete Goto Github PK
View Code? Open in Web Editor NEWSoft delete behavior for ActiveRecord
License: Other
Soft delete behavior for ActiveRecord
License: Other
Optimistic lock logic is not taken into account when soft delete/restore
my quick fix
replace in delete/restore internal methods
$result = $this->owner->updateAttributes($attributes);
with
$this->owner->setAttributes($attributes, false);
$result = $this->owner->update(false, array_keys($attributes));
$query = xx::find()->alias('t1')->select('t1.aa')
->where(['>', 't2.aa', 0])
->leftJoin(yy::tableName() . ' t2', 't1.aa=t2.aa');
$deals = $query->orderBy('t2.aa desc')->limit(10)->asArray()->all();
error:
Column not found: 1054 Unknown column 'xx.is_delete' in 'where clause'
The SQL being executed was: SELECT t1
.aa
FROM xx
t1
LEFT JOIN yy
t2
ON t1.aa=t2.aa WHERE (t2
.aa
> 0) AND (xx.is_delete
=0)
model :
/**
* @return \yii\db\ActiveQuery|SoftDeleteQueryBehavior
*/
public static function find(){
// $query = parent::find();
$query->attachBehavior('softDelete', SoftDeleteQueryBehavior::className());
return $query;
}
controller :
$query = TappsPrincipalHolding::find()
->notDeleted()->one();
iam has alot of query for it, so how if remove notDeleted
in controller, better if not used it. Cz i'll not need it in App, just need in database if really needed..
$query = parent::find()->andWhere(['=', 'isDeleted', 0]);
is it right ?
or it should works without my changes ?
Thanks for pay attention..
There should be a method, which will attempt to call regular delete()
method and if it fails with IntegrityException
exception, fall-back to softDelete()
.
Thus in relational database: if record has no restricted foreign key dependencies it will be deleted, but if is has been linked to some other one it will be 'soft' deleted instead.
Would it not make sense to use a unix timestamp to indicate deletion as opposed to a simple boolean?
It is certainly important to know when a record was deleted, not just whether it was. It could both be done with one column by storing unix timestamps instead of booleans. A set value means that the record was deleted AND it also tells you when. The column being NULL means the record has not been deleted. Furthermore this could be done consistently with TimestampBehavior by calling the attribute "deleted_at".
The only (and perhaps negligible) downside is the possibility of slightly higher storage requirement (using INT instead of BIT).
At the very least this could be a configurable option of SoftDelete.
I am using softdelete in our model, when we go for delete then we get this error yii\base\UnknownPropertyException .
Used code in model is
use yii\base\ModelEvent;
use yii2tech\ar\softdelete\SoftDeleteBehavior;
.......
{
public function behaviors()
{
return [
'softDeleteBehavior' => [
'class' => SoftDeleteBehavior::className(),
'softDeleteAttributeValues' => [
'isDeleted' => true
],
],
];
}
.......
}
I have inserted the behaviour in the active model now i need for soft delete all based on certain condition I cannot as there is no option for that
Want some kind of function like SoftDeleteAll("condition") which will be same as delete all
I had to wirite an update all like where i set all isdelete flag as 1
I had to use it in a relational model
Hello! DeleteAction expects not false if deletion successful.
https://github.com/yiisoft/yii2/blob/4f80cda7130da5259ce93fe41eb681cbb70f30be/framework/rest/DeleteAction.php#L36
Maybe this line is wrong?
ar-softdelete/src/SoftDeleteBehavior.php
Line 391 in 9a5a741
This code wont work, because the method softDeleteInternal() will rewrite the values of the attributes during the execution of lines https://github.com/yii2tech/ar-softdelete/blob/master/SoftDeleteBehavior.php#L179-L185 which will only update the attributes defined in the softDeleteAttributeValues
property using the values defined there.
public function beforeSoftDelete()
{
$this->deletedAt = time(); // log the deletion date
return true;
}
Is the documented example which doesn't work.
ar-softdelete/src/SoftDeleteBehavior.php
Line 185 in 9a5a741
updateAttributes() return int the number of rows affected, but DeleteAction expects bool.
https://github.com/yiisoft/yii2/blob/4f80cda7130da5259ce93fe41eb681cbb70f30be/framework/rest/DeleteAction.php#L36
When I restore the record I get an error,
Call to a member function restore () on null
which is probably related to this. By using:
public static function find (){ return parent: find () -> where (['isDeleted' => false]); }
for the record deleted
$item = Item :: findOne ($ id);
$item
will be null
$item->restore(); // restore record
This way, you can not restore marked items as deleted
php composer.phar require --prefer-dist yii2tech/ar-softdelete
Instalation success
Using version ^1.0 for yii2tech/ar-softdelete
./composer.json has been updated
Loading composer repositories with package information
Updating dependencies (including require-dev)
Your requirements could not be resolved to an installable set of packages.
Problem 1
- mpdf/mpdf 7.0.2 requires php ^5.6 || ~7.0.0 || ~7.1.0 || ~7.2.0 -> your PHP version (7.3.7) does not satisfy that requirement.
- mpdf/mpdf 7.0.2 requires php ^5.6 || ~7.0.0 || ~7.1.0 || ~7.2.0 -> your PHP version (7.3.7) does not satisfy that requirement.
- mpdf/mpdf 7.0.2 requires php ^5.6 || ~7.0.0 || ~7.1.0 || ~7.2.0 -> your PHP version (7.3.7) does not satisfy that requirement.
- Installation request for mpdf/mpdf (locked at 7.0.2) -> satisfiable by mpdf/mpdf[7.0.2].
| Q | A
| --------------------- | ---
| This Package Version | ^1.0.0
| Yii Framework Version | 2.0.0
| PHP version | 7.3.7
| Operating system | Ubuntu 18.04
I know you have to stop a hard delete in the beforeDelete event. Which eventually returns false to the delete() function. Is there a proper way to get the delete function to not return false?
public function behaviors()
{
return [
'softDeleteBehavior' => [
'class' => SoftDeleteBehavior::className(),
'softDeleteAttributeValues' => [
'whenDeleted' => new Expression('NOW()')
],
'restoreAttributeValues' => [
'whenDeleted' => null
],
'replaceRegularDelete' => true
],
];
}
What I have so far was override the deleteAll static function in the model so that the ActiveRecord deleteInternal function would not hard delete the record
public static function deleteAll($condition = '', $params = [])
{
return 1;
}
And remove the $event->isValid = false;
line in the beforeDelete event function from SoftDeleteBehavior so that $model->delete()
would eventually return true
public function beforeDelete($event)
{
if (!$this->isDeleteAllowed()) {
$this->softDeleteInternal();
// $event->isValid = false;
}
}
CREATE TABLE `Customer`
(
`id` integer NOT NULL AUTO_INCREMENT,
`name` varchar(64) NOT NULL,
`address` varchar(64) NOT NULL,
`phone` varchar(20) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE InnoDB;
CREATE TABLE `Purchase`
(
`id` integer NOT NULL AUTO_INCREMENT,
`customerId` integer NOT NULL,
`itemId` integer NOT NULL,
`amount` integer NOT NULL,
PRIMARY KEY (`id`)
FOREIGN KEY (`customerId`) REFERENCES `Customer` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
FOREIGN KEY (`itemId`) REFERENCES `Item` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
) ENGINE InnoDB;
I have mysql table like this with foreign key to another table and I set ON DELETE CASCADE
if I perform soft delete record on table Customer, the contain record on Purchase table should mark as soft deleted
when I 'soft deleted' record on table Customer, the contain record on Purchase table not mark as soft deleted.
I tried both command, softDelete
and safeDelete
, it still just mark soft deleted on table Customer, not on Purchase table..
Q | A |
---|---|
This Package Version | 1.0.4 |
Yii Framework Version | 2.0.38 |
PHP version | 7.4.9 |
Operating system | Windows 10 build 2004 |
Unknown Property – yii\base\UnknownPropertyException
Setting unknown property: app\models\Employee::isDeleted
To use soft delete should i insert the isDeleted
attribute into the database employee table?
I get a problem when I want to update yii2 version to 2.0.14.1 hotfix version
Problem 1
- The requested package yiisoft/yii2 2.0.14.1 exists as yiisoft/yii2[2.0.0, 2.0.0-alpha, 2.0.0-beta, 2.0.0-rc, 2.0.1, 2.0.10, 2.0.11, 2.0.11.1, 2.0.11.2, 2. 0.12, 2.0.13, 2.0.13.1, 2.0.14, 2.0.2, 2.0.3, 2.0.4, 2.0.5, 2.0.6, 2.0.7, 2.0.8, 2.0.9, 2.1.x-dev, dev-master, 2.0.x-dev] but these are rejected by your constra int.
Problem 2
- yii2tech/ar-softdelete 1.0.1 requires yiisoft/yii2 * -> satisfiable by yii soft/yii2[2.0.0, 2.0.0-alpha, 2.0.0-beta, 2.0.0-rc, 2.0.1, 2.0.10, 2.0.11, 2.0.1 1.1, 2.0.11.2, 2.0.12, 2.0.13, 2.0.13.1, 2.0.14, 2.0.2, 2.0.3, 2.0.4, 2.0.5, 2.0 .6, 2.0.7, 2.0.8, 2.0.9, 2.1.x-dev, dev-master, 2.0.x-dev] but these conflict wi th your requirements or minimum-stability.
- yii2tech/ar-softdelete 1.0.1 requires yiisoft/yii2 * -> satisfiable by yii soft/yii2[2.0.0, 2.0.0-alpha, 2.0.0-beta, 2.0.0-rc, 2.0.1, 2.0.10, 2.0.11, 2.0.1 1.1, 2.0.11.2, 2.0.12, 2.0.13, 2.0.13.1, 2.0.14, 2.0.2, 2.0.3, 2.0.4, 2.0.5, 2.0 .6, 2.0.7, 2.0.8, 2.0.9, 2.1.x-dev, dev-master, 2.0.x-dev] but these conflict wi th your requirements or minimum-stability.
- Installation request for yii2tech/ar-softdelete ^1.0.1 -> satisfiable by y ii2tech/ar-softdelete[1.0.1].
hi. i am test sample find:
Contacts::find() ->alias('c') ->joinWith(['sexuality' => function (\yii\db\ActiveQuery $query) { $query->alias('s'); }])->createCommand()->getSql();
query result:
SELECT "c".* FROM "contacts" "c" LEFT JOIN "domain" "s" ON ("c"."sexuality_id" = "s"."id") AND("domain"."deleted_at" IS NULL) WHERE "contacts"."deleted_at" IS NULL
alias does not apply in query.
find()
на фильтрацию? Только тут нельзя забывать про возможность добавления public static function find()
{
return new ItemQuery(get_called_class());
}
При этом остается необходимость выборки удаленных записей. В этом плане есть хорошие реализации у Laravel, RoR, Sequelize (nodejs).
When AR transactions on scenario have OP_ALL or OP_DELETE, event return false and transaction rollback.
1) Issue 1:
My model:
class Expense extends ActiveRecord
{
...
public static function find()
{
return parent::find()->where(['is_deleted' => 0]);
}
...
}
My search model:
public function search($params)
{
$query = Expense::find();
$query->where(['expense.company_id' => Yii::$app->user->identity->company_id]);
$dataProvider = new ActiveDataProvider([
'query' => $query,
]);
$this->load($params);
if (!$this->validate()) {
return $dataProvider;
}
}
My Controller:
$searchModel = new ExpenseSearch();
$dataProvider = $searchModel->search(Yii::$app->request->queryParams);
The behavior stop working because of this code in my search model:
$query->where(['expense.company_id' => Yii::$app->user->identity->company_id]);
2) Issue 2:
The following code doesn't work as well:
return Notification::find()
->with(['user'])
->where(['to_user_id' => Yii::$app->user->id])
->orderBy(['id' => SORT_DESC])
->limit(Notification::LIMIT_PER_PAGE)
->all();
3) Issue 3:
It's impossible to use join when two tables have the is_deleted field.
Integrity constraint violation – yii\db\IntegrityException
SQLSTATE[23000]: Integrity constraint violation: 1052 Column 'isDeleted' in where clause is ambiguous
How to use AND (table
.isDeleted
<> 1) for default?
protected function softDeleteInternal()
{
$result = false;
if ($this->beforeSoftDelete()) {
//$attributes = [];
**$attributes = $this->owner->getAttributes();**
foreach ($this->softDeleteAttributeValues as $attribute => $value) {
if (!is_scalar($value) && is_callable($value)) {
$value = call_user_func($value, $this->owner);
}
$attributes[$attribute] = $value;
}
$result = $this->owner->updateAttributes($attributes);
$this->afterSoftDelete();
}
return $result;
}
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.