Add support for dashes in variable names, mangle them #2345

paulmillr opened this Issue May 18, 2012 · 8 comments


None yet

5 participants


Why dashes?

  1. More readable than underscores.
  2. JS has its own variable naming style (camelCase), which obviously sucks in readability.
  3. Vars with dashes are invalid in js, so if we'll compile it with mangling, it won't violate js naming style.


  1. It would add more complexity
  2. - will be prohibited from using as OP without indenation like a - b (which is good IMO).


add-user = (name, age) -> ...
remove-users-with-age = (age) ->
  remove-user user for user in users when user.age is age
add-users = (users) ->
  add-user user for user in users
class Thread-post
addUser ...
removeUsersWithAge ...
addUsers ...
ThreadPost ...


Clojure. Pretty readable.


We've talked about doing this before -- see previous tickets. The reason why we don't is because it breaks interoperability with JavaScript, and with naming properties on your object at runtime.

If CoffeeScript was an entirely new engine, we would absolutely use dashes -- but it isn't, so we have to use JS identifiers.

@jashkenas jashkenas closed this May 21, 2012

Not sure how exactly it breaks interop with js.

JS module:

exports.forEach = function() {return 1};
exports['for-each'] = function() {return 2}
exports.reduceLeft = function() {return 3};

Coffee module analog:

exports.for-each = -> 1
exports['for-each'] = -> 2
exports.reduce-left = -> 3

So, because exports.for-each can't be done at the runtime (only exports['for-each'] can), it won't break it. Coffee would be able to reuse existing js code.


user = document.query-selector('.user')
user.add-event-listener 'click', ((event) -> console.log event), yes

id = window.set-interval ->
  console.log 'hello'
, 1000
window.set-timeout (-> window.clear-timeout id), 1500

encoded = encode-URI-component string
number = parse-int '5'
string =!

page-text = document.query-selector('body').inner-text
logged-in = $('body').has-class 'logged-in'
obj = {a: 1, b: 2}
descriptors = Object.get-own-property-names(obj)
  .map((name) -> Object.get-property-descriptor obj, name)

I never really understood the interoperability argument from @jashkenas. See #1452, #1982, #918, #1334, #425 where he makes this argument.


All that I mean by "interoperability" is that functions and variables are named the same thing in JS as they are in CoffeeScript. If you always have to do the mental translation between the two names, interoperability suffers. Especially when properties can be named dynamically.

method = object[name]

Should name be written as "toString", or "to-string"? Does it depend if you originally defined it with a string, or with a raw identifier? We don't want to open that can of worms.



o = {parse-int}

Should o be {parseInt: parseInt} or {"parse-int": parseInt}?


@satyr the first one. Just one simple rule: identifiers (whatever these are called) always mangled.

parse-int without string is identifier (etc). 'parse-int' isn't.


Sounds like workable. After all:

coffee> o = {}; o[on] = yes; o
{ true: true }


Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment