Skip to content

Commit

Permalink
feat: Extend httpProxy options to allow more options (#875)
Browse files Browse the repository at this point in the history
  • Loading branch information
jpeyper authored and ovidiuch committed Oct 17, 2018
1 parent d648733 commit f389fe0
Show file tree
Hide file tree
Showing 5 changed files with 109 additions and 4 deletions.
1 change: 1 addition & 0 deletions README.md
Expand Up @@ -1107,6 +1107,7 @@ module.exports = {
hot: false,

// HTTP proxy specific requests to a different target
// For advanced usage see https://github.com/react-cosmos/react-cosmos/pull/875
httpProxy: {
context: '/api',
target: 'http://localhost:4000/api'
Expand Down
6 changes: 5 additions & 1 deletion packages/react-cosmos-flow/config.js
Expand Up @@ -9,6 +9,10 @@ type WebpackConfigOverride = (WebpackConfig, { env: string }) => WebpackConfig;

export type PluginConfig = { [prop: string]: mixed };

type BasicHttpProxyConfig = { context: string };
type AdvancedHttpProxyConfig = { [contextKey: string]: string | {} };
export type HttpProxyConfig = BasicHttpProxyConfig | AdvancedHttpProxyConfig;

export type Config = {
next: boolean,
rootPath: string,
Expand All @@ -26,7 +30,7 @@ export type Config = {
publicPath?: string,
publicUrl: string,
containerQuerySelector?: string,
httpProxy?: {| context: string, target: string |},
httpProxy?: HttpProxyConfig,
watchDirs: Array<string>,
modulesPath: string,
plugin: PluginConfig,
Expand Down
82 changes: 82 additions & 0 deletions packages/react-cosmos/src/server/shared/__tests__/http-proxy.js
@@ -0,0 +1,82 @@
import httpProxyMiddleware from 'http-proxy-middleware';

import { setupHttpProxy } from '../http-proxy';

jest.mock('http-proxy-middleware');

describe('setup http proxy', () => {
beforeEach(() => {
httpProxyMiddleware.mockReset();
});

it('with basic configuration', () => {
const app = {
use: jest.fn()
};

const httpProxyConfig = {
context: '/api',
target: 'https://example.com',
otherValue: {
test: 'value'
}
};

httpProxyMiddleware.mockReturnValueOnce('__MOCKED_MIDDLEWARE__');

setupHttpProxy(app, httpProxyConfig);

expect(app.use).toHaveBeenCalledWith('/api', '__MOCKED_MIDDLEWARE__');
expect(httpProxyMiddleware).toHaveBeenCalledWith({
target: 'https://example.com',
otherValue: {
test: 'value'
}
});
});

it('with advanced configuration', () => {
const app = {
use: jest.fn()
};

const httpProxyConfig = {
'/api': {
target: 'https://example-api.com',
apiStuff: {
api: 'value'
}
},
'/assets': {
target: 'https://example-assets.com',
assetsStuff: {
asset: 'value'
}
}
};

httpProxyMiddleware.mockReturnValueOnce('__MOCKED_API_MIDDLEWARE__');
httpProxyMiddleware.mockReturnValueOnce('__MOCKED_ASSETS_MIDDLEWARE__');

setupHttpProxy(app, httpProxyConfig);

expect(app.use).toHaveBeenCalledWith('/api', '__MOCKED_API_MIDDLEWARE__');
expect(httpProxyMiddleware).toHaveBeenCalledWith({
target: 'https://example-api.com',
apiStuff: {
api: 'value'
}
});

expect(app.use).toHaveBeenCalledWith(
'/assets',
'__MOCKED_ASSETS_MIDDLEWARE__'
);
expect(httpProxyMiddleware).toHaveBeenCalledWith({
target: 'https://example-assets.com',
assetsStuff: {
asset: 'value'
}
});
});
});
19 changes: 19 additions & 0 deletions packages/react-cosmos/src/server/shared/http-proxy.js
@@ -0,0 +1,19 @@
// @flow

import httpProxyMiddleware from 'http-proxy-middleware';
import type { HttpProxyConfig } from 'react-cosmos-flow/config';

export function setupHttpProxy(
app: express$Application,
httpProxy: HttpProxyConfig
) {
const { context, ...options } = httpProxy;
if (typeof context === 'string') {
app.use(context, httpProxyMiddleware(options));
} else {
Object.keys(httpProxy).forEach(contextKey => {
const options = httpProxy[contextKey];
app.use(contextKey, httpProxyMiddleware(options));
});
}
}
5 changes: 2 additions & 3 deletions packages/react-cosmos/src/server/shared/server.js
Expand Up @@ -4,9 +4,9 @@ import { join, relative } from 'path';
import { createServer as createHttpServer } from 'http';
import promisify from 'util.promisify';
import express from 'express';
import httpProxyMiddleware from 'http-proxy-middleware';
import launchEditor from 'react-dev-utils/launchEditor';
import { getPlaygroundHtml, getPlaygroundHtmlNext } from './playground-html';
import { setupHttpProxy } from './http-proxy';

import type { Config } from 'react-cosmos-flow/config';
import type { PlaygroundOpts } from 'react-cosmos-flow/playground';
Expand All @@ -22,8 +22,7 @@ export function createServerApp({
const app = express();

if (httpProxy) {
const { context, target } = httpProxy;
app.use(context, httpProxyMiddleware(target));
setupHttpProxy(app, httpProxy);
}

const playgroundHtml =
Expand Down

0 comments on commit f389fe0

Please sign in to comment.