Search code examples
javascriptnode.jshttpcoap

How to assign anonymous function variables to class method variables?


I'm trying to implement communication with coap server by using coap package. My goal is to get response (in coap.request() response event handler) and then pass it to other variables and functions.

Event: 'response'

function (response) { }

Emitted when a response is received. response is an instance of IncomingMessage.

If the observe flag is specified, the 'response' event will return an instance of ObserveReadStream. Which represent the updates coming from the server, according to the observe spec.

I've created class someClass, which contains serverRequest() method.

Method serverRequest() takes mandatory options argument (which sets request options for coap.request()) and optional argument which sets message body if needed. Purpose of this method is to send a request to server and return response, which is instance of coap.IncomingMessage.

const coap = require('coap');

class someClass {
  constructor(someOption) {
    this.someOption = someOption;
  }

  serverRequest(options, messageBody=undefined) {
    const request = coap.request(options);
    let response;
    request.on('response', res => {
      console.log(response); // undefined
      response = res;
      console.log(response);  // valid response
    });
    if (messageBody !== undefined) {
      request.write(messageBody);
    }
    request.end();
    console.log(response);  // undefined
    return response;
  }
}

I send message and obtain response successfully, however response variable inside anonymous function seems to be unique and different from response variable inside serverRequest method.

Question: How can I pass variables from anonymous functions to other scopes?


Solution

  • You can call your method inside the body of an anonymous function:

    class Test 
    {
      constructor(someOption) {
        this.someOption = someOption;
      }
    
      myMethod ( data ) {
        //.. do something
      }
    
      anotherMethod() {
        var data = {answer:42};
        var that = this;
        functionWithCallback( function(differentOption) {
          that.myMethod(data);
          that.someOption = differentOption;
        });
      }       
    }
    

    Edit based on comments: Using var that = this; is a common way to cheat the scope. this will always belong to the scope of a function, method or anonymous, both are still functions.

    Therefore to keep a reference to the class scope, I assign the this from the class method's scope to var that so that when this changes to the anonymous' function scope, we still have access to it.

    In ECMAscript 6 and above when using arrow functions, the this keyword is not re-bound and we don't have to cheat the scope.

    class Test 
    {
      constructor(someOption) {
        this.someOption = someOption;
      }
    
      myMethod ( data ) {
        //.. do something
      }
    
      anotherMethod() {
        var data = {answer:42};
        functionWithCallback( (differentOption) => {
          this.myMethod(data);
          this.someOption = differentOption;
        });
      }        
    }
    

    Edit made by question author:

    I didn't have problems by using this keyword, script produced same results.