Skip to content

Commit d6ee5f1

Browse files
fix(memory): Use for loop in _find() for better performance (#2844)
1 parent 50e7463 commit d6ee5f1

File tree

2 files changed

+33
-10
lines changed

2 files changed

+33
-10
lines changed

packages/memory/src/index.ts

Lines changed: 32 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -75,26 +75,49 @@ export class MemoryAdapter<T = any, D = Partial<T>, P extends Params = Params> e
7575
const { paginate } = this.getOptions(params)
7676
const { query, filters } = this.getQuery(params)
7777

78-
let values = _.values(this.store).filter(this.options.matcher(query))
78+
let values = _.values(this.store)
7979
const total = values.length
80+
const hasSkip = filters.$skip !== undefined
81+
const hasSort = filters.$sort !== undefined
82+
const hasLimit = filters.$limit !== undefined
83+
const hasQuery = _.keys(query).length > 0
8084

81-
if (filters.$sort !== undefined) {
85+
if (hasSort) {
8286
values.sort(this.options.sorter(filters.$sort))
8387
}
8488

85-
if (filters.$skip !== undefined) {
86-
values = values.slice(filters.$skip)
87-
}
89+
if (hasQuery || hasLimit || hasSkip) {
90+
let skipped = 0
91+
const matcher = this.options.matcher(query)
92+
const matched = []
93+
94+
for (let index = 0, length = values.length; index < length; index++) {
95+
const value = values[index]
96+
97+
if (hasQuery && !matcher(value, index, values)) {
98+
continue
99+
}
100+
101+
if (hasSkip && filters.$skip > skipped) {
102+
skipped++
103+
continue
104+
}
105+
106+
matched.push(_select(value, params))
107+
108+
if (hasLimit && filters.$limit === matched.length) {
109+
break
110+
}
111+
}
88112

89-
if (filters.$limit !== undefined) {
90-
values = values.slice(0, filters.$limit)
113+
values = matched
91114
}
92115

93116
const result: Paginated<T> = {
94-
total,
117+
total: hasQuery ? values.length : total,
95118
limit: filters.$limit,
96119
skip: filters.$skip || 0,
97-
data: values.map((value) => _select(value, params))
120+
data: filters.$limit === 0 ? [] : values
98121
}
99122

100123
if (!paginate) {

packages/memory/test/index.test.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -172,7 +172,7 @@ describe('Feathers Memory Service', () => {
172172
)
173173

174174
await app.service('matcher').find({
175-
query: { $sort: { something: 1 } }
175+
query: { something: 1, $sort: { something: 1 } }
176176
})
177177

178178
assert.ok(sorterCalled, 'sorter called')

0 commit comments

Comments
 (0)