Skip to content

Instantly share code, notes, and snippets.

@samsoft00
Created May 8, 2020 18:31
Show Gist options
  • Save samsoft00/9cee0116da74dd5a208d71260f04cf12 to your computer and use it in GitHub Desktop.
Save samsoft00/9cee0116da74dd5a208d71260f04cf12 to your computer and use it in GitHub Desktop.
require("dotenv").config({ path: "../.env" });
const express = require("express");
const bodyParser = require("body-parser");
const graphqlHttp = require("express-graphql");
const graphqlSchema = require("../graphql/schema");
const graphqlResolver = require("../graphql/resolver");
const app = express();
const port = 8080;
app.use(bodyParser.json());
app.get("/", (req, res) => res.send("Hello World!"));
app.use(
"/graphql",
graphqlHttp({
schema: graphqlSchema,
rootValue: graphqlResolver,
graphiql: true,
customFormatErrorFn(error) {
if (!error.originalError) {
return error;
}
const data = error.originalError.data;
const message = error.message || "An error occured!";
const code = error.originalError.code || 500;
return { message, status: code, data };
},
})
);
app.listen(port, () =>
console.log(`Claim app listening at http://localhost:${port}`)
);
const validator = require("validator");
module.exports = {
createUser: async function ({ userInput }, req) {
const errors = [];
if (validator.isEmail(userInput.email)) {
errors.push({ message: "E-mail is invalid" });
}
if (
validator.isEmpty(userInput.password) ||
!validator.isLength(userInput.password, { min: 5 })
) {
errors.push({ message: "Password too short" });
}
if (errors.length > 0) {
const error = new Error("Invalid input");
error.data = errors;
error.code = 422;
throw error;
}
const existingUser = await User.findOne({ email: userInput.email });
if (existingUser) {
const error = new Error("User already register");
throw error;
}
const hashedPwd = bcrypt.hash(userInput.password, 12);
const user = new User({
email: userInput.email,
name: userInput.name,
password: hashedPwd,
});
const createdUser = await user.save();
return {
...createdUser,
_id: createdUser._id.toString(),
};
},
login: async function ({ email, password }) {
console.log(email, password);
const user = await User.findOne({ email });
if (!user) {
const error = new Error("User not found!");
error.code = 401;
throw error;
}
const isEqual = await bcrypt.compare(password, user.password);
if (!isEqual) {
const error = new Error("password is incorrect");
error.code = 401;
throw error;
}
const token = jwt.sign(
{
userId: user._id.toString(),
email: user.email,
},
"somesupersecretsecret",
{ expiresIn: "1h" }
);
return { token: token, userId: user._id.toString() };
},
createPost: async function ({ postInput }, req) {
const errors = [];
if (req.isAuth) {
const error = new Error("Not authenticated");
error.code = 401;
throw error;
}
if (
validator.isEmpty(postInput.title) ||
validator.isLength(postInput.title, { min: 5 })
) {
errors.push({ message: "Title is invalid" });
}
if (errors.length > 0) {
const error = new Error("Invalid input");
error.data = errors;
error.code = 422;
throw error;
}
const user = await User.findById(req.userId);
if (!user) {
const error = new Error("Invalid user");
error.data = errors;
error.code = 422;
throw error;
}
const post = new post({
title: postInput.title,
content: postInput.content,
imageUrl: postInput.imageUrl,
creator: user,
});
const createdPost = await post.save();
user.posts.push(createdPost);
await user.save();
return {
...createdPost,
_id: createdPost._id.toString(),
createdAt: createdPost.createdAt.toISOString(),
updatedAt: createdPost.updatedAt.toISOString(),
};
},
posts: async function ({ page }, req) {
const errors = [];
if (req.isAuth) {
const error = new Error("Not authenticated");
error.code = 401;
throw error;
}
if (!page) {
page = 1;
}
const perPage = 2;
const totalPost = await Post.find().countDocuments();
const posts = await Post.find()
.sort({ createdAt: -1 })
.skip((page - 1) * perPage)
.limit(perPage)
.populate("creator");
return {
posts: posts.map((p) => {
return {
...p,
_id: p._id.toString(),
createdAt: p.createdAt.toISOString(),
updatedAt: p.updatedAt.toISOString(),
};
}),
totalPost,
};
},
post: async function ({ id }, req) {
if (req.isAuth) {
const error = new Error("Not authenticated");
error.code = 401;
throw error;
}
const post = await Post.findById(id).populate("creator");
if (!post) {
const error = new Error("No post found!");
error.code = 404;
throw error;
}
return {
...post,
_id: post._id.toString(),
createdAt: post.createdAt.toISOString(),
updatedAt: post.updatedAt.toISOString(),
};
},
};
const { buildSchema } = require("graphql");
module.exports = buildSchema(`
type Post {
_id: ID!
title: String!
content: String!
imageUrl: String!
creator: User!
createAt: String!
updateAt: String!
}
type User {
_id: ID!
email: String!
name: String!
password: String
status: String!
posts: [Post]
}
input UserInputData {
email: String!
name: String!
password: String!
}
input PostInputData{
title: String!
content: String!
imageUrl: String!
}
type AuthData {
token: String!
userId: String!
}
type PostData{
posts: [Post!],
totalPosts: Int!
}
type RootQuery {
login(email: String!, password: String!): AuthData!
posts(page: Int!): PostData
post(id: ID!): Post!
}
type RootMutation {
createUser(userInput: UserInputData) : User!
createPost(postInput: PostInputData) : Post!
}
schema {
query: RootQuery
mutation: RootMutation
}
`);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment