Skip to content

Commit

Permalink
feat: call Express directly instead of via a proxy server running on …
Browse files Browse the repository at this point in the history
…a local socket

Only Express has been implemented so far
  • Loading branch information
brett-vendia committed Jan 5, 2021
1 parent 6b54daf commit a468c72
Show file tree
Hide file tree
Showing 16 changed files with 411 additions and 468 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ Set this to true to have serverless-express include the error stack trace in the

### eventFns

serverless-express natively supports API Gateway, ALB, and Lambda@Edge. If you want to use Express with other AWS Services which can invoke a Lambda Function you can provide your own custom request/response mappings via `eventFns`. See the [custom-mapper-dynamodb example](examples/custom-mapper-dynamodb).
serverless-express natively supports API Gateway, ALB, and Lambda@Edge. If you want to use Express with other AWS Services integrated with Lambda you can provide your own custom request/response mappings via `eventFns`. See the [custom-mapper-dynamodb example](examples/custom-mapper-dynamodb).

```js
function requestMapper ({ event }) {
Expand Down
98 changes: 3 additions & 95 deletions __tests__/integration.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ const apiGatewayEvent = require('../examples/basic-starter/api-gateway-event.jso
const app = require('../examples/basic-starter/src/app')

const serverlessExpress = vendiaServerlessExpress.configure({ app })
const server = serverlessExpress.server
const nodeMajorVersion = process.version.split('.')[0].split('v')[1]

function clone (json) {
Expand Down Expand Up @@ -45,7 +44,6 @@ function makeResponse (response) {
}
const baseHeaders = {
'access-control-allow-origin': ['*'],
connection: ['close'],
'content-type': ['application/json; charset=utf-8'],
'x-powered-by': ['Express']
}
Expand Down Expand Up @@ -120,7 +118,7 @@ describe('integration tests', () => {
expect(response.body.startsWith('<!DOCTYPE html>')).toBe(true)
const expectedResponse = makeResponse({
multiValueHeaders: {
'content-length': ['151'],
'content-length': [151],
'content-security-policy': ["default-src 'none'"],
'content-type': ['text/html; charset=utf-8'],
'x-content-type-options': ['nosniff']
Expand Down Expand Up @@ -189,24 +187,6 @@ describe('integration tests', () => {
}))
})

test('GET JSON single (resolutionMode = PROMISE; new server)', async () => {
const newServererlessExpress = vendiaServerlessExpress.configure({ app, resolutionMode: 'PROMISE' })
const event = makeEvent({
path: '/users/1',
httpMethod: 'GET'
})
const response = await newServererlessExpress.handler(event)
delete response.multiValueHeaders.date
expect(response).toEqual(makeResponse({
body: '{"id":1,"name":"Joe"}',
multiValueHeaders: {
'content-length': ['21'],
etag: ['W/"15-rRboW+j/yFKqYqV6yklp53+fANQ"']
}
}))
newServererlessExpress.server.close()
})

test('GET JSON single 404', async () => {
const response = await serverlessExpress.handler(makeEvent({
path: '/users/3',
Expand All @@ -224,16 +204,12 @@ describe('integration tests', () => {
})

test('success - image response', async () => {
const serverWithBinaryTypes = serverlessExpress.createServer({
app,
binaryMimeTypes: ['image/*']
})
const event = makeEvent({
path: '/sam',
httpMethod: 'GET'
})
const response = await serverlessExpress.proxy({
server: serverWithBinaryTypes,
binaryMimeTypes: ['image/*'],
event
})
delete response.multiValueHeaders.date
Expand All @@ -249,12 +225,11 @@ describe('integration tests', () => {
multiValueHeaders: {
'accept-ranges': ['bytes'],
'cache-control': ['public, max-age=0'],
'content-length': ['15933'],
'content-length': [15933],
'content-type': ['image/png']
},
isBase64Encoded: true
}))
serverWithBinaryTypes.close()
})
const newName = 'Sandy Samantha Salamander'

Expand Down Expand Up @@ -341,9 +316,6 @@ describe('integration tests', () => {
'access-control-allow-origin': [
'*'
],
connection: [
'close'
],
'content-length': [
'24'
],
Expand All @@ -361,30 +333,6 @@ describe('integration tests', () => {
}))
})

// TODO: This test is failing on Node.js 10 as this isn't forcing a connection error like earlier versions of Node do.
// Need to determine a new way of forcing a connection error which works in both 8 and 10 before re-enabling this.
// For now, we still have a unit test for forwardConnectionErrorResponseToApiGateway.
test.skip('forwardConnectionErrorResponseToApiGateway', async () => {
const response = await serverlessExpress.handler(makeEvent({
path: '/',
httpMethod: 'GET',
body: '{"name": "Sam502"}',
multiValueHeaders: {
'Content-Length': ['-1']
}
}))
delete response.multiValueHeaders.date
expect(response).toEqual({
body: '',
multiValueHeaders: {},
statusCode: 502
})
})

const mockApp = function (req, res) {
res.end('')
}

test.skip('forwardLibraryErrorResponseToApiGateway', async () => {
const response = await serverlessExpress.handler(null)
expect(response).toEqual({
Expand All @@ -394,23 +342,6 @@ describe('integration tests', () => {
})
})

test('serverListenCallback', async () => {
const serverListenCallback = jest.fn()
const serverWithListenCallback = serverlessExpress.createServer({
app: mockApp
})
serverWithListenCallback.on('listening', serverListenCallback)

const response = await serverlessExpress.proxy({
server: serverWithListenCallback,
event: makeEvent()
})

expect(response.statusCode).toBe(200)
expect(serverListenCallback).toHaveBeenCalled()
serverWithListenCallback.close()
})

test('Multiple headers of the same name (set-cookie)', async () => {
const response = await serverlessExpress.handler(makeEvent({
path: '/cookie',
Expand All @@ -432,27 +363,4 @@ describe('integration tests', () => {
statusCode: 200
}))
})

// NOTE: These must remain as the final tests as the EADDRINUSE test breaks
// the main `server` used by tests since the socket is deleted
// and the server.onClose also closes `server`
test('server.onError EADDRINUSE', async () => {
const serverWithSameSocketPath = serverlessExpress.createServer({ app: mockApp })
serverWithSameSocketPath._serverlessExpress.socketPath = server._serverlessExpress.socketPath

const response = await serverlessExpress.proxy({
server: serverWithSameSocketPath,
event: makeEvent()
})
expect(response.statusCode).toBe(200)
expect(serverWithSameSocketPath._serverlessExpress.socketPath).not.toBe(server._serverlessExpress.socketPath)
serverWithSameSocketPath.close()
})

test('server.onClose', async () => {
server.on('close', () => {
expect(server.listening).toBe(false)
})
server.close()
})
})

0 comments on commit a468c72

Please sign in to comment.