Skip to content
This repository was archived by the owner on Nov 16, 2023. It is now read-only.

Update packages, add tests, add type casts #229

Merged
merged 3 commits into from
Sep 29, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .eslintrc
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
"semi": ["error", "always"],
"quotes": ["error", "double"],
"@typescript-eslint/explicit-function-return-type": "off",
"@typescript-eslint/no-explicit-any": "off"
"@typescript-eslint/no-explicit-any": "off",
"@typescript-eslint/no-inferrable-types": "off"
}
}
2,441 changes: 1,395 additions & 1,046 deletions package-lock.json

Large diffs are not rendered by default.

195 changes: 99 additions & 96 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,98 +1,101 @@
{
"name": "express-typescript-starter",
"version": "0.1.0",
"description": "A starting point for Node.js express apps with TypeScript",
"repository": {
"type": "git",
"url": "https://github.com/Microsoft/TypeScript-Node-Starter"
},
"author": "Bowden Kelly",
"license": "MIT",
"scripts": {
"start": "npm run serve",
"build": "npm run build-sass && npm run build-ts && npm run lint && npm run copy-static-assets",
"serve": "node dist/server.js",
"watch-node": "nodemon dist/server.js",
"watch": "concurrently -k -p \"[{name}]\" -n \"Sass,TypeScript,Node\" -c \"yellow.bold,cyan.bold,green.bold\" \"npm run watch-sass\" \"npm run watch-ts\" \"npm run watch-node\"",
"test": "jest --forceExit --coverage --verbose",
"watch-test": "npm run test -- --watchAll",
"build-ts": "tsc",
"watch-ts": "tsc -w",
"build-sass": "node-sass src/public/css/main.scss dist/public/css/main.css",
"watch-sass": "node-sass -w src/public/css/main.scss dist/public/css/main.css",
"lint": "tsc --noEmit && eslint \"**/*.{js,ts}\" --quiet --fix",
"copy-static-assets": "ts-node copyStaticAssets.ts",
"debug": "npm run build && npm run watch-debug",
"serve-debug": "nodemon --inspect dist/server.js",
"watch-debug": "concurrently -k -p \"[{name}]\" -n \"Sass,TypeScript,Node\" -c \"yellow.bold,cyan.bold,green.bold\" \"npm run watch-sass\" \"npm run watch-ts\" \"npm run serve-debug\""
},
"dependencies": {
"async": "^3.0.1",
"bcrypt-nodejs": "^0.0.3",
"bluebird": "^3.5.5",
"body-parser": "^1.19.0",
"compression": "^1.7.4",
"connect-mongo": "^3.0.0",
"dotenv": "^8.0.0",
"errorhandler": "^1.5.1",
"express": "^4.17.1",
"express-flash": "0.0.2",
"express-session": "^1.16.2",
"express-validator": "^6.0.1",
"fbgraph": "^1.4.4",
"lodash": "^4.17.13",
"lusca": "^1.6.1",
"mongoose": "^5.6.0",
"nodemailer": "^6.2.1",
"passport": "^0.4.0",
"passport-facebook": "^3.0.0",
"passport-local": "^1.0.0",
"pug": "^2.0.4",
"request": "^2.88.0",
"request-promise": "^4.2.4",
"winston": "^2.4.2"
},
"devDependencies": {
"@types/async": "^3.0.0",
"@types/bcrypt-nodejs": "^0.0.30",
"@types/bluebird": "^3.5.27",
"@types/body-parser": "^1.17.0",
"@types/chai": "^4.1.7",
"@types/compression": "^0.0.36",
"@types/connect-mongo": "^0.0.42",
"@types/dotenv": "^6.1.1",
"@types/errorhandler": "^0.0.32",
"@types/express": "^4.17.0",
"@types/express-flash": "0.0.0",
"@types/express-session": "^1.15.13",
"@types/jest": "^24.0.15",
"@types/jquery": "^3.3.29",
"@types/lodash": "^4.14.134",
"@types/lusca": "^1.6.0",
"@types/mongodb": "^3.1.28",
"@types/mongoose": "^5.5.6",
"@types/morgan": "^1.7.35",
"@types/node": "^12.0.10",
"@types/nodemailer": "^6.2.0",
"@types/passport": "^1.0.0",
"@types/passport-facebook": "^2.1.9",
"@types/passport-local": "^1.0.33",
"@types/request": "^2.48.1",
"@types/shelljs": "^0.8.5",
"@types/supertest": "^2.0.7",
"@types/winston": "^2.3.9",
"@typescript-eslint/eslint-plugin": "^1.12.0",
"@typescript-eslint/parser": "^1.12.0",
"chai": "^4.2.0",
"concurrently": "^4.1.0",
"eslint": "^5.0.0",
"jest": "^24.8.0",
"node-sass": "^4.12.0",
"nodemon": "^1.19.1",
"shelljs": "^0.8.3",
"supertest": "^4.0.2",
"ts-jest": "^24.0.2",
"ts-node": "^8.3.0",
"typescript": "^3.5.2"
}
"name": "express-typescript-starter",
"version": "0.1.0",
"description": "A starting point for Node.js express apps with TypeScript",
"repository": {
"type": "git",
"url": "https://github.com/Microsoft/TypeScript-Node-Starter"
},
"author": "Bowden Kelly",
"license": "MIT",
"scripts": {
"start": "npm run serve",
"build": "npm run build-sass && npm run build-ts && npm run lint && npm run copy-static-assets",
"serve": "node dist/server.js",
"watch-node": "nodemon dist/server.js",
"watch": "concurrently -k -p \"[{name}]\" -n \"Sass,TypeScript,Node\" -c \"yellow.bold,cyan.bold,green.bold\" \"npm run watch-sass\" \"npm run watch-ts\" \"npm run watch-node\"",
"test": "jest --forceExit --coverage --verbose",
"watch-test": "npm run test -- --watchAll",
"build-ts": "tsc",
"watch-ts": "tsc -w",
"build-sass": "node-sass src/public/css/main.scss dist/public/css/main.css",
"watch-sass": "node-sass -w src/public/css/main.scss dist/public/css/main.css",
"lint": "tsc --noEmit && eslint \"**/*.{js,ts}\" --quiet --fix",
"copy-static-assets": "ts-node copyStaticAssets.ts",
"debug": "npm run build && npm run watch-debug",
"serve-debug": "nodemon --inspect dist/server.js",
"watch-debug": "concurrently -k -p \"[{name}]\" -n \"Sass,TypeScript,Node\" -c \"yellow.bold,cyan.bold,green.bold\" \"npm run watch-sass\" \"npm run watch-ts\" \"npm run serve-debug\""
},
"dependencies": {
"async": "^3.1.0",
"bcrypt-nodejs": "^0.0.3",
"bluebird": "^3.5.5",
"body-parser": "^1.19.0",
"compression": "^1.7.4",
"connect-mongo": "^3.0.0",
"dotenv": "^8.1.0",
"errorhandler": "^1.5.1",
"express": "^4.17.1",
"express-flash": "0.0.2",
"express-session": "^1.16.2",
"express-validator": "^6.2.0",
"fbgraph": "^1.4.4",
"lodash": "^4.17.15",
"lusca": "^1.6.1",
"mongoose": "^5.7.1",
"nodemailer": "^6.3.0",
"passport": "^0.4.0",
"passport-facebook": "^3.0.0",
"passport-local": "^1.0.0",
"pug": "^2.0.4",
"request": "^2.88.0",
"request-promise": "^4.2.4",
"winston": "^3.2.1"
},
"devDependencies": {
"@types/async": "^3.0.2",
"@types/bcrypt-nodejs": "^0.0.30",
"@types/bluebird": "^3.5.27",
"@types/body-parser": "^1.17.1",
"@types/chai": "^4.2.3",
"@types/compression": "^1.0.1",
"@types/concurrently": "^4.1.0",
"@types/connect-mongo": "^0.0.43",
"@types/dotenv": "^6.1.1",
"@types/errorhandler": "^0.0.32",
"@types/eslint": "^6.1.1",
"@types/express": "^4.17.1",
"@types/express-flash": "0.0.1",
"@types/express-session": "^1.15.14",
"@types/jest": "^24.0.18",
"@types/jquery": "^3.3.31",
"@types/lodash": "^4.14.141",
"@types/lusca": "^1.6.1",
"@types/mongoose": "^5.5.18",
"@types/node": "^12.7.8",
"@types/node-sass": "^4.11.0",
"@types/nodemailer": "^6.2.1",
"@types/passport": "^1.0.1",
"@types/passport-facebook": "^2.1.9",
"@types/passport-local": "^1.0.33",
"@types/pug": "^2.0.4",
"@types/request": "^2.48.3",
"@types/request-promise": "^4.1.44",
"@types/shelljs": "^0.8.5",
"@types/supertest": "^2.0.8",
"@types/winston": "^2.4.4",
"@typescript-eslint/eslint-plugin": "^2.3.1",
"@typescript-eslint/parser": "^2.3.1",
"chai": "^4.2.0",
"concurrently": "^4.1.2",
"eslint": "^6.4.0",
"jest": "^24.9.0",
"node-sass": "^4.12.0",
"nodemon": "^1.19.2",
"shelljs": "^0.8.3",
"supertest": "^4.0.2",
"ts-jest": "^24.1.0",
"ts-node": "^8.4.1",
"typescript": "^3.6.3"
}
}
2 changes: 1 addition & 1 deletion src/app.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ const app = express();
const mongoUrl = MONGODB_URI;
mongoose.Promise = bluebird;

mongoose.connect(mongoUrl, { useNewUrlParser: true, useCreateIndex: true } ).then(
mongoose.connect(mongoUrl, { useNewUrlParser: true, useCreateIndex: true, useUnifiedTopology: true } ).then(
() => { /** ready to use. The `mongoose.connect()` promise resolves to undefined. */ },
).catch(err => {
console.log("MongoDB connection error. Please make sure MongoDB is running. " + err);
Expand Down
5 changes: 3 additions & 2 deletions src/config/passport.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import passportFacebook from "passport-facebook";
import _ from "lodash";

// import { User, UserType } from '../models/User';
import { User } from "../models/User";
import { User, UserDocument } from "../models/User";
import { Request, Response, NextFunction } from "express";

const LocalStrategy = passportLocal.Strategy;
Expand Down Expand Up @@ -133,7 +133,8 @@ export const isAuthenticated = (req: Request, res: Response, next: NextFunction)
export const isAuthorized = (req: Request, res: Response, next: NextFunction) => {
const provider = req.path.split("/").slice(-1)[0];

if (_.find(req.user.tokens, { kind: provider })) {
const user = req.user as UserDocument;
if (_.find(user.tokens, { kind: provider })) {
next();
} else {
res.redirect(`/auth/${provider}`);
Expand Down
6 changes: 4 additions & 2 deletions src/controllers/api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import graph from "fbgraph";
import { Response, Request, NextFunction } from "express";
import { UserDocument } from "../models/User";


/**
Expand All @@ -19,9 +20,10 @@ export const getApi = (req: Request, res: Response) => {
* Facebook API example.
*/
export const getFacebook = (req: Request, res: Response, next: NextFunction) => {
const token = req.user.tokens.find((token: any) => token.kind === "facebook");
const user = req.user as UserDocument;
const token = user.tokens.find((token: any) => token.kind === "facebook");
graph.setAccessToken(token.accessToken);
graph.get(`${req.user.facebook}?fields=id,name,email,first_name,last_name,gender,link,locale,timezone`, (err: Error, results: graph.FacebookUser) => {
graph.get(`${user.facebook}?fields=id,name,email,first_name,last_name,gender,link,locale,timezone`, (err: Error, results: graph.FacebookUser) => {
if (err) { return next(err); }
res.render("api/facebook", {
title: "Facebook API",
Expand Down
12 changes: 8 additions & 4 deletions src/controllers/user.ts
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,8 @@ export const postUpdateProfile = (req: Request, res: Response, next: NextFunctio
return res.redirect("/account");
}

User.findById(req.user.id, (err, user: UserDocument) => {
const user = req.user as UserDocument;
User.findById(user.id, (err, user: UserDocument) => {
if (err) { return next(err); }
user.email = req.body.email || "";
user.profile.name = req.body.name || "";
Expand Down Expand Up @@ -178,7 +179,8 @@ export const postUpdatePassword = (req: Request, res: Response, next: NextFuncti
return res.redirect("/account");
}

User.findById(req.user.id, (err, user: UserDocument) => {
const user = req.user as UserDocument;
User.findById(user.id, (err, user: UserDocument) => {
if (err) { return next(err); }
user.password = req.body.password;
user.save((err: WriteError) => {
Expand All @@ -194,7 +196,8 @@ export const postUpdatePassword = (req: Request, res: Response, next: NextFuncti
* Delete user account.
*/
export const postDeleteAccount = (req: Request, res: Response, next: NextFunction) => {
User.remove({ _id: req.user.id }, (err) => {
const user = req.user as UserDocument;
User.remove({ _id: user.id }, (err) => {
if (err) { return next(err); }
req.logout();
req.flash("info", { msg: "Your account has been deleted." });
Expand All @@ -208,7 +211,8 @@ export const postDeleteAccount = (req: Request, res: Response, next: NextFunctio
*/
export const getOauthUnlink = (req: Request, res: Response, next: NextFunction) => {
const provider = req.params.provider;
User.findById(req.user.id, (err, user: any) => {
const user = req.user as UserDocument;
User.findById(user.id, (err, user: any) => {
if (err) { return next(err); }
user[provider] = undefined;
user.tokens = user.tokens.filter((token: AuthToken) => token.kind !== provider);
Expand Down
10 changes: 5 additions & 5 deletions src/util/logger.ts
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
import { Logger, LoggerOptions, transports } from "winston";
import winston from "winston";

const options: LoggerOptions = {
const options: winston.LoggerOptions = {
transports: [
new transports.Console({
new winston.transports.Console({
level: process.env.NODE_ENV === "production" ? "error" : "debug"
}),
new transports.File({ filename: "debug.log", level: "debug" })
new winston.transports.File({ filename: "debug.log", level: "debug" })
]
};

const logger = new Logger(options);
const logger = winston.createLogger(options);

if (process.env.NODE_ENV !== "production") {
logger.debug("Logging initialized at debug level");
Expand Down
14 changes: 14 additions & 0 deletions test/user.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,27 @@ describe("GET /login", () => {
});
});


describe("GET /forgot", () => {
it("should return 200 OK", () => {
return request(app).get("/forgot")
.expect(200);
});
});

describe("GET /signup", () => {
it("should return 200 OK", () => {
return request(app).get("/signup")
.expect(200);
});
});

describe("GET /reset", () => {
it("should return 302 Found for redirection", () => {
return request(app).get("/reset/1")
.expect(302);
});
});

describe("POST /login", () => {
it("should return some defined error message with valid parameters", (done) => {
Expand Down