diff --git a/.github/workflows/esrupgrade-common.yml b/.github/workflows/esrupgrade-common.yml index 782a3cc881a..ba5fbdb0beb 100644 --- a/.github/workflows/esrupgrade-common.yml +++ b/.github/workflows/esrupgrade-common.yml @@ -32,6 +32,7 @@ jobs: run: | cd server/build docker compose --no-ansi run --rm start_dependencies + cat ../tests/custom-schema-cpa.ldif | docker compose --ansi never exec -T openldap bash -c 'ldapadd -Y EXTERNAL -H ldapi:/// -w mostest || true'; cat ../tests/test-data.ldif | docker compose --no-ansi exec -T openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest'; docker compose --no-ansi exec -T minio sh -c 'mkdir -p /data/mattermost-test'; docker compose --no-ansi ps @@ -103,6 +104,7 @@ jobs: run: | cd server/build docker compose --no-ansi run --rm start_dependencies + cat ../tests/custom-schema-cpa.ldif | docker compose --ansi never exec -T openldap bash -c 'ldapadd -Y EXTERNAL -H ldapi:/// -w mostest || true'; cat ../tests/test-data.ldif | docker compose --no-ansi exec -T openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest'; docker compose --no-ansi exec -T minio sh -c 'mkdir -p /data/mattermost-test'; docker compose --no-ansi ps diff --git a/.github/workflows/mmctl-test-template.yml b/.github/workflows/mmctl-test-template.yml index 128f6a3d1d4..1826504d635 100644 --- a/.github/workflows/mmctl-test-template.yml +++ b/.github/workflows/mmctl-test-template.yml @@ -49,6 +49,7 @@ jobs: run: | cd server/build docker compose --ansi never run --rm start_dependencies + cat ../tests/custom-schema-cpa.ldif | docker compose --ansi never exec -T openldap bash -c 'ldapadd -Y EXTERNAL -H ldapi:/// -w mostest || true'; cat ../tests/test-data.ldif | docker compose --ansi never exec -T openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest'; docker compose --ansi never exec -T minio sh -c 'mkdir -p /data/mattermost-test'; docker compose --ansi never ps diff --git a/.github/workflows/server-test-template.yml b/.github/workflows/server-test-template.yml index d9cfe651930..b51d16a9f4c 100644 --- a/.github/workflows/server-test-template.yml +++ b/.github/workflows/server-test-template.yml @@ -41,6 +41,7 @@ jobs: run: | cd server/build docker compose --ansi never run --rm start_dependencies + cat ../tests/custom-schema-cpa.ldif | docker compose --ansi never exec -T openldap bash -c 'ldapadd -Y EXTERNAL -H ldapi:/// -w mostest || true'; cat ../tests/test-data.ldif | docker compose --ansi never exec -T openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest'; docker compose --ansi never exec -T minio sh -c 'mkdir -p /data/mattermost-test'; docker compose --ansi never ps diff --git a/e2e-tests/.ci/server.prepare.sh b/e2e-tests/.ci/server.prepare.sh index 9430f5c0b81..024f67ae55c 100755 --- a/e2e-tests/.ci/server.prepare.sh +++ b/e2e-tests/.ci/server.prepare.sh @@ -55,6 +55,7 @@ for SERVICE in $ENABLED_DOCKER_SERVICES; do continue fi mme2e_log "Configuring the $SERVICE container" + ${MME2E_DC_SERVER} exec -T -- openldap bash -c 'ldapadd -Y EXTERNAL -H ldapi:/// -w mostest || true' < ../../server/tests/custom-schema-cpa.ldif ${MME2E_DC_SERVER} exec -T -- openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest' <../../server/tests/test-data.ldif ;; minio) diff --git a/server/Makefile b/server/Makefile index 87e4b58a20a..86fa1d3e39e 100644 --- a/server/Makefile +++ b/server/Makefile @@ -224,7 +224,8 @@ else docker compose rm start_dependencies $(GO) run ./build/docker-compose-generator/main.go $(ENABLED_DOCKER_SERVICES) | docker compose -f docker-compose.makefile.yml -f /dev/stdin $(DOCKER_COMPOSE_OVERRIDE) run -T --rm start_dependencies ifneq (,$(findstring openldap,$(ENABLED_DOCKER_SERVICES))) - cat tests/${LDAP_DATA}-data.ldif | docker compose -f docker-compose.makefile.yml $(DOCKER_COMPOSE_OVERRIDE) exec -T openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest || true'; + cat tests/custom-schema-cpa.ldif | docker compose -f docker-compose.makefile.yml ${DOCKER_COMPOSE_OVERRIDE} exec -T openldap bash -c 'ldapadd -Y EXTERNAL -H ldapi:/// -w mostest || true'; + cat tests/${LDAP_DATA}-data.ldif | docker compose -f docker-compose.makefile.yml ${DOCKER_COMPOSE_OVERRIDE} exec -T openldap bash -c 'ldapadd -x -D "cn=admin,dc=mm,dc=test,dc=com" -w mostest || true'; endif ifneq (,$(findstring mysql-read-replica,$(ENABLED_DOCKER_SERVICES))) ./scripts/replica-mysql-config.sh diff --git a/server/i18n/en.json b/server/i18n/en.json index 106663a4799..88d42d4e024 100644 --- a/server/i18n/en.json +++ b/server/i18n/en.json @@ -8036,6 +8036,10 @@ "id": "ent.ldap.app_error", "translation": "ldap interface was nil." }, + { + "id": "ent.ldap.cpa_field_mapping.list_error", + "translation": "Failed to retrieve CPA fields" + }, { "id": "ent.ldap.create_fail", "translation": "Unable to create LDAP user." @@ -8124,6 +8128,14 @@ "id": "ent.ldap.syncronize.search_failure_size_exceeded.app_error", "translation": "Size Limit Exceeded. Try increasing your Maximum page size setting. Check out https://docs.mattermost.com/onboard/ad-ldap.html#i-see-the-log-error-ldap-result-code-4-size-limit-exceeded for more details." }, + { + "id": "ent.ldap.update_cpa.empty_attribute", + "translation": "Empty LDAP attribute value" + }, + { + "id": "ent.ldap.update_cpa.multiple_errors", + "translation": "Error(s) patching CPA value" + }, { "id": "ent.ldap.validate_admin_filter.app_error", "translation": "Invalid AD/LDAP Admin Filter." diff --git a/server/tests/custom-schema-cpa.ldif b/server/tests/custom-schema-cpa.ldif new file mode 100644 index 00000000000..db2d72ce296 --- /dev/null +++ b/server/tests/custom-schema-cpa.ldif @@ -0,0 +1,55 @@ +dn: cn=schema,cn=config +changetype: modify +add: olcAttributeTypes +olcAttributeTypes: ( 1.3.6.1.4.1.4203.666.1.101 + NAME 'textCustomAttribute' + DESC 'A text custom attribute for inetOrgPerson' + EQUALITY caseIgnoreMatch + SUBSTR caseIgnoreSubstringsMatch + SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 ) +- +add: olcAttributeTypes +olcAttributeTypes: ( 1.3.6.1.4.1.4203.666.1.104 + NAME 'dateCustomAttribute' + DESC 'A date attribute' + EQUALITY generalizedTimeMatch + ORDERING generalizedTimeOrderingMatch + SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 ) +- +add: olcAttributeTypes +olcAttributeTypes: ( 1.3.6.1.4.1.4203.666.1.105 + NAME 'selectCustomAttribute' + DESC 'A selection attribute with values: option1, option2, option3' + EQUALITY caseIgnoreMatch + SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 + SINGLE-VALUE ) +- +add: olcAttributeTypes +olcAttributeTypes: ( 1.3.6.1.4.1.4203.666.1.106 + NAME 'multiSelectCustomAttribute' + DESC 'A multi-selection attribute with values: choice1, choice2, choice3, choice4' + EQUALITY caseIgnoreMatch + SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 ) +- +add: olcAttributeTypes +olcAttributeTypes: ( 1.3.6.1.4.1.4203.666.1.107 + NAME 'userReferenceCustomAttribute' + DESC 'A reference to a single user' + EQUALITY distinguishedNameMatch + SYNTAX 1.3.6.1.4.1.1466.115.121.1.12 + SINGLE-VALUE ) +- +add: olcAttributeTypes +olcAttributeTypes: ( 1.3.6.1.4.1.4203.666.1.108 + NAME 'multiUserReferenceCustomAttribute' + DESC 'References to multiple users' + EQUALITY distinguishedNameMatch + SYNTAX 1.3.6.1.4.1.1466.115.121.1.12 ) +- +add: olcObjectClasses +olcObjectClasses: ( 1.3.6.1.4.1.4203.666.1.103 + NAME 'customInetOrgPerson' + DESC 'inetOrgPerson with custom attributes' + SUP top + AUXILIARY + MAY ( textCustomAttribute $ dateCustomAttribute $ selectCustomAttribute $ multiSelectCustomAttribute $ userReferenceCustomAttribute $ multiUserReferenceCustomAttribute)) diff --git a/server/tests/test-data.ldif b/server/tests/test-data.ldif index 7a9bcab28d8..ce1f1bf1b3a 100644 --- a/server/tests/test-data.ldif +++ b/server/tests/test-data.ldif @@ -6,143 +6,269 @@ objectclass: organizationalunit dn: uid=test.one,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Test1 title: Test1 Title mail: success+testone@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Test User 1 +dateCustomAttribute: 20240217120000Z +selectCustomAttribute: option1 +multiSelectCustomAttribute: choice1 +multiSelectCustomAttribute: choice2 +userReferenceCustomAttribute: uid=test.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=test.three,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=test.four,ou=testusers,dc=mm,dc=test,dc=com dn: uid=test.two,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Test2 title: Test2 Title mail: success+testtwo@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Test User 2 +dateCustomAttribute: 20240217130000Z +selectCustomAttribute: option2 +multiSelectCustomAttribute: choice2 +multiSelectCustomAttribute: choice3 +userReferenceCustomAttribute: uid=test.three,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=test.four,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=test.five,ou=testusers,dc=mm,dc=test,dc=com dn: uid=test.three,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Test3 title: Test3 Title mail: success+testthree@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Test User 3 +dateCustomAttribute: 20240217140000Z +selectCustomAttribute: option3 +multiSelectCustomAttribute: choice3 +multiSelectCustomAttribute: choice4 +userReferenceCustomAttribute: uid=test.four,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=test.five,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev-ops.one,ou=testusers,dc=mm,dc=test,dc=com dn: uid=test.four,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Test4 title: Test4 Title mail: success+testfour@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Test User 4 +dateCustomAttribute: 20240217150000Z +selectCustomAttribute: option1 +multiSelectCustomAttribute: choice4 +multiSelectCustomAttribute: choice2 +userReferenceCustomAttribute: uid=test.five,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev-ops.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.one,ou=testusers,dc=mm,dc=test,dc=com dn: uid=test.five,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Test5 # No title to allow testing that path mail: success+testfive@simulator.amazonses.com userPassword: Password1 - +textCustomAttribute: Custom Value for Test User 5 +dateCustomAttribute: 20240217160000Z +selectCustomAttribute: option2 +multiSelectCustomAttribute: choice1 +multiSelectCustomAttribute: choice2 +userReferenceCustomAttribute: uid=dev-ops.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.two,ou=testusers,dc=mm,dc=test,dc=com # developers dn: uid=dev-ops.one,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Dev3 title: DevOps Engineer mail: success+devopsone@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for DevOps 1 +dateCustomAttribute: 20240217170000Z +selectCustomAttribute: option3 +multiSelectCustomAttribute: choice2 +multiSelectCustomAttribute: choice3 +userReferenceCustomAttribute: uid=dev.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.three,ou=testusers,dc=mm,dc=test,dc=com dn: uid=dev.one,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Dev1 title: Senior Software Design Engineer mail: success+devone@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Dev 1 +dateCustomAttribute: 20240217180000Z +selectCustomAttribute: option1 +multiSelectCustomAttribute: choice3 +multiSelectCustomAttribute: choice4 +userReferenceCustomAttribute: uid=dev.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.three,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.four,ou=testusers,dc=mm,dc=test,dc=com dn: uid=dev.two,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Dev2 title: Software Design Engineer || mail: success+devtwo@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Dev 2 +dateCustomAttribute: 20240217190000Z +selectCustomAttribute: option2 +multiSelectCustomAttribute: choice4 +multiSelectCustomAttribute: choice1 +userReferenceCustomAttribute: uid=dev.three,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=dev.four,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=exec.one,ou=testusers,dc=mm,dc=test,dc=com dn: uid=dev.three,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Dev3 title: Software Design Engineer mail: success+devthree@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Dev 3 +dateCustomAttribute: 20240217200000Z +selectCustomAttribute: option3 +multiSelectCustomAttribute: choice1 +multiSelectCustomAttribute: choice2 +userReferenceCustomAttribute: uid=dev.four,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=exec.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=exec.two,ou=testusers,dc=mm,dc=test,dc=com dn: uid=dev.four,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Dev4 title: Staff Software Design Engineer mail: success+devfour@simulator.amazonses.com userPassword: Password1 - +textCustomAttribute: Custom Value for Dev 4 +dateCustomAttribute: 20240217210000Z +selectCustomAttribute: option1 +multiSelectCustomAttribute: choice2 +multiSelectCustomAttribute: choice3 +userReferenceCustomAttribute: uid=exec.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=exec.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=board.one,ou=testusers,dc=mm,dc=test,dc=com # executive dn: uid=exec.one,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Exec1 title: CEO mail: success+execone@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Exec 1 +dateCustomAttribute: 20240217220000Z +selectCustomAttribute: option2 +multiSelectCustomAttribute: choice3 +multiSelectCustomAttribute: choice4 +userReferenceCustomAttribute: uid=exec.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=board.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=board.two,ou=testusers,dc=mm,dc=test,dc=com dn: uid=exec.two,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Exec2 title: CTO mail: success+exectwo@simulator.amazonses.com userPassword: Password1 - +textCustomAttribute: Custom Value for Exec 2 +dateCustomAttribute: 20240217230000Z +selectCustomAttribute: option3 +multiSelectCustomAttribute: choice4 +multiSelectCustomAttribute: choice1 +userReferenceCustomAttribute: uid=board.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=board.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=board.three,ou=testusers,dc=mm,dc=test,dc=com # board of directors dn: uid=board.one,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Board1 title: Director mail: success+boardone@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Board 1 +dateCustomAttribute: 20240218000000Z +selectCustomAttribute: option1 +multiSelectCustomAttribute: choice1 +multiSelectCustomAttribute: choice2 +userReferenceCustomAttribute: uid=board.two,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=board.three,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=firstloginuser.one,ou=testusers,dc=mm,dc=test,dc=com dn: uid=board.two,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Board2 title: Inside Director mail: success+boardtwo@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Board 2 +dateCustomAttribute: 20240218010000Z +selectCustomAttribute: option2 +multiSelectCustomAttribute: choice2 +multiSelectCustomAttribute: choice3 +userReferenceCustomAttribute: uid=board.three,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=firstloginuser.one,ou=testusers,dc=mm,dc=test,dc=com +multiUserReferenceCustomAttribute: uid=firstloginuser.two,ou=testusers,dc=mm,dc=test,dc=com dn: uid=board.three,ou=testusers,dc=mm,dc=test,dc=com changetype: add objectclass: iNetOrgPerson +objectclass: customInetOrgPerson sn: User cn: Board3 title: Outside Director mail: success+boardthree@simulator.amazonses.com userPassword: Password1 +textCustomAttribute: Custom Value for Board 3 +dateCustomAttribute: 20240218020000Z dn: uid=firstloginuser.one,ou=testusers,dc=mm,dc=test,dc=com changetype: add