Assume that I have Foo.class in Java:
public class Foo {
public int id;
public String data;
}
And that I have Foo "class" in JavaScript:
function Foo(id, data) {
this.id = id;
this.data = data;
}
Also, assume that I have Java controller that returns instance of Foo.class as a response to a REST request. In my JavaScript (AngularJS) code the request is sent as:
$http.get(url + 'bar/get-foo/')
.success(function (response) {
var foo = new Foo(response.id, response.data);
logger.info("SUCCESS: /get-foo");
})
.error(function (error_message) {
logger.error(error_message)
});
And it works. But is there a way to avoid passing every property from response to Foo constructor (some sort of expecting the Foo object, or casting it into a Foo object)?
I tried using Object.create(Foo, response)
but I get TypeError: Property description must be an object: true
Of course there's always a possibility of refactoring the JavaScript side Foo constructor into:
function Foo(foo) {
this.id = foo.id;
this.data = foo.data;
}
But, that would require refactor of large portion of the codebase.
Thanks for your time. I appreciate it!
PS: For those who wonder why do I need this: It's not a problem with small classes like Foo, but some responses are instances of a much larger classes (with over a dozen of fields), which are not under my control.
EDIT: I accepted Chichozell's answer simply because it requires the least amount of work. Robin's and jonnyknowsbest's answers also work, (and will work for pure JavaScript, unlike Chichozell's answer, which is AngularJS specific). Haven't tried Laurentiu L.'s answer, but looks like it should also work. Anyway this is A solution (not THE solution):
.success(function (response) {
var foo = new Foo();
angular.extend(foo, response); // angular.merge() for "deep-copy"
//...
}
Big thanks to everyone who answered/commented/edited in this thread.
If you want to keep your Java thinking on javascript, try using angular.extend(), which will "copy" the properties of an object to another
this = angular.extend(this, response)
In the foo function, or directly on the controler:
Foo = angular.extend(Foo, response)
You can do something like this to "deserialise" the JSON you receive back as the response to an initialised object:
function JSONToObj(jsondata) {
var json = JSON.parse(jsondata);
var name = null;
for(var i in json) { //Use first property as name
name = i;
break;
}
if (name == null)
return null;
var obj = new window[name]();
for(var i in json[name])
obj[i] = json[name][i];
return obj;
}
This assumes that the constructor exists in the global scope and that the response is JSON-formatted as such:
{
"Foo": {
"id": "the id",
"data": "the data"
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With