Home Forums Front-end Issues Frontend Custom Validation for acf_form


Frontend Custom Validation for acf_form

  • Hello,

    This is a bit of a doozy for me as I’ve been working on this for two full days and I’m stumped. I am using ACF to create a registration form for users on our website.

    I created some custom validation for the email (to make sure the email isn’t already in use) and the password (to make sure it’s strong enough and matches the confirmation password). Both are added as follows:

    add_filter( 'acf/validate_value/key=field_644ad72c57f66', 'validate_email_field', 10, 4 );
    add_filter( 'acf/validate_value/key=field_644ad77c63bc6', 'validate_password_field', 10, 4 );

    Here is an example of this validation code:

    function validate_email_field( $valid, $value, $field, $input ) {
        if( $valid !== true )
            return $valid;
        if( ! is_email( $value ) )
            return __( 'Your email is invalid.' );
        if( email_exists( $value ) )
            return __( 'The email you provided is already associated with an account.' );
        return $valid;

    I include the acf_form_head() as follows:

    add_action( 'template_include', 'add_acf_form_head', 1, 1 );
    function add_acf_form_head( $template ) {
        return $template;

    When a user submits the form on the front end, the javascript validation does not work, it only works when they submit and they get a wp_die() type error with the correct error message. The default ACF validation work (required fields get a red box and error message) but any custom validation is not included. Any ideas as to why this might be the case?

  • The issue you describe is caused by a PHP error during the ajax request done by ACF or the site creating some type of output during the ajax request that breaks the response.

    To look for PHP errors during the request:

    If it is the latter, it could be anywhere, even the output of a single white space character, like a return, can cause it.

  • When I look at my network tab the AJAX request comes back with an 200 OK and response is as follows:

    Validation failed

    • Your email value is required

    This is generated by ACF. Wouldn’t a white space or other character also break other ACF validation? All the vanilla validation rules work, just the custom ones break.

  • What does the return look like if you remove your filter during other validation failure?

  • It’s the same. Basically the viewport scrolls to the top of the form where a notification bar can be found “Validation failed. X fields require attention”. However, each blank field has an error message “Please fill out this field.”. If I look at the admin-ajax.php request the response looks the same as above (except my custom validation errors are omitted).

    Is vanilla validation baked directly into the ACF’s javascript?

  • I do not think so. There would be no point in doing so, but I could be wrong.

    But the thing I do know is that for some reason when you add your validation what is being returned is somehow different than what ACF expects to be returned.

    What should be returned is JSON object.

    You could add custom javascript and use this filter to log the returned value to console to see.

    Maybe it has something to do with __() calls, try removing those, I doubt it, but you never know.

  • So I did some digging around if I could see other threads that had similar issues and found this old thread here ( There was no harm in checking to see if removing the NOT from acf_verify_ajax() and surprisingly all the frontend validation works as intended.

    Obviously editing the core isn’t a real solution but sadly this thread didn’t have a conclusion. One poster mentions that making sure both the the admin and the form’s action match when it comes to passing via https but my action is blank so it goes to the current page.

    Hilariously enough I found an old thread of mine from April ( where I was going through a similar issue and it had to do with when I called acf_form_head() but I’m already doing this in template_include.

    So I put everything back to what it should be and I also went and replaced the __() calls to just return 'bad bad bad'; and got the same HTML response from the AJAX validation but now my custom validation is replaced with “bad bad bad”.

    This is a bit of a doozy!

  • Are you using an ACF email field for the email field or a text field?

    ACF already validates for a valid email address.

    If you are using an email field, just for giggles, try changing the priority of your validation filter to something > 10

    add_filter( 'acf/validate_value/key=field_644ad72c57f66', 'validate_email_field', 20, 4 );
  • It is an email field and the redundancy is more of an oversight on my part.

    I commented out the is_email() call and changed the priority to 11. I then tried to submit the form with an email already associated with a user and oddly enough my weak password validation is included in the response but my email one no longer appears.

    Validation failed

    • Your password must contain at least eight (8) characters; including letters, numbers, and special characters.
    • First name value is required
    • Last name value is required
    • Address value is required
    • City value is required
  • Apologies for the double post but I just noticed that the custom validation for the email never seems to run during the AJAX call. If the email is already in use it fails with an error when the form is submitted but the AJAX never tells me the email is in use and neither does the AJAX response (even when the response is HTML).

    Nevermind, there was a typo in the email used in the system.

  • This is what I would do next. I would start at the top of the function and I would add

    return 'This is a test';

    I would return this value without checking anything to see if the code is called and got that far. Meaning you should always see the message for the field.

    I would then move the return, alter the text so I was sure I was seeing the new message. I would keep moving it and testing until is stopped working.

  • Sorry, I understand the forum restricts certain things for a reason but I was unable to delete my reply or edit the previous one. The validation code does get called but my testing data was wrong which is why it wasn’t triggering that particular error.

    If I add “This is a test” at the top of my email validation function it shows it in the Ajax’s return value. What I don’t understand is why all the other validation errors show but not the custom one. I took a screenshot because I thought it would be easier to show than try and explain:

    Notice the custom errors (as well as the default validation) appears in the response but only the default validation errors show up on the form fields themselves.

  • I just did a test and everything is working as expected using this code

    add_filter('acf/validate_value/key=field_64ba92e423e65', 'validate_email_field', 20, 4);
    function validate_email_field( $valid, $value, $field, $input ) {
      if (!$valid) {
        return $valid;
      if( email_exists( $value ) ) {
        $valid = 'email exists';
       return $valid;

    You must have something else that is interfering, as I said in my original response, something that is breaking the ajax response. Either another plugin or some code in the theme.

  • I’m sorry but I never thought it was related to my validation code and more so with acf_form_head() — the former was included to show that I wasn’t doing anything silly that would be causing the issue.

    That being said, I seem to have solved it. I have a custom admin area that needs the use of ACF so I include acf_form_head() on that page. What I didn’t realize was that my code to add it was being called during AJAX calls on the frontend (because admin-ajax.php is considering part of the backend) so it would validate the submission.

    I wrapped it around a wp_doing_ajax() condition and it solved it. I’m frustrated with myself because I’m sure I grepped my plugin for acf_form_head() in my plugin and I’m sure it didn’t come up — clearly a user error there.

    I know I’m not supposed to do what I’m doing but I couldn’t figure out a way to add ACF to an options page that isn’t created with ACF but I digress and I’ve taken enough of your time!

    Thank you so much for your help and I apologize for wasting your time — just know that I’ve been working on this for three days and I posted here out of desperation.

  • You did not do it wrong. The only way to add ACF fields to a page not created by WP or ACF is to insert acf_form() into the existing form of the other plugin. While not the best solution, it is the only solution.

    Glad you worked it out and I maybe I’ll remember this if someone else has a similar problem.

  • @hube2 Perhaps it should be made explicit in the documentation that invoking acf_form_head during ajax calls causes this error. We just ran into this one pretty hard.

Viewing 17 posts - 1 through 17 (of 17 total)

You must be logged in to reply to this topic.