5

I have a function that has a constructor within it. It creates a new object and returns it:

function car() {
   function Car() {}
   return new Car();
}

As a result uglify renames Car to some letter and when this returns it looks like the object name is just some letter. In chrome for instance it will say the type of the object is "t".

Is there a way to tell uglify to preserve some function's name?

Parris
  • 17,833
  • 17
  • 90
  • 133
  • 1
    Why does it matter? Just for debugging purposes? You shouldn't be using the uglified version for debugging anyway. – Ruan Mendes Oct 09 '12 at 19:44
  • I'd say it is more semantic than anything else. If you are exposing a library out to people they should know what type of object they are working with. – Parris Oct 09 '12 at 19:46
  • How does it help to know that the name of the constructor is `Car`? It looks like you are trying to keep it private so there should be no need for users of your library to know what the name of the constructor is. If it's a public object, there's no need to declare it within the function. – Ruan Mendes Oct 09 '12 at 19:52
  • 1
    I believe that there are people out there that check type based on the name of an object: http://stackoverflow.com/questions/332422/how-do-i-get-the-name-of-an-objects-type-in-javascript Which may be useful in some cases? Hmmm.. perhaps not? – Parris Oct 09 '12 at 20:17

2 Answers2

10

You need to use the reserved-names parameter:

--reserved-names “Car”
Bill
  • 25,119
  • 8
  • 94
  • 125
6

Even if you follow Bill's suggestion, there's still a problem with your approach.

car().constructor !== car().constructor

One would expect those to be equal

I would change your approach to creating a constructor and giving it a Factory constructor

/** @private */
function Car() {
   ...
}

Car.create = function() {
    return new Car();
}

Or the following (module pattern), combined with Bill's approach. Then you're not returning an object with a different prototype every time

var car  = (function() {
   function Car() {...}
   return function() {
       return new Car();
   }
})();

// car().constructor === car().constructor // true
Daryn
  • 4,791
  • 4
  • 39
  • 52
Ruan Mendes
  • 90,375
  • 31
  • 153
  • 217
  • I think I am doing this, except the extra returning of a function at the end: https://github.com/parris/iz/blob/master/iz.js#L388 , why return function() { return new Car(); } why not just directly return a new Car? – Parris Oct 09 '12 at 20:15
  • 3
    @Parris Because this way, a new constructor `Car` is not being created every time you call `car()`. The self calling function puts the constructor into a closure and uses the same one every time. Your example re-declares `function Car() {}` every time – Ruan Mendes Oct 09 '12 at 21:28