-
Notifications
You must be signed in to change notification settings - Fork 96
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow $select to catch and use string syntax #158
Conversation
mongoose allows a string to be passed to the `.select()` function ie. `select('+someExtraField')`. Using this syntax allows you to keep all existing fields selected, but select additional fields you might have hidden in your schema by using `select: false` as a "column/field" option. I hope that this change will allow the other forms to be used, but still catch this case. I still need to check/write tests
@@ -37,7 +37,9 @@ class Service { | |||
const q = this.Model.find(query).lean(this.lean); | |||
|
|||
// $select uses a specific find syntax, so it has to come first. | |||
if (filters.$select && filters.$select.length) { | |||
if (typeof filters.$select === 'string') { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think you might be able to just add this check to line 51, which would pass the string to the mongoose query.select()
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think I can because of how the current check works on line 43, a string has a length right?(I just double checked in my console :)
I could modify it, but I'd rather leave it alone....
ok, I've added test for $select on strings, arrays and objects. Works for me! thanks so much for you time and this wonderful codebase! |
Can you try this with your tests? if (filters.$select) {
// $select uses a specific find syntax, so it has to come first.
if (typeof filters.$select === 'string' || typeof filters.$select === 'object') {
q.select(filters.$select);
} else if (Array.isArray(filters.$select)) {
let fields = {};
for (let key of filters.$select) {
fields[key] = 1;
}
q.select(fields);
}
} I think it's actually more lines of code, but it's a bit cleaner. |
Actually, I don't think the outer // $select uses a specific find syntax, so it has to come first.
if (typeof filters.$select === 'string' || typeof filters.$select === 'object') {
q.select(filters.$select);
} else if (Array.isArray(filters.$select)) {
let fields = {};
for (let key of filters.$select) {
fields[key] = 1;
}
q.select(fields);
} |
@marshallswain I've updated the logic to simplify it, take a look when you have a chance, thanks! Close to what you had suggested, but I found the array needs to be checked first because an array is an object. |
Oh right. Looks good to me. |
Nice, I didn't know this was possible. Released as v3.6.2. Thanks @jamesjnadeau! |
mongoose allows a string to be passed to the
.select()
function ie.select('+someExtraField')
.Using this syntax allows you to keep all existing fields selected, but select additional fields you might have hidden in your schema by using
select: false
as a "column/field" option. It's also a more succinct and flexible way of passing the select information IMHO.I hope that this change will allow the other forms to be used, but allow this use case.
I still need to check/write tests and clean up the code a bit, but getting this out early for concerns/comment.