Index: src/object-observe.js |
diff --git a/src/object-observe.js b/src/object-observe.js |
index 9c7ac3889eb573b04ae6c4612dc5d4791174fda0..9fd611ae8f59eb1d15ad1e04fd05682770cb03a4 100644 |
--- a/src/object-observe.js |
+++ b/src/object-observe.js |
@@ -386,8 +386,28 @@ function ObserverEnqueueIfActive(observer, objectInfo, changeRecord, |
%SetObserverDeliveryPending(); |
} |
-function ObjectInfoEnqueueChangeRecord(objectInfo, changeRecord, |
- skipAccessCheck) { |
+function ObjectInfoEnqueueExternalChangeRecord(objectInfo, changeRecord, type) { |
+ if (!ObjectInfoHasActiveObservers(objectInfo)) |
+ return; |
+ |
+ var hasType = !IS_UNDEFINED(type); |
+ var newRecord = hasType ? |
+ { object: ObjectInfoGetObject(objectInfo), type: type } : |
+ { object: ObjectInfoGetObject(objectInfo) }; |
+ |
+ for (var prop in changeRecord) { |
arv (Not doing code reviews)
2013/10/23 14:48:34
Do we want inherited properties?
Do we want non e
|
+ if (prop === 'object' || (hasType && prop === 'type')) continue; |
+ %DefineOrRedefineDataProperty(newRecord, prop, changeRecord[prop], |
+ READ_ONLY + DONT_DELETE); |
+ } |
+ ObjectFreeze(newRecord); |
+ |
+ ObjectInfoEnqueueInternalChangeRecord(objectInfo, newRecord, |
+ true /* skip access check */); |
+} |
+ |
+function ObjectInfoEnqueueInternalChangeRecord(objectInfo, changeRecord, |
+ skipAccessCheck) { |
// TODO(rossberg): adjust once there is a story for symbols vs proxies. |
if (IS_SYMBOL(changeRecord.name)) return; |
@@ -435,7 +455,7 @@ function EnqueueSpliceRecord(array, index, removed, addedCount) { |
ObjectFreeze(changeRecord); |
ObjectFreeze(changeRecord.removed); |
- ObjectInfoEnqueueChangeRecord(objectInfo, changeRecord); |
+ ObjectInfoEnqueueInternalChangeRecord(objectInfo, changeRecord); |
} |
function NotifyChange(type, object, name, oldValue) { |
@@ -447,7 +467,7 @@ function NotifyChange(type, object, name, oldValue) { |
{ type: type, object: object, name: name } : |
{ type: type, object: object, name: name, oldValue: oldValue }; |
ObjectFreeze(changeRecord); |
- ObjectInfoEnqueueChangeRecord(objectInfo, changeRecord); |
+ ObjectInfoEnqueueInternalChangeRecord(objectInfo, changeRecord); |
} |
var notifierPrototype = {}; |
@@ -462,19 +482,7 @@ function ObjectNotifierNotify(changeRecord) { |
if (!IS_STRING(changeRecord.type)) |
throw MakeTypeError("observe_type_non_string"); |
- if (!ObjectInfoHasActiveObservers(objectInfo)) |
- return; |
- |
- var newRecord = { object: ObjectInfoGetObject(objectInfo) }; |
- for (var prop in changeRecord) { |
- if (prop === 'object') continue; |
- %DefineOrRedefineDataProperty(newRecord, prop, changeRecord[prop], |
- READ_ONLY + DONT_DELETE); |
- } |
- ObjectFreeze(newRecord); |
- |
- ObjectInfoEnqueueChangeRecord(objectInfo, newRecord, |
- true /* skip access check */); |
+ ObjectInfoEnqueueExternalChangeRecord(objectInfo, changeRecord); |
} |
function ObjectNotifierPerformChange(changeType, changeFn) { |
@@ -491,11 +499,16 @@ function ObjectNotifierPerformChange(changeType, changeFn) { |
throw MakeTypeError("observe_perform_non_function"); |
ObjectInfoAddPerformingType(objectInfo, changeType); |
+ |
+ var changeRecord; |
try { |
- %_CallFunction(UNDEFINED, changeFn); |
+ changeRecord = %_CallFunction(UNDEFINED, changeFn); |
} finally { |
ObjectInfoRemovePerformingType(objectInfo, changeType); |
} |
+ |
+ if (IS_SPEC_OBJECT(changeRecord)) |
+ ObjectInfoEnqueueExternalChangeRecord(objectInfo, changeRecord, changeType); |
} |
function ObjectGetNotifier(object) { |