Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
mvorisek committed Aug 5, 2022
1 parent c4b16bf commit 34f86c4
Show file tree
Hide file tree
Showing 4 changed files with 123 additions and 92 deletions.
10 changes: 6 additions & 4 deletions src/Model.php
Original file line number Diff line number Diff line change
Expand Up @@ -1634,6 +1634,7 @@ protected function _insert(array $row): void
$reloadAfterSaveBackup = $this->reloadAfterSave;
try {
if (count($this->getModel()->scope()->elements) === 0) {
// assert entity exists and match all model conditions
$this->getModel()->reloadAfterSave = false;
}
$this->save($row);
Expand Down Expand Up @@ -1854,12 +1855,13 @@ public function delete($id = null)
}

$this->atomic(function () {
if ($this->hook(self::HOOK_BEFORE_DELETE) === false) {
return;
if (count($this->getModel()->scope()->elements) !== 0) {
// assert entity exists and match all model conditions
$this->getModel()->load($this->getId());
}

if (count($this->getModel()->scope()->elements) !== 0) {
$this->getModel()->load($this->getId()); // assert entity exists and match all model conditions
if ($this->hook(self::HOOK_BEFORE_DELETE) === false) {
return;
}

$this->getPersistence()->delete($this->getModel(), $this->getId());
Expand Down
201 changes: 115 additions & 86 deletions tests/ModelCheckedUpdateTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -42,15 +42,17 @@ public function testCheckedInsertSimple(): void

$user->insert(['name' => 'John']);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'Jennifer'],
['id' => 4, 'name' => 'John'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user->insert(['name' => 'Benjamin']);
try {
$user->insert(['name' => 'Benjamin']);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'Jennifer'],
['id' => 4, 'name' => 'John'],
], $user->export());
}
}

public function testCheckedInsertDependent(): void
Expand All @@ -60,15 +62,17 @@ public function testCheckedInsertDependent(): void

$user->insert(['name' => 'John']);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'Jennifer'],
['id' => 4, 'name' => 'John'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user->insert(['name' => 'John']);
try {
$user->insert(['name' => 'John']);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'Jennifer'],
['id' => 4, 'name' => 'John'],
], $user->export());
}
}

public function testCheckedUpdateSimple(): void
Expand All @@ -78,75 +82,65 @@ public function testCheckedUpdateSimple(): void
$user3 = $user->load(3);
$user3->save(['name' => 'John']);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'John'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user3->save(['name' => 'Benjamin']);
try {
$user3->save(['name' => 'Benjamin']);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'John'],
], $user->export());
}
}

public function testCheckedUpdateDeleted(): void
{
$user = $this->setupCheckedModel();

$user3 = $user->load(3);
$user->delete(3);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());

$this->assertTrue($user3->isLoaded());
$user3->onHook(Model::HOOK_BEFORE_UPDATE, function (Model $entity) {
(clone $entity)->delete();
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $entity->getModel()->export());
});

$this->expectException(Exception::class);
$this->expectExceptionMessage('Update failed, exactly 1 row was expected to be affected');
$user3->save(['name' => 'Jan']);
try {
$user3->save(['name' => 'Jan']);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'Jennifer'],
], $user->export());
}
}

public function testCheckedUpdateRestrictedLoaded(): void
public function testCheckedUpdateRestricted(): void
{
$user = $this->setupCheckedModel();

$user3 = $user->load(3);
$user3->save(['name' => 'John']);

$user->addCondition('id', '<', 3);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user3->save(['name' => 'Jan']);
}

public function testCheckedUpdateRestrictedUnloaded(): void
{
$user = $this->setupCheckedModel();

$markIdFieldAsNonDirtyForMssqlFx = function (Model $model): void {
unset($model->getDirtyRef()['id']);
};

$user3 = $user->createEntity()->setId(3);
$markIdFieldAsNonDirtyForMssqlFx($user3);
$user3->save(['name' => 'John']);
$user3 = $user->createEntity()->setId(3);
$markIdFieldAsNonDirtyForMssqlFx($user3);

$user->addCondition('id', '<', 3);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user3->save(['name' => 'Jan']);
try {
$user3->save(['name' => 'Jan']);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());
$user->scope()->clear();
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 2, 'name' => 'Roman'],
['id' => 3, 'name' => 'John'],
], $user->export());
}
}

public function testCheckedUpdateDependent(): void
Expand All @@ -157,14 +151,16 @@ public function testCheckedUpdateDependent(): void
$user3 = $user->load(3);
$user3->save(['name' => 'John']);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'John'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user3->save(['name' => 'James']);
try {
$user3->save(['name' => 'James']);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'John'],
], $user->export());
}
}

public function testCheckedDeleteSimple(): void
Expand All @@ -173,50 +169,83 @@ public function testCheckedDeleteSimple(): void

$user->delete(3);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user->delete(3);
try {
$user->delete(3);
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());
}
}

public function testCheckedDeleteDeleted(): void
{
$user = $this->setupCheckedModel();

$user3 = $user->load(3);
$user->delete(3);

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());

$this->assertTrue($user3->isLoaded());
$user3->onHook(Model::HOOK_BEFORE_DELETE, function (Model $entity) {
(clone $entity)->delete();
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $entity->getModel()->export());
});

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
// would require delete in pre delete hook $this->expectExceptionMessage('Delete failed, exactly 1 row was expected to be affected');
$user3->delete();
$this->expectExceptionMessage('Delete failed, exactly 1 row was expected to be affected');
try {
$user3->delete();
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 3, 'name' => 'Jennifer'],
], $user->export());
}
}

public function testCheckedDeleteRestricted(): void
{
$user = $this->setupCheckedModel();

$user3 = $user->load(3);

$user->addCondition('id', '<', 3);
$this->assertTrue($user3->isLoaded());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
try {
$user3->delete();
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());
$user->scope()->clear();
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
['id' => 2, 'name' => 'Roman'],
['id' => 3, 'name' => 'Jennifer'],
], $user->export());
}
}

$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());
public function testCheckedDeleteDependent(): void
{
$user = $this->setupCheckedModel();
$this->addUniqueNameConditionToModel($user);

$user3 = $user->load(3);
$user->load(3)->delete();
$this->assertTrue($user3->isLoaded());

$this->expectException(Exception::class);
$this->expectExceptionMessage('not found');
$user3->delete();
try {
$user3->delete();
} finally {
$this->assertSameExportUnordered([
['id' => 1, 'name' => 'James'],
], $user->export());
}
}
}
2 changes: 1 addition & 1 deletion tests/ModelNestedArrayTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -227,9 +227,9 @@ public function testDelete(): void
['inner', Model::HOOK_BEFORE_LOAD, [null]],
['inner', Model::HOOK_AFTER_LOAD, []],
['inner', '>>>'],
['inner', Model::HOOK_BEFORE_DELETE, []],
['inner', Model::HOOK_BEFORE_LOAD, [2]],
['inner', Model::HOOK_AFTER_LOAD, []],
['inner', Model::HOOK_BEFORE_DELETE, []],
['inner', Model::HOOK_AFTER_DELETE, []],
['inner', '<<<'],
['inner', Model::HOOK_BEFORE_UNLOAD, []],
Expand Down
2 changes: 1 addition & 1 deletion tests/ModelNestedSqlTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -278,10 +278,10 @@ public function testDelete(): void
['inner', Persistence\Sql::HOOK_INIT_SELECT_QUERY, [Query::class, 'select']],
['inner', Model::HOOK_AFTER_LOAD, []],
['inner', '>>>'],
['inner', Model::HOOK_BEFORE_DELETE, []],
['inner', Model::HOOK_BEFORE_LOAD, [2]],
['inner', Persistence\Sql::HOOK_INIT_SELECT_QUERY, [Query::class, 'select']],
['inner', Model::HOOK_AFTER_LOAD, []],
['inner', Model::HOOK_BEFORE_DELETE, []],
['inner', Persistence\Sql::HOOK_BEFORE_DELETE_QUERY, [Query::class]],
['inner', Persistence\Sql::HOOK_AFTER_DELETE_QUERY, [Query::class]],
['inner', Model::HOOK_AFTER_DELETE, []],
Expand Down

0 comments on commit 34f86c4

Please sign in to comment.