GraphQL 解析器逻辑 - 从突变调用查询/突变?

时间:2020-12-18 23:31:01

标签: javascript graphql graphql-js

我正在创建一个锻炼/锻炼记录器,用户可以在其中将他们的一组锻炼记录添加到他们的帐户中。用户还可以查看他们的锻炼和锻炼历史(使用设定数据)。我使用 mongoDB 来存储这些数据,使用 GraphQL 和 mongoose 来查询和改变数据。我将锻炼和锻炼分成了自己的类型,因为锻炼对象将只保存过去 4 小时(锻炼持续时间)内记录的锻炼和组,而锻炼对象将保存所有记录的组用户。

类型定义

type Workout {
  id: ID!
  workoutName: String!
  username: String!
  createdAt: String
  exercises: [Exercise]!
  notes: String
}
    
type Exercise {
  id: ID!
  exerciseName: String!
  username: String!
  sets: [Set]!
}

type Set {
  id: ID!
  reps: Int!
  weight: Float!
  createdAt: String!
  notes: String
}

我的问题在于我添加一个集合(突变)的解析器代码。这个解析器应该:

  1. 查询数据库用户是否做过该运动,通过检查数据库中匹配的运动名称,如果匹配,则添加用户输入的设置数据,否则,创建首先创建一个新的练习条目,然后将集合添加到其中。
  2. 查询数据库是否有在过去 4 小时内完成的锻炼。如果不匹配,则在数据库中创建一个新的锻炼条目。如果有锻炼,请检查锻炼对象上是否有匹配的锻炼名称,以将设置的数据添加到其中或为其创建新的锻炼条目。

我意识到这个变化会相当大,并且会将数据的查询和变化结合在一起。所以我想知道是否可以从类似于函数调用的 addSet 解析器调用单独的查询/突变?或者我应该采用另一种方法吗?

addSet 解析器

async addSet(_, { exerciseName, reps, weight, notes }, context) {
            const user = checkAuth(context); // Authenticates and gets logged in user's details

            if (exerciseName.trim() === '') {
                throw new UserInputError('Empty Field', {
                    // Attached payload of errors - can be used on client side
                    errors: {
                        body: 'Choose an exercise'
                    }
                })
            } else {
                exerciseName = exerciseName.toLowerCase();
                console.log(exerciseName);
            }

            if ((isNaN(reps) || reps === null) || (isNaN(weight) || reps === null)) {
                throw new UserInputError('Empty Fields', {
                    // Attached payload of errors - can be used on client side
                    errors: {
                        reps: 'Enter the number of reps you did for this set',
                        weight: 'Enter the amount of weight you did for this set'
                    }
                })
            }

            // TODO: Check to see if the exercise has been done before by the user. If it has, then update the entry by adding the set data to it. If not create a new entry for the 
            // exercise and then add the data to it - Completed and working.
            const exerciseExists = await Exercise.findOne({ exerciseName: exerciseName, username: user.username });

            if (exerciseExists) {
                console.log("This exercise exists");
                exerciseExists.sets.unshift({
                    reps,
                    weight,
                    username: user.username,
                    createdAt: Date.now(),
                    notes
                })
                await exerciseExists.save();
                //return exerciseExists;
            } else {
                console.log("I don't exist");
                const newExercise = new Exercise({
                    exerciseName,
                    user: user.id,
                    username: user.username,
                });
                const exercise = await newExercise.save();
                console.log("new exercise entry");
                exercise.sets.unshift({
                    reps,
                    weight,
                    username: user.username,
                    createdAt: Date.now(),
                    notes
                })
                await exercise.save();
                //return exercise;
            }

            // TODO: Get the most recent workout from the user and check if the time it was done was from the last 4 hours. If it wasn't, create a new workout entry for the user. 
            // If it was within the ast 4 hours, check to see if the workout has an exercise that matches with one the user inputted. If there isn't an exercise, create a new entry 
            // and add the set data to it, otherwise update the existing entry for the exercise.
            const workoutExists = await Workout.findOne({ username: username }).sort({ createdAt: -1 }); // Gets most recent workout by user
            const now = Date.now();
            if (now > workoutExists.createdAt + 14400000) { // Checks to see if the workout was less than 4 hours ago
                console.log("workout was from another session");
                // rest of code not implemented yet
            } else {
                console.log("workout is still in progress");
                // rest of code not implemented yet
            }

        },

0 个答案:

没有答案