http-proxy-middleware 0.19.0 → 0.19.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +35 -5
- package/README.md +278 -264
- package/index.js +1 -1
- package/lib/config-factory.js +14 -12
- package/lib/context-matcher.js +9 -9
- package/lib/errors.js +8 -4
- package/lib/handlers.js +17 -9
- package/lib/index.js +50 -20
- package/lib/logger.js +19 -19
- package/lib/path-rewriter.js +16 -10
- package/lib/router.js +8 -6
- package/package.json +20 -20
package/index.js
CHANGED
package/lib/config-factory.js
CHANGED
|
@@ -7,7 +7,7 @@ module.exports = {
|
|
|
7
7
|
createConfig: createConfig
|
|
8
8
|
}
|
|
9
9
|
|
|
10
|
-
function createConfig
|
|
10
|
+
function createConfig(context, opts) {
|
|
11
11
|
// structure of config object to be returned
|
|
12
12
|
var config = {
|
|
13
13
|
context: undefined,
|
|
@@ -19,8 +19,8 @@ function createConfig (context, opts) {
|
|
|
19
19
|
config.context = '/'
|
|
20
20
|
config.options = _.assign(config.options, context)
|
|
21
21
|
|
|
22
|
-
|
|
23
|
-
|
|
22
|
+
// app.use('/api', proxy('http://localhost:9000'));
|
|
23
|
+
// app.use(proxy('http://localhost:9000/api'));
|
|
24
24
|
} else if (isStringShortHand(context)) {
|
|
25
25
|
var oUrl = url.parse(context)
|
|
26
26
|
var target = [oUrl.protocol, '//', oUrl.host].join('')
|
|
@@ -31,7 +31,7 @@ function createConfig (context, opts) {
|
|
|
31
31
|
if (oUrl.protocol === 'ws:' || oUrl.protocol === 'wss:') {
|
|
32
32
|
config.options.ws = true
|
|
33
33
|
}
|
|
34
|
-
|
|
34
|
+
// app.use('/api', proxy({target:'http://localhost:9000'}));
|
|
35
35
|
} else {
|
|
36
36
|
config.context = context
|
|
37
37
|
config.options = _.assign(config.options, opts)
|
|
@@ -63,9 +63,9 @@ function createConfig (context, opts) {
|
|
|
63
63
|
* @param {String} context [description]
|
|
64
64
|
* @return {Boolean} [description]
|
|
65
65
|
*/
|
|
66
|
-
function isStringShortHand
|
|
66
|
+
function isStringShortHand(context) {
|
|
67
67
|
if (_.isString(context)) {
|
|
68
|
-
return !!
|
|
68
|
+
return !!url.parse(context).host
|
|
69
69
|
}
|
|
70
70
|
}
|
|
71
71
|
|
|
@@ -80,16 +80,18 @@ function isStringShortHand (context) {
|
|
|
80
80
|
* @param {*} opts [description]
|
|
81
81
|
* @return {Boolean} [description]
|
|
82
82
|
*/
|
|
83
|
-
function isContextless
|
|
84
|
-
return
|
|
83
|
+
function isContextless(context, opts) {
|
|
84
|
+
return _.isPlainObject(context) && _.isEmpty(opts)
|
|
85
85
|
}
|
|
86
86
|
|
|
87
|
-
function mapLegacyProxyHostOption
|
|
87
|
+
function mapLegacyProxyHostOption(options) {
|
|
88
88
|
// set options.headers.host when option.proxyHost is provided
|
|
89
89
|
if (options.proxyHost) {
|
|
90
90
|
logger.warn('*************************************')
|
|
91
91
|
logger.warn('[HPM] Deprecated "option.proxyHost"')
|
|
92
|
-
logger.warn(
|
|
92
|
+
logger.warn(
|
|
93
|
+
' Use "option.changeOrigin" or "option.headers.host" instead'
|
|
94
|
+
)
|
|
93
95
|
logger.warn(' "option.proxyHost" will be removed in future release.')
|
|
94
96
|
logger.warn('*************************************')
|
|
95
97
|
|
|
@@ -101,7 +103,7 @@ function mapLegacyProxyHostOption (options) {
|
|
|
101
103
|
}
|
|
102
104
|
|
|
103
105
|
// Warn deprecated proxyTable api usage
|
|
104
|
-
function mapLegacyProxyTableOption
|
|
106
|
+
function mapLegacyProxyTableOption(options) {
|
|
105
107
|
if (options.proxyTable) {
|
|
106
108
|
logger.warn('*************************************')
|
|
107
109
|
logger.warn('[HPM] Deprecated "option.proxyTable"')
|
|
@@ -116,7 +118,7 @@ function mapLegacyProxyTableOption (options) {
|
|
|
116
118
|
return options
|
|
117
119
|
}
|
|
118
120
|
|
|
119
|
-
function configureLogger
|
|
121
|
+
function configureLogger(options) {
|
|
120
122
|
if (options.logLevel) {
|
|
121
123
|
logger.setLevel(options.logLevel)
|
|
122
124
|
}
|
package/lib/context-matcher.js
CHANGED
|
@@ -8,7 +8,7 @@ module.exports = {
|
|
|
8
8
|
match: matchContext
|
|
9
9
|
}
|
|
10
10
|
|
|
11
|
-
function matchContext
|
|
11
|
+
function matchContext(context, uri, req) {
|
|
12
12
|
// single path
|
|
13
13
|
if (isStringPath(context)) {
|
|
14
14
|
return matchSingleStringPath(context, uri)
|
|
@@ -45,18 +45,18 @@ function matchContext (context, uri, req) {
|
|
|
45
45
|
* @param {String} uri 'http://example.org/api/b/c/d.html'
|
|
46
46
|
* @return {Boolean}
|
|
47
47
|
*/
|
|
48
|
-
function matchSingleStringPath
|
|
48
|
+
function matchSingleStringPath(context, uri) {
|
|
49
49
|
var pathname = getUrlPathName(uri)
|
|
50
50
|
return pathname.indexOf(context) === 0
|
|
51
51
|
}
|
|
52
52
|
|
|
53
|
-
function matchSingleGlobPath
|
|
53
|
+
function matchSingleGlobPath(pattern, uri) {
|
|
54
54
|
var pathname = getUrlPathName(uri)
|
|
55
55
|
var matches = micromatch(pathname, pattern)
|
|
56
|
-
return matches &&
|
|
56
|
+
return matches && matches.length > 0
|
|
57
57
|
}
|
|
58
58
|
|
|
59
|
-
function matchMultiGlobPath
|
|
59
|
+
function matchMultiGlobPath(patternList, uri) {
|
|
60
60
|
return matchSingleGlobPath(patternList, uri)
|
|
61
61
|
}
|
|
62
62
|
|
|
@@ -65,7 +65,7 @@ function matchMultiGlobPath (patternList, uri) {
|
|
|
65
65
|
* @param {String} uri 'http://example.org/api/b/c/d.html'
|
|
66
66
|
* @return {Boolean}
|
|
67
67
|
*/
|
|
68
|
-
function matchMultiPath
|
|
68
|
+
function matchMultiPath(contextList, uri) {
|
|
69
69
|
for (var i = 0; i < contextList.length; i++) {
|
|
70
70
|
var context = contextList[i]
|
|
71
71
|
if (matchSingleStringPath(context, uri)) {
|
|
@@ -81,14 +81,14 @@ function matchMultiPath (contextList, uri) {
|
|
|
81
81
|
* @param {String} uri from req.url
|
|
82
82
|
* @return {String} RFC 3986 path
|
|
83
83
|
*/
|
|
84
|
-
function getUrlPathName
|
|
84
|
+
function getUrlPathName(uri) {
|
|
85
85
|
return uri && url.parse(uri).pathname
|
|
86
86
|
}
|
|
87
87
|
|
|
88
|
-
function isStringPath
|
|
88
|
+
function isStringPath(context) {
|
|
89
89
|
return _.isString(context) && !isGlob(context)
|
|
90
90
|
}
|
|
91
91
|
|
|
92
|
-
function isGlobPath
|
|
92
|
+
function isGlobPath(context) {
|
|
93
93
|
return isGlob(context)
|
|
94
94
|
}
|
package/lib/errors.js
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
1
|
/* eslint-disable max-len */
|
|
2
2
|
|
|
3
3
|
module.exports = {
|
|
4
|
-
ERR_CONFIG_FACTORY_TARGET_MISSING:
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
4
|
+
ERR_CONFIG_FACTORY_TARGET_MISSING:
|
|
5
|
+
'[HPM] Missing "target" option. Example: {target: "http://www.example.org"}',
|
|
6
|
+
ERR_CONTEXT_MATCHER_GENERIC:
|
|
7
|
+
'[HPM] Invalid context. Expecting something like: "/api" or ["/api", "/ajax"]',
|
|
8
|
+
ERR_CONTEXT_MATCHER_INVALID_ARRAY:
|
|
9
|
+
'[HPM] Invalid context. Expecting something like: ["/api", "/ajax"] or ["/api/**", "!**.html"]',
|
|
10
|
+
ERR_PATH_REWRITER_CONFIG:
|
|
11
|
+
'[HPM] Invalid pathRewrite config. Expecting object with pathRewrite config or a rewrite function'
|
|
8
12
|
}
|
package/lib/handlers.js
CHANGED
|
@@ -6,22 +6,29 @@ module.exports = {
|
|
|
6
6
|
getHandlers: getProxyEventHandlers
|
|
7
7
|
}
|
|
8
8
|
|
|
9
|
-
function init
|
|
9
|
+
function init(proxy, opts) {
|
|
10
10
|
var handlers = getProxyEventHandlers(opts)
|
|
11
11
|
|
|
12
|
-
_.forIn(handlers, function
|
|
12
|
+
_.forIn(handlers, function(handler, eventName) {
|
|
13
13
|
proxy.on(eventName, handlers[eventName])
|
|
14
14
|
})
|
|
15
15
|
|
|
16
16
|
logger.debug('[HPM] Subscribed to http-proxy events: ', _.keys(handlers))
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
function getProxyEventHandlers
|
|
19
|
+
function getProxyEventHandlers(opts) {
|
|
20
20
|
// https://github.com/nodejitsu/node-http-proxy#listening-for-proxy-events
|
|
21
|
-
var proxyEvents = [
|
|
21
|
+
var proxyEvents = [
|
|
22
|
+
'error',
|
|
23
|
+
'proxyReq',
|
|
24
|
+
'proxyReqWs',
|
|
25
|
+
'proxyRes',
|
|
26
|
+
'open',
|
|
27
|
+
'close'
|
|
28
|
+
]
|
|
22
29
|
var handlers = {}
|
|
23
30
|
|
|
24
|
-
_.forEach(proxyEvents, function
|
|
31
|
+
_.forEach(proxyEvents, function(event) {
|
|
25
32
|
// all handlers for the http-proxy events are prefixed with 'on'.
|
|
26
33
|
// loop through options and try to find these handlers
|
|
27
34
|
// and add them to the handlers object for subscription in init().
|
|
@@ -46,8 +53,8 @@ function getProxyEventHandlers (opts) {
|
|
|
46
53
|
return handlers
|
|
47
54
|
}
|
|
48
55
|
|
|
49
|
-
function defaultErrorHandler
|
|
50
|
-
var host =
|
|
56
|
+
function defaultErrorHandler(err, req, res) {
|
|
57
|
+
var host = req.headers && req.headers.host
|
|
51
58
|
var code = err.code
|
|
52
59
|
|
|
53
60
|
if (res.writeHead && !res.headersSent) {
|
|
@@ -60,7 +67,8 @@ function defaultErrorHandler (err, req, res) {
|
|
|
60
67
|
case 'ECONNREFUSED':
|
|
61
68
|
res.writeHead(504)
|
|
62
69
|
break
|
|
63
|
-
default:
|
|
70
|
+
default:
|
|
71
|
+
res.writeHead(500)
|
|
64
72
|
}
|
|
65
73
|
}
|
|
66
74
|
}
|
|
@@ -68,7 +76,7 @@ function defaultErrorHandler (err, req, res) {
|
|
|
68
76
|
res.end('Error occured while trying to proxy to: ' + host + req.url)
|
|
69
77
|
}
|
|
70
78
|
|
|
71
|
-
function logClose
|
|
79
|
+
function logClose(req, socket, head) {
|
|
72
80
|
// view disconnected websocket connections
|
|
73
81
|
logger.info('[HPM] Client disconnected')
|
|
74
82
|
}
|
package/lib/index.js
CHANGED
|
@@ -10,7 +10,7 @@ var getArrow = require('./logger').getArrow
|
|
|
10
10
|
|
|
11
11
|
module.exports = HttpProxyMiddleware
|
|
12
12
|
|
|
13
|
-
function HttpProxyMiddleware
|
|
13
|
+
function HttpProxyMiddleware(context, opts) {
|
|
14
14
|
// https://github.com/chimurai/http-proxy-middleware/issues/57
|
|
15
15
|
var wsUpgradeDebounced = _.debounce(handleUpgrade)
|
|
16
16
|
var wsInitialized = false
|
|
@@ -19,7 +19,12 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
19
19
|
|
|
20
20
|
// create proxy
|
|
21
21
|
var proxy = httpProxy.createProxyServer({})
|
|
22
|
-
logger.info(
|
|
22
|
+
logger.info(
|
|
23
|
+
'[HPM] Proxy created:',
|
|
24
|
+
config.context,
|
|
25
|
+
' -> ',
|
|
26
|
+
proxyOptions.target
|
|
27
|
+
)
|
|
23
28
|
|
|
24
29
|
var pathRewriter = PathRewriter.create(proxyOptions.pathRewrite) // returns undefined when "pathRewrite" is not provided
|
|
25
30
|
|
|
@@ -35,7 +40,7 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
35
40
|
|
|
36
41
|
return middleware
|
|
37
42
|
|
|
38
|
-
function middleware
|
|
43
|
+
function middleware(req, res, next) {
|
|
39
44
|
if (shouldProxy(config.context, req)) {
|
|
40
45
|
var activeProxyOptions = prepareProxyRequest(req)
|
|
41
46
|
proxy.web(req, res, activeProxyOptions)
|
|
@@ -49,7 +54,7 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
49
54
|
}
|
|
50
55
|
}
|
|
51
56
|
|
|
52
|
-
function catchUpgradeRequest
|
|
57
|
+
function catchUpgradeRequest(server) {
|
|
53
58
|
// subscribe once; don't subscribe on every request...
|
|
54
59
|
// https://github.com/chimurai/http-proxy-middleware/issues/113
|
|
55
60
|
if (!wsInitialized) {
|
|
@@ -58,7 +63,7 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
58
63
|
}
|
|
59
64
|
}
|
|
60
65
|
|
|
61
|
-
function handleUpgrade
|
|
66
|
+
function handleUpgrade(req, socket, head) {
|
|
62
67
|
// set to initialized when used externally
|
|
63
68
|
wsInitialized = true
|
|
64
69
|
|
|
@@ -77,8 +82,8 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
77
82
|
* @param {Object} req [description]
|
|
78
83
|
* @return {Boolean}
|
|
79
84
|
*/
|
|
80
|
-
function shouldProxy
|
|
81
|
-
var path =
|
|
85
|
+
function shouldProxy(context, req) {
|
|
86
|
+
var path = req.originalUrl || req.url
|
|
82
87
|
return contextMatcher.match(context, path, req)
|
|
83
88
|
}
|
|
84
89
|
|
|
@@ -90,10 +95,10 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
90
95
|
* @param {Object} req
|
|
91
96
|
* @return {Object} proxy options
|
|
92
97
|
*/
|
|
93
|
-
function prepareProxyRequest
|
|
98
|
+
function prepareProxyRequest(req) {
|
|
94
99
|
// https://github.com/chimurai/http-proxy-middleware/issues/17
|
|
95
100
|
// https://github.com/chimurai/http-proxy-middleware/issues/94
|
|
96
|
-
req.url =
|
|
101
|
+
req.url = req.originalUrl || req.url
|
|
97
102
|
|
|
98
103
|
// store uri before it gets rewritten for logging
|
|
99
104
|
var originalPath = req.url
|
|
@@ -107,29 +112,44 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
107
112
|
|
|
108
113
|
// debug logging for both http(s) and websockets
|
|
109
114
|
if (proxyOptions.logLevel === 'debug') {
|
|
110
|
-
var arrow = getArrow(
|
|
111
|
-
|
|
115
|
+
var arrow = getArrow(
|
|
116
|
+
originalPath,
|
|
117
|
+
req.url,
|
|
118
|
+
proxyOptions.target,
|
|
119
|
+
newProxyOptions.target
|
|
120
|
+
)
|
|
121
|
+
logger.debug(
|
|
122
|
+
'[HPM] %s %s %s %s',
|
|
123
|
+
req.method,
|
|
124
|
+
originalPath,
|
|
125
|
+
arrow,
|
|
126
|
+
newProxyOptions.target
|
|
127
|
+
)
|
|
112
128
|
}
|
|
113
129
|
|
|
114
130
|
return newProxyOptions
|
|
115
131
|
}
|
|
116
132
|
|
|
117
133
|
// Modify option.target when router present.
|
|
118
|
-
function __applyRouter
|
|
134
|
+
function __applyRouter(req, options) {
|
|
119
135
|
var newTarget
|
|
120
136
|
|
|
121
137
|
if (options.router) {
|
|
122
138
|
newTarget = Router.getTarget(req, options)
|
|
123
139
|
|
|
124
140
|
if (newTarget) {
|
|
125
|
-
logger.debug(
|
|
141
|
+
logger.debug(
|
|
142
|
+
'[HPM] Router new target: %s -> "%s"',
|
|
143
|
+
options.target,
|
|
144
|
+
newTarget
|
|
145
|
+
)
|
|
126
146
|
options.target = newTarget
|
|
127
147
|
}
|
|
128
148
|
}
|
|
129
149
|
}
|
|
130
150
|
|
|
131
151
|
// rewrite path
|
|
132
|
-
function __applyPathRewrite
|
|
152
|
+
function __applyPathRewrite(req, pathRewriter) {
|
|
133
153
|
if (pathRewriter) {
|
|
134
154
|
var path = pathRewriter(req.url, req)
|
|
135
155
|
|
|
@@ -141,12 +161,22 @@ function HttpProxyMiddleware (context, opts) {
|
|
|
141
161
|
}
|
|
142
162
|
}
|
|
143
163
|
|
|
144
|
-
function logError
|
|
145
|
-
var hostname =
|
|
164
|
+
function logError(err, req, res) {
|
|
165
|
+
var hostname =
|
|
166
|
+
(req.headers && req.headers.host) || (req.hostname || req.host) // (websocket) || (node0.10 || node 4/5)
|
|
146
167
|
var target = proxyOptions.target.host || proxyOptions.target
|
|
147
|
-
var errorMessage =
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
168
|
+
var errorMessage =
|
|
169
|
+
'[HPM] Error occurred while trying to proxy request %s from %s to %s (%s) (%s)'
|
|
170
|
+
var errReference =
|
|
171
|
+
'https://nodejs.org/api/errors.html#errors_common_system_errors' // link to Node Common Systems Errors page
|
|
172
|
+
|
|
173
|
+
logger.error(
|
|
174
|
+
errorMessage,
|
|
175
|
+
req.url,
|
|
176
|
+
hostname,
|
|
177
|
+
target,
|
|
178
|
+
err.code || err,
|
|
179
|
+
errReference
|
|
180
|
+
)
|
|
151
181
|
}
|
|
152
182
|
}
|
package/lib/logger.js
CHANGED
|
@@ -22,7 +22,7 @@ var LEVELS = {
|
|
|
22
22
|
|
|
23
23
|
module.exports = {
|
|
24
24
|
// singleton
|
|
25
|
-
getInstance: function
|
|
25
|
+
getInstance: function() {
|
|
26
26
|
if (!loggerInstance) {
|
|
27
27
|
loggerInstance = new Logger()
|
|
28
28
|
}
|
|
@@ -32,7 +32,7 @@ module.exports = {
|
|
|
32
32
|
getArrow: getArrow
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
function Logger
|
|
35
|
+
function Logger() {
|
|
36
36
|
var logLevel
|
|
37
37
|
var provider
|
|
38
38
|
|
|
@@ -42,12 +42,12 @@ function Logger () {
|
|
|
42
42
|
info: info,
|
|
43
43
|
warn: warn,
|
|
44
44
|
error: error,
|
|
45
|
-
setLevel: function
|
|
45
|
+
setLevel: function(v) {
|
|
46
46
|
if (isValidLevel(v)) {
|
|
47
47
|
logLevel = v
|
|
48
48
|
}
|
|
49
49
|
},
|
|
50
|
-
setProvider: function
|
|
50
|
+
setProvider: function(fn) {
|
|
51
51
|
if (fn && isValidProvider(fn)) {
|
|
52
52
|
provider = fn(defaultProvider)
|
|
53
53
|
}
|
|
@@ -58,37 +58,37 @@ function Logger () {
|
|
|
58
58
|
|
|
59
59
|
return api
|
|
60
60
|
|
|
61
|
-
function init
|
|
61
|
+
function init() {
|
|
62
62
|
api.setLevel('info')
|
|
63
|
-
api.setProvider(function
|
|
63
|
+
api.setProvider(function() {
|
|
64
64
|
return defaultProvider
|
|
65
65
|
})
|
|
66
66
|
}
|
|
67
67
|
|
|
68
68
|
// log will log messages, regardless of logLevels
|
|
69
|
-
function log
|
|
69
|
+
function log() {
|
|
70
70
|
provider.log(_interpolate.apply(null, arguments))
|
|
71
71
|
}
|
|
72
72
|
|
|
73
|
-
function debug
|
|
73
|
+
function debug() {
|
|
74
74
|
if (_showLevel('debug')) {
|
|
75
75
|
provider.debug(_interpolate.apply(null, arguments))
|
|
76
76
|
}
|
|
77
77
|
}
|
|
78
78
|
|
|
79
|
-
function info
|
|
79
|
+
function info() {
|
|
80
80
|
if (_showLevel('info')) {
|
|
81
81
|
provider.info(_interpolate.apply(null, arguments))
|
|
82
82
|
}
|
|
83
83
|
}
|
|
84
84
|
|
|
85
|
-
function warn
|
|
85
|
+
function warn() {
|
|
86
86
|
if (_showLevel('warn')) {
|
|
87
87
|
provider.warn(_interpolate.apply(null, arguments))
|
|
88
88
|
}
|
|
89
89
|
}
|
|
90
90
|
|
|
91
|
-
function error
|
|
91
|
+
function error() {
|
|
92
92
|
if (_showLevel('error')) {
|
|
93
93
|
provider.error(_interpolate.apply(null, arguments))
|
|
94
94
|
}
|
|
@@ -99,11 +99,11 @@ function Logger () {
|
|
|
99
99
|
* @param {String} showLevel [debug, info, warn, error, silent]
|
|
100
100
|
* @return {Boolean}
|
|
101
101
|
*/
|
|
102
|
-
function _showLevel
|
|
102
|
+
function _showLevel(showLevel) {
|
|
103
103
|
var result = false
|
|
104
104
|
var currentLogLevel = LEVELS[logLevel]
|
|
105
105
|
|
|
106
|
-
if (currentLogLevel &&
|
|
106
|
+
if (currentLogLevel && currentLogLevel <= LEVELS[showLevel]) {
|
|
107
107
|
result = true
|
|
108
108
|
}
|
|
109
109
|
|
|
@@ -112,14 +112,14 @@ function Logger () {
|
|
|
112
112
|
|
|
113
113
|
// make sure logged messages and its data are return interpolated
|
|
114
114
|
// make it possible for additional log data, such date/time or custom prefix.
|
|
115
|
-
function _interpolate
|
|
115
|
+
function _interpolate() {
|
|
116
116
|
var fn = _.spread(util.format)
|
|
117
117
|
var result = fn(_.slice(arguments))
|
|
118
118
|
|
|
119
119
|
return result
|
|
120
120
|
}
|
|
121
121
|
|
|
122
|
-
function isValidProvider
|
|
122
|
+
function isValidProvider(fnProvider) {
|
|
123
123
|
var result = true
|
|
124
124
|
|
|
125
125
|
if (fnProvider && !_.isFunction(fnProvider)) {
|
|
@@ -129,7 +129,7 @@ function Logger () {
|
|
|
129
129
|
return result
|
|
130
130
|
}
|
|
131
131
|
|
|
132
|
-
function isValidLevel
|
|
132
|
+
function isValidLevel(levelName) {
|
|
133
133
|
var validLevels = _.keys(LEVELS)
|
|
134
134
|
var isValid = _.includes(validLevels, levelName)
|
|
135
135
|
|
|
@@ -153,10 +153,10 @@ function Logger () {
|
|
|
153
153
|
* @param {String} newTarget
|
|
154
154
|
* @return {String}
|
|
155
155
|
*/
|
|
156
|
-
function getArrow
|
|
156
|
+
function getArrow(originalPath, newPath, originalTarget, newTarget) {
|
|
157
157
|
var arrow = ['>']
|
|
158
|
-
var isNewTarget =
|
|
159
|
-
var isNewPath =
|
|
158
|
+
var isNewTarget = originalTarget !== newTarget // router
|
|
159
|
+
var isNewPath = originalPath !== newPath // pathRewrite
|
|
160
160
|
|
|
161
161
|
if (isNewPath && !isNewTarget) {
|
|
162
162
|
arrow.unshift('~')
|
package/lib/path-rewriter.js
CHANGED
|
@@ -12,7 +12,7 @@ module.exports = {
|
|
|
12
12
|
* @param {Object} rewriteConfig
|
|
13
13
|
* @return {Function} Function to rewrite paths; This function should accept `path` (request.url) as parameter
|
|
14
14
|
*/
|
|
15
|
-
function createPathRewriter
|
|
15
|
+
function createPathRewriter(rewriteConfig) {
|
|
16
16
|
var rulesCache
|
|
17
17
|
|
|
18
18
|
if (!isValidRewriteConfig(rewriteConfig)) {
|
|
@@ -27,10 +27,10 @@ function createPathRewriter (rewriteConfig) {
|
|
|
27
27
|
return rewritePath
|
|
28
28
|
}
|
|
29
29
|
|
|
30
|
-
function rewritePath
|
|
30
|
+
function rewritePath(path) {
|
|
31
31
|
var result = path
|
|
32
32
|
|
|
33
|
-
_.forEach(rulesCache, function
|
|
33
|
+
_.forEach(rulesCache, function(rule) {
|
|
34
34
|
if (rule.regex.test(path)) {
|
|
35
35
|
result = result.replace(rule.regex, rule.value)
|
|
36
36
|
logger.debug('[HPM] Rewriting path from "%s" to "%s"', path, result)
|
|
@@ -42,30 +42,36 @@ function createPathRewriter (rewriteConfig) {
|
|
|
42
42
|
}
|
|
43
43
|
}
|
|
44
44
|
|
|
45
|
-
function isValidRewriteConfig
|
|
45
|
+
function isValidRewriteConfig(rewriteConfig) {
|
|
46
46
|
if (_.isFunction(rewriteConfig)) {
|
|
47
47
|
return true
|
|
48
48
|
} else if (!_.isEmpty(rewriteConfig) && _.isPlainObject(rewriteConfig)) {
|
|
49
49
|
return true
|
|
50
|
-
} else if (
|
|
51
|
-
|
|
52
|
-
|
|
50
|
+
} else if (
|
|
51
|
+
_.isUndefined(rewriteConfig) ||
|
|
52
|
+
_.isNull(rewriteConfig) ||
|
|
53
|
+
_.isEqual(rewriteConfig, {})
|
|
54
|
+
) {
|
|
53
55
|
return false
|
|
54
56
|
} else {
|
|
55
57
|
throw new Error(ERRORS.ERR_PATH_REWRITER_CONFIG)
|
|
56
58
|
}
|
|
57
59
|
}
|
|
58
60
|
|
|
59
|
-
function parsePathRewriteRules
|
|
61
|
+
function parsePathRewriteRules(rewriteConfig) {
|
|
60
62
|
var rules = []
|
|
61
63
|
|
|
62
64
|
if (_.isPlainObject(rewriteConfig)) {
|
|
63
|
-
_.forIn(rewriteConfig, function
|
|
65
|
+
_.forIn(rewriteConfig, function(value, key) {
|
|
64
66
|
rules.push({
|
|
65
67
|
regex: new RegExp(key),
|
|
66
68
|
value: rewriteConfig[key]
|
|
67
69
|
})
|
|
68
|
-
logger.info(
|
|
70
|
+
logger.info(
|
|
71
|
+
'[HPM] Proxy rewrite rule created: "%s" ~> "%s"',
|
|
72
|
+
key,
|
|
73
|
+
rewriteConfig[key]
|
|
74
|
+
)
|
|
69
75
|
})
|
|
70
76
|
}
|
|
71
77
|
|
package/lib/router.js
CHANGED
|
@@ -5,7 +5,7 @@ module.exports = {
|
|
|
5
5
|
getTarget: getTarget
|
|
6
6
|
}
|
|
7
7
|
|
|
8
|
-
function getTarget
|
|
8
|
+
function getTarget(req, config) {
|
|
9
9
|
var newTarget
|
|
10
10
|
var router = config.router
|
|
11
11
|
|
|
@@ -18,22 +18,24 @@ function getTarget (req, config) {
|
|
|
18
18
|
return newTarget
|
|
19
19
|
}
|
|
20
20
|
|
|
21
|
-
function getTargetFromProxyTable
|
|
21
|
+
function getTargetFromProxyTable(req, table) {
|
|
22
22
|
var result
|
|
23
23
|
var host = req.headers.host
|
|
24
24
|
var path = req.url
|
|
25
25
|
|
|
26
26
|
var hostAndPath = host + path
|
|
27
27
|
|
|
28
|
-
_.forIn(table, function
|
|
28
|
+
_.forIn(table, function(value, key) {
|
|
29
29
|
if (containsPath(key)) {
|
|
30
|
-
if (hostAndPath.indexOf(key) > -1) {
|
|
30
|
+
if (hostAndPath.indexOf(key) > -1) {
|
|
31
|
+
// match 'localhost:3000/api'
|
|
31
32
|
result = table[key]
|
|
32
33
|
logger.debug('[HPM] Router table match: "%s"', key)
|
|
33
34
|
return false
|
|
34
35
|
}
|
|
35
36
|
} else {
|
|
36
|
-
if (key === host) {
|
|
37
|
+
if (key === host) {
|
|
38
|
+
// match 'localhost:3000'
|
|
37
39
|
result = table[key]
|
|
38
40
|
logger.debug('[HPM] Router table match: "%s"', host)
|
|
39
41
|
return false
|
|
@@ -44,6 +46,6 @@ function getTargetFromProxyTable (req, table) {
|
|
|
44
46
|
return result
|
|
45
47
|
}
|
|
46
48
|
|
|
47
|
-
function containsPath
|
|
49
|
+
function containsPath(v) {
|
|
48
50
|
return v.indexOf('/') > -1
|
|
49
51
|
}
|