I have a webhook that fetches an entry, modifies one of its custom Text field values and then saves the entry. However there is also a required Categories field on the entry, and when I do this, I get a validation error because the Categories field is blank.

Here’s the relevant code:

$entry = craft()->entries->getEntryById($entryId);

    'myTextField' => $newValue

// Let's see if it saves.
// Field validation should happen automatically
if (craft()->entries->saveEntry($entry))
    Craft::log('Entry updated (ID: '.$entry->id.').');
    Craft::log('Could not updated the entry (ID: '.$entry->id.').', LogLevel::Error);

How do I save the entry without losing its existing Categories field value?


Update - Craft 3

This has been fixed. The relational field will retain its original value when an entry is re-saved.

You no longer need to apply a workaround to get the expected behavior.

Original - Craft 2

This is, admittedly, super awkward right now. To prevent a relational field from losing its value when saving an entry, you have to explicitly set its value to null:

    'myCategoriesField' => null
    // ...

However, this only works for relational fields that aren’t set to Required. If the field is set to Required, you have to just re-set the field to the same element IDs that were already selected:

    'myCategoriesField' => $entry->myCategoriesField->ids()
    // ...

(FWIW, this will stop being awkward in Craft 3, as we done some major refactoring under the hood to fix issues like this.)

  • Ideally I don't want to change at all as it's already set. I only want to change the stock level and leave everything else as is, but having the Category as a required field is not letting me do that. – divinemonkey Aug 24 '15 at 14:08
  • @divinemonkey Just updated your question and my answer after getting some clarification on it from carlcs. – Brandon Kelly Aug 24 '15 at 14:19
  • Got it. All working now. Thanks, and to you also @carlcs – divinemonkey Aug 25 '15 at 9:28
  • @BrandonKelly Is there a way to easily re-populate all the existing content an entry already has, without knowing exactly what fields it has? I'm trying to make a generic function that can be used across sections and would prefer not to have to manually specify all required relational fields, but do a single function call to cover every possible case. – Mike Pierce Dec 15 '15 at 13:17
  • 1
    @BrandonKelly Sorry, not sure I follow you...? How does that help me exactly? – Mike Pierce Dec 16 '15 at 10:05

I'm probably missing something here, but can't you just query for the entry model and only modify the field you want to change?

$criteria = craft()->elements->getCriteria(ElementType::Entry);
$criteria->id = 1;
$entries = $criteria->first();

if ($entry)
        'fieldToChange' => 'newValue'

    // Validate the entry model here if necessary

  • I've updated my original post as a response to see if this would still work. – divinemonkey Aug 24 '15 at 3:06
  • Yes, should really be the same. Have a look at the full gist I created for you gist.github.com/carlcs/ef4664ceb281db7068fd. Test that code and tell me if you're still getting errors in the log! :) – carlcs Aug 24 '15 at 6:59
  • Unfortunately I am still getting the same error. 2015/08/24 09:42:43 [warning] [application] Craft\ContentModel->productCategory failed validation: Product Category cannot be blank. I am tempted to remove it has a required field currently. Seems the easiest solution. – divinemonkey Aug 24 '15 at 9:48
  • And it did validate / saved without errors from the CP when you created that entry? Is there a category selected at all for that entry? – carlcs Aug 24 '15 at 9:56
  • The webhook did complete with no errors, no stock update in the backend though and the Craft log receives that error. Yes, it is defined as Hardware. – divinemonkey Aug 24 '15 at 10:06

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.