| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511 |
- describe('UNIT: Observer', function () {
- var Observer = require('vue/src/observer'),
- Emitter = require('emitter'),
- DepsOb = require('vue/src/deps-parser').observer
-
- describe('Observing Object', function () {
- it('should not watch a ViewModel instance', function () {
- var obj = new Vue(), ob = new Emitter()
- Observer.observe(obj, 'test', ob)
- assert.notOk(obj.__observer__)
- })
-
- it('should attach hidden observer and values to the object', function () {
- var obj = {}, ob = new Emitter()
- Observer.observe(obj, 'test', ob)
- assert.ok(obj.__observer__ instanceof Emitter)
- assert.ok(obj.__observer__.values)
- })
- it('should emit set events with correct path', setTestFactory({
- obj: { a: 1, b: { c: 2 } },
- expects: [
- { key: 'test.a', val: 1 },
- { key: 'test.b.c', val: 3 }
- ],
- path: 'test'
- }))
- it('should emit multiple events when a nested object is set', setTestFactory({
- obj: { a: 1, b: { c: 2 } },
- expects: [
- { key: 'test.b', val: { c: 3 } },
- { key: 'test.b.c', val: 3, skip: true }
- ],
- path: 'test'
- }))
- it('should emit get events on tip values', function () {
- DepsOb.active = true
- getTestFactory({
- obj: { a: 1, b: { c: 2 } },
- expects: [
- 'test.a',
- 'test.b.c'
- ],
- path: 'test'
- })()
- DepsOb.active = false
- })
- it('should emit set when first observing', function () {
- var obj = { a: 1, b: { c: 2} },
- ob = new Emitter(), i = 0
- var expects = [
- { key: 'test.a', val: obj.a },
- { key: 'test.b', val: obj.b },
- { key: 'test.b.c', val: obj.b.c }
- ]
- ob.on('set', function (key, val) {
- var exp = expects[i]
- assert.strictEqual(key, exp.key)
- assert.strictEqual(val, exp.val)
- i++
- })
- Observer.observe(obj, 'test', ob)
- assert.strictEqual(i, expects.length)
- })
- it('should emit set when watching an already observed object', function () {
- var obj = { a: 1, b: { c: 2} },
- ob1 = new Emitter(),
- ob2 = new Emitter(),
- i = 0
- Observer.observe(obj, 'test', ob1) // watch first time
- var expects = [
- { key: 'test.a', val: obj.a },
- { key: 'test.b', val: obj.b },
- { key: 'test.b.c', val: obj.b.c }
- ]
- ob2.on('set', function (key, val) {
- console.log(key)
- var exp = expects[i]
- assert.strictEqual(key, exp.key)
- assert.strictEqual(val, exp.val)
- i++
- })
- Observer.observe(obj, 'test', ob2) // watch again
- assert.strictEqual(i, expects.length)
- })
- })
- describe('Observing Array', function () {
- var arr = [],
- ob = new Emitter()
- Observer.observe(arr, 'test', ob)
-
- it('should attach the hidden observer', function () {
- assert.ok(arr.__observer__ instanceof Emitter)
- })
- it('should overwrite the native array mutator methods', function () {
- ['push', 'pop', 'shift', 'unshift', 'splice', 'sort', 'reverse'].forEach(function (method) {
- assert.notStrictEqual(arr[method], Array.prototype[method])
- })
- })
- it('should emit set for .length when it mutates', function () {
- var emitted = false
- ob.once('set', function (key, val) {
- assert.strictEqual(key, 'test.length')
- assert.strictEqual(val, 1)
- emitted = true
- })
- arr.push(1)
- assert.ok(emitted)
- })
- describe('Mutator Methods', function () {
-
- it('push', function () {
- var arg1 = 123,
- arg2 = 234,
- emitted = false
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(array.length, 3)
- assert.strictEqual(mutation.method, 'push')
- assert.strictEqual(mutation.args.length, 2)
- assert.strictEqual(mutation.args[0], arg1)
- assert.strictEqual(mutation.args[1], arg2)
- assert.strictEqual(mutation.result, arr.length)
- emitted = true
- })
- var r = arr.push(arg1, arg2)
- assert.ok(emitted)
- assert.strictEqual(r, arr.length)
- })
- it('pop', function () {
- var emitted = false,
- expected = arr[arr.length - 1]
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(array.length, 2)
- assert.strictEqual(mutation.method, 'pop')
- assert.strictEqual(mutation.args.length, 0)
- assert.strictEqual(mutation.result, expected)
- emitted = true
- })
- var r = arr.pop()
- assert.ok(emitted)
- assert.strictEqual(r, expected)
- })
- it('shift', function () {
- var emitted = false,
- expected = arr[0]
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(array.length, 1)
- assert.strictEqual(mutation.method, 'shift')
- assert.strictEqual(mutation.args.length, 0)
- assert.strictEqual(mutation.result, expected)
- emitted = true
- })
- var r = arr.shift()
- assert.ok(emitted)
- assert.strictEqual(r, expected)
- })
- it('unshift', function () {
- var emitted = false,
- arg1 = 456,
- arg2 = 678
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(array.length, 3)
- assert.strictEqual(mutation.method, 'unshift')
- assert.strictEqual(mutation.args.length, 2)
- assert.strictEqual(mutation.args[0], arg1)
- assert.strictEqual(mutation.args[1], arg2)
- assert.strictEqual(mutation.result, arr.length)
- emitted = true
- })
- var r = arr.unshift(arg1, arg2)
- assert.ok(emitted)
- assert.strictEqual(r, arr.length)
- })
- it('splice', function () {
- var emitted = false,
- arg1 = 789,
- arg2 = 910,
- expected = arr[1]
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(array.length, 4)
- assert.strictEqual(mutation.method, 'splice')
- assert.strictEqual(mutation.args.length, 4)
- assert.strictEqual(mutation.args[0], 1)
- assert.strictEqual(mutation.args[1], 1)
- assert.strictEqual(mutation.args[2], arg1)
- assert.strictEqual(mutation.args[3], arg2)
- assert.strictEqual(mutation.result.length, 1)
- assert.strictEqual(mutation.result[0], expected)
- emitted = true
- })
- var r = arr.splice(1, 1, arg1, arg2)
- assert.ok(emitted)
- assert.strictEqual(r.length, 1)
- assert.strictEqual(r[0], expected)
- })
- it('sort', function () {
- var emitted = false,
- sorter = function (a, b) {
- return a > b ? -1 : 1
- },
- copy = arr.slice().sort(sorter)
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(mutation.method, 'sort')
- assert.strictEqual(mutation.args.length, 1)
- assert.strictEqual(mutation.result, arr)
- for (var i = 0; i < copy.length; i++) {
- assert.strictEqual(array[i], copy[i])
- }
- emitted = true
- })
- var r = arr.sort(sorter)
- assert.ok(emitted)
- assert.strictEqual(r, arr)
- })
- it('reverse', function () {
- var emitted = false,
- copy = arr.slice().reverse()
- ob.once('mutate', function (key, array, mutation) {
- assert.strictEqual(key, 'test')
- assert.strictEqual(array, arr)
- assert.strictEqual(mutation.method, 'reverse')
- assert.strictEqual(mutation.args.length, 0)
- assert.strictEqual(mutation.result, arr)
- for (var i = 0; i < copy.length; i++) {
- assert.strictEqual(array[i], copy[i])
- }
- emitted = true
- })
- var r = arr.reverse()
- assert.ok(emitted)
- assert.strictEqual(r, arr)
- })
- })
- describe('Augmentations', function () {
- it('remove (index)', function () {
- var emitted = false,
- index = ~~(Math.random() * arr.length),
- expected = arr[index] = { a: 1 }
- ob.once('mutate', function (key, array, mutation) {
- emitted = true
- assert.strictEqual(mutation.method, 'splice')
- assert.strictEqual(mutation.args.length, 2)
- assert.strictEqual(mutation.args[0], index)
- })
- var r = arr.remove(index)
- assert.ok(emitted)
- assert.strictEqual(r, expected)
- })
-
- it('remove (object)', function () {
- var emitted = false,
- index = ~~(Math.random() * arr.length),
- expected = arr[index] = { a: 1 }
- ob.once('mutate', function (key, array, mutation) {
- emitted = true
- assert.strictEqual(mutation.method, 'splice')
- assert.strictEqual(mutation.args.length, 2)
- assert.strictEqual(mutation.args[0], index)
- })
- var r = arr.remove(expected)
- assert.ok(emitted)
- assert.strictEqual(r, expected)
- })
- it('remove (function)', function () {
- var expected = [1001, 1002]
- arr.push.apply(arr, expected)
- var filter = function (e) {
- return e > 1000
- },
- copy = arr.filter(function (e) {
- return e <= 1000
- })
- var removed = arr.remove(filter)
- assert.deepEqual(arr, copy)
- assert.deepEqual(expected, removed)
- })
- it('replace (index)', function () {
- var emitted = false,
- index = ~~(Math.random() * arr.length),
- expected = arr[index] = { a: 1 },
- arg = 34567
- ob.once('mutate', function (key, array, mutation) {
- emitted = true
- assert.strictEqual(mutation.method, 'splice')
- assert.strictEqual(mutation.args.length, 3)
- assert.strictEqual(mutation.args[0], index)
- })
- var r = arr.replace(index, arg)
- assert.ok(emitted)
- assert.strictEqual(r, expected)
- assert.strictEqual(arr[index], arg)
- })
- it('replace (object)', function () {
- var emitted = false,
- index = ~~(Math.random() * arr.length),
- expected = arr[index] = { a: 1 },
- arg = 45678
- ob.once('mutate', function (key, array, mutation) {
- emitted = true
- assert.strictEqual(mutation.method, 'splice')
- assert.strictEqual(mutation.args.length, 3)
- assert.strictEqual(mutation.args[0], index)
- })
- var r = arr.replace(expected, arg)
- assert.ok(emitted)
- assert.strictEqual(r, expected)
- assert.strictEqual(arr[index], arg)
- })
- it('replace (function)', function () {
- arr[0] = 1
- arr[1] = 2
- arr[2] = 3
- var expected = [2, 3, 3],
- expectRet = [1, 2]
- var replaced = arr.replace(function (e) {
- if (e < 3) return e + 1
- })
- assert.deepEqual(arr, expected)
- assert.deepEqual(replaced, expectRet)
- })
- })
- })
- describe('Multiple observers', function () {
- var ob1 = new Emitter(),
- ob2 = new Emitter(),
- obj = {a:1}
- Observer.observe(obj, 'test', ob1)
- Observer.observe(obj, 'test', ob2)
- var ob1Called = false,
- ob2Called = false
- ob1.on('set', function () {
- ob1Called = true
- })
- ob2.on('set', function () {
- ob2Called = true
- })
- it('should trigger events for multiple observers observing the same object', function () {
- obj.a = 2
- assert.ok(ob1Called)
- assert.ok(ob2Called)
- })
- })
- describe('.unobserve()', function () {
-
- var ob1 = new Emitter(),
- ob2 = new Emitter(),
- obj = {a:1}
- Observer.observe(obj, 'test', ob1)
- Observer.observe(obj, 'test', ob2)
- Observer.unobserve(obj, 'test', ob1)
- var ob1Called = false
- ob1.on('set', function () {
- ob1Called = true
- })
- var ob2Called = false
- ob2.on('set', function () {
- ob2Called = true
- })
- it('should set observer proxies path to null', function () {
- assert.strictEqual(ob1.proxies['test.'], null)
- })
- it('should turn off corresponding event listeners', function () {
- var callbacks = obj.__observer__._callbacks
- for (var e in callbacks) {
- assert.strictEqual(callbacks[e].length, 1)
- }
- })
- it('should no longer emit events', function () {
- obj.a = 2
- assert.notOk(ob1Called)
- assert.ok(ob2Called)
- })
- })
- describe('.ensurePath()', function () {
-
- it('should ensure a path can be accessed without error', function () {
- var obj = {},
- path = 'a.b.c'
- Observer.ensurePath(obj, path)
- assert.strictEqual(obj.a.b.c, undefined)
- })
- })
- describe('.ensurePaths()', function () {
-
- it('should ensure path for all paths that start with the given key', function () {
- var key = 'a',
- obj = {},
- paths = {
- 'a.b.c': 1,
- 'a.d': 2,
- 'e.f': 3,
- 'g': 4
- }
- Observer.ensurePaths(key, obj, paths)
- assert.strictEqual(obj.b.c, undefined)
- assert.strictEqual(obj.d, undefined)
- assert.notOk('f' in obj)
- assert.strictEqual(Object.keys(obj).length, 2)
- })
- })
- function setTestFactory (opts) {
- return function () {
- var ob = new Emitter(),
- i = 0,
- obj = opts.obj,
- expects = opts.expects
- Observer.observe(obj, opts.path, ob)
- ob.on('set', function (key, val) {
- var expect = expects[i]
- assert.strictEqual(key, expect.key)
- assert.strictEqual(val, expect.val)
- i++
- })
- expects.forEach(function (expect) {
- if (expect.skip) return
- var path = expect.key.split('.'),
- j = 1,
- scope = obj
- while (j < path.length - 1) {
- scope = scope[path[j]]
- j++
- }
- scope[path[j]] = expect.val
- })
- assert.strictEqual(i, expects.length)
- }
- }
- function getTestFactory (opts) {
- return function () {
- var ob = new Emitter(),
- i = 0,
- obj = opts.obj,
- expects = opts.expects
- Observer.observe(obj, opts.path, ob)
- ob.on('get', function (key) {
- var expected = expects[i]
- assert.strictEqual(key, expected)
- i++
- })
- expects.forEach(function (key) {
- var path = key.split('.'),
- j = 1,
- scope = obj
- while (j < path.length) {
- scope = scope[path[j]]
- j++
- }
- })
- assert.strictEqual(i, expects.length)
- }
- }
- })
|