Skip to content

Commit

Permalink
Fix tests
Browse files Browse the repository at this point in the history
  • Loading branch information
ardatan committed Aug 29, 2022
1 parent 665071c commit d9e567d
Show file tree
Hide file tree
Showing 4 changed files with 80 additions and 93 deletions.
2 changes: 0 additions & 2 deletions packages/loaders/openapi/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -42,12 +42,10 @@
"@graphql-tools/utils": "8.10.0",
"@graphql-yoga/node": "2.13.9",
"@types/cookie-parser": "1.4.3",
"@types/eventsource": "1.1.9",
"@types/multer": "1.4.7",
"@whatwg-node/fetch": "0.3.2",
"body-parser": "1.20.0",
"cookie-parser": "1.4.6",
"eventsource": "2.0.2",
"express": "4.18.1",
"json-bigint-patch": "0.0.8",
"multer": "1.4.5-lts.1"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,9 @@ export async function getJSONSchemaOptionsFromOpenAPIOptions(

function handleCallback(callbackKey: string, callbackObj: OpenAPIV3.CallbackObject) {
for (const callbackUrlRefKey in callbackObj) {
if (callbackUrlRefKey.startsWith('$')) {
continue;
}
const pubsubTopic = callbackUrlRefKey.split('$request.query').join('args').split('$request.body#/').join('args.');
const callbackOperationConfig: JSONSchemaPubSubOperationConfig = {
type: OperationTypeNode.SUBSCRIPTION,
Expand All @@ -108,6 +111,7 @@ export async function getJSONSchemaOptionsFromOpenAPIOptions(
for (const method in callbackUrlObj) {
const callbackOperation: OpenAPIV3.OperationObject = callbackUrlObj[method];
callbackOperationConfig.field = callbackOperation.operationId;
callbackOperationConfig.description = callbackOperation.description || callbackOperation.summary;
const requestBodyContents = (callbackOperation.requestBody as OpenAPIV3.RequestBodyObject)?.content;
if (requestBodyContents) {
callbackOperationConfig.responseSchema = requestBodyContents[Object.keys(requestBodyContents)[0]]
Expand Down
149 changes: 71 additions & 78 deletions packages/loaders/openapi/tests/example_api7.test.ts
Original file line number Diff line number Diff line change
@@ -1,57 +1,48 @@
/* eslint-disable no-unreachable-loop */
import { createServer, YogaNodeServerInstance } from '@graphql-yoga/node';
import { fetch } from '@whatwg-node/fetch';
import { graphql, GraphQLSchema } from 'graphql';
import EventSource from 'eventsource';
import { AbortController, fetch } from '@whatwg-node/fetch';
import { GraphQLSchema } from 'graphql';

import { loadGraphQLSchemaFromOpenAPI } from '../src/loadGraphQLSchemaFromOpenAPI';
import { startServer, stopServer, pubsub } from './example_api7_server';

let createdSchema: GraphQLSchema;
const TEST_PORT = 3009;
const HTTP_PORT = 3008;
// Update PORT for this test case:
const baseUrl = `http://localhost:${HTTP_PORT}/api`;
const GRAPHQL_PORT = 3009;
const API_PORT = 3008;

let yogaServer: YogaNodeServerInstance<any, any, any>;

describe('OpenAPI Loader: example_api7', () => {
// Set up the schema first and run example API servers
beforeAll(async () => {
const schema = await loadGraphQLSchemaFromOpenAPI('example_api7', {
createdSchema = await loadGraphQLSchemaFromOpenAPI('example_api7', {
fetch,
baseUrl,
baseUrl: `http://localhost:${API_PORT}/api`,
source: './fixtures/example_oas7.json',
cwd: __dirname,
pubsub,
});

createdSchema = schema;
try {
yogaServer = createServer({
schema,
port: TEST_PORT,
context: { pubsub },
});
yogaServer = createServer({
schema: createdSchema,
port: GRAPHQL_PORT,
context: { pubsub },
maskedErrors: false,
logging: false,
});

await yogaServer.start();
} catch (e) {
console.log('error', e);
}
await startServer(HTTP_PORT);
await Promise.all([yogaServer.start(), startServer(API_PORT)]);
});

/**
* Shut down API servers
*/
afterAll(async () => {
await new Promise(resolve => setTimeout(resolve, 500));
await Promise.all([yogaServer.stop(), stopServer()]);
});

it('Receive data from the subscription after creating a new instance', async () => {
const userName = 'Carlos';
const deviceName = 'Bot';

const query = /* GraphQL */ `
const subscriptionOperation = /* GraphQL */ `
subscription watchDevice($method: String!, $userName: String!) {
devicesEventListener(method: $method, userName: $userName) {
name
Expand All @@ -60,8 +51,8 @@ describe('OpenAPI Loader: example_api7', () => {
}
`;

const query2 = /* GraphQL */ `
mutation ($deviceInput: Device_Input!) {
const mutationOperation = /* GraphQL */ `
mutation triggerEvent($deviceInput: Device_Input!) {
createDevice(input: $deviceInput) {
... on Device {
name
Expand All @@ -71,62 +62,64 @@ describe('OpenAPI Loader: example_api7', () => {
}
}
`;

await new Promise<void>((resolve, reject) => {
const url = new URL(`http://localhost:${TEST_PORT}/graphql`);

url.searchParams.append('query', query);
url.searchParams.append(
'variables',
JSON.stringify({
method: 'POST',
userName,
})
);

const eventsource = new EventSource(url.href, {
withCredentials: true, // is this needed?
});

eventsource.onerror = e => {
eventsource.close();
reject(e);
};

eventsource.onmessage = event => {
const res = JSON.parse(event.data);

expect(res.data).toEqual({
devicesEventListener: {
name: deviceName,
status: false,
},
});

eventsource.close();
resolve();
};

setTimeout(() => {
graphql({
schema: createdSchema,
source: query2,
variableValues: {
const baseUrl = `http://localhost:${GRAPHQL_PORT}/graphql`;
const url = new URL(baseUrl);

url.searchParams.append('query', subscriptionOperation);
url.searchParams.append(
'variables',
JSON.stringify({
method: 'POST',
userName,
})
);

setTimeout(async () => {
const response = await fetch(baseUrl, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify({
query: mutationOperation,
variables: {
deviceInput: {
name: `${deviceName}`,
userName: `${userName}`,
status: false,
},
},
})
.then(res => {
if (!res.data) {
console.log(res.errors?.[0]);
reject(new Error('Failed mutation'));
}
})
.catch(reject);
}, 500);
}),
});
const result = await response.json();
expect(result.errors).toBeFalsy();
}, 300);

const abortCtrl = new AbortController();

const response = await fetch(url.toString(), {
method: 'GET',
headers: {
Accept: 'text/event-stream',
},
signal: abortCtrl.signal,
});

for await (const chunk of response.body) {
const data = Buffer.from(chunk).toString('utf-8');
expect(data.trim()).toBe(
`data: ${JSON.stringify({
data: {
devicesEventListener: {
name: deviceName,
status: false,
},
},
})}`
);
break;
}

abortCtrl.abort();
});
});
18 changes: 5 additions & 13 deletions packages/loaders/openapi/tests/example_api7_server.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
/* eslint-disable import/no-extraneous-dependencies */
/* eslint-disable import/no-nodejs-modules */
// Copyright IBM Corp. 2017,2018. All Rights Reserved.
// Node module: openapi-to-graphql
// This file is licensed under the MIT License.
// License text available at https://opensource.org/licenses/MIT

import { PubSub } from '@graphql-mesh/utils';
import * as bodyParser from 'body-parser';
import express from 'express';
import { Server } from 'http';

Expand All @@ -29,7 +30,7 @@ const Devices = {
* Starts the server at the given port
*/
export function startServer(HTTP_PORT: number) {
app.use(bodyParser.json());
app.use(express.json());

app.get('/api/user', (req, res) => {
res.send({
Expand Down Expand Up @@ -88,21 +89,12 @@ export function startServer(HTTP_PORT: number) {
new Promise(resolve => {
server = app.listen(HTTP_PORT, resolve as () => void);
}),
]).then(() => {
console.log(`Example HTTP API accessible on port ${HTTP_PORT}`);
});
]);
}

/**
* Stops server.
*/
export function stopServer() {
return Promise.all([server.close()]).then(() => {
console.log(`Stopped HTTP API server`);
});
}

// If run from command line, start server:
if (require.main === module) {
startServer(3008).catch(console.error);
return new Promise(resolve => server.close(resolve));
}

0 comments on commit d9e567d

Please sign in to comment.