0

I feel stupid asking this and searched similar questions but I don't understand why I'm able to set private String title but unable to get it.

I have a class that makes an HTTP request to get some JSON, parse it and set the instance variables from processResponse(). When I use GWT.log() inside setTitle() and getTitle(), the console shows that setTitle() has the value but getTitle() is undefined.

I'm using GWT if that makes a difference. This class will be used to create objects and these variables will be used throughout the program. What am I doing wrong here?

public class Requester {
    //other variables
    private String title;

    public Requester(UrlBuilder url) {
        this.setURL(url);
        this.generateRequest();
    }

    public void setURL(UrlBuilder url) {
        this.url = url;
    }

    private void generateRequest() {
        RequestBuilder builder = new RequestBuilder(RequestBuilder.GET, URL.encode(url.getUrl()));
        builder.setHeader("Authorization", authHeader);

        try {
            builder.sendRequest(null, new RequestCallback() {
                // onError() method

                public void onResponseReceived(Request request, Response response) {
                    processResponse(response);
                }

            });
        } catch (RequestException e) {
            //exception code
        }
    }

    private void processResponse(Response response) {
        //code to get title and assign it to String output
        setTitle(output);
    }

    private void setTitle(String output) {
        this.title = output;
    }

    public String getTitle() {
        return this.title;
    }
}
Anish Sana
  • 518
  • 1
  • 12
  • 30
  • In the `processResponse` method, where/how are you accessing the variable `output` that is used as a parameter to `setTitle`? – Chris Sprague Jul 26 '17 at 14:10
  • 3
    If `setTitle` is called and sets a particular value, and a subsequent call to `getTitle` shows `null`, then it is not the same *instance* of `Requester`. The calling code is making the call on another `Requester` object. Insert log statement into constructor to confirm, then look at code making the calls, since problem is *there*, not here in this code. – Andreas Jul 26 '17 at 14:11
  • @ChrisSprague I declared a local String for the assignment - `String output = jsonArray.get(0).isObject().get("title").toString();` – Anish Sana Jul 26 '17 at 14:13
  • 1
    It is bad form to execute lots of logic (especially integration logic such as making a web request) in an object's constructor. You probably want a separate method for making your web request that can be called after the object is constructed. This will help avoid possible state issues like the one @Andreas mentioned. Constructors are for constructing the object, not necessarily initializing it (use a separate init() method for that if you must) – java-addict301 Jul 26 '17 at 14:38
  • 1
    @java-addict301 That was really good advice. Not executing logic inside the constructor made things simpler. – Anish Sana Jul 28 '17 at 17:10

1 Answers1

0

I was able to figure out the problem with the help from a related question that I had asked.

The asynchronous call to generateRequest() had not finished by the time I was calling getTitle(). Since title was not set at that point, I was getting undefined.

Based on the suggestions in the other question, I modified my code to execute a method where title was passed as a parameter after generateRequest() was done -

public void onResponseReceived(Request request, Response response) {
                    MyOtherClass.newMethod(processResponse(response));
                }
Anish Sana
  • 518
  • 1
  • 12
  • 30