graphql-toolsを使用してスキーマとリゾルバーを接続しようとしました。これを行うために、それらを別のフォルダーに移動し、mergeSchemasおよびmergeResolvers関数を使用しました。多くのモデルがあり、ファイルが大きくなり、混乱が生じるため、これを行う必要があります。ファイルをフォルダーに移動し、graphql-tools の使用を開始した後、エラーが発生しました。正しい合体方法を教えてください。以下は、スキーマとリゾルバーのコードです (いくつかのフィールドを削除しました。以前は正常に機能していたため、graphql-tools を使用しようとした後に問題が発生しました)。
スキーマ コード (私は ES6 構文を使用しています):
import { buildSchema } from 'graphql';
export default buildSchema(`
type User {
_id: ID!
name: String!
email: String!
password: String!
avatar: String
date: String
}
type Auth {
token: String!
}
input UserInput {
name: String!
email: String!
password: String!
date: String
token: String!
}
input UserUpdate {
_id: ID!
name: String!
email: String!
password: String!
token: String!
}
input UserRemove {
_id: ID!
token: String!
}
input UserAuth {
email: String!
password: String!
}
type RootQuery {
users: [User!]!
findUser(id: ID!): User
}
type RootMutation {
createUser(userInput: UserInput): User
deleteUser(userRemove: UserRemove): User
updateUser(userUpdate: UserUpdate): User
authUser(userAuth: UserAuth): Auth
}
schema {
query: RootQuery
mutation: RootMutation
}
`);
index.js (スキーマ フォルダー内):
import { mergeSchemas } from 'graphql-tools';
import user from './user';
export default schema = mergeSchemas({
schemas: [
user
]
});
リゾルバー コード:
import User from '../models/User';
export default {
users: () => {
return User.find().select('-password')
.then(users => {
return users.map(user => {
return {
...user._doc,
_id: user.id,
date: new Date(user.date).toISOString()
};
});
})
.catch(err => {
throw err;
});
},
findUser: async (args) => {
try {
let user = await User.findById(args.id).select('-password');
return {
...user._doc,
date: new Date(user.date).toISOString()
};
} catch (err) {
console.log(err);
throw err;
}
},
createUser: async args => {
const { name, email, password, token } = args.userInput;
try {
// Check if user exists:
let user = await User.findOne({ email });
if (user) {
return new Error('User already exists');
}
// Get users gravatar:
const avatar = gravatar.url(email, {
s: '200',
r: 'pg',
d: 'mm'
});
user = new User({
name,
email,
password,
avatar,
date: new Date(args.userInput.date)
});
// Encrypt password:
const salt = await bcrypt.genSalt(10);
user.password = await bcrypt.hash(password, salt);
await user.save();
return {
_id: user._id,
name: user.name,
email: user.email,
avatar: user.avatar,
date: new Date(user.date).toISOString()
}
} catch (err) {
throw err;
}
},
deleteUser: async (args) => {
const { _id, token } = args.userRemove;
try {
const user = await User.findById(_id);
return user.remove().then(result => {
return { ...result._doc, _id: result._doc._id.toString() };
});
} catch (err) {
throw err;
}
},
updateUser: async (args) => {
const { _id, name, email, password, token } = args.userUpdate;
try {
// Get users gravatar:
const avatar = gravatar.url(email, {
s: '200',
r: 'pg',
d: 'mm'
});
const user = await User.findById(_id);
user.name = name;
user.email = email;
// Encrypt password:
const salt = await bcrypt.genSalt(10);
user.password = await bcrypt.hash(password, salt);
user.avatar = avatar;
await user.save();
return user;
} catch (err) {
console.log(err);
throw err;
}
},
authUser: async (args) => {
const { email, password } = args.userAuth;
try {
// Check if user exists:
let user = await User.findOne({ email });
if (!user) {
return new Error('Invalid Credentials');
}
// Compare password
const isMatch = await bcrypt.compare(password, user.password);
if (!isMatch) {
return new Error('Invalid Credentials');
}
// JWT Token:
const payload = {
user: {
id: user._id
}
};
let token = await jwt.sign(
payload,
process.env.JWT_SECRET,
{ expiresIn: 360000 }, // Expiration (optional)
);
return {
token: token
}
} catch (err) {
throw err;
}
}
};
index.js (リゾルバーフォルダー内):
import { mergeResolvers } from 'graphql-tools';
import user from './user';
export default resolvers = mergeResolvers({
resolvers: [
user
]
});
server.js (スターター):
import express from 'express';
import cors from 'cors';
import connectDB from './db';
import { graphqlHTTP } from 'express-graphql';
import schema from './schema';
import resolvers from './resolvers';
const app = express();
app.use(express.json({ extended: false }));
app.use(cors());
app.use(
'/graphql',
graphqlHTTP({
schema: schema,
rootValue: resolvers,
graphiql: true
})
);
app.get('/', (req, res) => {
res.send('12345');
});
connectDB();
app.listen(5000, _ => console.log('Server started at 5000...'));
ファイルとフォルダーの構造:
schema
|__ index.js
|__ user.js (schema)
resolvers
|__ index.js
|__ user.js (resolver)
server.js
ご清聴ありがとうございました。