Skip to content

Commit

Permalink
test: update server
Browse files Browse the repository at this point in the history
  • Loading branch information
Akryum committed Jun 12, 2023
1 parent 2077502 commit 13bfbbe
Show file tree
Hide file tree
Showing 4 changed files with 630 additions and 77 deletions.
20 changes: 13 additions & 7 deletions packages/test-e2e-composable-vue3/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,27 +6,33 @@
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"test": "pnpm run test:e2e && kill-port 4042",
"test:e2e": "start-server-and-test api http://localhost:4042/.well-known/apollo/server-health test:e2e:client",
"test:e2e": "start-server-and-test api 'http-get://localhost:4042/graphql?query=%7B__typename%7D' test:e2e:client",
"test:e2e:client": "vue-cli-service test:e2e --mode production --headless",
"test:e2e:dev": "start-server-and-test api http://localhost:4042/.well-known/apollo/server-health test:e2e:dev:client",
"test:e2e:dev": "start-server-and-test api:dev 'http-get://localhost:4042/graphql?query=%7B__typename%7D' test:e2e:dev:client",
"test:e2e:dev:client": "vue-cli-service test:e2e --mode development",
"api": "node server.js"
"api": "node server.mjs --simulate-latency 100",
"api:dev": "node server.mjs --simulate-latency 500"
},
"dependencies": {
"@apollo/client": "^3.7.7",
"@apollo/server": "^4.7.3",
"@graphql-tools/schema": "^10.0.0",
"@vue/apollo-composable": "workspace:*",
"@vue/apollo-util": "workspace:*",
"apollo-server-express": "^2.25.4",
"body-parser": "^1.20.2",
"core-js": "^3.23.2",
"cors": "^2.8.5",
"express": "^4.18.1",
"graphql": "^15.8.0",
"graphql": "^16.6.0",
"graphql-subscriptions": "^2.0.0",
"graphql-tag": "^2.12.6",
"graphql-ws": "^5.13.1",
"regenerator-runtime": "^0.13.9",
"shortid": "^2.2.16",
"vue": "^3.2.37",
"vue-demi": "^0.13.1",
"vue-router": "^4.0.16"
"vue-router": "^4.0.16",
"ws": "^8.13.0"
},
"devDependencies": {
"@babel/core": "^7.18.5",
Expand All @@ -36,7 +42,7 @@
"@vue/cli-plugin-typescript": "^5.0.6",
"@vue/cli-service": "^5.0.6",
"axios": "^0.24.0",
"cypress": "^10.2.0",
"cypress": "^12.14.0",
"kill-port": "^1.6.1",
"start-server-and-test": "^1.14.0",
"tailwindcss": "^1.9.6"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,37 @@
const express = require('express')
const cors = require('cors')
const { gql, ApolloServer, ApolloError, PubSub, withFilter } = require('apollo-server-express')
const shortid = require('shortid')
import { createServer } from 'node:http'
import express from 'express'
import cors from 'cors'
import bodyParser from 'body-parser'
import { ApolloServer } from '@apollo/server'
import { expressMiddleware } from '@apollo/server/express4'
import { makeExecutableSchema } from '@graphql-tools/schema'
import { WebSocketServer } from 'ws'
import { useServer } from 'graphql-ws/lib/use/ws'
import { PubSub, withFilter } from 'graphql-subscriptions'
import shortid from 'shortid'
import gql from 'graphql-tag'
import { GraphQLError } from 'graphql'

const shouldSimulateLatency = process.argv.includes('--simulate-latency')

let latency = 500
if (shouldSimulateLatency) {
const index = process.argv.indexOf('--simulate-latency')
if (index !== -1 && process.argv.length > index + 1) {
latency = parseInt(process.argv[index + 1])
}
}

export class GraphQLErrorWithCode extends GraphQLError {
constructor (message, code, extensions) {
super(message, {
extensions: {
code,
...extensions,
},
})
}
}

const typeDefs = gql`
type Channel {
Expand Down Expand Up @@ -68,14 +98,25 @@ function resetDatabase () {

resetDatabase()

function simulateLatency () {
return new Promise(resolve => {
if (shouldSimulateLatency) {
setTimeout(resolve, latency)
} else {
resolve()
}
})
}

const resolvers = {
Query: {
hello: () => 'Hello world!',
channels: () => channels,
channel: (root, { id }) => channels.find(c => c.id === id),
list: () => ['a', 'b', 'c'],
good: () => 'good',
bad: () => {
hello: () => simulateLatency().then(() => 'Hello world!'),
channels: () => simulateLatency().then(() => channels),
channel: (root, { id }) => simulateLatency().then(() => channels.find(c => c.id === id)),
list: () => simulateLatency().then(() => ['a', 'b', 'c']),
good: () => simulateLatency().then(() => 'good'),
bad: async () => {
await simulateLatency()
throw new Error('An error')
},
},
Expand All @@ -84,7 +125,7 @@ const resolvers = {
addMessage: (root, { input }) => {
const channel = channels.find(c => c.id === input.channelId)
if (!channel) {
throw new ApolloError(`Channel ${input.channelId} not found`, 'not-found')
throw new GraphQLErrorWithCode(`Channel ${input.channelId} not found`, 'not-found')
}
const message = {
id: shortid(),
Expand All @@ -99,7 +140,7 @@ const resolvers = {
updateMessage: (root, { input }) => {
const channel = channels.find(c => c.id === input.channelId)
if (!channel) {
throw new ApolloError(`Channel ${input.channelId} not found`, 'not-found')
throw new GraphQLErrorWithCode(`Channel ${input.channelId} not found`, 'not-found')
}
const message = channel.messages.find(m => m.id === input.id)
Object.assign(message, {
Expand Down Expand Up @@ -127,26 +168,60 @@ const resolvers = {
},
}

const schema = makeExecutableSchema({
typeDefs,
resolvers,
})

const app = express()

app.use(cors('*'))

app.use(bodyParser.json())

app.get('/_reset', (req, res) => {
resetDatabase()
res.status(200).end()
})

const server = new ApolloServer({
typeDefs,
resolvers,
schema,
context: () => new Promise(resolve => {
setTimeout(() => resolve({}), 50)
}),
plugins: [
// Proper shutdown for the WebSocket server.
{
async serverWillStart () {
return {
async drainServer () {
await serverCleanup.dispose()
},
}
},
},
],
csrfPrevention: false,
})

await server.start()

app.use('/graphql', expressMiddleware(server))

const httpServer = createServer(app)

// Websocket

const wsServer = new WebSocketServer({
server: httpServer,
path: '/graphql',
})

server.applyMiddleware({ app })
const serverCleanup = useServer({
schema,
}, wsServer)

app.listen({
httpServer.listen({
port: 4042,
}, () => {
console.log('🚀 Server ready at http://localhost:4042')
Expand Down
67 changes: 36 additions & 31 deletions packages/test-e2e-composable-vue3/src/components/ChannelView.vue
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ export default defineComponent({
id: props.id,
}), {
notifyOnNetworkStatusChange: true,
keepPreviousResult: true,
})
const channel = computed(() => result.value?.channel)
Expand Down Expand Up @@ -63,42 +64,46 @@ export default defineComponent({
</script>
<template>
<div
v-if="loading"
class="loading-channel"
>
Loading channel...
</div>
<div
v-else
class="flex flex-col"
>
<div class="flex-none p-6 border-b border-gray-200 bg-white">
Currently viewing # {{ channel.label }}
<a
class="text-green-500 cursor-pointer"
data-test-id="refetch"
@click="refetch()"
>Refetch</a>
<div>
<div
v-if="loading"
class="loading-channel fixed top-0 left-0 w-full flex"
>
<div class="px-4 py-2 rounded-b mx-auto bg-white border-b border-l border-r border-gray-200">
Loading channel...
</div>
</div>
<div
ref="messagesEl"
class="flex-1 overflow-y-auto"
v-if="channel"
class="flex flex-col h-full"
>
<MessageItem
v-for="message of channel.messages"
:key="message.id"
:message="message"
class="m-2"
<div class="flex-none p-6 border-b border-gray-200 bg-white">
Currently viewing # {{ channel.label }}
<a
class="text-green-500 cursor-pointer"
data-test-id="refetch"
@click="refetch()"
>Refetch</a>
</div>
<div
ref="messagesEl"
class="flex-1 overflow-y-auto"
>
<MessageItem
v-for="message of channel.messages"
:key="message.id"
:message="message"
class="m-2"
/>
</div>
<MessageForm
:channel-id="channel.id"
class="flex-none m-2 mt-0"
/>
</div>
<MessageForm
:channel-id="channel.id"
class="flex-none m-2 mt-0"
/>
</div>
</template>
Loading

0 comments on commit 13bfbbe

Please sign in to comment.