You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@apisix.apache.org by GitBox <gi...@apache.org> on 2022/03/11 14:26:25 UTC
[GitHub] [apisix] azilentech opened a new pull request #6586: feat-6574-keycloak-plugin-password-grant-support
azilentech opened a new pull request #6586:
URL: https://github.com/apache/apisix/pull/6586
Support of password grant type for token generation (#6574)
Committing changes after adding new feature for generating token based on `user id/password` and also taking support of grant type `password`
feat: #6574
### Pre-submission checklist:
<!--
Please follow the PR manners:
1. Use Draft if the PR is not ready to be reviewed
2. Test is required for the feat/fix PR, unless you have a good reason
3. Doc is required for the feat PR
4. Use a new commit to resolve review instead of `push -f`
5. If you need to resolve merge conflicts after the PR is reviewed, please merge master but do not rebase
6. Use "request review" to notify the reviewer once you have resolved the review
7. Only reviewer can click "Resolve conversation" to mark the reviewer's review resolved
-->
* [ ] Did you explain what problem does this PR solve? Or what new features have been added?
* [ ] Have you added corresponding test cases?
* [ ] Have you modified the corresponding document?
* [ ] Is this PR backward compatible? **If it is not backward compatible, please discuss on the [mailing list](https://github.com/apache/apisix/tree/master#community) first**
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] starsz commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
starsz commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r825536697
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
Review comment:
You can use `core.request.get_body()` instead.
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
Review comment:
Why should we use `warn` level ?
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
+ local username = nil
+ local password = nil
+ --split by &
+ local parameters_array = util.split(request_body, "&")
+
+ if #parameters_array == 2 then
+ for k, parameter in ipairs(parameters_array) do
+ if str_find(parameter, "username") then
+ --split by =
+ local username_value_array = util.split(parameter, "=")
+ if #username_value_array == 2 then
+ username = username_value_array[2]
+ end
+ end
+ if str_find(parameter, "password") then
+ --split by =
+ local password_value_array = util.split(parameter, "=")
+ if #password_value_array == 2 then
+ password = password_value_array[2]
+ end
+ end
+ end
+ end
+
+ if not username then
+ local err = "username is missing"
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing"
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+
+ if conf.password_grant_token_generation_incoming_uri then
+ if ngx.var.request_uri:upper()
+ == conf.password_grant_token_generation_incoming_uri:upper() then
Review comment:
Use `and` would be better.
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
+ local username = nil
+ local password = nil
+ --split by &
+ local parameters_array = util.split(request_body, "&")
+
+ if #parameters_array == 2 then
+ for k, parameter in ipairs(parameters_array) do
+ if str_find(parameter, "username") then
+ --split by =
+ local username_value_array = util.split(parameter, "=")
+ if #username_value_array == 2 then
+ username = username_value_array[2]
+ end
+ end
+ if str_find(parameter, "password") then
+ --split by =
+ local password_value_array = util.split(parameter, "=")
+ if #password_value_array == 2 then
+ password = password_value_array[2]
+ end
+ end
+ end
+ end
+
+ if not username then
+ local err = "username is missing"
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing"
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
Review comment:
```suggestion
return res.status, res.body
```
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
+ local username = nil
+ local password = nil
+ --split by &
+ local parameters_array = util.split(request_body, "&")
Review comment:
Why the username, password in the request body and use & to concat.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] spacewander commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
spacewander commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828692698
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
Review comment:
```suggestion
body = ngx.encode_args({
```
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
Review comment:
```suggestion
return 503, err
```
New feature is encouraged to avoid 500
##########
File path: t/plugin/authz-keycloak.t
##########
@@ -621,3 +622,104 @@ GET /t
--- response_headers
Location: http://127.0.0.1/test
--- error_code: 307
+
+
+
+=== TEST 18: Add https endpoint with password_grant_token_generation_incoming_uri
+--- config
+ location /t {
+ content_by_lua_block {
+ local t = require("lib.test_admin").test
+ local code, body = t('/apisix/admin/routes/1',
+ ngx.HTTP_PUT,
+ [[{
+ "plugins": {
+ "authz-keycloak": {
+ "token_endpoint": "https://127.0.0.1:8443/auth/realms/University/protocol/openid-connect/token",
+ "permissions": ["course_resource#view"],
+ "client_id": "course_management",
+ "client_secret": "d1ec69e9-55d2-4109-a3ea-befa071579d5",
+ "grant_type": "urn:ietf:params:oauth:grant-type:uma-ticket",
+ "timeout": 3000,
+ "ssl_verify": false,
+ "password_grant_token_generation_incoming_uri": "/api/token"
+ }
+ },
+ "upstream": {
+ "nodes": {
+ "127.0.0.1:1982": 1
+ },
+ "type": "roundrobin"
+ },
+ "uri": "/api/token"
+ }]],
+ [[{
Review comment:
We need to remove the echo response data as https://github.com/apache/apisix/pull/6545
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
Review comment:
Is it required to compare case-insensitive?
Also, the `var.request_uri` will contain `?argument=part`, is it desirable?
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
+ core.request.get_method() == "POST" then
Review comment:
We should also check the "Content-Type"?
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] starsz commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
starsz commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r827025532
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,88 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
+ ctx.curr_req_matched["_method"]:upper() == "POST" then
Review comment:
`ctx.curr_req_matched["_method"]:upper()` looks strange.
I think you can use `core.req.get_method` instead.
##########
File path: docs/en/latest/plugins/authz-keycloak.md
##########
@@ -122,6 +123,27 @@ of the same name. The scope is then added to every permission to check.
If `lazy_load_paths` is `false`, the plugin adds the mapped scope to any of the static permissions configured
in the `permissions` attribute, even if they contain one or more scopes already.
+### Password Grant Token Generation Incoming URI
+
+If you want to generate a token using `password` grant, you can set value of `password_grant_token_generation_incoming_uri`.
+
+Incoming request URI will be matched with this value and if matched, it will generate token using `Token Endpoint`.
+It will also check, if REST method is `POST`.
Review comment:
```suggestion
It will also check if the request method is `POST`.
```
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,88 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+
Review comment:
redundant line ?
##########
File path: docs/en/latest/plugins/authz-keycloak.md
##########
@@ -122,6 +123,27 @@ of the same name. The scope is then added to every permission to check.
If `lazy_load_paths` is `false`, the plugin adds the mapped scope to any of the static permissions configured
in the `permissions` attribute, even if they contain one or more scopes already.
+### Password Grant Token Generation Incoming URI
+
+If you want to generate a token using `password` grant, you can set value of `password_grant_token_generation_incoming_uri`.
Review comment:
```suggestion
If you want to generate a token using `password` grant, you can set the value of `password_grant_token_generation_incoming_uri`.
```
##########
File path: docs/en/latest/plugins/authz-keycloak.md
##########
@@ -122,6 +123,27 @@ of the same name. The scope is then added to every permission to check.
If `lazy_load_paths` is `false`, the plugin adds the mapped scope to any of the static permissions configured
in the `permissions` attribute, even if they contain one or more scopes already.
+### Password Grant Token Generation Incoming URI
+
+If you want to generate a token using `password` grant, you can set value of `password_grant_token_generation_incoming_uri`.
+
+Incoming request URI will be matched with this value and if matched, it will generate token using `Token Endpoint`.
Review comment:
```suggestion
Incoming request URI will be matched with this value and if matched, it will generate a token using `Token Endpoint`.
```
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828757694
##########
File path: t/plugin/authz-keycloak.t
##########
@@ -621,3 +622,104 @@ GET /t
--- response_headers
Location: http://127.0.0.1/test
--- error_code: 307
+
+
+
+=== TEST 18: Add https endpoint with password_grant_token_generation_incoming_uri
+--- config
+ location /t {
+ content_by_lua_block {
+ local t = require("lib.test_admin").test
+ local code, body = t('/apisix/admin/routes/1',
+ ngx.HTTP_PUT,
+ [[{
+ "plugins": {
+ "authz-keycloak": {
+ "token_endpoint": "https://127.0.0.1:8443/auth/realms/University/protocol/openid-connect/token",
+ "permissions": ["course_resource#view"],
+ "client_id": "course_management",
+ "client_secret": "d1ec69e9-55d2-4109-a3ea-befa071579d5",
+ "grant_type": "urn:ietf:params:oauth:grant-type:uma-ticket",
+ "timeout": 3000,
+ "ssl_verify": false,
+ "password_grant_token_generation_incoming_uri": "/api/token"
+ }
+ },
+ "upstream": {
+ "nodes": {
+ "127.0.0.1:1982": 1
+ },
+ "type": "roundrobin"
+ },
+ "uri": "/api/token"
+ }]],
+ [[{
Review comment:
Alright. I removed it from this new test case.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r825596710
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
Review comment:
Agree... it should be debug level log. I changed it.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] soulbird commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
soulbird commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1065757694
you should sing the CLA first
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] tzssangglass commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
tzssangglass commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829678553
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,89 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 503, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ local headers = core.request.headers(ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri ==
+ conf.password_grant_token_generation_incoming_uri and
+ headers["content-type"] == "application/x-www-form-urlencoded" and
+ core.request.get_method() == "POST" then
Review comment:
```suggestion
local headers = core.request.headers(ctx)
local need_grant_token = conf.password_grant_token_generation_incoming_uri and
ngx.var.request_uri ==
conf.password_grant_token_generation_incoming_uri and
headers["content-type"] == "application/x-www-form-urlencoded" and
core.request.get_method() == "POST"
if need_grant_token then
```
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] soulbird commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
soulbird commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1065777377
Missing unit tests
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r825597553
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
+ local username = nil
+ local password = nil
+ --split by &
+ local parameters_array = util.split(request_body, "&")
Review comment:
As url encoded parameters were coming, they were automatically appended using '&'. Having said that, your comment helped me to utilize "ngx.decode_args" which makes code much cleaner. Thanks!
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r825596812
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
Review comment:
Done. I changed it.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] tzssangglass commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
tzssangglass commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829678553
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,89 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 503, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ local headers = core.request.headers(ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri ==
+ conf.password_grant_token_generation_incoming_uri and
+ headers["content-type"] == "application/x-www-form-urlencoded" and
+ core.request.get_method() == "POST" then
Review comment:
```suggestion
local headers = core.request.headers(ctx)
local need_grant_token = conf.password_grant_token_generation_incoming_uri and
ngx.var.request_uri ==
conf.password_grant_token_generation_incoming_uri and
headers["content-type"] == "application/x-www-form-urlencoded" and
core.request.get_method() == "POST"
if need_grant_token then
```
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] spacewander commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
spacewander commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829659989
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
Review comment:
The `request_uri` will contain the query string part of the uri. For example,
With request `/path?query=string`
The `ngx.var.request_uri` will return `/path?query=string`, and `ctx.var.uri` will return `/path`. By looking at the doc of `password_grant_token_generation_incoming_uri`, I guess we can use `ctx.var.uri` so both `/path?query=string` and `/path` can match.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r830639264
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,89 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 503, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ local headers = core.request.headers(ctx)
+ local need_grant_token = conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri == conf.password_grant_token_generation_incoming_uri and
Review comment:
Done. Made the change.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1067901042
@sshniro
I didn't test that way earlier, but just now, I did that and it is working. Also when I see the above checks, that test case is starting to pass now.
I have got the idea what things might cause that. Earlier I was using '&' to split the incoming parameters. but now I am using "ngx.decode_args" ( https://github.com/apache/apisix/pull/6586#discussion_r825597553 ).
Because of that earlier, username (which is email) wouldn't parse properly.
That should be the root cause of the same.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828756255
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
Review comment:
done and also incorporated this in the same file at other places.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r825597007
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
+ local username = nil
+ local password = nil
+ --split by &
+ local parameters_array = util.split(request_body, "&")
+
+ if #parameters_array == 2 then
+ for k, parameter in ipairs(parameters_array) do
+ if str_find(parameter, "username") then
+ --split by =
+ local username_value_array = util.split(parameter, "=")
+ if #username_value_array == 2 then
+ username = username_value_array[2]
+ end
+ end
+ if str_find(parameter, "password") then
+ --split by =
+ local password_value_array = util.split(parameter, "=")
+ if #password_value_array == 2 then
+ password = password_value_array[2]
+ end
+ end
+ end
+ end
+
+ if not username then
+ local err = "username is missing"
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing"
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+
+ if conf.password_grant_token_generation_incoming_uri then
+ if ngx.var.request_uri:upper()
+ == conf.password_grant_token_generation_incoming_uri:upper() then
Review comment:
Good Suggestion and changed it to use and for all three conditions.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828756762
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
+ core.request.get_method() == "POST" then
Review comment:
Yes. it was missed. I introduced that now.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829957937
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
Review comment:
@spacewander I understood your idea. I am curious, as to why we should treat both strings (/path?query=string or /path) the same way and proceed with token generation.
Token generation is a very specific use case, and shouldn't we say if and only if a specific URL will be submitted then we will generate token and submit result back.
if the request is made with /path?query=string, it shouldn't be assumed for token generation and it should be treated the same as any other request. (e.g. proceed to forward to upstream for further processing).
Please share your view. Accordingly, I can make changes, if needed.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r825596837
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +703,107 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.warn("generate_token_using_password_grant Function Called")
+ --Read Body
+ ngx.req.read_body()
+ --Get Body Data
+ local request_body=ngx.req.get_body_data()
+ local username = nil
+ local password = nil
+ --split by &
+ local parameters_array = util.split(request_body, "&")
+
+ if #parameters_array == 2 then
+ for k, parameter in ipairs(parameters_array) do
+ if str_find(parameter, "username") then
+ --split by =
+ local username_value_array = util.split(parameter, "=")
+ if #username_value_array == 2 then
+ username = username_value_array[2]
+ end
+ end
+ if str_find(parameter, "password") then
+ --split by =
+ local password_value_array = util.split(parameter, "=")
+ if #password_value_array == 2 then
+ password = password_value_array[2]
+ end
+ end
+ end
+ end
+
+ if not username then
+ local err = "username is missing"
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing"
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
Review comment:
Done.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1065934827
Hi,
I will need little guidance for the CLA signing process from your side.
In PR, I have made the following changes.
- Added test cases. As these test cases require keycloak installation, I tested with my local environment by adjusting parameters and configuration settings. Please let me know If I need to perform further steps.
- I updated code by using better configuration setting "password_grant_token_generation_incoming_uri" instead of using "token_generation_endpoint" which can be confusing with "token_endpoint".
- I updated the documentation by following contribution guidelines.
- I also ran "make lint" and followed all the suggestions.
Please let me know the next actions for me.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] niketrk commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
niketrk commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1066141219
@sshniro
I checked the logs of above test runs.
error is: "status=401, body={\"error\":\"invalid_grant\",\"error_description\":\"Invalid user credentials\"}"
I have used following settings in my test scenario:
"client_id": "course_management"
"client_secret": "d1ec69e9-55d2-4109-a3ea-befa071579d5"
username = "teacher@gmail.com"
password = "123456"
grant_type = "password"
I took the above settings from other Keycloak test cases.
I am doubting that these settings are not proper for the test Keycloak instance. In my local environment, I put my Keycloak settings and then run test scenario via
`TEST_NGINX_BINARY=/usr/local/bin/openresty prove -Itest-nginx/lib -r t/plugin/authz-keycloak.t`
And it worked properly.
-------------
Another issue is reported as: "ERROR: apisix/plugins/authz-keycloak.lua: line 719: getting the Lua global "string""
For which I made fix "local str_find = string.find", so it should be fixed now.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829959869
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,89 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 503, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ local headers = core.request.headers(ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri ==
+ conf.password_grant_token_generation_incoming_uri and
+ headers["content-type"] == "application/x-www-form-urlencoded" and
+ core.request.get_method() == "POST" then
Review comment:
Done. This one is giving better readability. Thanks!
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] spacewander commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
spacewander commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829659989
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
Review comment:
The `request_uri` will contain the query string part of the uri. For example,
With request `/path?query=string`
The `ngx.var.request_uri` will return `/path?query=string`, and `ctx.var.uri` will return `/path`. By looking at the doc of `password_grant_token_generation_incoming_uri`, I guess we can use `ctx.var.uri` so both `/path?query=string` and `/path` can match.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] sshniro commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
sshniro commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1067864904
> scenario
Hi, are you getting the same error when you run the docker image instance (sshniro/keycloak-apisix:latest) locally?
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] spacewander commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
spacewander commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r830565569
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,89 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 503, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ local headers = core.request.headers(ctx)
+ local need_grant_token = conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri == conf.password_grant_token_generation_incoming_uri and
Review comment:
```suggestion
ctx.var.request_uri == conf.password_grant_token_generation_incoming_uri and
```
would be better, which provides a cache of the var.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] spacewander commented on pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
spacewander commented on pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#issuecomment-1066089223
> I will need little guidance for the CLA signing process from your side.
There is no CLA file for APISIX :)
> Added test cases. As these test cases require keycloak installation, I tested with my local environment by adjusting parameters and configuration settings. Please let me know If I need to perform further steps.
As the keycloak environment is set up by @sshniro,
@sshniro
Could you provide some help for @azilentech to test this feature? Thanks!
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r829957937
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
Review comment:
@spacewander I understood your idea. I am curious, as to why we should treat both strings (/path?query=string or /path) the same way and proceed with token generation.
Token generation is a very specific use case, and shouldn't we say if and only if a specific URL will be submitted then we will generate token and submit result back.
if the request is made with /path?query=string, it shouldn't be assumed for token generation and it should be treated the same as any other request. (e.g. proceed to forward to upstream for further processing).
Please share your view. Accordingly, I can make changes, if needed.
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,89 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 503, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ local headers = core.request.headers(ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri ==
+ conf.password_grant_token_generation_incoming_uri and
+ headers["content-type"] == "application/x-www-form-urlencoded" and
+ core.request.get_method() == "POST" then
Review comment:
Done. This one is giving better readability. Thanks!
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828756255
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
Review comment:
done and also incorporated this in same file at other places.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828757524
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
+ end
+ local httpc = authz_keycloak_get_http_client(conf)
+
+ local params = {
+ method = "POST",
+ body = ngx.encode_args({
+ grant_type = "password",
+ client_id = client_id,
+ client_secret = conf.client_secret,
+ username = username,
+ password = password
+ }),
+ headers = {
+ ["Content-Type"] = "application/x-www-form-urlencoded"
+ }
+ }
+
+ params = authz_keycloak_configure_params(params, conf)
+
+ local res, err = httpc:request_uri(token_endpoint, params)
+
+ if not res then
+ err = "Accessing token endpoint URL (" .. token_endpoint
+ .. ") failed: " .. err
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ log.debug("Response data: " .. res.body)
+ local json, err = authz_keycloak_parse_json_response(res)
+
+ if not json then
+ err = "Could not decode JSON from response"
+ .. (err and (": " .. err) or '.')
+ log.error(err)
+ return 401, {message = err}
+ end
+
+ return res.status, res.body
+end
function _M.access(conf, ctx)
+ if conf.password_grant_token_generation_incoming_uri and
+ ngx.var.request_uri:upper() ==
+ conf.password_grant_token_generation_incoming_uri:upper() and
Review comment:
URL should be case sensitive so removed that "upper" from code.
For the part of request_uri, I believe, as we are checking uri, method, and header, all three parts, this should be fine.
Basically for the operation of token generation, exact uri matching will be helpful.
Your thoughts?
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] azilentech commented on a change in pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
azilentech commented on a change in pull request #6586:
URL: https://github.com/apache/apisix/pull/6586#discussion_r828756638
##########
File path: apisix/plugins/authz-keycloak.lua
##########
@@ -695,8 +700,87 @@ local function fetch_jwt_token(ctx)
return token
end
+-- To get new access token by calling get token api
+local function generate_token_using_password_grant(conf,ctx)
+ log.debug("generate_token_using_password_grant Function Called")
+
+ local body, err = core.request.get_body()
+ if err or not body then
+ log.error("Failed to get request body: ", err)
+ return 503
+ end
+ local parameters = ngx.decode_args(body)
+
+ local username = parameters["username"]
+ local password = parameters["password"]
+
+ if not username then
+ local err = "username is missing."
+ log.error(err)
+ return 422, err
+ end
+ if not password then
+ local err = "password is missing."
+ log.error(err)
+ return 422, err
+ end
+
+ local client_id = authz_keycloak_get_client_id(conf)
+
+ local token_endpoint = authz_keycloak_get_token_endpoint(conf)
+
+ if not token_endpoint then
+ local err = "Unable to determine token endpoint."
+ log.error(err)
+ return 500, err
Review comment:
Valid point. I updated it. I didn't update at other places because there can be backward compatibility issues and there should be separate PR for the same.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] spacewander merged pull request #6586: feat: add support for password grant in keycloak plugin
Posted by GitBox <gi...@apache.org>.
spacewander merged pull request #6586:
URL: https://github.com/apache/apisix/pull/6586
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org