From e8082f641090394cdbd22ff67616f4f3e1b9c476 Mon Sep 17 00:00:00 2001 From: brandonkelly Date: Thu, 28 Nov 2024 05:04:56 -0800 Subject: [PATCH 1/6] Try inserting search keywords 3 times fixes #15221 --- CHANGELOG.md | 1 + src/services/Search.php | 16 +++++++++++++++- 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9a22f132030..7708d2e9564 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,7 @@ ## Unreleased - Fixed an error that could occur when duplicating an element with an Assets field that had a dynamic subpath. ([#16214](https://github.com/craftcms/cms/issues/16214)) +- Reduced the likelihood of a deadlock error occurring when updating search indexes. ([#15221](https://github.com/craftcms/cms/issues/15221)) ## 4.13.3 - 2024-11-22 diff --git a/src/services/Search.php b/src/services/Search.php index 05237a58725..e045e5f6eea 100644 --- a/src/services/Search.php +++ b/src/services/Search.php @@ -27,6 +27,7 @@ use craft\search\SearchQueryTermGroup; use Throwable; use yii\base\Component; +use yii\db\Exception; use yii\db\Expression; use yii\db\Schema; @@ -483,7 +484,20 @@ private function _indexKeywords(ElementInterface $element, string $keywords, ?st } // Insert/update the row in searchindex - Db::insert(Table::SEARCHINDEX, $columns); + for ($try = 0; $try < 3; $try++) { + try { + Db::insert(Table::SEARCHINDEX, $columns); + return; + } catch (Exception $e) { + if (str_contains($e->getPrevious()?->getMessage(), 'deadlock')) { + // A gap lock was probably hit. Try again in one second + // https://github.com/craftcms/cms/issues/15221 + sleep(1); + } else { + throw $e; + } + } + } } /** From ca10a5a5163040296e1722b66d882c3a3023dbf2 Mon Sep 17 00:00:00 2001 From: ps-paxxion <114239155+ps-paxxion@users.noreply.github.com> Date: Thu, 28 Nov 2024 09:26:18 +0100 Subject: [PATCH 2/6] FIX - folder renaming on windows host --- src/fs/Local.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/fs/Local.php b/src/fs/Local.php index 35bf9ab8914..8135b95fe90 100644 --- a/src/fs/Local.php +++ b/src/fs/Local.php @@ -377,10 +377,10 @@ public function renameDirectory(string $path, string $newName): void throw new FsObjectNotFoundException('No folder exists at path: ' . $path); } - $components = explode("/", $this->prefixPath($path)); + $components = explode(DIRECTORY_SEPARATOR, $this->prefixPath($path)); array_pop($components); $components[] = $newName; - $newPath = implode("/", $components); + $newPath = implode(DIRECTORY_SEPARATOR, $components); @rename($this->prefixPath($path), $newPath); } From 1f7f4a2d02defbc2f426a6d84b7d0898496420b1 Mon Sep 17 00:00:00 2001 From: brandonkelly Date: Fri, 29 Nov 2024 05:56:47 -0800 Subject: [PATCH 3/6] Cleanup --- src/fs/Local.php | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/src/fs/Local.php b/src/fs/Local.php index 8135b95fe90..1f429c933df 100644 --- a/src/fs/Local.php +++ b/src/fs/Local.php @@ -373,16 +373,18 @@ public function deleteDirectory(string $path): void */ public function renameDirectory(string $path, string $newName): void { - if (!is_dir($this->prefixPath($path))) { + $fullPath = $this->prefixPath($path); + + if (!is_dir($fullPath)) { throw new FsObjectNotFoundException('No folder exists at path: ' . $path); } - $components = explode(DIRECTORY_SEPARATOR, $this->prefixPath($path)); + $components = explode(DIRECTORY_SEPARATOR, $fullPath); array_pop($components); $components[] = $newName; $newPath = implode(DIRECTORY_SEPARATOR, $components); - @rename($this->prefixPath($path), $newPath); + @rename($fullPath, $newPath); } /** From a71a1f2b4a06a451b791483f7225f63c0e661d03 Mon Sep 17 00:00:00 2001 From: brandonkelly Date: Fri, 29 Nov 2024 05:57:08 -0800 Subject: [PATCH 4/6] Normalize $path --- src/fs/Local.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/fs/Local.php b/src/fs/Local.php index 1f429c933df..d4e1daa1c38 100644 --- a/src/fs/Local.php +++ b/src/fs/Local.php @@ -415,7 +415,7 @@ protected function prefixPath(string $path = ''): string throw new FsException("The path `$path` is not contained."); } - return $this->getRootPath() . DIRECTORY_SEPARATOR . $path; + return $this->getRootPath() . DIRECTORY_SEPARATOR . FileHelper::normalizePath($path); } /** From efd819add40c6a6dbc56042181488f5f7c0e35f9 Mon Sep 17 00:00:00 2001 From: brandonkelly Date: Fri, 29 Nov 2024 06:00:24 -0800 Subject: [PATCH 5/6] Release note --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7708d2e9564..d1ed4dfe7c7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,7 @@ - Fixed an error that could occur when duplicating an element with an Assets field that had a dynamic subpath. ([#16214](https://github.com/craftcms/cms/issues/16214)) - Reduced the likelihood of a deadlock error occurring when updating search indexes. ([#15221](https://github.com/craftcms/cms/issues/15221)) +- Fixed a bug where renaming asset folders could move them to the webroot on Windows. ([#16215](https://github.com/craftcms/cms/issues/16215)) ## 4.13.3 - 2024-11-22 From 718173ab1f40e94b60bd78faa613b6ab7ca4efc9 Mon Sep 17 00:00:00 2001 From: brandonkelly Date: Sat, 30 Nov 2024 19:29:37 -0800 Subject: [PATCH 6/6] Fixed testIsValidIntervalString --- tests/unit/helpers/DateTimeHelperTest.php | 4 ---- 1 file changed, 4 deletions(-) diff --git a/tests/unit/helpers/DateTimeHelperTest.php b/tests/unit/helpers/DateTimeHelperTest.php index 02f182b894c..fc3a2fd636c 100644 --- a/tests/unit/helpers/DateTimeHelperTest.php +++ b/tests/unit/helpers/DateTimeHelperTest.php @@ -696,10 +696,6 @@ public function isInvalidIntervalStringDataProvider(): array [true, '1 year'], [true, '1 month'], [true, '1 minutes'], - - [false, ''], - [false, 'random string'], - ]; }