craftcms/cms

[4.x]: `Entry::EVENT_AFTER_SAVE` executes before any changes are committed to the database

ericdrosas87 opened this issue · 3 comments

What happened?

Our client builds which need to be triggered via an explicit request are not functioning as expected due to a timing issue between when the database is updated and when Entry::EVENT_AFTER_SAVE gets fired.

Description

We have a use case where we need to send a request to a Next.js server to trigger a static build for a page based on the entry being saved in Craft. We have a custom plugin that is hooking into Entry::EVENT_AFTER_SAVE to send the revalidate request to the Next.js server, but the client rebuild is not occurring in the way that we expect - or rather, it is rebuilding based on the last-state saved of the entry not the new state. The Next.js client makes a GQL request to the Craft API endpoint to retrieve the entry data and it is receiving back the last-saved state. This led us to narrowing down the cause to a timing issue between when the database gets updated and when the Entry::EVENT_AFTER_SAVE gets fired.

The temporary workaround for this is for us to ask the content creators to save the pages twice - in this way the first page save is useless for the client and the second save triggers the actual page build because the data is finally in the database.

The same thing happens with Entry::EVENT_AFTER_PROPAGATE.

Steps to reproduce

  1. Create a plugin or module that hooks into Entry::EVENT_AFTER_SAVE
  2. Drop a sleep(60); into the module/plugin
  3. Pull the database terminal and run the following query: select count(*) from elements;
  4. Save an entry in the Craft dashboard
  5. Periodically rerun the count(*) query while the sleep(60); takes effect
  6. Observe how a new element is not inserted into the elements table until the sleep(60); ends

Expected behavior

The database is updated immediately and before the Entry::EVENT_AFTER_SAVE is fired

Actual behavior

The database is updated immediately and after the Entry::EVENT_AFTER_SAVE is fired

We are running both an English and Spanish site, in a Kubernetes orchestration within Google Cloud if that's helpful info.

Craft CMS version

4.8.4

PHP version

8.1

Operating system and version

Linux Alpine

Database type and version

PostgreSQL 13.7

Image driver and version

No response

Installed plugins and versions

  • carlcs/Asset Metadata v4.0.0
  • Venveo/Bulk Edit v4.0.1
  • NyStudio/Canto DAM Assets v4.0.12
  • P&T/Contact Form v3.1.0
  • P&T/Contact Form Honeypot v2.1.0
  • P&T/Google Cloud Storage v2.1.0
  • James Edmonston/GraphQL Authentication v2.5.0
  • Spicy Web/Neo v4.0.7
  • Cast Iron Coding/Next Builds v1.0.0
  • Ryan Pascoe/Phone Number v2.2.0
  • P&T/Redactor v3.0.4
  • Verbb/Supertable v3.0.12
  • Sebastian Lenz/Typed linked field v2.1.5

Hi, thanks for getting in touch! Are you using Craft::$app->onAfterRequest() when hooking into Entry::EVENT_AFTER_SAVE? You can find more details and an example here: #13942.

I will close this now but don’t hesitate to get in touch if you have any further questions.

@i-just That was exactly it - thank you! Apologies about not finding that previous Issue before posting this one

Not a problem. Glad it’s working as expected!