Skip to content

Commit

Permalink
Update dependencies (#8)
Browse files Browse the repository at this point in the history
* Update dependencies

Also move to use declaration overrides for describing additional possible fields in session data

Also removing/moving unnecessary prod dependencies

Moving jest tests to run in parallel

* Fix types for user

* Do not allow any warnings

* Correcting test results path
  • Loading branch information
andrewrlee authored Dec 7, 2020
1 parent 49ace58 commit ccc0c03
Show file tree
Hide file tree
Showing 10 changed files with 341 additions and 634 deletions.
4 changes: 2 additions & 2 deletions .circleci/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ jobs:
name: unit tests
command: npm run test
- store_test_results:
path: test-results
path: test_results
- store_artifacts:
path: test-results/unit-test-reports.html

Expand Down Expand Up @@ -95,7 +95,7 @@ jobs:
name: integration tests
command: npm run int-test
- store_test_results:
path: test-results
path: test_results
- store_artifacts:
path: integration-tests/videos
- store_artifacts:
Expand Down
847 changes: 277 additions & 570 deletions package-lock.json

Large diffs are not rendered by default.

57 changes: 27 additions & 30 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,9 @@
"watch-node-feature": "export $(cat feature.env) && nodemon --watch dist/ $NODE_DEBUG_OPTION dist/server.js | bunyan -o short",
"start-feature:dev": "npm run build && concurrently -k -p \"[{name}]\" -n \"Views,TypeScript,Node,Sass\" -c \"yellow.bold,cyan.bold,green.bold,blue.bold\" \"npm run watch-views\" \"npm run watch-ts\" \"npm run watch-node-feature\" \"npm run watch-sass\"",
"record-build-info": "node ./bin/record-build-info",
"lint": "eslint . --cache --max-warnings 200",
"lint": "eslint . --cache --max-warnings 0",
"typecheck": "tsc",
"test": "jest --runInBand",
"test": "jest",
"security_audit": "npx audit-ci --config audit-ci.json",
"int-test": "cypress run --config video=false",
"int-test-ui": "cypress open",
Expand Down Expand Up @@ -87,9 +87,8 @@
]
},
"dependencies": {
"@types/connect-flash": "0.0.35",
"agentkeepalive": "^4.1.3",
"applicationinsights": "^1.8.7",
"applicationinsights": "^1.8.8",
"body-parser": "^1.19.0",
"bunyan": "^1.8.14",
"bunyan-format": "^0.2.1",
Expand All @@ -98,18 +97,15 @@
"connect-redis": "^5.0.0",
"cookie-session": "^1.4.0",
"csurf": "^1.11.0",
"date-fns": "^2.16.1",
"dotenv": "^8.2.0",
"express": "^4.17.1",
"express-request-id": "^1.4.1",
"express-session": "^1.17.1",
"govuk-elements-sass": "^3.1.3",
"govuk-frontend": "^3.9.0",
"helmet": "^4.1.1",
"govuk-frontend": "^3.10.1",
"helmet": "^4.2.0",
"http-errors": "^1.8.0",
"joi": "^17.2.1",
"jquery": "^3.5.1",
"jwt-decode": "^2.2.0",
"jwt-decode": "^3.1.2",
"nocache": "^2.1.0",
"nunjucks": "^3.2.2",
"passport": "^0.4.1",
Expand All @@ -118,38 +114,39 @@
"superagent": "^6.1.0"
},
"devDependencies": {
"@types/csurf": "^1.9.36",
"@types/express-session": "^1.17.0",
"@types/jest": "^26.0.14",
"@types/connect-flash": "0.0.36",
"@types/csurf": "^1.11.0",
"@types/express-session": "^1.17.3",
"@types/jest": "^26.0.16",
"@types/node": "^14.14.10",
"@types/passport": "^1.0.4",
"@types/superagent": "^4.1.10",
"@types/supertest": "^2.0.10",
"@typescript-eslint/eslint-plugin": "^4.4.1",
"@typescript-eslint/parser": "^4.4.1",
"@typescript-eslint/eslint-plugin": "^4.9.0",
"@typescript-eslint/parser": "^4.9.0",
"concurrently": "^5.3.0",
"cypress": "^5.4.0",
"cypress": "^6.0.1",
"cypress-multi-reporters": "^1.4.0",
"eslint": "^7.11.0",
"eslint-config-airbnb-base": "^14.2.0",
"eslint-config-prettier": "^6.13.0",
"eslint": "^7.14.0",
"eslint-config-airbnb-base": "^14.2.1",
"eslint-config-prettier": "^6.15.0",
"eslint-import-resolver-typescript": "^2.3.0",
"eslint-plugin-cypress": "^2.11.2",
"eslint-plugin-import": "^2.22.1",
"eslint-plugin-prettier": "^3.1.4",
"husky": "^4.3.0",
"jest": "^26.5.3",
"jest": "^26.6.3",
"jest-html-reporter": "^3.3.0",
"jest-junit": "^11.1.0",
"jest-junit": "^12.0.0",
"jsonwebtoken": "^8.5.1",
"lint-staged": "^10.4.1",
"mocha": "^8.1.3",
"lint-staged": "^10.5.2",
"mocha-junit-reporter": "^2.0.0",
"nock": "^13.0.4",
"nodemon": "^2.0.5",
"prettier": "^2.1.2",
"sass": "^1.27.0",
"supertest": "^4.0.2",
"ts-jest": "^26.4.1",
"typescript": "^4.0.3"
"nock": "^13.0.5",
"nodemon": "^2.0.6",
"prettier": "^2.2.1",
"sass": "^1.29.0",
"supertest": "^6.0.1",
"ts-jest": "^26.4.4",
"typescript": "^4.1.2"
}
}
21 changes: 21 additions & 0 deletions server/@types/express/index.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
export default {}

declare module 'express-session' {
// Declare that the session will potentially contain these additional fields
interface SessionData {
returnTo: string
nowInMinutes: number
}
}

export declare global {
namespace Express {
interface Request {
verified?: boolean
user: {
username: string
token: string
}
}
}
}
16 changes: 3 additions & 13 deletions server/authentication/auth.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import passport from 'passport'
import { Strategy } from 'passport-oauth2'
import type { Request, RequestHandler } from 'express'
import type { RequestHandler } from 'express'

import config from '../config'
import generateOauthClientToken from './clientCredentials'
import type { VerifiableRequest, TokenVerifier } from '../data/tokenVerification'
import type { TokenVerifier } from '../data/tokenVerification'

passport.serializeUser((user, done) => {
// Not used but required for Passport
Expand All @@ -19,7 +19,7 @@ passport.deserializeUser((user, done) => {
export type AuthenticationMiddleware = (tokenVerifier: TokenVerifier) => RequestHandler

const authenticationMiddleware: AuthenticationMiddleware = verifyToken => {
return async (req: VerifiableRequest, res, next) => {
return async (req, res, next) => {
if (req.isAuthenticated() && (await verifyToken(req))) {
return next()
}
Expand All @@ -28,16 +28,6 @@ const authenticationMiddleware: AuthenticationMiddleware = verifyToken => {
}
}

export interface UserDetails {
username: string
token: string
authSource: string
}

export interface UserRequest extends Request {
user: UserDetails
}

function init(): void {
const strategy = new Strategy(
{
Expand Down
14 changes: 7 additions & 7 deletions server/data/tokenVerification.test.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import nock from 'nock'

import verifyToken, { VerifiableRequest } from './tokenVerification'
import { Request } from 'express'
import verifyToken from './tokenVerification'
import config from '../config'

describe('token verification api tests', () => {
Expand All @@ -22,7 +22,7 @@ describe('token verification api tests', () => {

it('Token always considered valid', async () => {
fakeApi.post('/token/verify', '').reply(200, { active: true })
const data = await verifyToken({} as VerifiableRequest)
const data = await verifyToken({} as Request)
expect(data).toEqual(true)
expect(nock.isDone()).toBe(false) // assert api was not called
})
Expand All @@ -34,26 +34,26 @@ describe('token verification api tests', () => {
})
it('Calls verify and parses response', async () => {
fakeApi.post('/token/verify', '').reply(200, { active: true })
const data = await verifyToken({ user: {}, verified: false } as VerifiableRequest)
const data = await verifyToken({ user: {}, verified: false } as Request)
expect(data).toEqual(true)
expect(nock.isDone()).toBe(true) // assert api was called
})

it('Calls verify and parses inactive response', async () => {
fakeApi.post('/token/verify', '').reply(200, { active: false })
const data = await verifyToken({ user: {}, verified: false } as VerifiableRequest)
const data = await verifyToken({ user: {}, verified: false } as Request)
expect(data).toEqual(false)
})

it('Calls verify and parses no response', async () => {
fakeApi.post('/token/verify', '').reply(200, {})
const data = await verifyToken({ user: {}, verified: false } as VerifiableRequest)
const data = await verifyToken({ user: {}, verified: false } as Request)
expect(data).toEqual(false)
})

it('Already verified', async () => {
fakeApi.post('/token/verify', '').reply(200, {})
const data = await verifyToken({ verified: true } as VerifiableRequest)
const data = await verifyToken({ verified: true } as Request)
expect(data).toEqual(true)
expect(nock.isDone()).toBe(false) // assert api was not called
})
Expand Down
10 changes: 1 addition & 9 deletions server/data/tokenVerification.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,15 +15,7 @@ function getApiClientToken(token: string) {
})
}

export interface VerifiableRequest extends Request {
verified?: boolean
user: {
username: string
token: string
}
}

export type TokenVerifier = (request: VerifiableRequest) => Promise<boolean | void>
export type TokenVerifier = (request: Request) => Promise<boolean | void>

const tokenVerifier: TokenVerifier = async request => {
const { user, verified } = request
Expand Down
2 changes: 1 addition & 1 deletion server/middleware/authorisationMiddleware.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import logger from '../../log'
export default function authorisationMiddleware(authorisedRoles: string[] = []): RequestHandler {
return (req, res, next) => {
if (res.locals && res.locals.user && res.locals.user.token) {
const { authorities: roles = [] } = jwtDecode(res.locals.user.token)
const { authorities: roles = [] } = jwtDecode(res.locals.user.token) as { authorities?: string[] }

if (authorisedRoles.length && !roles.some(role => authorisedRoles.includes(role))) {
logger.error('User is not authorised to access this')
Expand Down
1 change: 0 additions & 1 deletion server/routes/testutils/appSetup.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,6 @@ function appSetup(route: Router, production: boolean): Express {
nunjucksSetup(app, path)

app.use((req, res, next) => {
req.user = user
res.locals = {}
res.locals.user = req.user
next()
Expand Down
3 changes: 2 additions & 1 deletion tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,8 @@
"resolveJsonModule": true,
"esModuleInterop": true,
"allowSyntheticDefaultImports": true,
"experimentalDecorators": true
"experimentalDecorators": true,
"typeRoots": ["./server/@types", "./node_modules/@types"]
},
"exclude": ["node_modules", "assets/**/*.js", "integration_tests", "dist"],
"include": ["**/*.js", "**/*.ts"]
Expand Down

0 comments on commit ccc0c03

Please sign in to comment.