Current Behavior
When using the OPA plugin with "with_route" set to true an error is thrown by APISIX which returns a 500 error code.
Expected Behavior
When using the OPA plugin with "with_route" set to true, the policy related to the route would receive information about the route, validate the the input against the policy and if the policy allows the request, the request would be proxied to the upstream.
Error Logs
2023-11-07 17:35:37 2023/11/07 15:35:37 [error] 267#267: *4727521 lua entry thread aborted: runtime error: /usr/local/apisix/apisix/init.lua:244: attempt to index field 'upstream' (a nil value)
2023-11-07 17:35:37 stack traceback:
2023-11-07 17:35:37 coroutine 0:
2023-11-07 17:35:37 /usr/local/apisix/apisix/init.lua: in function 'parse_domain_in_route'
2023-11-07 17:35:37 /usr/local/apisix/apisix/init.lua:496: in function 'handle_upstream'
2023-11-07 17:35:37 /usr/local/apisix/apisix/init.lua:730: in function 'http_access_phase'
2023-11-07 17:35:37 access_by_lua(nginx.conf:301):2: in main chunk, client: 172.18.0.1, server: _, request: "GET /products HTTP/1.1", host: "127.0.0.1:9080"
Steps to Reproduce
- Run APISIX with the getting started command - curl -sL https://run.api7.ai/apisix/quickstart | sh
- Start a OPA instance : docker run -d --name opa -p 8181:8181 openpolicyagent/opa:0.35.0 run -s
- Step test routes
Example Route that works fine without OPA (Route A)
{
"uri": "/products",
"name": "fake-products",
"desc": "fake-products",
"methods": [
"GET", "POST"
],
"upstream": {
"nodes": {
"fakestoreapi.com": 1
},
"scheme": "https",
"pass_host": "node"
}
}
Example Route that fails with OPA (Route B)
{
"uri": "/products",
"name": "fake-products",
"desc": "fake-products",
"methods": [
"GET","POST"
],
"plugins": {
"opa": {
"host": "http://<insert-opa-ip-address>:8181/",
"ssl_verify": false,
"policy": "products_policy",
"with_route": true
}
},
"upstream": {
"nodes": {
"fakestoreapi.com": 1
},
"scheme": "https",
"pass_host": "node"
}
}
- Step up a OPA policy :
package products_policy
default allow = false
allow { input.request.method == "GET"}
status_code = 201 {not allow}
- Call Route B via a POST request to reproduce the error
The issue seems to occur here :
local function build_http_route(conf, ctx, remove_upstream)
local route = core.table.clone(ctx.matched_route).value
if remove_upstream and route and route.upstream then
route.upstream = nil
end
return route
end
What should local route = core.table.clone(ctx.matched_route).value be not to change the route ctx ?
Environment
- APISIX version 3.6
- OPA version 0.35.0
versions from curl -sL https://run.api7.ai/apisix/quickstart | sh
Current Behavior
When using the OPA plugin with "with_route" set to true an error is thrown by APISIX which returns a 500 error code.
Expected Behavior
When using the OPA plugin with "with_route" set to true, the policy related to the route would receive information about the route, validate the the input against the policy and if the policy allows the request, the request would be proxied to the upstream.
Error Logs
2023-11-07 17:35:37 2023/11/07 15:35:37 [error] 267#267: *4727521 lua entry thread aborted: runtime error: /usr/local/apisix/apisix/init.lua:244: attempt to index field 'upstream' (a nil value)
2023-11-07 17:35:37 stack traceback:
2023-11-07 17:35:37 coroutine 0:
2023-11-07 17:35:37 /usr/local/apisix/apisix/init.lua: in function 'parse_domain_in_route'
2023-11-07 17:35:37 /usr/local/apisix/apisix/init.lua:496: in function 'handle_upstream'
2023-11-07 17:35:37 /usr/local/apisix/apisix/init.lua:730: in function 'http_access_phase'
2023-11-07 17:35:37 access_by_lua(nginx.conf:301):2: in main chunk, client: 172.18.0.1, server: _, request: "GET /products HTTP/1.1", host: "127.0.0.1:9080"
Steps to Reproduce
Example Route that works fine without OPA (Route A)
Example Route that fails with OPA (Route B)
The issue seems to occur here :
What should
local route = core.table.clone(ctx.matched_route).valuebe not to change the route ctx ?Environment
versions from curl -sL https://run.api7.ai/apisix/quickstart | sh