Skip to content

feat: Add ldap-auth plugin #3894

Merged
spacewander merged 34 commits into
apache:masterfrom
jp-gouin:master
Oct 13, 2021
Merged

feat: Add ldap-auth plugin #3894
spacewander merged 34 commits into
apache:masterfrom
jp-gouin:master

Conversation

@jp-gouin

Copy link
Copy Markdown
Contributor

What this PR does / why we need it:

This PR add a new authentication plugin that use a LDAP server to authenticate the user

This add a new type of consumer

"ldap-auth": {
    "userdn": "cn=user01,dc=example,dc=org"
 }

This plugin can also automatically create a consumer upon request if auto_create_consumer = true
This fixes : #3861 and #1128

Test cases are not fully operational yet.

Help needed

Also need help to add the deployment of an Openldap server on Github Action.
FYI i used the (bitnami/openldap:2)(https://hub.docker.com/r/bitnami/openldap/) docker image

openldap:
    image: bitnami/openldap:2
    ports:
      - '389:1389'
      - '636:1636'
    environment:
      - LDAP_ADMIN_USERNAME=admin
      - LDAP_ADMIN_PASSWORD=adminpassword
      - LDAP_USERS=user01,user02
      - LDAP_PASSWORDS=password1,password2

Next feature

Add a group variable in the consumer , this group would come from the memberOf (configurable) attribute of the ldap user and add it in the consumer.
Then plugins such as consumer_restriction could be updated to take into account groups -> (which can also be used on basic-auth (and more) plugin where a consumer can also be part of a group)

Pre-submission checklist:

  • 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 first

@jp-gouin jp-gouin changed the title feat : Add ldap-auth plugin feat: Add ldap-auth plugin Mar 23, 2021

`ldap-auth` is an authentication plugin that can works with `consumer`. Add Ldap Authentication to a `service` or `route`.

The `consumer` then authenticate against the Ldap server using Basic authentication.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"authenticates"?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes corrected

Comment thread apisix/plugins/ldap-auth.lua Outdated
ok, err = core.schema.check(schema, conf)
end

if not ok then

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

return ok, err is enough.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok added

Comment thread apisix/plugins/ldap-auth.lua Outdated
end

-- 3. Retreive consumer for authorization plugin
if conf.auto_create_consumer then

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Better to avoid creating temporary consumers. The temporary consumer may be broken somewhere else.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok remove this feature .
It was more to act like the oidc plugin , that does not require a consumer to be created , but i see your point

Comment thread docs/en/latest/plugins/ldap-auth.md Outdated
| basedn | string | required | | | the base dn of the `ldap` server (example : `ou=users,dc=example,dc=org`) |
| ldapuri | string | required | | | the uri of the ldap server |
| usetls | boolean | optional | `true` | | Boolean flag indicating if Transport Layer Security (TLS) should be used. |
| uid | string | optional | `cn` | | the user's password |

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it the password?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No indeed it's the uid attribute that changes depending of the ldap server solution

Comment thread apisix/plugins/ldap-auth.lua Outdated
properties = {
basedn = { type = "string" },
ldapuri = { type = "string" },
usetls = { type = "boolean" },

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would you use a snake case for the field name, like base_dn / ldap_uri?

@jp-gouin jp-gouin Apr 2, 2021

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok changed

@spacewander

Copy link
Copy Markdown
Member

@jp-gouin
You can install the docker in:

And the libldap in:

sudo apt-get install "$openresty" lua5.1 liblua5.1-0-dev

@spacewander

Copy link
Copy Markdown
Member

@membphis @moonming
Can we introduce libldap as an extern dependency? This library needs to be installed manually.

Comment thread rockspec/apisix-master-0.rockspec Outdated
"luasec = 0.9-1",
"lua-resty-consul = 0.3-2",
"penlight = 1.9.2-1",
"lualdap = 1.2.3-1",

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not use the latest release: 1.2.6?

@membphis

Copy link
Copy Markdown
Member

@membphis @moonming
Can we introduce libldap as an extern dependency? This library needs to be installed manually.

https://github.com/lualdap/lualdap does not declare the license, the author needs to declare the license first, otherwise APISIX cannot use this open-source project.

@jp-gouin

Copy link
Copy Markdown
Contributor Author

@membphis there is a licence in their website https://lualdap.github.io/lualdap/license
We can open a ticket if the licence needs to be at project level

@spacewander

Copy link
Copy Markdown
Member

The spirit of the license is that you are free to use LuaLDAP for any purpose at no cost without having to ask us. The only requirement is that if you do use LuaLDAP, then you should give us credit by including the appropriate copyright notice somewhere in your product or its documentation.

IMHO, it seems we can use it after adding the copyright notice.

There is the raw file of the License page: https://github.com/lualdap/lualdap/blob/master/docs/license.md.

@membphis

Copy link
Copy Markdown
Member

@jp-gouin

jp-gouin commented Apr 6, 2021

Copy link
Copy Markdown
Contributor Author

@jp-gouin
You can install the docker in:

And the libldap in:

sudo apt-get install "$openresty" lua5.1 liblua5.1-0-dev

The CI doesn't seems to install libldap2-dev before installing apisix. Am i missing something ?

@spacewander

Copy link
Copy Markdown
Member

@jp-gouin
Thank you for your contribution.
However, as @membphis mentioned, we need to wait for the author's confirmation in
lualdap/lualdap#21

@spacewander

Copy link
Copy Markdown
Member

@jp-gouin
You can install the docker in:

And the libldap in:

sudo apt-get install "$openresty" lua5.1 liblua5.1-0-dev

The CI doesn't seems to install libldap2-dev before installing apisix. Am i missing something ?

Some ci cases have their own way to install the library, like:

yum install -y wget tar gcc automake autoconf libtool make unzip \

sudo apt-get install lua5.1 liblua5.1-0-dev

@tzssangglass

Copy link
Copy Markdown
Member

@jp-gouin hi, are you still interested in continuing this PR?

@jp-gouin

Copy link
Copy Markdown
Contributor Author

I am , however there is still the licence issue on the lualdap/lualdap#21
As soon has the licence has been validated by @membphis , i will update this PR

@membphis

Copy link
Copy Markdown
Member

@membphis @moonming
Can we introduce libldap as an extern dependency? This library needs to be installed manually.

@moonming need your help. ^_^

@jp-gouin

jp-gouin commented Aug 18, 2021

Copy link
Copy Markdown
Contributor Author

@membphis is the information provided in the lualdap/lualdap#21 enough for the use of lualdap in Apisix ?
If so i would be happy to continue working on the PR

@membphis

Copy link
Copy Markdown
Member

@membphis is the information provided in the lualdap/lualdap#21 enough for the use of lualdap in Apisix ?
If so i would be happy to continue working on the PR

cool, I think you can continue this PR, it fine now.

@membphis

Copy link
Copy Markdown
Member

I think you need to resolve the conflicting files ^_^

@jp-gouin

jp-gouin commented Oct 2, 2021

Copy link
Copy Markdown
Contributor Author

Failed tests do not seems to be related to ldap-auth plugin, do you confirm ?
Chaos test should be ok once PR apache/apisix-docker#222 is merged

local decoded = ngx.decode_base64(m[1])

local res
res, err = ngx_re.split(decoded, ":")

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Better to check if decoded is not nil and the split result has two elements.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually it’s a copy paste from

local decoded = ngx.decode_base64(m[1])
, I’ll try to update the code

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Feel free to submit another PR to update basic-auth.

Comment thread docs/en/latest/plugins/ldap-auth.md Outdated
}'
```

you can visit Dashboard `http://127.0.0.1:9080/apisix/dashboard/` and add a Consumer through the web console.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can remove this part now. The dashboard is not shipped by default.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok will remove , actually it’s a copy paste from

you also can add a Consumer through the web console:

@spacewander

Copy link
Copy Markdown
Member

Failed tests do not seems to be related to ldap-auth plugin, do you confirm ? Chaos test should be ok once PR apache/apisix-docker#222 is merged

Look like they are just flaky test results.

@membphis

membphis commented Oct 7, 2021

Copy link
Copy Markdown
Member

@membphis @moonming Can we introduce libldap as an extern dependency? This library needs to be installed manually.

LGTM ^_^

@membphis

membphis commented Oct 7, 2021

Copy link
Copy Markdown
Member

Needs to install the libldap2-dev in ChaosMesh case.

https://github.com/apache/apisix/pull/3894/checks?check_run_id=3788501510#step:5:1004

Error: Failed installing dependency: https://luarocks.org/lualdap-1.2.6-1.src.rock - Could not find header file for LDAP
  No file ldap.h in /usr/local/include
  No file ldap.h in /usr/include
  No file ldap.h in /include

Comment thread apisix/plugins/ldap-auth.lua Outdated
return nil, "split authorization err:" .. err
end
if #res < 2 then
return nil, "split authorization length is invalid"

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
return nil, "split authorization length is invalid"
return nil, "split authorization err: invalid decoded data: " .. decoded


if err then
return nil, "failed to decode authentication header"
end

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if not decoded then
        return nil, "failed to decode authentication header: " .. m[1]
end

@jp-gouin

jp-gouin commented Oct 7, 2021

Copy link
Copy Markdown
Contributor Author

@membphis , the chaos mesh test is using the apisix-docker project to build apisix :

docker build -t apache/apisix:alpine-local --build-arg APISIX_PATH=. -f Dockerfile .

I submitted a PR to add the library in the apisix-docker apache/apisix-docker#222

@spacewander

Copy link
Copy Markdown
Member

@jp-gouin
Would you update this PR? It is almost done.

@jp-gouin

Copy link
Copy Markdown
Contributor Author

@jp-gouin Would you update this PR? It is almost done.

Done :)

Comment thread .github/workflows/cli.yml
Comment thread apisix/plugins/ldap-auth.lua Outdated
@tzssangglass

Copy link
Copy Markdown
Member

LGTM

@spacewander
spacewander merged commit d1c178d into apache:master Oct 13, 2021
@lijing-21

Copy link
Copy Markdown
Contributor

@jp-gouin,
Hi, Thank you for your contribution! We are excited to hear about your story with APISIX, so we want to invite you to write an article, for reference,you could introduce the reason why you choose to use APISIX, and why you wrote this plugin, or show the readers how to use this plugin. We will publish this article on the official website of Apahce APISIX, I believe it will be of great help to our readers.
Here is my e-mail: [email protected]. Looking forward to your reply!~

@Zeeeeta

Zeeeeta commented Jan 11, 2024

Copy link
Copy Markdown

Thanks for the effort.
May I know if base_dn only support searching in one level of directory and not searching for the AD objects in subdirectory?

@AlinsRan AlinsRan mentioned this pull request Dec 16, 2024
5 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Proposition ldap-auth plugin

7 participants