Skip to content

Commit f0716ab

Browse files
authored
PHPORM-211 Fix unsetting property in embedded model (#3052)
1 parent acaba1a commit f0716ab

File tree

3 files changed

+41
-14
lines changed

3 files changed

+41
-14
lines changed

CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ All notable changes to this project will be documented in this file.
88
* Add `Schema\Builder::getTables()` and `getTableListing()` by @GromNaN in [#3044](https://github.com/mongodb/laravel-mongodb/pull/3044)
99
* Add `Schema\Builder::getColumns()` and `getIndexes()` by @GromNaN in [#3045](https://github.com/mongodb/laravel-mongodb/pull/3045)
1010
* Add `Schema\Builder::hasColumn` and `hasColumns` method by @Alex-Belyi in [#3001](https://github.com/mongodb/laravel-mongodb/pull/3001)
11+
* Fix unsetting a field in an embedded model by @GromNaN in [#3052](https://github.com/mongodb/laravel-mongodb/pull/3052)
1112

1213
## [4.6.0] - 2024-07-09
1314

src/Relations/EmbedsOneOrMany.php

+8-1
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,10 @@
1515
use Throwable;
1616

1717
use function array_merge;
18+
use function assert;
1819
use function count;
1920
use function is_array;
21+
use function str_starts_with;
2022
use function throw_if;
2123

2224
abstract class EmbedsOneOrMany extends Relation
@@ -392,7 +394,12 @@ public static function getUpdateValues($array, $prepend = '')
392394
$results = [];
393395

394396
foreach ($array as $key => $value) {
395-
$results[$prepend . $key] = $value;
397+
if (str_starts_with($key, '$')) {
398+
assert(is_array($value), 'Update operator value must be an array.');
399+
$results[$key] = static::getUpdateValues($value, $prepend);
400+
} else {
401+
$results[$prepend . $key] = $value;
402+
}
396403
}
397404

398405
return $results;

tests/EmbeddedRelationsTest.php

+32-13
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,6 @@
1010
use Mockery;
1111
use MongoDB\BSON\ObjectId;
1212
use MongoDB\Laravel\Tests\Models\Address;
13-
use MongoDB\Laravel\Tests\Models\Book;
14-
use MongoDB\Laravel\Tests\Models\Client;
15-
use MongoDB\Laravel\Tests\Models\Group;
16-
use MongoDB\Laravel\Tests\Models\Item;
17-
use MongoDB\Laravel\Tests\Models\Photo;
18-
use MongoDB\Laravel\Tests\Models\Role;
1913
use MongoDB\Laravel\Tests\Models\User;
2014

2115
use function array_merge;
@@ -25,14 +19,7 @@ class EmbeddedRelationsTest extends TestCase
2519
public function tearDown(): void
2620
{
2721
Mockery::close();
28-
2922
User::truncate();
30-
Book::truncate();
31-
Item::truncate();
32-
Role::truncate();
33-
Client::truncate();
34-
Group::truncate();
35-
Photo::truncate();
3623
}
3724

3825
public function testEmbedsManySave()
@@ -951,4 +938,36 @@ public function testGetQueueableRelationsEmbedsOne()
951938
$this->assertEquals(['father'], $user->getQueueableRelations());
952939
$this->assertEquals([], $user->father->getQueueableRelations());
953940
}
941+
942+
public function testUnsetPropertyOnEmbed()
943+
{
944+
$user = User::create(['name' => 'John Doe']);
945+
$user->addresses()->save(new Address(['city' => 'New York']));
946+
$user->addresses()->save(new Address(['city' => 'Tokyo']));
947+
948+
// Set property
949+
$user->addresses->first()->city = 'Paris';
950+
$user->addresses->first()->save();
951+
952+
$user = User::where('name', 'John Doe')->first();
953+
$this->assertSame('Paris', $user->addresses->get(0)->city);
954+
$this->assertSame('Tokyo', $user->addresses->get(1)->city);
955+
956+
// Unset property
957+
unset($user->addresses->first()->city);
958+
$user->addresses->first()->save();
959+
960+
$user = User::where('name', 'John Doe')->first();
961+
$this->assertNull($user->addresses->get(0)->city);
962+
$this->assertSame('Tokyo', $user->addresses->get(1)->city);
963+
964+
// Unset and reset property
965+
unset($user->addresses->get(1)->city);
966+
$user->addresses->get(1)->city = 'Kyoto';
967+
$user->addresses->get(1)->save();
968+
969+
$user = User::where('name', 'John Doe')->first();
970+
$this->assertNull($user->addresses->get(0)->city);
971+
$this->assertSame('Kyoto', $user->addresses->get(1)->city);
972+
}
954973
}

0 commit comments

Comments
 (0)