简体   繁体   中英

node.js, require() and prototypal-inheritance

I'm pretty new to node.js, and probably javascript as well, so feel free to point out anything that seems awkward. I'm here to learn.

Here's what I'm trying to do:

  • "John" object should inherit everything from "Client" object, including functions
  • Use Object.create() instead of "new" keyword in instantiating new objects and inheritance

Here is a single file test that worked:

var sys=require('sys');
var Client = {
  ip: null,
  stream : null,
  state: "Connecting",
  eyes: 2,
  legs: 4,
  name: null,
  toString: function () {
      return this.name + " with " +
      this.eyes + " eyes and " +
      this.legs + " legs, " + this.state + ".";
  }
}
var john = Object.create(Client, {
  name: {value: "John", writable: true},
  state :  {value: "Sleeping", writable: true}
}); 
sys.puts(john); // John with 2 eyes and 4 legs, Sleeping

Here is what happens when I split it up into different files:

---- client.js ----

module.exports = function (instream, inip){
    return  {
         ip: inip,
          stream : instream,
          state: "Connecting",
          eyes: 2,
          legs: 4,
          name: null,
          toString: function () {
            return this.name + " with " +
              this.eyes + " eyes and " +
              this.legs + " legs, " + this.state + ".";
          },
    };

}; 

---- john.js ----

var Client = require("./client");
module.exports = function (inname, instate){
    return Object.create(Client, {
      state : {value: inname, enumerable: false, writable: true},
      name: {value: instate, enumerable: true, writable: true},
    });

};

---- main.js ----

var sys = require("util");
var Client = require("./client")("stream","168.192.0.1");
sys.puts(Client); // null with 2 eyes and 4 legs, Connecting

var john = require("./john")("John","Sleeping");
sys.puts(john); //Function.prototype.toString no generic 
sys.puts(sys.inspect(john)); // { name: 'Sleeping' }
sys.puts(sys.inspect(john, true)); // {name: 'Sleeping', [state]: 'John'}

Questions:

  1. What am I doing something wrong in splitting up the files and in my use of require() that's causing the problems?
  2. Why does the john object have 'Sleeping' as name and 'John' as state? I know it's the order I put the lines, but should it not follow the parameters that I've put in the constructor?
  3. Is there a better way of doing this? I'm inclined to learn Object.create() rather than rely on the "new" keyword.

On #2:

return Object.create(Client, {
  state : {value: inname, enumerable: false, writable: true},
  name: {value: instate, enumerable: true, writable: true},
});

That's a simple mistyping on your side swapping inname and instate .

On #1:

I suspect another slight difference between the original single-file code and the new 3 file code is at fault. A particular comment caught my eye on MDN's page on Object.create , specifically,

Of course, if there is actual initialization code in the Constructor function, the Object.create cannot reflect it

Your client.js file is producing a constructor function. What you meant to write in john.js is (combining #1 and #2):

return Object.create(Client(), {
  state : {value: instate, enumerable: false, writable: true},
  name: {value: inname, enumerable: true, writable: true},
});

Call the Client function so it returns an object rather than a function, and then create a new object built on top of that.

On #3:

I don't see why you couldn't use this pattern, but you have just demonstrated that it is:

  1. Foreign to how most Javascript objects are created today (though no doubt a faster construction mechanism).
  2. Using a newer syntax (that drops new ) so syntax errors don't "jump out" at you like with the old, Java-style syntax.

Just keep that in mind. I'm glad you asked this question, though, because now I know about Object.create . :)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM