mirror of
https://github.com/hanzoai/gateway.git
synced 2026-11-02 15:19:24 +00:00
The endpoint pipeline ran a SECOND JWT validation to answer a question the edge had already answered one middleware earlier — a second crypto library, a second JWKS URL, and ALL-of audience semantics against the edge's ANY-of, which 401s every user JWT IAM issues. Requiring a credential and verifying one are different jobs; only the second needs a key, and only one thing should do it. Routes now declare `auth/public` and the edge is the one validator. The ingress binary, its config and its manifests leave this repo. They were a second copy of a service that has its own, and the two had drifted.
615 lines
19 KiB
JSON
615 lines
19 KiB
JSON
{
|
|
"version": 3,
|
|
"$schema": "https://gateway.hanzo.ai/schema/v3.json",
|
|
"name": "My lovely gateway",
|
|
"port": 8080,
|
|
"cache_ttl": "3600s",
|
|
"timeout": "3s",
|
|
"read_header_timeout":"200ms",
|
|
"extra_config": {
|
|
"router":{
|
|
"return_error_msg":true
|
|
},
|
|
"telemetry/logging": {
|
|
"level": "DEBUG",
|
|
"prefix": "[GATEWAY]",
|
|
"syslog": false,
|
|
"stdout": true
|
|
},
|
|
"telemetry/metrics": {
|
|
"collection_time": "60s",
|
|
"listen_address": ":8090"
|
|
},
|
|
"security/cors": {
|
|
"allow_origins": [ "*" ],
|
|
"allow_methods": [ "POST", "GET" ],
|
|
"allow_headers": [ "Origin", "Authorization", "Content-Type" ],
|
|
"expose_headers": [ "Content-Length" ],
|
|
"max_age": "12h"
|
|
},
|
|
"security/bot-detector": {
|
|
"deny": ["a", "b"],
|
|
"allow": ["c", "Pingdom.com_bot_version_1.1"],
|
|
"patterns": [
|
|
"(Pingdom.com_bot_version_).*",
|
|
"(facebookexternalhit)/.*"
|
|
]
|
|
}
|
|
},
|
|
"endpoints": [
|
|
{
|
|
"endpoint": "/",
|
|
"backend": [
|
|
{
|
|
"url_pattern": "/__debug/",
|
|
"host": [ "http://127.0.0.1:8080" ]
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/crash",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/unknown"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/timeout2/{param}",
|
|
"extra_config": {
|
|
"proxy": {
|
|
"sequential": true
|
|
}
|
|
},
|
|
"timeout": "150us",
|
|
"backend": [
|
|
{
|
|
"url_pattern": "/__debug/{param}",
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"timeout": "30us",
|
|
"allow": [ "message" ]
|
|
},
|
|
{
|
|
"url_pattern": "/__debug/{param}/{resp0_message}",
|
|
"timeout": "30us",
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"group": "second"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/no-op/ok",
|
|
"method": "POST",
|
|
"output_encoding": "no-op",
|
|
"backend": [
|
|
{
|
|
"encoding": "no-op",
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/no-op/ko",
|
|
"method": "POST",
|
|
"output_encoding": "no-op",
|
|
"backend": [
|
|
{
|
|
"encoding": "no-op",
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"url_pattern": "/unknown"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/xml/xml",
|
|
"output_encoding": "xml",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/xml",
|
|
"encoding": "xml"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/xml/json",
|
|
"output_encoding": "xml",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/negotiate",
|
|
"method": "GET",
|
|
"output_encoding": "negotiate",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/xml",
|
|
"encoding": "xml"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/static",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"url_pattern": "/__debug",
|
|
"deny": ["message"]
|
|
}
|
|
],
|
|
"extra_config": {
|
|
"proxy": {
|
|
"static": {
|
|
"strategy": "always",
|
|
"data": {
|
|
"foo": 42,
|
|
"bar": "foobar"
|
|
}
|
|
}
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"endpoint": "/static/merge",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"url_pattern": "/unknown"
|
|
},
|
|
{
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"url_pattern": "/not-really-a-url"
|
|
}
|
|
],
|
|
"extra_config": {
|
|
"proxy": {
|
|
"static": {
|
|
"strategy": "always",
|
|
"data": {
|
|
"foo": 42,
|
|
"bar": "foobar"
|
|
}
|
|
}
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"endpoint": "/cel/req-resp/{id}",
|
|
"input_headers": ["X-Header"],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"url_pattern": "/__debug/1/{id}",
|
|
"group": "backend1",
|
|
"extra_config":{
|
|
"validation/cel": [
|
|
{
|
|
"check_expr": "int(req_params.Id) % 3 == 0"
|
|
}
|
|
]
|
|
}
|
|
},
|
|
{
|
|
"host": [ "http://127.0.0.1:8080" ],
|
|
"url_pattern": "/__debug/2/{id}",
|
|
"group": "backend2",
|
|
"extra_config":{
|
|
"validation/cel": [
|
|
{
|
|
"check_expr": "int(req_params.Id) % 5 == 0"
|
|
}
|
|
]
|
|
}
|
|
}
|
|
],
|
|
"extra_config":{
|
|
"validation/cel": [
|
|
{
|
|
"check_expr": "'something' in req_headers['X-Header']"
|
|
},
|
|
{
|
|
"check_expr": "int(req_params.Id) % 2 == 0"
|
|
}
|
|
]
|
|
}
|
|
},
|
|
{
|
|
"endpoint": "/param_forwarding/some/{foo}/{bar}",
|
|
"input_headers": [
|
|
"Authorization",
|
|
"X-Y-Z"
|
|
],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/{bar}?foo={foo}"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/param_forwarding/some/{foo}/{bar}",
|
|
"method": "POST",
|
|
"input_headers": [
|
|
"Authorization",
|
|
"X-Y-Z"
|
|
],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/{bar}?foo={foo}&dump_body=1"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/param_forwarding/all/{foo}/{bar}",
|
|
"input_headers": [ "*" ],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/{bar}?foo={foo}"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/query_forwarding/all/{name}",
|
|
"input_query_strings": [ "*" ],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/{name}"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/query_forwarding/some/{name}",
|
|
"input_query_strings": [ "a" ],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/{name}"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/sequential/ok/{param}",
|
|
"extra_config": {
|
|
"proxy": {
|
|
"sequential": true
|
|
}
|
|
},
|
|
"backend": [
|
|
{
|
|
"url_pattern": "/param_forwarding/{param}",
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"allow": [ "foo" ]
|
|
},
|
|
{
|
|
"url_pattern": "/param_forwarding/{resp0_foo}",
|
|
"host": [ "http://127.0.0.1:8081" ]
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/sequential/propagate",
|
|
"extra_config": {
|
|
"proxy": {
|
|
"sequential": true,
|
|
"sequential_propagated_params": ["resp0_first.foo"]
|
|
}
|
|
},
|
|
"backend": [
|
|
{
|
|
"url_pattern": "/param_forwarding/1",
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"group": "first",
|
|
"allow": [ "foo" ]
|
|
},
|
|
{
|
|
"url_pattern": "/param_forwarding/",
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"group": "second",
|
|
"allow": [ "path" ],
|
|
"extra_config": {
|
|
"modifier/lua-backend": {
|
|
"pre": "local req = request.load(); local foo = req:params(\"Resp0_first.foo\"); req:url(req:url() .. foo)"
|
|
}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/sequential/propagate-full",
|
|
"extra_config": {
|
|
"proxy": {
|
|
"sequential": true,
|
|
"sequential_propagated_params": ["resp0"]
|
|
}
|
|
},
|
|
"backend": [
|
|
{
|
|
"encoding": "no-op",
|
|
"url_pattern": "/__debug/",
|
|
"host": [ "http://localhost:8080" ]
|
|
},
|
|
{
|
|
"url_pattern": "/param_forwarding/",
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"extra_config": {
|
|
"modifier/lua-backend": {
|
|
"allow_open_libs": true,
|
|
"sources": [
|
|
"fixtures/lua/base64.lua"
|
|
],
|
|
"pre": "local req = request.load(); local m = req:params(\"Resp0\"); req:url(req:url() .. to_base64(m))"
|
|
}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/sequential/incomplete/{param}",
|
|
"extra_config": {
|
|
"proxy": {
|
|
"sequential": true
|
|
}
|
|
},
|
|
"backend": [
|
|
{
|
|
"url_pattern": "/param_forwarding/{param}",
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"allow": [ "foo" ]
|
|
},
|
|
{
|
|
"url_pattern": "/{resp0_foo}",
|
|
"host": [ "http://127.0.0.1:8081" ]
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/flatmap/{id}",
|
|
"method": "GET",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/collection/{id}",
|
|
"is_collection": true,
|
|
"extra_config": {
|
|
"proxy": {
|
|
"flatmap_filter": [
|
|
{
|
|
"type": "move",
|
|
"args": ["collection", "paths"]
|
|
},
|
|
{
|
|
"type": "del",
|
|
"args": ["paths.*.i"]
|
|
},
|
|
{
|
|
"type": "move",
|
|
"args": ["paths.*.path", "paths.*.url"]
|
|
}
|
|
]
|
|
}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/combination/{id}",
|
|
"method": "GET",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/collection/{id}",
|
|
"is_collection": true,
|
|
"mapping": {
|
|
"collection": "posts"
|
|
}
|
|
},
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/param_forwarding/{id}",
|
|
"allow": [ "foo" ]
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/show/{id}",
|
|
"backend": [
|
|
{
|
|
"host": [
|
|
"http://127.0.0.1:8081"
|
|
],
|
|
"url_pattern": "/rss/schedule/{id}",
|
|
"encoding": "rss",
|
|
"group": "schedule",
|
|
"allow": ["title"],
|
|
"extra_config": {
|
|
"qos/circuit-breaker": {
|
|
"interval": 60,
|
|
"timeout": 10,
|
|
"max_errors": 1
|
|
},
|
|
"qos/http-cache": {}
|
|
}
|
|
},
|
|
{
|
|
"host": [
|
|
"http://127.0.0.1:8081"
|
|
],
|
|
"url_pattern": "/rss/user/{id}",
|
|
"encoding": "rss",
|
|
"group": "available",
|
|
"allow": ["title"],
|
|
"extra_config": {
|
|
"qos/circuit-breaker": {
|
|
"interval": 60,
|
|
"timeout": 10,
|
|
"max_errors": 1
|
|
},
|
|
"qos/http-cache": {}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/timeout",
|
|
"timeout": "100ms",
|
|
"backend": [
|
|
{
|
|
"host": ["http://127.0.0.1:8081"],
|
|
"url_pattern": "/param_forwarding/123",
|
|
"group": "first"
|
|
},
|
|
{
|
|
"host": ["http://127.0.0.1:8081"],
|
|
"url_pattern": "/delayed/",
|
|
"group": "second"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/detail_error",
|
|
"backend": [
|
|
{
|
|
"host": ["http://127.0.0.1:8081"],
|
|
"url_pattern": "/param_forwarding/",
|
|
"extra_config": {
|
|
"backend/http": {
|
|
"return_error_details": "backend_a"
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"host": ["http://127.0.0.1:8081"],
|
|
"url_pattern": "/",
|
|
"extra_config": {
|
|
"backend/http": {
|
|
"return_error_details": "backend_b"
|
|
}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/redirect/{code}",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/redirect/?status={code}"
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/lua/custom_error",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/collection/",
|
|
"is_collection": true,
|
|
"extra_config": {
|
|
"modifier/lua-backend": {
|
|
"sources": [
|
|
"fixtures/lua/collection.lua"
|
|
],
|
|
"pre": "json_error()"
|
|
}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
{
|
|
"endpoint": "/lua/collection",
|
|
"input_headers": ["*"],
|
|
"backend": [
|
|
{
|
|
"host": [ "http://127.0.0.1:8081" ],
|
|
"url_pattern": "/collection/",
|
|
"is_collection": true,
|
|
"extra_config": {
|
|
"modifier/lua-backend": {
|
|
"sources": [
|
|
"fixtures/lua/json.lua",
|
|
"fixtures/lua/base64.lua",
|
|
"fixtures/lua/collection.lua"
|
|
],
|
|
"pre": "pre_backend(request.load())",
|
|
"allow_open_libs": true
|
|
}
|
|
}
|
|
}
|
|
],
|
|
"extra_config": {
|
|
"modifier/lua-proxy": {
|
|
"sources": [
|
|
"fixtures/lua/json.lua",
|
|
"fixtures/lua/base64.lua",
|
|
"fixtures/lua/collection.lua"
|
|
],
|
|
"post": "post_proxy(response.load())",
|
|
"live": true,
|
|
"allow_open_libs": true
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"endpoint": "/lua/modify_response/fail",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://www.mocky.io" ],
|
|
"url_pattern": "/v2/5d765eb4320000925b297af6",
|
|
"group": "source_result"
|
|
}
|
|
],
|
|
"extra_config": {
|
|
"modifier/lua-proxy": {
|
|
"sources": [
|
|
"fixtures/lua/decorator.lua"
|
|
],
|
|
"post": "post_proxy_decorator(response.load())",
|
|
"allow_open_libs": true
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"endpoint": "/lua/modify_response/success",
|
|
"backend": [
|
|
{
|
|
"host": [ "http://www.mocky.io" ],
|
|
"url_pattern": "/v2/5d765f653200004f25297afd",
|
|
"group": "source_result"
|
|
}
|
|
],
|
|
"extra_config": {
|
|
"modifier/lua-proxy": {
|
|
"sources": [
|
|
"fixtures/lua/decorator.lua"
|
|
],
|
|
"post": "post_proxy_decorator(response.load())",
|
|
"allow_open_libs": true
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"endpoint": "/jsonschema",
|
|
"method": "POST",
|
|
"backend": [
|
|
{
|
|
"host": ["http://127.0.0.1:8080"],
|
|
"url_pattern": "/__debug/"
|
|
}
|
|
],
|
|
"extra_config":{
|
|
"validation/json-schema": {"type": "number"}
|
|
}
|
|
}
|
|
]
|
|
}
|