Hello.
I’m using version 3.6.30. Tailor blueprints created to define several content types.
What I want to accomplish is to set the “updated_at” field of any content type to the current date/time, whenever a ‘fileupload’ or ‘entries’ field is dirty (modified on the backend form). Currently, if I change an uploaded file or an entry selection only, the parent record keeps its current value of “updated_at”, despite the fact that related records did change.
My current approach to accomplish this goal is to use the ‘boot’ method of a custom plugin, like this (not working):
public function boot()
{
// Extend the blueprint for your content types
Event::listen('tailor.extendBlueprint', function (Blueprint $blueprint) {
\Log::info('Current Handle is: '. $blueprint->handle);
if ($blueprint->handle == 'Content\\Video') { // Adjust the handle for your content type
\Log::info('Handle Video matches');
// Listen for the form saving event
$blueprint->extendModel(function($model) {
$model->bindEvent('model.save', function() use ($model) {
// Check if specific fields like fileupload or entries are dirty
if ($model->isDirty('hero_image') || $model->isDirty('authors')) {
// Manually update the updated_at field
$model->updated_at = now();
\Log::info('updated_at field was set to current date/time for video record');
}
});
});
}
});
}
After reviewing the documentation about model extension, I came up with this new approach. However, I have trouble comparing the old and new values of the fields. After testing the following code, the old and new values are always the same (the old ones). So, the update is executed all the time.
public function boot()
{
// Extend the EntryRecord model for the 'Content\\Video' section
EntryRecord::extendInSection('Content\\Video', function($model) {
// Property to store old values before saving
$model->addDynamicProperty('originalRelations', []);
// Listen for the beforeSave event to capture old values
$model->bindEvent('model.beforeSave', function () use ($model) {
// Reload the hero_image relationship (single file)
$model->reloadRelations('hero_image', 'authors');
// Store the original value for hero_image (single file)
$model->originalRelations['hero_image'] = $model->hero_image
? $model->hero_image->only(['disk_name', 'file_name', 'file_size'])
: null;
// Store the original values for authors (multiple entries)
$model->originalRelations['authors'] = $model->authors->map(function ($author) {
return $author->only(['id', 'title']); // Extract relevant properties of authors
})->toArray();
// Log the original values
Log::info('Original hero_image:', $model->originalRelations['hero_image']);
Log::info('Original authors:', $model->originalRelations['authors']);
});
// Listen for the afterSave event to compare new and old values
$model->bindEvent('model.afterSave', function () use ($model) {
// Reload the relationships after save
$model->reloadRelations('hero_image', 'authors');
// Get the new value for hero_image (single file)
$newHeroImage = $model->hero_image
? $model->hero_image->only(['disk_name', 'file_name', 'file_size'])
: null;
// Get the new values for authors (multiple entries)
$newAuthors = $model->authors->map(function ($author) {
return $author->only(['id', 'title']);
})->toArray();
// Log the new values
Log::info('New hero_image:', $newHeroImage);
Log::info('New authors:', $newAuthors);
// Compare the old and new values (from the beforeSave event)
$originalHeroImage = $model->originalRelations['hero_image'];
$originalAuthors = $model->originalRelations['authors'];
// If there's a difference, update the updated_at field
if ($originalHeroImage !== $newHeroImage || $originalAuthors !== $newAuthors) {
// Manually update the updated_at field
DB::table($model->getTable())
->where('id', $model->id)
->update(['updated_at' => now()]);
Log::info('updated_at field was set to current date/time for this video content type record.');
}
});
});
}
Can you suggest some solution? Or maybe I’m overcomplicating things and there is an easier way?