From 89935954b55d1f529fd8d1d39c560961a5d14032 Mon Sep 17 00:00:00 2001 From: "bigopon.777@gmail.com" Date: Sat, 2 Mar 2019 11:25:00 +1100 Subject: [PATCH 1/2] fix(name-binding): add extra props to update one time mode --- src/name-expression.js | 22 ++++++++++++++++++---- test/name-expression.spec.js | 21 +++++++++++++++++++++ 2 files changed, 39 insertions(+), 4 deletions(-) diff --git a/src/name-expression.js b/src/name-expression.js index eb6f31ce..ee83d004 100644 --- a/src/name-expression.js +++ b/src/name-expression.js @@ -1,3 +1,5 @@ +import { bindingMode } from './binding-mode'; + function getAU(element) { let au = element.au; @@ -43,10 +45,17 @@ export class NameExpression { } class NameBinder { + /** + * Name binding for reference + * @param {Expression} sourceExpression + * @param {any} target + * @param {any} lookupFunctions + */ constructor(sourceExpression, target, lookupFunctions) { this.sourceExpression = sourceExpression; this.target = target; this.lookupFunctions = lookupFunctions; + this.mode = bindingMode.oneTime; } bind(source) { @@ -64,16 +73,21 @@ class NameBinder { this.sourceExpression.assign(this.source, this.target, this.lookupFunctions); } + call() { + this.sourceExpression.assign(this.source, this.target, this.lookupFunctions); + } + unbind() { if (!this.isBound) { return; } this.isBound = false; - if (this.sourceExpression.evaluate(this.source, this.lookupFunctions) === this.target) { - this.sourceExpression.assign(this.source, null, this.lookupFunctions); + const { source, lookupFunctions, sourceExpression } = this; + if (sourceExpression.evaluate(source, lookupFunctions) === this.target) { + sourceExpression.assign(source, null, lookupFunctions); } - if (this.sourceExpression.unbind) { - this.sourceExpression.unbind(this, this.source); + if (sourceExpression.unbind) { + sourceExpression.unbind(this, source); } this.source = null; } diff --git a/test/name-expression.spec.js b/test/name-expression.spec.js index 43f1895b..595cc3e2 100644 --- a/test/name-expression.spec.js +++ b/test/name-expression.spec.js @@ -8,6 +8,7 @@ import { } from '../src/ast'; import {createScopeForTest} from '../src/scope'; import {NameExpression} from '../src/name-expression'; +import { bindingMode } from '../src/binding-mode'; describe('NameExpression', () => { let element; @@ -23,6 +24,13 @@ describe('NameExpression', () => { }; }); + it('creates one time binding mode binding', () => { + let sourceExpression = new AccessScope('foo'); + let expression = new NameExpression(sourceExpression, 'element'); + let binding = expression.createBinding(element); + expect(binding.mode).toBe(bindingMode.oneTime); + }); + it('binds element to scope', () => { let sourceExpression = new AccessScope('foo'); let expression = new NameExpression(sourceExpression, 'element'); @@ -104,4 +112,17 @@ describe('NameExpression', () => { binding.unbind(); expect(scope.bindingContext.foo).toBe('should remain'); }); + + it('re-assigns value when invoking call()', () => { + let sourceExpression = new AccessScope('foo'); + let expression = new NameExpression(sourceExpression, 'element'); + let scope = createScopeForTest({}); + let binding = expression.createBinding(element); + binding.bind(scope); + expect(scope.bindingContext.foo).toBe(element); + scope.bindingContext.foo = null; + expect(binding.target).toBe(element); + binding.call(); + expect(scope.bindingContext.foo).toBe(element); + }); }); From 5412fb6ca96548f38562d71ab4c0fd9e55578e45 Mon Sep 17 00:00:00 2001 From: "bigopon.777@gmail.com" Date: Sat, 2 Mar 2019 11:36:48 +1100 Subject: [PATCH 2/2] fix(name-binding): add unbound guard --- src/name-expression.js | 3 +++ test/name-expression.spec.js | 17 +++++++++++++++++ 2 files changed, 20 insertions(+) diff --git a/src/name-expression.js b/src/name-expression.js index ee83d004..06d43c3d 100644 --- a/src/name-expression.js +++ b/src/name-expression.js @@ -74,6 +74,9 @@ class NameBinder { } call() { + if (!this.isBound) { + return; + } this.sourceExpression.assign(this.source, this.target, this.lookupFunctions); } diff --git a/test/name-expression.spec.js b/test/name-expression.spec.js index 595cc3e2..44b8bf06 100644 --- a/test/name-expression.spec.js +++ b/test/name-expression.spec.js @@ -125,4 +125,21 @@ describe('NameExpression', () => { binding.call(); expect(scope.bindingContext.foo).toBe(element); }); + + it('does nothing when not bound + invoking call()', () => { + let sourceExpression = new AccessScope('foo'); + let expression = new NameExpression(sourceExpression, 'element'); + let scope = createScopeForTest({}); + let binding = expression.createBinding(element); + binding.bind(scope); + expect(scope.bindingContext.foo).toBe(element); + scope.bindingContext.foo = null; + expect(binding.target).toBe(element); + binding.isBound = false; + binding.call(); + expect(scope.bindingContext.foo).toBe(null); + binding.isBound = true; + binding.call(); + expect(scope.bindingContext.foo).toBe(element); + }); });