Exports whole object with functions - node.js

i tried found answer in stackoverflow and can't find any answer about this
i just started learning NodeJS . and i got a question, is there any way how can i exports whole object with his functions or i can exports only functions of object?
thanks for advice!
when i try it i got error like this
TypeError: object is not a function
i got simple code like this :
animal.js
var Animal = {
name : null,
setName : function(name) {
this.name = name;
},
getName : function() {
console.log("name of animal is " + this.name);
}
}
exports.Animal = Animal;
and server.js
var animal = require('./animal');
var ani = new animal.Animal();

The error is because new expects a Function while Animal is a plain Object.
Though, with the Object, you could use Object.create() to create instances:
// ...
var ani = Object.create(animal.Animal);
Otherwise, you'll have to define Animal as a constructor Function:
function Animal() {
this.name = null;
// ...
}
exports.Animal = Animal;
Note: Depending on precisely what you want to accomplish, Functions are a type of Object and can hold additional properties.
function Animal(name) {
this.name = name || Animal.defaultName;
}
Animal.defaultName = null;

Related

Arrow function use that is assigned by a module.export object cannot correctly resolve this

It seems that only if I fill out the child object directly in the Base function that is the only way that the getSettings function can see the this.name property correctly, but I was trying to have my objects in different files to avoid having one large file.
***child.js***
module.exports : {
getSettings: ()=>{
return this.name === 'foobar'
}
}
***base.js***
var Child = require('./child.js')
function Base(){
this.name = 'foobar'
this.child = Child
this.child2 = {}
for (var prop in Child){
this.child2[prop] = Child[prop]
}
this.child3 = {
getSettings: ()=>{
return this.name === 'foobar'
}
}
}
***index.js****
var Base = require('./base.js')
var b = new Base()
b.child.getSettings() //FAILS BECAUSE this.name is undefined
b.child2.getSettings() //FAILS BECAUSE this.name is undefined
b.child3.getSettings() //PASSES. this.name is defined
It's conventional in JS OOP to refer class instance as this, so it's semantically incorrect for child objects to refer to parent object as this. This also makes it difficult to work with an object like child that doesn't get desirable context as lexical this (like child3 does).
child object likely should be a class that are injected with parent instance as a dependency.
module.exports = class Child(parent) {
constructor(parent) {
this.parent = parent;
}
getSettings() {
return this.parent.name === 'foobar'
}
}
var Child = require('./child.js')
function Base(){
this.name = 'foobar'
this.child = new Child(this);
...
}

Define a literal Javascript object so a property referenced directly calls a function and not its sub-ordinates [duplicate]

JavaScript allows functions to be treated as objects--if you first define a variable as a function, you can subsequently add properties to that function. How do you do the reverse, and add a function to an "object"?
This works:
var foo = function() { return 1; };
foo.baz = "qqqq";
At this point, foo() calls the function, and foo.baz has the value "qqqq".
However, if you do the property assignment part first, how do you subsequently assign a function to the variable?
var bar = { baz: "qqqq" };
What can I do now to arrange for bar.baz to have the value "qqqq" and bar() to call the function?
It's easy to be confused here, but you can't (easily or clearly or as far as I know) do what you want. Hopefully this will help clear things up.
First, every object in Javascript inherits from the Object object.
//these do the same thing
var foo = new Object();
var bar = {};
Second, functions ARE objects in Javascript. Specifically, they're a Function object. The Function object inherits from the Object object. Checkout the Function constructor
var foo = new Function();
var bar = function(){};
function baz(){};
Once you declare a variable to be an "Object" you can't (easily or clearly or as far as I know) convert it to a Function object. You'd need to declare a new Object of type Function (with the function constructor, assigning a variable an anonymous function etc.), and copy over any properties of methods from your old object.
Finally, anticipating a possible question, even once something is declared as a function, you can't (as far as I know) change the functionBody/source.
There doesn't appear to be a standard way to do it, but this works.
WHY however, is the question.
function functionize( obj , func )
{
out = func;
for( i in obj ){ out[i] = obj[i]; } ;
return out;
}
x = { a: 1, b: 2 };
x = functionize( x , function(){ return "hello world"; } );
x() ==> "hello world"
There is simply no other way to acheive this,
doing
x={}
x()
WILL return a "type error". because "x" is an "object" and you can't change it. its about as sensible as trying to do
x = 1
x[50] = 5
print x[50]
it won't work. 1 is an integer. integers don't have array methods. you can't make it.
Object types are functions and an object itself is a function instantiation.
alert([Array, Boolean, Date, Function, Number, Object, RegExp, String].join('\n\n'))
displays (in FireFox):
function Array() {
[native code]
}
function Boolean() {
[native code]
}
function Date() {
[native code]
}
function Function() {
[native code]
}
function Number() {
[native code]
}
function Object() {
[native code]
}
function RegExp() {
[native code]
}
function String() {
[native code]
}
In particular, note a Function object, function Function() { [native code] }, is defined as a recurrence relation (a recursive definition using itself).
Also, note that the answer 124402#124402 is incomplete regarding 1[50]=5. This DOES assign a property to a Number object and IS valid Javascript. Observe,
alert([
[].prop="a",
true.sna="fu",
(new Date()).tar="fu",
function(){}.fu="bar",
123[40]=4,
{}.forty=2,
/(?:)/.forty2="life",
"abc".def="ghi"
].join("\t"))
displays
a fu fu bar 4 2 life ghi
interpreting and executing correctly according to Javascript's "Rules of Engagement".
Of course there is always a wrinkle and manifest by =. An object is often "short-circuited" to its value instead of a full fledged entity when assigned to a variable. This is an issue with Boolean objects and boolean values.
Explicit object identification resolves this issue.
x=new Number(1); x[50]=5; alert(x[50]);
"Overloading" is quite a legitimate Javascript exercise and explicitly endorsed with mechanisms like prototyping though code obfuscation can be a hazard.
Final note:
alert( 123 . x = "not" );
alert( (123). x = "Yes!" ); /* ()'s elevate to full object status */
Use a temporary variable:
var xxx = function()...
then copy all the properties from the original object:
for (var p in bar) { xxx[p] = bar[p]; }
finally reassign the new function with the old properties to the original variable:
bar = xxx;
var A = function(foo) {
var B = function() {
return A.prototype.constructor.apply(B, arguments);
};
B.prototype = A.prototype;
return B;
};
NB: Post written in the style of how I solved the issue. I'm not 100% sure it is usable in the OP's case.
I found this post while looking for a way to convert objects created on the server and delivered to the client by JSON / ajax.
Which effectively left me in the same situation as the OP, an object that I wanted to be convert into a function so as to be able to create instances of it on the client.
In the end I came up with this, which is working (so far at least):
var parentObj = {}
parentObj.createFunc = function (model)
{
// allow it to be instantiated
parentObj[model._type] = function()
{
return (function (model)
{
// jQuery used to clone the model
var that = $.extend(true, null, model);
return that;
})(model);
}
}
Which can then be used like:
var data = { _type: "Example", foo: "bar" };
parentObject.createFunc(data);
var instance = new parentObject.Example();
In my case I actually wanted to have functions associated with the resulting object instances, and also be able to pass in parameters at the time of instantiating it.
So my code was:
var parentObj = {};
// base model contains client only stuff
parentObj.baseModel =
{
parameter1: null,
parameter2: null,
parameterN: null,
func1: function ()
{
return this.parameter2;
},
func2: function (inParams)
{
return this._variable2;
}
}
// create a troop type
parentObj.createModel = function (data)
{
var model = $.extend({}, parentObj.baseModel, data);
// allow it to be instantiated
parentObj[model._type] = function(parameter1, parameter2, parameterN)
{
return (function (model)
{
var that = $.extend(true, null, model);
that.parameter1 = parameter1;
that.parameter2 = parameter2;
that.parameterN = parameterN;
return that;
})(model);
}
}
And was called thus:
// models received from an AJAX call
var models = [
{ _type="Foo", _variable1: "FooVal", _variable2: "FooVal" },
{ _type="Bar", _variable1: "BarVal", _variable2: "BarVal" },
{ _type="FooBar", _variable1: "FooBarVal", _variable2: "FooBarVal" }
];
for(var i = 0; i < models.length; i++)
{
parentObj.createFunc(models[i]);
}
And then they can be used:
var test1 = new parentObj.Foo(1,2,3);
var test2 = new parentObj.Bar("a","b","c");
var test3 = new parentObj.FooBar("x","y","z");
// test1.parameter1 == 1
// test1._variable1 == "FooVal"
// test1.func1() == 2
// test2.parameter2 == "a"
// test2._variable2 == "BarVal"
// test2.func2() == "BarVal"
// etc
Here's easiest way to do this that I've found:
let bar = { baz: "qqqq" };
bar = Object.assign(() => console.log("do something"), bar)
This uses Object.assign to concisely make copies of all the the properties of bar onto a function.
Alternatively you could use some proxy magic.
JavaScript allows functions to be
treated as objects--you can add a
property to a function. How do you do
the reverse, and add a function to an
object?
You appear to be a bit confused. Functions, in JavaScript, are objects. And variables are variable. You wouldn't expect this to work:
var three = 3;
three = 4;
assert(three === 3);
...so why would you expect that assigning a function to your variable would somehow preserve its previous value? Perhaps some annotations will clarify things for you:
// assigns an anonymous function to the variable "foo"
var foo = function() { return 1; };
// assigns a string to the property "baz" on the object
// referenced by "foo" (which, in this case, happens to be a function)
foo.baz = "qqqq";
var bar = {
baz: "qqqq",
runFunc: function() {
return 1;
}
};
alert(bar.baz); // should produce qqqq
alert(bar.runFunc()); // should produce 1
I think you're looking for this.
can also be written like this:
function Bar() {
this.baz = "qqqq";
this.runFunc = function() {
return 1;
}
}
nBar = new Bar();
alert(nBar.baz); // should produce qqqq
alert(nBar.runFunc()); // should produce 1

How to use javascript to get instance name [duplicate]

function myClass(a,b,c) {
this.alertMyName=function(){alert(instancename)}
{...}
}
and then
foo = myClass(a,b,c);
boo = myClass(a,b,c);
foo.alertMyName(); //it should alert 'foo'
boo.alertMyName(); //it should alert 'boo'
In practice I'll need it for class that is creating a lot of html objects to prefix their ID's to differentiate them from same object created by another instance of this class.
I Couldn't find a solution on Stack Overflow so here is a solution I found from ronaldcs on dforge.net:
http://www.dforge.net/2013/01/27/how-to-get-the-name-of-an-instance-of-a-class-in-javascript/
myObject = function () {
this.getName = function () {
// search through the global object for a name that resolves to this object
for (var name in window)
if (window[name] == this)
return name;
};
};
Try it Out:
var o = new myObject();
alert(o.getName()); // alerts "o"
You could bring it in as a parameter:
function myClass(name, a, b, c) {
this.alertMyName = function(){ alert(name) }
}
foo = new myClass('foo', a, b, c);
Or assign it afterwards:
function myClass(a, b, c) {
this.setName = function(name) {
this.name = name;
}
this.alertMyName = function(){
alert(this.name)
}
}
foo = new myClass( a,b,c);
foo.setName('foo');
Further to David's answer, variables in javascript have a value that is either a primitive or a reference to an object. Where the value is a reference, then the thing it references has no idea what the "name" of the variable is.
Consider:
var foo = new MyThing();
var bar = foo;
So now what should foo.alertMyName() return? Or even:
(new MyThing()).alertMyName();
If you want instances to have a name, then give them a property and set its value to whatever suits.

util.inherits - how to call method of super on instance?

I'm playing with util.inherits method from node.js and can't seem to get the desired behavior.
var util = require("util");
function A() {
this.name = 'old';
}
A.prototype.log = function(){
console.log('my old name is: '+ this.name);
};
function B(){
A.call(this);
this.name = 'new';
}
util.inherits(B, A);
B.prototype.log = function(){
B.super_.prototype.log();
console.log('my new name is: ' + this.name);
}
var b = new B();
b.log();
The result is:
my old name is: undefined
my new name is: new
However what I would like is:
my old name is: new
my new name is: new
What am I missing?
Here's how to achieve what you are looking for:
B.prototype.log = function () {
B.super_.prototype.log.apply(this);
console.log('my new name is: ' + this.name);
};
This ensures the this context is the instance of B instead of being B.super_.prototype I suppose.
I prefer to call method of super through prototype chain instead of constructor chain like following.
var prototype = C.prototype;
prototype.log = function() {
Object.getPrototypeOf(prototype).log.call(this)
// or old style
prototype.__proto__.log.call(this)
}
They are all accessing prototype object of super class, but using prototype chain might be better than constructor.super_.prototype of constructor chain.
because usually I hide protected, private methods in separated files and under a prototype folder. Only public methods are with the constructor function in the same scope. In addition, to make them easy to move around different classes. All of them are named as prototype.method = function() {...}, so most of them can only access the prototype object.
Or it would be appreciated to know any benefit to go through constructor chain? This is why I found this post.

Accessing class and function after compiling ( CompiledAssembly )

Heres some example code. I successfully figured out how to compile this. I grabbed the location and was able to use visual studios object browser to look through the DLL. I cant figure out how to get a class instance and call a function.
public static void test()
{
JScriptCodeProvider js = new JScriptCodeProvider();
System.CodeDom.Compiler.CompilerParameters param = new System.CodeDom.Compiler.CompilerParameters();
var cr = js.CompileAssemblyFromSource(param, new string[] { "package pkg { class b { public function increment(x) { return x+1; } } }" });
foreach (var e in cr.Errors) {
var s = e.ToString();
}
var asm = cr.CompiledAssembly;
var module = cr.CompiledAssembly.GetModules();
//or var module = cr.CompiledAssembly.GetModule("JScript Module");
//...
}
Hmmm realy late on the answer but this is how you would invoke a method from a CodeDom compiled class
You have to use reflection to create an assembly from your compiler results...(your var cr)
Assembly assembly = cr.CompiledAssembly;
Then you have to create an instance of the class you want
object sourceClass = assembly.CreateInstance("YourNamespace.YourClass");
Then you invoke any method inside the class
var result = sourceClass.GetType().InvokeMember("YourMethod", BindingFlags.InvokeMethod, null, sourceClass, new object[] { *Parameters go here* });
And with that what ever the method you invoked had to returned would now be the value of the "result" var....pretty easy.

Resources