Drupal 8 Ajax Form Submit works only once? I am trying to create a simple form in D8 that submits with a submit button and then replaces the entire form content via ajax.

For some reason, my AJAX submit works perfectly on the first click but then kicks in a normal submit handler.

This Works

  public function getFormId() {
    return 'my_form';
  }

  public function buildForm(array $form, FormStateInterface $form_state) {

  $form['#prefix'] = '&lt;div id="form-test"&gt;';
  $form['#suffix'] = '&lt;/div&gt;';
  $form['title'] = array(
    '#type' =&gt; 'textfield',
    '#title' =&gt; t('Title'),
    '#required' =&gt; TRUE,
  );
  $form['submit'] = array(
    '#type' =&gt; 'submit',
    '#value' =&gt; t('Submit ').time(),
    '#ajax' =&gt; [
      'callback' =&gt; [$this, 'loadStep'],
      'wrapper' =&gt; 'form-test',
      'effect' =&gt; 'fade',
    ],
  );

return $form;
}

public function loadStep(array &amp;$form, FormStateInterface $form_state) {
$response = new AjaxResponse();
$form['submit']['#value'] = time();

$response-&gt;addCommand(new HtmlCommand('#form-test', $form));
return $response;

}

public function validateForm(array &amp;$form, FormStateInterface $form_state) {

}

public function submitForm(array &amp;$form, FormStateInterface $form_state) {
// TODO: Implement submitForm() method.
}


This Does NOT work

  public function getFormId() {
return 'my_form';
}

public function buildForm(array $form, FormStateInterface $form_state) {
  $form['#prefix'] = '&lt;div id="form-test"&gt;';
  $form['#suffix'] = '&lt;/div&gt;';
  $form['title'] = array(
    '#type' =&gt; 'textfield',
    '#title' =&gt; t('Title'),
    '#required' =&gt; TRUE,
  );
  $form['submit'] = array(
    '#type' =&gt; 'submit',
    '#value' =&gt; t('Submit ').time(),
    '#ajax' =&gt; [
      'callback' =&gt; [$this, 'loadStep'],
      'wrapper' =&gt; 'form-test',
      'effect' =&gt; 'fade',
    ],
  );

return $form;
}

public function loadStep(array &amp;$form, FormStateInterface $form_state) {
$response = new AjaxResponse();
$form['#prefix'] = '&lt;div id="form-test"&gt;';
$form['#suffix'] = '&lt;/div&gt;';
$form['title'] = array(
  '#type' =&gt; 'textfield',
  '#title' =&gt; t('Title'),
  '#required' =&gt; TRUE,
);
$form['submit'] = array(
  '#type' =&gt; 'submit',
  '#value' =&gt; t('Submit ').time(),
  '#ajax' =&gt; [
    'callback' =&gt; [$this, 'loadStep'],
    'wrapper' =&gt; 'form-test',
    'effect' =&gt; 'fade',
  ],
);
$response-&gt;addCommand(new HtmlCommand('#form-test', $form));
return $response;

}

public function validateForm(array &amp;$form, FormStateInterface $form_state) {

}

public function submitForm(array &amp;$form, FormStateInterface $form_state) {
// TODO: Implement submitForm() method.
}


It seem like as soon as I add something more substantially than just changing the label on the submit button, it seems to fail from the second submit where it just invokes a regular submit.

I want to replace the entire form on every submit (basically creating a multistep form).

I am running 8.3.2 btw

Many thanks for all help.
Your problem is probably here:

$form['submit']['#value'] = time();


You are changing the value of the submit button in the ajax callback. However, Drupal has already cached the form before the Ajax callback is hit. Why that matters is that Drupal uses the value of the submit button to determine which button was clicked, comparing it to the values in the cache. Since your cached value will be different than the submitted value, it cannot properly determine what it needs to do.

You need to change the value of the submit button either in the form definition, or in a form_alter hook.