From 4b66bc412986153aa3d60a244b6e142aedf25c56 Mon Sep 17 00:00:00 2001 From: joker-x Date: Thu, 3 Sep 2020 03:29:57 +0200 Subject: [PATCH 01/15] Add support to CAS --- server/config/default.yaml | 12 ++++++++ server/lib/passport.js | 59 +++++++++++++++++++++++++++++++++++++- 2 files changed, 70 insertions(+), 1 deletion(-) diff --git a/server/config/default.yaml b/server/config/default.yaml index 14b07bf9..00c89f30 100644 --- a/server/config/default.yaml +++ b/server/config/default.yaml @@ -171,6 +171,18 @@ postfixBounce: # allow connections from localhost only host: 127.0.0.1 +cas: + # enable to use CAS user backend + enabled: false + urlsso: https://example.cas-server.com + # nameTag identifies the attribute to be used for user's full name + nameTag: username + # mailTag identifies the attribute to be used for user's email address + mailTag: mail + newUserRole: campaignsAdmin + # Global namespace id + newUserNamespaceId: 1 + # extra options for nodemailer nodemailer: #textEncoding: base64 diff --git a/server/lib/passport.js b/server/lib/passport.js index d5784464..efbc3033 100644 --- a/server/lib/passport.js +++ b/server/lib/passport.js @@ -175,8 +175,65 @@ module.exports.restLogin = (req, res, next) => { }); })(req, res, next); }; +let CasStrategy; +let CasStrategyOpts; +if (config.cas.enabled) { + try { + CasStrategy = require('passport-cas2').Strategy; + authMode = 'cas'; + log.info('CAS', 'Found module "passport-cas2". It will be used for CAS auth.'); + CasStrategyOpts = { + casURL: config.cas.urlsso, + propertyMap: { + name: config.cas.nameTag, + email: config.cas.mailTag + } + }; + } catch (exc) { + log.info('CAS', 'Module passport-cas2 not installed.'); + } +} +if (CasStrategy) { + log.info('Using CAS auth (passport-cas2)'); + module.exports.authMethod = 'cas'; + module.exports.isAuthMethodLocal = false; -if (LdapStrategy) { + passport.use(new CasStrategy(CasStrategyOpts, + nodeifyFunction(async (username, profile) => { + try { + const user = await users.getByUsername(username); + + return { + id: user.id, + username: username, + name: profile[config.cas.nameTag], + email: profile[config.cas.mailTag], + role: user.role + }; + } catch (err) { + if (err instanceof interoperableErrors.NotFoundError) { + const userId = await users.create(contextHelpers.getAdminContext(), { + username: username, + role: config.cas.newUserRole, + namespace: config.cas.newUserNamespaceId + }); + + return { + id: userId, + username: username, + name: profile[config.cas.nameTag], + email: profile[config.cas.mailTag], + role: config.cas.newUserRole + }; + } else { + throw err; + } + } + })); + passport.serializeUser((user, done) => done(null, user)); + passport.deserializeUser((user, done) => done(null, user)); + +} else if (LdapStrategy) { log.info('Using LDAP auth (passport-' + authMode === 'ldap' ? 'ldapjs' : authMode + ')'); module.exports.authMethod = 'ldap'; module.exports.isAuthMethodLocal = false; From 28938b679bab293cee7c0d53160b2f3b647eb3de Mon Sep 17 00:00:00 2001 From: joker-x Date: Sun, 6 Sep 2020 02:26:48 +0200 Subject: [PATCH 02/15] Passport CAS Strategy --- server/config/default.yaml | 2 +- server/lib/passport.js | 41 ++++++++++++++++++++++++-------------- 2 files changed, 27 insertions(+), 16 deletions(-) diff --git a/server/config/default.yaml b/server/config/default.yaml index 00c89f30..55db15fa 100644 --- a/server/config/default.yaml +++ b/server/config/default.yaml @@ -174,7 +174,7 @@ postfixBounce: cas: # enable to use CAS user backend enabled: false - urlsso: https://example.cas-server.com + url: https://example.cas-server.com # nameTag identifies the attribute to be used for user's full name nameTag: username # mailTag identifies the attribute to be used for user's email address diff --git a/server/lib/passport.js b/server/lib/passport.js index efbc3033..6b869ba7 100644 --- a/server/lib/passport.js +++ b/server/lib/passport.js @@ -148,6 +148,9 @@ module.exports.restLogout = (req, res) => { res.json(); }; + +module.exports.casLogin = passport.authenticate('cas', { failureRedirect: '/login' }); + module.exports.restLogin = (req, res, next) => { passport.authenticate(authMode, (err, user, info) => { if (err) { @@ -176,19 +179,11 @@ module.exports.restLogin = (req, res, next) => { })(req, res, next); }; let CasStrategy; -let CasStrategyOpts; -if (config.cas.enabled) { +if (config.cas && config.cas.enabled === true) { try { CasStrategy = require('passport-cas2').Strategy; authMode = 'cas'; log.info('CAS', 'Found module "passport-cas2". It will be used for CAS auth.'); - CasStrategyOpts = { - casURL: config.cas.urlsso, - propertyMap: { - name: config.cas.nameTag, - email: config.cas.mailTag - } - }; } catch (exc) { log.info('CAS', 'Module passport-cas2 not installed.'); } @@ -198,16 +193,23 @@ if (CasStrategy) { module.exports.authMethod = 'cas'; module.exports.isAuthMethodLocal = false; - passport.use(new CasStrategy(CasStrategyOpts, + const cas = new CasStrategy({ + casURL: config.cas.url, + propertyMap: { + displayName: config.cas.nameTag, + emails: config.cas.mailTag + } + }, nodeifyFunction(async (username, profile) => { try { const user = await users.getByUsername(username); + log.info('CAS', 'Old User: '+JSON.stringify(profile)); return { id: user.id, username: username, - name: profile[config.cas.nameTag], - email: profile[config.cas.mailTag], + name: profile.displayName, + email: profile.emails[0].value, role: user.role }; } catch (err) { @@ -215,14 +217,17 @@ if (CasStrategy) { const userId = await users.create(contextHelpers.getAdminContext(), { username: username, role: config.cas.newUserRole, - namespace: config.cas.newUserNamespaceId + namespace: config.cas.newUserNamespaceId, + name: profile.displayName, + email: profile.emails[0].value }); + log.info('CAS', 'New User: '+JSON.stringify(profile)); return { id: userId, username: username, - name: profile[config.cas.nameTag], - email: profile[config.cas.mailTag], + name: profile.displayName, + email: profile.emails[0].value, role: config.cas.newUserRole }; } else { @@ -230,9 +235,15 @@ if (CasStrategy) { } } })); + passport.use(cas); passport.serializeUser((user, done) => done(null, user)); passport.deserializeUser((user, done) => done(null, user)); + module.exports.authenticateCas = passport.authenticate('cas', { failureRedirect: '/login?cas-login-error' }); + module.exports.logoutCas = function (req, res) { + cas.logout(req, res, config.www.trustedUrlBase+'/login?cas-logout-success'); + }; + } else if (LdapStrategy) { log.info('Using LDAP auth (passport-' + authMode === 'ldap' ? 'ldapjs' : authMode + ')'); module.exports.authMethod = 'ldap'; From 0738cddcd65e1f67e7f59a1f1ca19030e3f9d523 Mon Sep 17 00:00:00 2001 From: joker-x Date: Sun, 6 Sep 2020 02:28:20 +0200 Subject: [PATCH 03/15] Routes /cas/login and /cas/logout --- client/src/lib/page.js | 15 ++++++++++++--- client/src/login/Login.js | 25 ++++++++++++++++++++++--- server/app-builder.js | 8 ++++++++ 3 files changed, 42 insertions(+), 6 deletions(-) diff --git a/client/src/lib/page.js b/client/src/lib/page.js index d5222617..9854bf73 100644 --- a/client/src/lib/page.js +++ b/client/src/lib/page.js @@ -414,6 +414,11 @@ export class SectionContent extends Component { } componentDidMount() { + const queryParams = this.props.location.search; + if (queryParams.indexOf('cas-login-success') > -1) this.setFlashMessage('success', 'Successful authentication'); + if (queryParams.indexOf('cas-logout-success') > -1) this.setFlashMessage('success', 'Successful logout'); + if (queryParams.indexOf('cas-login-error') > -1) this.setFlashMessage('danger', 'Fail authentication'); + window.addEventListener('beforeunload', this.beforeUnloadHandler); this.historyUnblock = this.props.history.block('Changes you made may not be saved. Are you sure you want to leave this page?'); } @@ -445,7 +450,11 @@ export class SectionContent extends Component { ensureAuthenticated() { if (!mailtrainConfig.isAuthenticated) { - this.navigateTo('/login?next=' + encodeURIComponent(window.location.pathname)); + if (mailtrainConfig.authMethod == 'cas') { + window.location.href=getUrl('cas/login?next=' + encodeURIComponent(window.location.pathname)); + } else { + this.navigateTo('/login?next=' + encodeURIComponent(window.location.pathname)); + } } } @@ -602,7 +611,7 @@ export class DropdownLink extends Component { const clsName = "dropdown-item" + (props.className ? " " + props.className : "") return ( - {props.children} + window.location.href=props.to}>{props.children} ); } } @@ -729,4 +738,4 @@ export function getLanguageChooser(t) { ); return languageChooser; -} \ No newline at end of file +} diff --git a/client/src/login/Login.js b/client/src/login/Login.js index 1942b639..4f562279 100644 --- a/client/src/login/Login.js +++ b/client/src/login/Login.js @@ -110,8 +110,8 @@ export default class Login extends Component { } else if (mailtrainConfig.externalPasswordResetLink) { passwordResetLink = {t('forgotYourPassword?')}; } - - return ( + if (mailtrainConfig.authMethod != 'cas') { + return (
{t('signIn')} @@ -126,6 +126,25 @@ export default class Login extends Component {
- ); + ); + } else { + if (mailtrainConfig.isAuthenticated) { + return ( +
+ {t('logOut')} CAS + {{t('logOut')}} + {passwordResetLink} +
+ ); + } else { + return ( +
+ {t('signIn')} CAS + {{t('signIn')}} + {passwordResetLink} +
+ ); + } + } } } diff --git a/server/app-builder.js b/server/app-builder.js index da1a89da..e72bb671 100644 --- a/server/app-builder.js +++ b/server/app-builder.js @@ -324,6 +324,14 @@ async function createApp(appType) { app.use('/rest', reportsRest); } install404Fallback('/rest'); + if (config.cas && config.cas.enabled === true) { + app.get('/cas/login', + passport.authenticateCas, + function(req, res) { + res.redirect('/?cas-login-success'); + }); + app.get('/cas/logout', passport.logoutCas); + } } app.use('/', await index.getRouter(appType)); From 56daa40ffb48ff02f4ac7bd99f015ee8bddc7958 Mon Sep 17 00:00:00 2001 From: joker-x Date: Sun, 6 Sep 2020 02:31:02 +0200 Subject: [PATCH 04/15] Allow set name and email of user from external auth --- server/models/users.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/models/users.js b/server/models/users.js index 6ce7aee2..13482a36 100644 --- a/server/models/users.js +++ b/server/models/users.js @@ -27,7 +27,7 @@ const namespaceHelpers = require('../lib/namespace-helpers'); const allowedKeys = new Set(['username', 'name', 'email', 'password', 'namespace', 'role']); const ownAccountAllowedKeys = new Set(['name', 'email', 'password']); -const allowedKeysExternal = new Set(['username', 'namespace', 'role']); +const allowedKeysExternal = new Set(['username', 'namespace', 'role', 'name', 'email']); const hashKeys = new Set(['username', 'name', 'email', 'namespace', 'role']); const shares = require('./shares'); const contextHelpers = require('../lib/context-helpers'); From 0d5ab221d5fe5808f76f3d2883a509fb028f77d0 Mon Sep 17 00:00:00 2001 From: joker-x Date: Sun, 6 Sep 2020 02:58:34 +0200 Subject: [PATCH 05/15] Add docker support --- README.md | 6 ++++++ docker-entrypoint.sh | 27 +++++++++++++++++++++++++++ 2 files changed, 33 insertions(+) diff --git a/README.md b/README.md index 7c949544..9e8cfa17 100644 --- a/README.md +++ b/README.md @@ -263,6 +263,12 @@ variables (e.g. `URL_BASE_TRUSTED=https://mailtrain.domain.com (and more env-var | LDAP_UIDTAG | LDAP UID tag (e.g. uid/cn/username) | | WITH_ZONE_MTA | enables or disables builtin Zone-MTA (default: true) | | POOL_NAME | sets builtin Zone-MTA pool name (default: os.hostname()) | +| WITH_CAS | use if you want to use CAS | +| CAS_URL | CAS base URL | +| CAS_NAMETAG | The field used to save the name (default: username) | +| CAS_MAILTAG | The field used to save the email (default: mail) | +| CAS_NEWUSERROLE | The role of new users (default: nobody) | +| CAS_NEWUSERNAMESPACEID | The namespace id of new users (default: 1) | If you don't want to modify the original `docker-compose.yml`, you can put your overrides to another file (e.g. `docker-compose.override.yml`) -- like the one below. diff --git a/docker-entrypoint.sh b/docker-entrypoint.sh index f2e879f9..d1c55ea2 100644 --- a/docker-entrypoint.sh +++ b/docker-entrypoint.sh @@ -26,6 +26,12 @@ LDAP_UIDTAG=${LDAP_UIDTAG:-'username'} LDAP_MAILTAG=${LDAP_MAILTAG:-'mail'} LDAP_NAMETAG=${LDAP_NAMETAG:-'username'} LDAP_METHOD=${LDAP_METHOD:-'ldapjs'} +WITH_CAS=${WITH_CAS:-'false'} +CAS_URL=${CAS_URL:-'https://example.cas-server.com'} +CAS_NAMETAG=${CAS_NAMETAG:-'username'} +CAS_MAILTAG=${CAS_MAILTAG:-'mail'} +CAS_NEWUSERROLE=${CAS_NEWUSERROLE:-'nobody'} +CAS_NEWUSERNAMESPACEID=${CAS_NEWUSERNAMESPACEID:-'1'} MONGO_HOST=${MONGO_HOST:-'mongo'} WITH_REDIS=${WITH_REDIS:-'true'} REDIS_HOST=${REDIS_HOST:-'redis'} @@ -110,6 +116,27 @@ ldap: EOT fi + # Manage CAS if enabled + if [ "$WITH_CAS" = "true" ]; then + echo 'Info: CAS enabled' + cat >> server/config/production.yaml <> server/config/production.yaml < Date: Sun, 6 Sep 2020 03:05:25 +0200 Subject: [PATCH 06/15] Fix --- client/src/lib/page.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/lib/page.js b/client/src/lib/page.js index 9854bf73..5bfccd3f 100644 --- a/client/src/lib/page.js +++ b/client/src/lib/page.js @@ -11,7 +11,7 @@ import {ActionLink, Button, DismissibleAlert, DropdownActionLink, Icon} from "./ import mailtrainConfig from "mailtrainConfig"; import styles from "./styles.scss"; import {getRoutes, renderRoute, Resolver, SectionContentContext, withPageHelpers} from "./page-common"; -import {getBaseDir} from "./urls"; +import {getBaseDir, getUrl} from "./urls"; import {createComponentMixin, withComponentMixins} from "./decorator-helpers"; import {getLang} from "../../../shared/langs"; From 60586c3611462c6d254b5a1d4691b93939380760 Mon Sep 17 00:00:00 2001 From: joker-x Date: Sun, 6 Sep 2020 03:18:55 +0200 Subject: [PATCH 07/15] Fix logout CAS from menu --- client/src/root.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/client/src/root.js b/client/src/root.js index f6e3dfea..5a3f7e55 100644 --- a/client/src/root.js +++ b/client/src/root.js @@ -96,7 +96,8 @@ class Root extends Component { {getLanguageChooser(t)} {t('account')} - {t('logOut')} + {mailtrainConfig.authMethod == 'cas' && {t('logOut')}} + {mailtrainConfig.authMethod != 'cas' && {t('logOut')}} From 10e55d94d7fe35ca6ad6e134113974c44ee65eef Mon Sep 17 00:00:00 2001 From: joker-x Date: Sun, 6 Sep 2020 03:32:04 +0200 Subject: [PATCH 08/15] Clean --- server/lib/passport.js | 3 --- 1 file changed, 3 deletions(-) diff --git a/server/lib/passport.js b/server/lib/passport.js index 6b869ba7..c5de995c 100644 --- a/server/lib/passport.js +++ b/server/lib/passport.js @@ -148,9 +148,6 @@ module.exports.restLogout = (req, res) => { res.json(); }; - -module.exports.casLogin = passport.authenticate('cas', { failureRedirect: '/login' }); - module.exports.restLogin = (req, res, next) => { passport.authenticate(authMode, (err, user, info) => { if (err) { From e980e4d34fe51c864d192599eda5acc5c71831e9 Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 13:52:25 +0200 Subject: [PATCH 09/15] cas.newUserRole set to nobody in default.yaml --- server/config/default.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/config/default.yaml b/server/config/default.yaml index 55db15fa..4412d783 100644 --- a/server/config/default.yaml +++ b/server/config/default.yaml @@ -179,7 +179,7 @@ cas: nameTag: username # mailTag identifies the attribute to be used for user's email address mailTag: mail - newUserRole: campaignsAdmin + newUserRole: nobody # Global namespace id newUserNamespaceId: 1 From b8088acfaec80d6b37df0233d40b006c6501f3c3 Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 14:26:11 +0200 Subject: [PATCH 10/15] Fix flash message text and mark them to traslation --- client/src/lib/page.js | 7 ++++--- locales/de-DE/common.json | 5 ++++- locales/en-US/common.json | 5 ++++- locales/es-ES/common.json | 5 ++++- locales/fr-FR/common.json | 5 ++++- locales/pt-BR/common.json | 5 ++++- 6 files changed, 24 insertions(+), 8 deletions(-) diff --git a/client/src/lib/page.js b/client/src/lib/page.js index 5bfccd3f..898c96cd 100644 --- a/client/src/lib/page.js +++ b/client/src/lib/page.js @@ -414,10 +414,11 @@ export class SectionContent extends Component { } componentDidMount() { + const t = this.props.t; const queryParams = this.props.location.search; - if (queryParams.indexOf('cas-login-success') > -1) this.setFlashMessage('success', 'Successful authentication'); - if (queryParams.indexOf('cas-logout-success') > -1) this.setFlashMessage('success', 'Successful logout'); - if (queryParams.indexOf('cas-login-error') > -1) this.setFlashMessage('danger', 'Fail authentication'); + if (queryParams.indexOf('cas-login-success') > -1) this.setFlashMessage('success', t('authenticationSuccessful')); + if (queryParams.indexOf('cas-logout-success') > -1) this.setFlashMessage('success', t('logoutSuccessful')); + if (queryParams.indexOf('cas-login-error') > -1) this.setFlashMessage('danger', t('authenticationFailed')); window.addEventListener('beforeunload', this.beforeUnloadHandler); this.historyUnblock = this.props.history.block('Changes you made may not be saved. Are you sure you want to leave this page?'); diff --git a/locales/de-DE/common.json b/locales/de-DE/common.json index 0802c0da..3498f472 100644 --- a/locales/de-DE/common.json +++ b/locales/de-DE/common.json @@ -1064,5 +1064,8 @@ "channelName": "Channel \"{{name}}\"", "cloneCampaign": "Clone Campaign", "next": "Next", - "selectCampaignToBeCloned": "Select campaign to be cloned." + "selectCampaignToBeCloned": "Select campaign to be cloned.", + "authenticationSuccessful": "Authentication successful", + "logoutSucessful": "Logout successful", + "authenticationFailed": "Authentication failed" } diff --git a/locales/en-US/common.json b/locales/en-US/common.json index 215b703a..cc08d156 100644 --- a/locales/en-US/common.json +++ b/locales/en-US/common.json @@ -1070,5 +1070,8 @@ "channelName": "Channel \"{{name}}\"", "cloneCampaign": "Clone Campaign", "next": "Next", - "selectCampaignToBeCloned": "Select campaign to be cloned." + "selectCampaignToBeCloned": "Select campaign to be cloned.", + "authenticationSuccessful": "Authentication successful", + "logoutSucessful": "Logout successful", + "authenticationFailed": "Authentication failed" } diff --git a/locales/es-ES/common.json b/locales/es-ES/common.json index a7fe842d..a59efeb9 100644 --- a/locales/es-ES/common.json +++ b/locales/es-ES/common.json @@ -1094,5 +1094,8 @@ "selectCampaignToBeCloned": "Elige la campaña que será clonada.", "tagLanguage": "Lenguaje de marcado", "tagLanguageMustBeSelected": "Debes seleccionar un lenguaje de marcado", - "helpText": "Texto de ayuda" + "helpText": "Texto de ayuda", + "authenticationSuccessful": "Autentificación completada con éxito", + "logoutSucessful": "Logout completado con éxito", + "authenticationFailed": "Autentificación fallida" } diff --git a/locales/fr-FR/common.json b/locales/fr-FR/common.json index a7dbe39f..33a4f3b3 100644 --- a/locales/fr-FR/common.json +++ b/locales/fr-FR/common.json @@ -1065,5 +1065,8 @@ "channelName": "Channel \"{{name}}\"", "cloneCampaign": "Clone Campaign", "next": "Next", - "selectCampaignToBeCloned": "Select campaign to be cloned." + "selectCampaignToBeCloned": "Select campaign to be cloned.", + "authenticationSuccessful": "Authentication successful", + "logoutSucessful": "Logout successful", + "authenticationFailed": "Authentication failed" } diff --git a/locales/pt-BR/common.json b/locales/pt-BR/common.json index 17d2d124..786366d4 100644 --- a/locales/pt-BR/common.json +++ b/locales/pt-BR/common.json @@ -1143,5 +1143,8 @@ "channelName": "Channel \"{{name}}\"", "cloneCampaign": "Clone Campaign", "next": "Next", - "selectCampaignToBeCloned": "Select campaign to be cloned." + "selectCampaignToBeCloned": "Select campaign to be cloned.", + "authenticationSuccessful": "Authentication successful", + "logoutSucessful": "Logout successful", + "authenticationFailed": "Authentication failed" } From 747d9f0c5143cb151abe26614feadeebb516104d Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 14:37:16 +0200 Subject: [PATCH 11/15] Add bool prop "forceReload" to DropdownLink component --- client/src/lib/page.js | 13 ++++++++++--- client/src/root.js | 2 +- 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/client/src/lib/page.js b/client/src/lib/page.js index 898c96cd..94d8505f 100644 --- a/client/src/lib/page.js +++ b/client/src/lib/page.js @@ -604,16 +604,23 @@ export class LinkButton extends Component { export class DropdownLink extends Component { static propTypes = { to: PropTypes.string, - className: PropTypes.string + className: PropTypes.string, + forceReload: PropTypes.bool } render() { const props = this.props; const clsName = "dropdown-item" + (props.className ? " " + props.className : "") - return ( + if (props.forceReload) { + return ( window.location.href=props.to}>{props.children} - ); + ); + } else { + return ( + {props.children} + ); + } } } diff --git a/client/src/root.js b/client/src/root.js index 5a3f7e55..5a40faad 100644 --- a/client/src/root.js +++ b/client/src/root.js @@ -96,7 +96,7 @@ class Root extends Component { {getLanguageChooser(t)} {t('account')} - {mailtrainConfig.authMethod == 'cas' && {t('logOut')}} + {mailtrainConfig.authMethod == 'cas' && {t('logOut')}} {mailtrainConfig.authMethod != 'cas' && {t('logOut')}} From d6e15ad0108079d2ca1a14d1e3ef70805e90f82c Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 14:50:45 +0200 Subject: [PATCH 12/15] Fix --- client/src/root.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/root.js b/client/src/root.js index 5a40faad..128a53bf 100644 --- a/client/src/root.js +++ b/client/src/root.js @@ -96,7 +96,7 @@ class Root extends Component { {getLanguageChooser(t)} {t('account')} - {mailtrainConfig.authMethod == 'cas' && {t('logOut')}} + {mailtrainConfig.authMethod == 'cas' && {t('logOut')}} {mailtrainConfig.authMethod != 'cas' && {t('logOut')}} From d02330e601937bb0ef34d75e2852521c75d2a48a Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 14:54:23 +0200 Subject: [PATCH 13/15] Fix --- locales/de-DE/common.json | 2 +- locales/en-US/common.json | 2 +- locales/es-ES/common.json | 2 +- locales/fr-FR/common.json | 2 +- locales/pt-BR/common.json | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/locales/de-DE/common.json b/locales/de-DE/common.json index 3498f472..5b73cf5e 100644 --- a/locales/de-DE/common.json +++ b/locales/de-DE/common.json @@ -1066,6 +1066,6 @@ "next": "Next", "selectCampaignToBeCloned": "Select campaign to be cloned.", "authenticationSuccessful": "Authentication successful", - "logoutSucessful": "Logout successful", + "logoutSuccessful": "Logout successful", "authenticationFailed": "Authentication failed" } diff --git a/locales/en-US/common.json b/locales/en-US/common.json index cc08d156..c48266b7 100644 --- a/locales/en-US/common.json +++ b/locales/en-US/common.json @@ -1072,6 +1072,6 @@ "next": "Next", "selectCampaignToBeCloned": "Select campaign to be cloned.", "authenticationSuccessful": "Authentication successful", - "logoutSucessful": "Logout successful", + "logoutSuccessful": "Logout successful", "authenticationFailed": "Authentication failed" } diff --git a/locales/es-ES/common.json b/locales/es-ES/common.json index a59efeb9..26ae3649 100644 --- a/locales/es-ES/common.json +++ b/locales/es-ES/common.json @@ -1096,6 +1096,6 @@ "tagLanguageMustBeSelected": "Debes seleccionar un lenguaje de marcado", "helpText": "Texto de ayuda", "authenticationSuccessful": "Autentificación completada con éxito", - "logoutSucessful": "Logout completado con éxito", + "logoutSuccessful": "Logout completado con éxito", "authenticationFailed": "Autentificación fallida" } diff --git a/locales/fr-FR/common.json b/locales/fr-FR/common.json index 33a4f3b3..418c7d4f 100644 --- a/locales/fr-FR/common.json +++ b/locales/fr-FR/common.json @@ -1067,6 +1067,6 @@ "next": "Next", "selectCampaignToBeCloned": "Select campaign to be cloned.", "authenticationSuccessful": "Authentication successful", - "logoutSucessful": "Logout successful", + "logoutSuccessful": "Logout successful", "authenticationFailed": "Authentication failed" } diff --git a/locales/pt-BR/common.json b/locales/pt-BR/common.json index 786366d4..f3c1f5d6 100644 --- a/locales/pt-BR/common.json +++ b/locales/pt-BR/common.json @@ -1145,6 +1145,6 @@ "next": "Next", "selectCampaignToBeCloned": "Select campaign to be cloned.", "authenticationSuccessful": "Authentication successful", - "logoutSucessful": "Logout successful", + "logoutSuccessful": "Logout successful", "authenticationFailed": "Authentication failed" } From 99e3f12c24e6392d9646e4141df03d382d74ca61 Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 16:10:05 +0200 Subject: [PATCH 14/15] Remove CAS logout from client login --- client/src/login/Login.js | 24 +++++++----------------- server/lib/passport.js | 2 +- 2 files changed, 8 insertions(+), 18 deletions(-) diff --git a/client/src/login/Login.js b/client/src/login/Login.js index 4f562279..8559467f 100644 --- a/client/src/login/Login.js +++ b/client/src/login/Login.js @@ -128,23 +128,13 @@ export default class Login extends Component { ); } else { - if (mailtrainConfig.isAuthenticated) { - return ( -
- {t('logOut')} CAS - {{t('logOut')}} - {passwordResetLink} -
- ); - } else { - return ( -
- {t('signIn')} CAS - {{t('signIn')}} - {passwordResetLink} -
- ); - } + return ( +
+ {t('signIn')} CAS + {{t('signIn')}} + {passwordResetLink} +
+ ); } } } diff --git a/server/lib/passport.js b/server/lib/passport.js index c5de995c..7673a0b2 100644 --- a/server/lib/passport.js +++ b/server/lib/passport.js @@ -238,7 +238,7 @@ if (CasStrategy) { module.exports.authenticateCas = passport.authenticate('cas', { failureRedirect: '/login?cas-login-error' }); module.exports.logoutCas = function (req, res) { - cas.logout(req, res, config.www.trustedUrlBase+'/login?cas-logout-success'); + cas.logout(req, res, config.www.trustedUrlBase+'/?cas-logout-success'); }; } else if (LdapStrategy) { From b4d7c1bfcf18b0cead0d4987260ce443eda4cd71 Mon Sep 17 00:00:00 2001 From: joker-x Date: Mon, 7 Sep 2020 17:41:38 +0200 Subject: [PATCH 15/15] DOCKER: Install passport-cas2 if CAS selected --- docker-entrypoint.sh | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/docker-entrypoint.sh b/docker-entrypoint.sh index 24bd4255..3d14492e 100644 --- a/docker-entrypoint.sh +++ b/docker-entrypoint.sh @@ -170,4 +170,9 @@ if [ "$WITH_ZONE_MTA" = "true" ]; then fi cd server +# Install passport-cas2 node package if CAS selected +if [ "$WITH_CAS" = "true" ]; then + echo 'Info: Installing passport-cas2' + NODE_ENV=production npm install passport-cas2 +fi NODE_ENV=production node index.js