Skip to content

Commit e39c749

Browse files
authored
feat: make insertBatch() and updateBatch() respect model rules (#9708)
* feat: make insertBatch() and updateBatch() respect model rules * update phpstan baseline
1 parent f03ce85 commit e39c749

File tree

4 files changed

+27
-60
lines changed

4 files changed

+27
-60
lines changed

system/BaseModel.php

Lines changed: 6 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -208,7 +208,8 @@ abstract class BaseModel
208208
protected bool $updateOnlyChanged = true;
209209

210210
/**
211-
* Rules used to validate data in insert(), update(), and save() methods.
211+
* Rules used to validate data in insert(), update(), save(),
212+
* insertBatch(), and updateBatch() methods.
212213
*
213214
* The array must match the format of data passed to the Validation
214215
* library.
@@ -909,7 +910,7 @@ public function insertBatch(?array $set = null, ?bool $escape = null, int $batch
909910

910911
if (is_array($set)) {
911912
foreach ($set as &$row) {
912-
$row = $this->transformDataRowToArray($row);
913+
$row = $this->transformDataToArray($row, 'insert');
913914

914915
// Validate every row.
915916
if (! $this->skipValidation && ! $this->validate($row)) {
@@ -1036,7 +1037,7 @@ public function updateBatch(?array $set = null, ?string $index = null, int $batc
10361037
{
10371038
if (is_array($set)) {
10381039
foreach ($set as &$row) {
1039-
$row = $this->transformDataRowToArray($row);
1040+
$row = $this->transformDataToArray($row, 'update');
10401041

10411042
// Validate data before saving.
10421043
if (! $this->skipValidation && ! $this->validate($row)) {
@@ -1667,52 +1668,6 @@ protected function trigger(string $event, array $eventData)
16671668
return $eventData;
16681669
}
16691670

1670-
/**
1671-
* If the model is using casts, this will convert the data
1672-
* in $row according to the rules defined in `$casts`.
1673-
*
1674-
* @param object|row_array|null $row Row data
1675-
*
1676-
* @return object|row_array|null Converted row data
1677-
*
1678-
* @used-by insertBatch()
1679-
* @used-by updateBatch()
1680-
*
1681-
* @throws ReflectionException
1682-
* @deprecated Since 4.6.4, temporary solution - will be removed in 4.7
1683-
*/
1684-
protected function transformDataRowToArray(array|object|null $row): array|object|null
1685-
{
1686-
// If casts are used, convert the data first
1687-
if ($this->useCasts()) {
1688-
if (is_array($row)) {
1689-
$row = $this->converter->toDataSource($row);
1690-
} elseif ($row instanceof stdClass) {
1691-
$row = (array) $row;
1692-
$row = $this->converter->toDataSource($row);
1693-
} elseif ($row instanceof Entity) {
1694-
$row = $this->converter->extract($row);
1695-
} elseif (is_object($row)) {
1696-
$row = $this->converter->extract($row);
1697-
}
1698-
} elseif (is_object($row) && ! $row instanceof stdClass) {
1699-
// If $row is using a custom class with public or protected
1700-
// properties representing the collection elements, we need to grab
1701-
// them as an array.
1702-
$row = $this->objectToArray($row, false, true);
1703-
}
1704-
1705-
// If it's still a stdClass, go ahead and convert to
1706-
// an array so doProtectFields and other model methods
1707-
// don't have to do special checks.
1708-
if (is_object($row)) {
1709-
$row = (array) $row;
1710-
}
1711-
1712-
// Convert any Time instances to appropriate $dateFormat
1713-
return $this->timeToString($row);
1714-
}
1715-
17161671
/**
17171672
* Sets the return type of the results to be as an associative array.
17181673
*
@@ -1830,7 +1785,9 @@ protected function objectToRawArray($object, bool $onlyChanged = true, bool $rec
18301785
* @throws ReflectionException
18311786
*
18321787
* @used-by insert()
1788+
* @used-by insertBatch()
18331789
* @used-by update()
1790+
* @used-by updateBatch()
18341791
*/
18351792
protected function transformDataToArray($row, string $type): array
18361793
{

tests/system/Models/UpdateModelTest.php

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -249,7 +249,9 @@ public function testUpdateBatchWithEntity(): void
249249
$entity2->deleted = 0;
250250
$entity2->syncOriginal();
251251

252-
$this->assertSame(2, $this->createModel(UserModel::class)->updateBatch([$entity1, $entity2], 'id'));
252+
$model = $this->createModel(UserModel::class);
253+
$this->setPrivateProperty($model, 'updateOnlyChanged', false);
254+
$this->assertSame(2, $model->updateBatch([$entity1, $entity2], 'id'));
253255
}
254256

255257
public function testUpdateNoPrimaryKey(): void

user_guide_src/source/changelogs/v4.7.0.rst

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,13 @@ update it to use double braces: ``regex_match[/^{{placeholder}}$/]``.
3333
This change was introduced to avoid ambiguity with regular expression syntax,
3434
where single curly braces (e.g., ``{1,3}``) are used for quantifiers.
3535

36+
BaseModel
37+
---------
38+
39+
The ``insertBatch()`` and ``updateBatch()`` methods now honor model settings like
40+
``updateOnlyChanged`` and ``allowEmptyInserts``. This change ensures consistent handling
41+
across all insert/update operations.
42+
3643
Interface Changes
3744
=================
3845

@@ -45,6 +52,7 @@ Removed Deprecated Items
4552
========================
4653

4754
- **Text Helper:** The deprecated types in ``random_string()`` function: ``basic``, ``md5``, and ``sha1`` has been removed.
55+
- **BaseModel:** The deprecated method ``transformDataRowToArray()`` has been removed.
4856

4957
************
5058
Enhancements
@@ -56,7 +64,7 @@ Libraries
5664
- **CLI:** Added ``SignalTrait`` to provide unified handling of operating system signals in CLI commands.
5765
- **CURLRequest:** Added ``shareConnection`` config item to change default share connection.
5866
- **CURLRequest:** Added ``dns_cache_timeout`` option to change default DNS cache timeout.
59-
- **CURLRequest:** Added ``fresh_connect`` options to enable/disabled request fresh connection.
67+
- **CURLRequest:** Added ``fresh_connect`` options to enable/disable request fresh connection.
6068
- **Email:** Added support for choosing the SMTP authorization method. You can change it via ``Config\Email::$SMTPAuthMethod`` option.
6169
- **Image:** The ``ImageMagickHandler`` has been rewritten to rely solely on the PHP ``imagick`` extension.
6270
- **Image:** Added ``ImageMagickHandler::clearMetadata()`` method to remove image metadata for privacy protection.
@@ -71,7 +79,7 @@ Testing
7179
Database
7280
========
7381

74-
- **Exception Logging:** All DB drivers now log database exceptions uniformly. Previously, each driver has its own log format.
82+
- **Exception Logging:** All DB drivers now log database exceptions uniformly. Previously, each driver had its own log format.
7583

7684
Query Builder
7785
-------------

utils/phpstan-baseline/missingType.property.neon

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -473,42 +473,42 @@ parameters:
473473
path: ../../tests/system/Models/UpdateModelTest.php
474474

475475
-
476-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$_options has no type specified\.$#'
476+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$_options has no type specified\.$#'
477477
count: 1
478478
path: ../../tests/system/Models/UpdateModelTest.php
479479

480480
-
481-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$country has no type specified\.$#'
481+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$country has no type specified\.$#'
482482
count: 1
483483
path: ../../tests/system/Models/UpdateModelTest.php
484484

485485
-
486-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$created_at has no type specified\.$#'
486+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$created_at has no type specified\.$#'
487487
count: 1
488488
path: ../../tests/system/Models/UpdateModelTest.php
489489

490490
-
491-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$deleted has no type specified\.$#'
491+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$deleted has no type specified\.$#'
492492
count: 1
493493
path: ../../tests/system/Models/UpdateModelTest.php
494494

495495
-
496-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$email has no type specified\.$#'
496+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$email has no type specified\.$#'
497497
count: 1
498498
path: ../../tests/system/Models/UpdateModelTest.php
499499

500500
-
501-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$id has no type specified\.$#'
501+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$id has no type specified\.$#'
502502
count: 1
503503
path: ../../tests/system/Models/UpdateModelTest.php
504504

505505
-
506-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$name has no type specified\.$#'
506+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$name has no type specified\.$#'
507507
count: 1
508508
path: ../../tests/system/Models/UpdateModelTest.php
509509

510510
-
511-
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:351\:\:\$updated_at has no type specified\.$#'
511+
message: '#^Property CodeIgniter\\Entity\\Entity@anonymous/tests/system/Models/UpdateModelTest\.php\:353\:\:\$updated_at has no type specified\.$#'
512512
count: 1
513513
path: ../../tests/system/Models/UpdateModelTest.php
514514

0 commit comments

Comments
 (0)