7

I am programmatically creating many nodes. Obviously they have to be valid before storing them. Such $node objects have CCK fields mixed with custom fields.

Because the validators only set a form_set_error() and hardly ever return the validation-result, I have to go trough the form-api in order to know if a node is valid, or so it seems.

I call node_validate(), then form_get_errors() (which, in turn calls form_set_error()).

There appear to be several problems with this approach:

  • form_set_error() sets a message with drupal_set_message(); for stuff like cron (a session-less user), this adds orphaned persistent error-messages to the database (they will never be printed, hence never deleted).
  • the returning array of errors is created to be used in a multidimensional form array. Especially with CCK-fields, I have to dig quite deep in order to find the actual error.
  • I just want to store a node, so I am not interested in a user-faced form; using the form API just feels wrong.

Is there a simpler, more elegant method?

  • Is the problem that your data source that you are using may have invalid data in it, or just that you are trying to validate your own code? – mpdonadio Oct 28 '11 at 13:24
  • I just want to avoid storing nodes that are "invalid", according to whatever defines if they are valid. If, say, an image is required, one can assume that the theme will be able to render that image, regardless. If my importers start saving nodes without these images, the theme will print broken image-links. – berkes Oct 28 '11 at 13:28
5

There aren't any other ways, as the hooks that the modules need to implement to validate a node are hook_validate() (if the module implements a content type) and hook_nodeapi('validate') (for all the other modules). Those hooks get a $form parameter, and are supposed to call form_set_error() in the case there is a validation error.

The easier way to find if there are errors set for a form is to use form_get_errors(), which returns the array with all the errors set with form_set_error(), the function that is also called from form_error().

In the case more than one node is validated, you would need to call form_set_error(NULL, '', TRUE) before node_validate(), and then get from form_get_errors() the array containing the error messages; if this is empty, there are no error messages.

form_set_error(NULL, '', TRUE);

// node_validate() call.

$errors = form_get_errors();

if (!empty($errors)) {
  // Some module reported an error.
}

Alternatively, you can use the following snippet to verify no module reported an error, after you call node_validate():

if (!empty($_SESSION['messages']['error'])) {
  // Some module reported an error.
}

Before calling node_validate() from the cron task, you would need to set $_SESSION['messages']['error'] to an empty array; in that way, you are sure the errors reported in the array are caused by the node validation hooks.

$_SESSION['messages'] is the variable used from drupal_set_message() to store the messages passed to the function.

function drupal_set_message($message = NULL, $type = 'status', $repeat = TRUE) {
  if ($message) {
    if (!isset($_SESSION['messages'])) {
      $_SESSION['messages'] = array();
    }

    if (!isset($_SESSION['messages'][$type])) {
      $_SESSION['messages'][$type] = array();
    }
    // …
  }
  // …
}
  • is this work on drupal 7 ? – Lucifer Sep 4 '14 at 11:43
  • The question is for Drupal 6; you need to slightly change the code for Drupal 7. – kiamlaluno Sep 4 '14 at 12:04
  • can you just give a direction how to do in drupal 7 – Lucifer Sep 4 '14 at 12:28

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.