Skip to content

Commit 5eddfd0

Browse files
author
Evan You
committed
make array filters work with objects
1 parent a249992 commit 5eddfd0

File tree

6 files changed

+99
-47
lines changed

6 files changed

+99
-47
lines changed

src/directives/repeat.js

Lines changed: 1 addition & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -305,7 +305,7 @@ module.exports = {
305305

306306
this.object = object
307307
var self = this,
308-
collection = objectToArray(object)
308+
collection = utils.objectToArray(object)
309309

310310
this.syncRepeater = function (key, val) {
311311
if (key in object) {
@@ -376,22 +376,6 @@ module.exports = {
376376

377377
// Helpers --------------------------------------------------------------------
378378

379-
/**
380-
* Convert an Object to a v-repeat friendly Array
381-
*/
382-
function objectToArray (obj) {
383-
var res = [], val, data
384-
for (var key in obj) {
385-
val = obj[key]
386-
data = utils.typeOf(val) === 'Object'
387-
? val
388-
: { $value: val }
389-
data.$key = key
390-
res.push(data)
391-
}
392-
return res
393-
}
394-
395379
/**
396380
* Find an object or a wrapped data object
397381
* from an Array

src/filters.js

Lines changed: 38 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -14,32 +14,6 @@ var keyCodes = {
1414
esc : 27
1515
}
1616

17-
/**
18-
* String contain helper
19-
*/
20-
function contains (val, search) {
21-
/* jshint eqeqeq: false */
22-
if (utils.typeOf(val) === 'Object') {
23-
for (var key in val) {
24-
if (contains(val[key], search)) {
25-
return true
26-
}
27-
}
28-
} else if (val != null) {
29-
return val.toString().toLowerCase().indexOf(search) > -1
30-
}
31-
}
32-
33-
/**
34-
* Test whether a string is in quotes,
35-
* if yes return stripped string
36-
*/
37-
function stripQuotes (str) {
38-
if (QUOTE_RE.test(str)) {
39-
return str.slice(1, -1)
40-
}
41-
}
42-
4317
var filters = module.exports = {
4418

4519
/**
@@ -131,6 +105,11 @@ var filters = module.exports = {
131105
// get the optional dataKey
132106
dataKey = dataKey && (stripQuotes(dataKey) || get(this, dataKey))
133107

108+
// convert object to array
109+
if (!Array.isArray(arr)) {
110+
arr = utils.objectToArray(arr)
111+
}
112+
134113
return arr.filter(function (item) {
135114
return dataKey
136115
? contains(get(item, dataKey), search)
@@ -144,6 +123,11 @@ var filters = module.exports = {
144123
var key = stripQuotes(sortKey) || get(this, sortKey)
145124
if (!key) return arr
146125

126+
// convert object to array
127+
if (!Array.isArray(arr)) {
128+
arr = utils.objectToArray(arr)
129+
}
130+
147131
var order = 1
148132
if (reverseKey) {
149133
if (reverseKey === '-1') {
@@ -167,6 +151,34 @@ var filters = module.exports = {
167151

168152
}
169153

154+
// Array filter helpers -------------------------------------------------------
155+
156+
/**
157+
* String contain helper
158+
*/
159+
function contains (val, search) {
160+
/* jshint eqeqeq: false */
161+
if (utils.typeOf(val) === 'Object') {
162+
for (var key in val) {
163+
if (contains(val[key], search)) {
164+
return true
165+
}
166+
}
167+
} else if (val != null) {
168+
return val.toString().toLowerCase().indexOf(search) > -1
169+
}
170+
}
171+
172+
/**
173+
* Test whether a string is in quotes,
174+
* if yes return stripped string
175+
*/
176+
function stripQuotes (str) {
177+
if (QUOTE_RE.test(str)) {
178+
return str.slice(1, -1)
179+
}
180+
}
181+
170182
// mark computed filters
171183
filters.filterBy.computed = true
172184
filters.orderBy.computed = true

src/utils.js

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -256,6 +256,23 @@ var utils = module.exports = {
256256
}
257257
el.className = cur.trim()
258258
}
259+
},
260+
261+
/**
262+
* Convert an object to Array
263+
* used in v-repeat and array filters
264+
*/
265+
objectToArray: function (obj) {
266+
var res = [], val, data
267+
for (var key in obj) {
268+
val = obj[key]
269+
data = utils.typeOf(val) === 'Object'
270+
? val
271+
: { $value: val }
272+
data.$key = key
273+
res.push(data)
274+
}
275+
return res
259276
}
260277
}
261278

test/functional/fixtures/array-filters.html

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,10 @@
1919
</tr>
2020
</table>
2121
<hr></hr>
22-
Filter by input in all fields and reversed
22+
Object, filtered by input in all fields and reversed
2323
<table id="t2">
2424
<tr><th>Name</th><th>Phone</th></tr>
25-
<tr v-repeat="friends | filterBy searchText | orderBy sortKey !reverse" class="item">
25+
<tr v-repeat="friendsObj | filterBy searchText | orderBy sortKey !reverse" class="item">
2626
<td>{{name}}</td>
2727
<td>{{phone}}</td>
2828
</tr>
@@ -58,7 +58,15 @@
5858
{name:'Adam', phone:'555-5678'},
5959
{name:'Julie', phone:'555-8765'},
6060
{name:'Juliette', phone:'555-5678'}
61-
]
61+
],
62+
friendsObj: {
63+
a: {name:'John', phone:'555-1276', hidden: { id: 'hidden!' } },
64+
b: {name:'Mary', phone:'800-BIG-MARY'},
65+
c: {name:'Mike', phone:'555-4321'},
66+
d: {name:'Adam', phone:'555-5678'},
67+
e: {name:'Julie', phone:'555-8765'},
68+
f: {name:'Juliette', phone:'555-5678'}
69+
}
6270
}
6371
})
6472
</script>

test/functional/specs/array-filters.js

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
casper.test.begin('Array Filters', 53, function (test) {
1+
casper.test.begin('Array Filters', 55, function (test) {
22

33
var names = ['Adam', 'John', 'Julie', 'Juliette', 'Mary', 'Mike'],
44
namesReversed = names.slice().reverse(),
@@ -56,6 +56,14 @@ casper.test.begin('Array Filters', 53, function (test) {
5656
test.assertElementCount('#t1 .item', 0)
5757
test.assertElementCount('#t2 .item', 5)
5858
})
59+
// enter search filter for nested properties
60+
.then(function () {
61+
this.sendKeys('#search', 'hidden', { reset: true })
62+
})
63+
.then(function () {
64+
test.assertElementCount('#t1 .item', 0)
65+
test.assertElementCount('#t2 .item', 1)
66+
})
5967
// change filterkey
6068
.thenEvaluate(function () {
6169
var dropdown = document.getElementById('filterby')

test/unit/specs/filters.js

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -166,6 +166,17 @@ describe('Filters', function () {
166166
assert.strictEqual(res[0], arr[0])
167167
})
168168

169+
it('should work with objects', function () {
170+
var obj = {
171+
a: arr[0],
172+
b: arr[1],
173+
c: arr[2]
174+
}
175+
var res = filter.call(vm, obj, "'a'", "'$key'")
176+
assert.strictEqual(res.length, 1)
177+
assert.strictEqual(res[0], arr[0])
178+
})
179+
169180
})
170181

171182
describe('orderBy', function () {
@@ -211,6 +222,18 @@ describe('Filters', function () {
211222
assert.strictEqual(res[2].c, 'c')
212223
})
213224

225+
it('should work with objects', function () {
226+
var obj = {
227+
a: arr[0],
228+
b: arr[1],
229+
c: arr[2]
230+
}
231+
var res = filter.call({}, obj, "'$key'", '-1')
232+
assert.strictEqual(res[0].c, 'a')
233+
assert.strictEqual(res[1].c, 'c')
234+
assert.strictEqual(res[2].c, 'b')
235+
})
236+
214237
})
215238

216239
})

0 commit comments

Comments
 (0)