#mongodb #meteor #graphql #mongodb-query #apollo
#mongodb #meteor #graphql #mongodb-запрос #apollo
Вопрос:
Я пытаюсь запустить запрос с агрегатом в Meteor, и мне не удалось выяснить, как вернуть запрос агрегации.
В моей схеме GraphQL:
type UserRelation {
date: String!
userID: String!
}
type UserData {
userID: String!
description: String!
friends_list: [UserRelation]!
}
extend type Query {
getFriends(userID: String!, friendID: String): [UserRelation]
}
В моем resolvers.js:
import UserData from "./userData";
export default {
Query: {
getFriends(obj, args, context) {
if (args.friendID) return UserData.rawCollection().aggregate([
{
$match: {
_id: 'cuS7KebEQDRv2iFpJ'
}
},
{
$unwind: '$friends_list'
},
{
$match: {
'friends_list._id': '8GW4gjwWhkEexfndd'
}
}
]);
return UserData.findOne({ userID: args.userID }, {fields: {_id: 0, friends_list: 1 }}).friends_list;
}
}
}
В этом жестко закодированном примере у меня есть следующий документ в моей базе данных:
И я хочу вернуть весь документ ТОЛЬКО с тем пользователем, у которого есть совпадающий _id и в списке друзей которого есть другой пользователь со вторым совпадающим _id. Таким образом, таким образом, я могу вернуть весь документ только с этим 1 элементом в массиве friends_list вместо всех других элементов.
Теперь этот запрос отлично работает в Robo3T (графический интерфейс MongoDB), но возникает проблема с оператором return, когда я запускаю его в Graphiql, поскольку выдается ошибка, в которой говорится: "Expected Iterable, but did not find one for field "Query.getFriends"."
Когда я регистрирую этот оператор, я вижу Mongo AggregationCursor. Но я не уверен, как мне следует «преобразовать» это в тип, который распознаватель может правильно возвращать.
Любая помощь приветствуется, спасибо!
Комментарии:
1. findOne не возвращает массив?
2. Нет, это не для findOne, эта часть работает нормально. findOne возвращает весь массив friends_list определенного пользователя. findOne выполняется только в том случае, если не указан необязательный аргумент FriendID, и в этом случае я возвращаю весь массив friends_list .
3. просто регистрируйте данные перед возвратом, проверяйте структуру, сравнивайте с ожидаемым
4. Я сделал это, и он показывает AggregationCursor. Я не был уверен, как «преобразовать» это во что-то правильное, но я думаю, что в соответствии с моим ответом ниже я, возможно (?), Понял это.
Ответ №1:
Я не знаю, действительно ли я понял это, потому что мне нужно протестировать это еще раз, но пока это работает, на мой взгляд. resolvers.js У меня есть:
import UserData from "./userData";
async function getFriend(userID, friendID) {
return UserData.rawCollection().aggregate([
{
$match: {
_id: userID
}
},
{
$unwind: '$friends_list'
},
{
$match: {
'friends_list._id': friendID
}
}
]).toArray();
}
export default {
Query: {
async getFriends(obj, args, context) {
if (args.friendID){
const result = await getFriend(args.userID, args.friendID);
return result[0].friends_list;
}
return UserData.findOne({ userID: args.userID }, {fields: {_id: 0, friends_list: 1 }}).friends_list;
}
}
}
Сделав это асинхронным, я смог это сделать. Не уверен, какие последствия это имеет, но пока это работает. Если кто-нибудь сможет просмотреть это и дать некоторую критику, чтобы улучшить это, я был бы искренне признателен, поскольку любую информацию об этом было мучительно трудно найти, поскольку я до сих пор не видел никаких примеров использования этого.