diff --git a/packages/@ember/-internals/metal/lib/observer.ts b/packages/@ember/-internals/metal/lib/observer.ts index 2de6b2887f1..67b5fb678d8 100644 --- a/packages/@ember/-internals/metal/lib/observer.ts +++ b/packages/@ember/-internals/metal/lib/observer.ts @@ -96,7 +96,7 @@ export function activateObserver(target: object, eventName: string, sync = false if (activeObservers.has(eventName)) { activeObservers.get(eventName)!.count++; } else { - let [path] = eventName.split(':'); + let path = eventName.substring(0, eventName.lastIndexOf(':')); let tag = getChainTagsForKey(target, path, tagMetaFor(target), peekMeta(target)); activeObservers.set(eventName, { diff --git a/packages/@ember/-internals/metal/tests/observer_test.js b/packages/@ember/-internals/metal/tests/observer_test.js index 161a535df06..1a78e8ea0c7 100644 --- a/packages/@ember/-internals/metal/tests/observer_test.js +++ b/packages/@ember/-internals/metal/tests/observer_test.js @@ -87,6 +87,21 @@ moduleFor( assert.equal(count, 1, 'should have invoked observer'); } + async ['@test observer supports keys with colons'](assert) { + obj = {}; + let count = 0; + + addObserver(obj, 'foo:bar:baz', function () { + assert.equal(get(obj, 'foo:bar:baz'), 'bar', 'should invoke AFTER value changed'); + count++; + }); + + set(obj, 'foo:bar:baz', 'bar'); + await runLoopSettled(); + + assert.equal(count, 1, 'should have invoked observer'); + } + async ['@test observer should fire when dependent property is modified'](assert) { obj = { bar: 'bar' }; defineProperty(