mirror of
https://github.com/jashkenas/coffeescript.git
synced 2022-11-09 12:23:24 -05:00
195 lines
3.4 KiB
CoffeeScript
195 lines
3.4 KiB
CoffeeScript
# Object Literals
|
|
# ---------------
|
|
|
|
# TODO: refactor object literal tests
|
|
# TODO: add indexing and method invocation tests: {a}['a'] is a, {a}.a()
|
|
|
|
trailingComma = {k1: "v1", k2: 4, k3: (-> true),}
|
|
ok trailingComma.k3() and (trailingComma.k2 is 4) and (trailingComma.k1 is "v1")
|
|
|
|
ok {a: (num) -> num is 10 }.a 10
|
|
|
|
moe = {
|
|
name: 'Moe'
|
|
greet: (salutation) ->
|
|
salutation + " " + @name
|
|
hello: ->
|
|
@['greet'] "Hello"
|
|
10: 'number'
|
|
}
|
|
ok moe.hello() is "Hello Moe"
|
|
ok moe[10] is 'number'
|
|
moe.hello = ->
|
|
this['greet'] "Hello"
|
|
ok moe.hello() is 'Hello Moe'
|
|
|
|
obj = {
|
|
is: -> yes,
|
|
'not': -> no,
|
|
}
|
|
ok obj.is()
|
|
ok not obj.not()
|
|
|
|
### Top-level object literal... ###
|
|
obj: 1
|
|
### ...doesn't break things. ###
|
|
|
|
# Object literals should be able to include keywords.
|
|
obj = {class: 'höt'}
|
|
obj.function = 'dog'
|
|
ok obj.class + obj.function is 'hötdog'
|
|
|
|
# Implicit objects as part of chained calls.
|
|
pluck = (x) -> x.a
|
|
eq 100, pluck pluck pluck a: a: a: 100
|
|
|
|
|
|
test "YAML-style object literals", ->
|
|
obj =
|
|
a: 1
|
|
b: 2
|
|
eq 1, obj.a
|
|
eq 2, obj.b
|
|
|
|
config =
|
|
development:
|
|
server: 'localhost'
|
|
timeout: 10
|
|
|
|
production:
|
|
server: 'dreamboat'
|
|
timeout: 1000
|
|
|
|
ok config.development.server is 'localhost'
|
|
ok config.production.server is 'dreamboat'
|
|
ok config.development.timeout is 10
|
|
ok config.production.timeout is 1000
|
|
|
|
obj =
|
|
a: 1,
|
|
b: 2,
|
|
ok obj.a is 1
|
|
ok obj.b is 2
|
|
|
|
# Implicit objects nesting.
|
|
obj =
|
|
options:
|
|
value: yes
|
|
fn: ->
|
|
{}
|
|
null
|
|
ok obj.options.value is yes
|
|
ok obj.fn() is null
|
|
|
|
# Implicit objects with wacky indentation:
|
|
obj =
|
|
'reverse': (obj) ->
|
|
Array.prototype.reverse.call obj
|
|
abc: ->
|
|
@reverse(
|
|
@reverse @reverse ['a', 'b', 'c'].reverse()
|
|
)
|
|
one: [1, 2,
|
|
a: 'b'
|
|
3, 4]
|
|
red:
|
|
orange:
|
|
yellow:
|
|
green: 'blue'
|
|
indigo: 'violet'
|
|
misdent: [[],
|
|
[],
|
|
[],
|
|
[]]
|
|
ok obj.abc().join(' ') is 'a b c'
|
|
ok obj.one.length is 5
|
|
ok obj.one[4] is 4
|
|
ok obj.one[2].a is 'b'
|
|
ok (key for key of obj.red).length is 2
|
|
ok obj.red.orange.yellow.green is 'blue'
|
|
ok obj.red.indigo is 'violet'
|
|
ok obj.misdent.toString() is ',,,'
|
|
|
|
#542: Objects leading expression statement should be parenthesized.
|
|
{f: -> ok yes }.f() + 1
|
|
|
|
# String-keyed objects shouldn't suppress newlines.
|
|
one =
|
|
'>!': 3
|
|
six: -> 10
|
|
ok not one.six
|
|
|
|
# Shorthand objects with property references.
|
|
obj =
|
|
### comment one ###
|
|
### comment two ###
|
|
one: 1
|
|
two: 2
|
|
object: -> {@one, @two}
|
|
list: -> [@one, @two]
|
|
result = obj.object()
|
|
eq result.one, 1
|
|
eq result.two, 2
|
|
eq result.two, obj.list()[1]
|
|
|
|
third = (a, b, c) -> c
|
|
obj =
|
|
one: 'one'
|
|
two: third 'one', 'two', 'three'
|
|
ok obj.one is 'one'
|
|
ok obj.two is 'three'
|
|
|
|
test "invoking functions with implicit object literals", ->
|
|
generateGetter = (prop) -> (obj) -> obj[prop]
|
|
getA = generateGetter 'a'
|
|
getArgs = -> arguments
|
|
a = b = 30
|
|
|
|
result = getA
|
|
a: 10
|
|
eq 10, result
|
|
|
|
result = getA
|
|
"a": 20
|
|
eq 20, result
|
|
|
|
result = getA a,
|
|
b:1
|
|
eq undefined, result
|
|
|
|
result = getA b:1
|
|
a:43
|
|
eq 43, result
|
|
|
|
result = getA b:1,
|
|
a:62
|
|
eq undefined, result
|
|
|
|
result = getA
|
|
b:1
|
|
a
|
|
eq undefined, result
|
|
|
|
result = getA
|
|
a:
|
|
b:2
|
|
b:1
|
|
eq 2, result.b
|
|
|
|
result = getArgs
|
|
a:1
|
|
b
|
|
c:1
|
|
ok result.length is 3
|
|
ok result[2].c is 1
|
|
|
|
test "some weird indentation in YAML-style object literals", ->
|
|
two = (a, b) -> b
|
|
obj = then two 1,
|
|
1: 1
|
|
a:
|
|
b: ->
|
|
fn c,
|
|
d: e
|
|
f: 1
|
|
eq 1, obj[1]
|