Skip to content

Commit

Permalink
Merge pull request #190 from knockout/root-filter-not-transitive
Browse files Browse the repository at this point in the history
Root filter not transitive
  • Loading branch information
brianmhunt authored Dec 10, 2024
2 parents 1533d60 + 3b47c2c commit 1acc633
Show file tree
Hide file tree
Showing 5 changed files with 45 additions and 4 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
For TODO between alpha and release, see https://github.com/knockout/tko/issues/1

## Beta 1.6

- Fix |filter1|filter2 filter2 not having root
- In the Knockout build, don't convert evil twins (`==`/`!=`) to strict counterparts (`===`/`!==`)

## Beta 1.5

- Make optional chaining the default for property lookups
Expand Down
6 changes: 6 additions & 0 deletions builds/reference/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,12 @@ import { filters } from '@tko/filter.punches'
import components from '@tko/utils.component'
import { createElement, Fragment } from '@tko/utils.jsx'

import { overloadOperator } from 'packages/utils.parser'

/** Overload "evil twins" with strict equivalents */
overloadOperator('==', (a, b) => a === b)
overloadOperator('!=', (a, b) => a !== b)

const builder = new Builder({
filters,
provider: new MultiProvider({
Expand Down
21 changes: 21 additions & 0 deletions packages/utils.parser/spec/filterBehaviors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -87,4 +87,25 @@ describe('filters', function () {
assert.equal(p.b(), 'ttey')
assert.equal(p.c(), 'ttez')
})

describe('root', () => {
let _testRoot = null
options.filters.setRoot = function (v) {
_testRoot = this
}

it('preserves the root across a single filter', () => {
const ourRoot = ctxStub({v: 'tt'})
const p = new Parser().parse('b: v | setRoot', ourRoot)
p.b()
assert.equal(_testRoot, ourRoot)
})

it('preserves the root across a multiple filters', () => {
const ourRoot = ctxStub({v: 'tt'})
const p = new Parser().parse('b: v | uppercase | setRoot', ourRoot)
p.b()
assert.strictEqual(_testRoot.lookup, ourRoot.lookup)
})
})
})
8 changes: 4 additions & 4 deletions packages/utils.parser/src/Parser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -433,14 +433,14 @@ export default class Parser {
ch = this.white()
}

var filter = function filter (value, ignored, context, globals, node) {
function filter (value, ignored, context, globals, node) {
var argValues = [value]

for (var i = 0, j = args.length; i < j; ++i) {
argValues.push(Node.value_of(args[i], context, globals, node))
}

return nextFilter(options.filters[name].apply(context, argValues))
return nextFilter(options.filters[name].apply(context, argValues), ignored, context, globals, node)
}

// Lowest precedence.
Expand All @@ -460,7 +460,7 @@ export default class Parser {
* allowed in this expression. When true (default), this method consumes
* subsequent comma-separated values.
* @see {@link Parser.singleValueExpression}
*
*
* @returns a function that computes the value of the expression
* when called or a primitive.
*/
Expand Down Expand Up @@ -555,7 +555,7 @@ export default class Parser {
/**
* Use this method to parse expressions that can be followed by additional markup
* seperated by a comma, such as in bindings strings.
*
*
* @returns an expression that cannot contain multiple values separated by commas.
* @see {@link Parser.expression}
*/
Expand Down
9 changes: 9 additions & 0 deletions packages/utils.parser/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import operators from './operators'

export {default as Parser} from './Parser'
export {default as Identifier} from './Identifier'
Expand All @@ -6,3 +7,11 @@ export {default as Ternary} from './Ternary'
export {default as Node} from './Node'

export {default as parseObjectLiteral} from './preparse'


export function overloadOperator (op: string, fn: (a, b) => any, precedence?: number) {
operators[op] = fn
if (Number.isInteger(precedence)) {
operators[op].precedence = precedence
}
}

0 comments on commit 1acc633

Please sign in to comment.