forked from OpenNeuroOrg/openneuro
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathapp.ts
More file actions
119 lines (106 loc) · 3.32 KB
/
Copy pathapp.ts
File metadata and controls
119 lines (106 loc) · 3.32 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
/*eslint no-console: ["error", { allow: ["log"] }] */
/**
* Express app setup
*/
import { createServer } from "http"
import cors from "cors"
import express, { json, urlencoded } from "express"
import passport from "passport"
import config from "./config"
import routes from "./routes"
import morgan from "morgan"
import schema from "./graphql/schema"
import { ApolloServer } from "@apollo/server"
import { ApolloServerPluginLandingPageLocalDefault } from "@apollo/server/plugin/landingPage/default"
import { expressMiddleware } from "@as-integrations/express5"
import { ApolloServerPluginDrainHttpServer } from "@apollo/server/plugin/drainHttpServer"
import { KeyvAdapter } from "@apollo/utils.keyvadapter"
import Keyv from "keyv"
import KeyvRedis from "@keyv/redis"
import cookieParser from "cookie-parser"
import * as jwt from "./libs/authentication/jwt"
import * as auth from "./libs/authentication/states"
import { sitemapHandler } from "./handlers/sitemap"
import { setupPassportAuth } from "./libs/authentication/passport"
import { getRedis } from "./libs/redis"
import { version } from "./lerna.json"
export { Express } from "express-serve-static-core"
interface OpenNeuroRequestContext {
user: string
userInfo: {
id: string
exp: string
scopes: string[]
}
}
export async function expressApolloSetup() {
const app = express()
app.set("trust proxy", true)
setupPassportAuth()
app.use(passport.initialize())
app.use((req, res, next) => {
res.set(config.headers)
res.type("application/json")
next()
})
app.use(morgan("short"))
app.use(cookieParser())
app.use(urlencoded({ extended: false, limit: "100mb" }))
app.use(json({ limit: "100mb" }))
// routing ---------------------------------------------------------
app.use("/sitemap.xml", sitemapHandler)
app.use(config.apiPrefix, routes)
app.use("/api/", routes)
const httpServer = createServer(app)
// Apollo server setup
const apolloServer = new ApolloServer<OpenNeuroRequestContext>({
schema,
// Always allow introspection - our schema is public
introspection: true,
// @ts-expect-error Type mismatch for keyv and ioredis recent releases
cache: new KeyvAdapter(new Keyv({ store: new KeyvRedis(getRedis()) })),
plugins: [
ApolloServerPluginLandingPageLocalDefault(),
ApolloServerPluginDrainHttpServer({
httpServer,
}),
{
async requestDidStart() {
return {
async willSendResponse(requestContext) {
const { response } = requestContext
if (
response.body.kind === "single" &&
"data" in response.body.singleResult
) {
response.body.singleResult.extensions = {
...response.body.singleResult.extensions,
openneuro: { version },
}
}
},
}
},
},
],
})
await apolloServer.start()
// Setup GraphQL middleware
app.use(
["/graphql", "/crn/graphql", "/api/graphql"],
cors<cors.CorsRequest>(),
jwt.authenticate,
auth.optional,
expressMiddleware(apolloServer, {
context: async ({ req }) => {
if (req.isAuthenticated()) {
return {
user: req.user.id,
userInfo: req.user,
}
}
},
}),
)
return app
}