Target unassigned


#1

Hi all,

My target is unassigned in a function and I not understand why…
In this controller this.bodyContentTarget is available in connect() function but is empty when the observer call bodyHandleSuccess().

import { Controller } from "stimulus"
export default class extends Controller {
  static targets = [ "bodyContent","bodyForm"]
  connect() {
    if ( this.hasBodyContentTarget && this.hasBodyFormTarget ) {
      this.bodyFormTarget.addEventListener('ajax:success', this.bodyHandleSuccess, false)
    }
  }

  bodyHandleSuccess(event) {
    this.bodyFormTarget..innerHTML = event.detail[2].response;
  }
}

where am I wrong?
Thank all,
Andrea


#2

When you pass function by reference like that you need to bind it to the controller:

this.bodyFormTarget.addEventListener('ajax:success', this.bodyHandleSuccess.bind(this))

Or, use an inline function:

this.bodyFormTarget.addEventListener('ajax:success', event => this.bodyHandleSuccess(event))

To really do it the Stimulus way, use an inline action instead of installing your own event listener:

  <div data-controller="foo">
    <form data-action="ajax:success->foo#handleBodySuccess">…</form>
  </div>

#3

Thanks for your suggestions!
The stimulus way is best solution, I have changed ajax:succes to ajax:complete for errors manage:

 <form data-action="ajax:complete->foo#bodyHandle">…</form>      

  bodyHandle(event) {
    if (event.detail[0].status == 200) {
      this.bodyContentTarget.innerHTML = event.detail[0].response;
    } else {
      var div = document.createElement("div");
      div.textContent = "Attenzione invio fallito!";
      div.className = "callout alert";
      this.bodyContentTarget.appendChild(div);
    }
  }

and all work fine!