'Express-Gateway, serve same API path/route, but under different ServiceEndpoints
I have a server in Node.js + Express, that exposes some APIs both to public and admins. Actually I have 2 cloned instances running, one for Test, one for Production. They are twins, exposing same routes (/admin, /public), but are connected to two different DataBases, and are deployed on two different addresses.
I want to use Express-Gateway to provide APIs to 3d parties, so I'll give them firstly access to the Test Server. Once it's all done, I'll give them also the Production access.
To do this, my Idea is to create just 1 eg user, with multiple eg application. Each eg application will have eg credentials to access to Server or Production.
http://server_test.com
|-------------| |-------------|
| App Prod | | Server Test |
+----► | scopes: |------+ +-----► | /public |
| | [api_prod] | | | | /admin |
| |-------------| ▼ | |-------------|
| http://gateway.com
|------| |------------|
| User | | Express |
|------| | Gateway |
| |-------------| |------------|
| | App Test | ▲ | http://server_prod.com
+----► | scopes: | | | |-------------|
| [api_test] |------+ +-----► | Server Prod |
|-------------| | /public |
| /admin |
|-------------|
According to the credentials provided, the Gateway should redirect requests to server_test.com or server_prod.com. My idea was to use eg scopes to address requests to the right endpoint. So Server Test policy, will require the scope api_test, while Server Prod will require api_prod scope.
Anyway this solution doesn't work, because if the first match in apiEndpoints fails, it just results in "Not Found".
Example: I make a request to http://gateway.com/public using App Prod credentials, with api_prod scope. It should be passed to http://server_prod.com/public, but instead It matches first paths: '/*' of testEndpoint, and fails the scopes condition. So it just fails, while the correct apiEndpoint should be prodEndpoint.
How can I solve this problem?
This is my gateway.config.yml
apiEndpoints:
testEndpoint
host:*
paths: '/*' # <--- match this
scopes: ["api_test"] # <--- but fails this
prodEndpoint
host:*
paths: '/*'
scopes: ["api_prod"] # <---- this is right
serviceEndpoints
testService
url: "http://server_test.com"
prodService
url: "http://server_prod.com"
policies
- proxy
pipelines
testEndpoint: # Test
apiEndpoints:
- testEndpoint
policies:
- proxy
- action
serviceEndpoint: testService
prodEndpoint: # Prod
apiEndpoints:
- prodEndpoint
policies:
- proxy
- action
serviceEndpoint: prodService
Solution 1:[1]
I solved in this way: using -rewrite policy.
- I prefix my clients' requests with
/testor/prod - Use the prefix to match
paththe correct apiEndpoint - rewrite the request, deleting the prefix
- choose the serviceEndpoint and go on...
http://server_test.com
|-------------| |-------------|
| App Prod | /prod/admin /admin | Server Test |
| scopes: |-------------+ +--------? | /public |
| [api_prod] | | | | /admin |
|-------------| ? | |-------------|
http://gateway.com
|------------|
| Express |
| Gateway |
|-------------| |------------|
| App Test | ? | http://server_prod.com
| scopes: | | | |-------------|
| [api_test] |-------------+ +---------? | Server Prod |
|-------------| /test/admin /admin | /public |
| /admin |
|-------------|
This is my config file:
apiEndpoints:
testEndpoint
host:*
paths: '/test/*'
scopes: ["api_test"]
prodEndpoint
host:*
paths: '/prod/*'
scopes: ["api_prod"]
serviceEndpoints
testService
url: "http://server_test.com"
prodService
url: "http://server_prod.com"
policies
- proxy
pipelines
testEndpoint: # Test
apiEndpoints:
- testEndpoint
policies:
- rewrite: # rewrite - delete '/test'
-
condition:
name: regexpmatch
match: ^/test/?(.*)$
action:
rewrite: /$1
- proxy
- action
serviceEndpoint: testService
prodEndpoint: # Prod
apiEndpoints:
- prodEndpoint
policies:
- rewrite: # rewrite - delete '/prod'
-
condition:
name: regexpmatch
match: ^/prod/?(.*)$
action:
rewrite: /$1
- proxy
- action
serviceEndpoint: prodService
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 |
