summaryrefslogtreecommitdiffstats
path: root/webapp/components
diff options
context:
space:
mode:
Diffstat (limited to 'webapp/components')
-rw-r--r--webapp/components/admin_console/ldap_settings.jsx21
-rw-r--r--webapp/components/admin_console/saml_settings.jsx21
-rw-r--r--webapp/components/user_profile.jsx17
-rw-r--r--webapp/components/user_settings/user_settings_general.jsx122
4 files changed, 181 insertions, 0 deletions
diff --git a/webapp/components/admin_console/ldap_settings.jsx b/webapp/components/admin_console/ldap_settings.jsx
index 5aa23fde6..b774d34f3 100644
--- a/webapp/components/admin_console/ldap_settings.jsx
+++ b/webapp/components/admin_console/ldap_settings.jsx
@@ -38,6 +38,7 @@ export default class LdapSettings extends AdminSettings {
config.LdapSettings.NicknameAttribute = this.state.nicknameAttribute;
config.LdapSettings.EmailAttribute = this.state.emailAttribute;
config.LdapSettings.UsernameAttribute = this.state.usernameAttribute;
+ config.LdapSettings.PositionAttribute = this.state.positionAttribute;
config.LdapSettings.IdAttribute = this.state.idAttribute;
config.LdapSettings.SyncIntervalMinutes = this.parseIntNonZero(this.state.syncIntervalMinutes);
config.LdapSettings.SkipCertificateVerification = this.state.skipCertificateVerification;
@@ -63,6 +64,7 @@ export default class LdapSettings extends AdminSettings {
nicknameAttribute: config.LdapSettings.NicknameAttribute,
emailAttribute: config.LdapSettings.EmailAttribute,
usernameAttribute: config.LdapSettings.UsernameAttribute,
+ positionAttribute: config.LdapSettings.PositionAttribute,
idAttribute: config.LdapSettings.IdAttribute,
syncIntervalMinutes: config.LdapSettings.SyncIntervalMinutes,
skipCertificateVerification: config.LdapSettings.SkipCertificateVerification,
@@ -300,6 +302,25 @@ export default class LdapSettings extends AdminSettings {
disabled={!this.state.enable}
/>
<TextSetting
+ id='positionAttribute'
+ label={
+ <FormattedMessage
+ id='admin.ldap.positionAttrTitle'
+ defaultMessage='Position Attribute:'
+ />
+ }
+ placeholder={Utils.localizeMessage('admin.ldap.positionAttrEx', 'E.g.: "title"')}
+ helpText={
+ <FormattedMessage
+ id='admin.ldap.positionAttrDesc'
+ defaultMessage='(Optional) The attribute in the AD/LDAP server that will be used to populate the position field in Mattermost.'
+ />
+ }
+ value={this.state.positionAttribute}
+ onChange={this.handleChange}
+ disabled={!this.state.enable}
+ />
+ <TextSetting
id='emailAttribute'
label={
<FormattedMessage
diff --git a/webapp/components/admin_console/saml_settings.jsx b/webapp/components/admin_console/saml_settings.jsx
index c7cd73399..1391df0b6 100644
--- a/webapp/components/admin_console/saml_settings.jsx
+++ b/webapp/components/admin_console/saml_settings.jsx
@@ -41,6 +41,7 @@ export default class SamlSettings extends AdminSettings {
config.SamlSettings.EmailAttribute = this.state.emailAttribute;
config.SamlSettings.UsernameAttribute = this.state.usernameAttribute;
config.SamlSettings.NicknameAttribute = this.state.nicknameAttribute;
+ config.SamlSettings.PositionAttribute = this.state.positionAttribute;
config.SamlSettings.LocaleAttribute = this.state.localeAttribute;
config.SamlSettings.LoginButtonText = this.state.loginButtonText;
@@ -65,6 +66,7 @@ export default class SamlSettings extends AdminSettings {
emailAttribute: settings.EmailAttribute,
usernameAttribute: settings.UsernameAttribute,
nicknameAttribute: settings.NicknameAttribute,
+ positionAttribute: settings.PositionAttribute,
localeAttribute: settings.LocaleAttribute,
loginButtonText: settings.LoginButtonText
};
@@ -509,6 +511,25 @@ export default class SamlSettings extends AdminSettings {
disabled={!this.state.enable}
/>
<TextSetting
+ id='positionAttribute'
+ label={
+ <FormattedMessage
+ id='admin.saml.positionAttrTitle'
+ defaultMessage='Position Attribute:'
+ />
+ }
+ placeholder={Utils.localizeMessage('admin.saml.positionAttrEx', 'E.g.: "Role"')}
+ helpText={
+ <FormattedMessage
+ id='admin.saml.positionAttrDesc'
+ defaultMessage='(Optional) The attribute in the SAML Assertion that will be used to populate the position of users in Mattermost.'
+ />
+ }
+ value={this.state.positionAttribute}
+ onChange={this.handleChange}
+ disabled={!this.state.enable}
+ />
+ <TextSetting
id='localeAttribute'
label={
<FormattedMessage
diff --git a/webapp/components/user_profile.jsx b/webapp/components/user_profile.jsx
index 21dbf9699..9cf2464cd 100644
--- a/webapp/components/user_profile.jsx
+++ b/webapp/components/user_profile.jsx
@@ -182,6 +182,23 @@ export default class UserProfile extends React.Component {
dataContent.push(webrtc);
+ const position = this.props.user.position.substring(0, Constants.MAX_POSITION_LENGTH);
+ if (position) {
+ dataContent.push(
+ <div
+ data-toggle='tooltip'
+ title={position}
+ key='user-popover-position'
+ >
+ <p
+ className='text-nowrap'
+ >
+ {position}
+ </p>
+ </div>
+ );
+ }
+
if (global.window.mm_config.ShowEmailAddress === 'true' || UserStore.isSystemAdminForCurrentUser() || this.props.user === UserStore.getCurrentUser()) {
dataContent.push(
<div
diff --git a/webapp/components/user_settings/user_settings_general.jsx b/webapp/components/user_settings/user_settings_general.jsx
index b9db1389f..abc0e02f0 100644
--- a/webapp/components/user_settings/user_settings_general.jsx
+++ b/webapp/components/user_settings/user_settings_general.jsx
@@ -69,6 +69,10 @@ const holders = defineMessages({
close: {
id: 'user.settings.general.close',
defaultMessage: 'Close'
+ },
+ position: {
+ id: 'user.settings.general.position',
+ defaultMessage: 'Position'
}
});
@@ -85,6 +89,7 @@ class UserSettingsGeneralTab extends React.Component {
this.submitEmail = this.submitEmail.bind(this);
this.submitUser = this.submitUser.bind(this);
this.submitPicture = this.submitPicture.bind(this);
+ this.submitPosition = this.submitPosition.bind(this);
this.updateUsername = this.updateUsername.bind(this);
this.updateFirstName = this.updateFirstName.bind(this);
@@ -94,6 +99,7 @@ class UserSettingsGeneralTab extends React.Component {
this.updateConfirmEmail = this.updateConfirmEmail.bind(this);
this.updatePicture = this.updatePicture.bind(this);
this.updateSection = this.updateSection.bind(this);
+ this.updatePosition = this.updatePosition.bind(this);
this.state = this.setupInitialState(props);
}
@@ -249,6 +255,22 @@ class UserSettingsGeneralTab extends React.Component {
);
}
+ submitPosition(e) {
+ e.preventDefault();
+
+ const user = Object.assign({}, this.props.user);
+ const position = this.state.position.trim();
+
+ if (user.position === position) {
+ this.updateSection('');
+ return;
+ }
+
+ user.position = position;
+
+ this.submitUser(user, Constants.UserUpdateEvents.Position, false);
+ }
+
updateUsername(e) {
this.setState({username: e.target.value});
}
@@ -265,6 +287,10 @@ class UserSettingsGeneralTab extends React.Component {
this.setState({nickname: e.target.value});
}
+ updatePosition(e) {
+ this.setState({position: e.target.value});
+ }
+
updateEmail(e) {
this.setState({email: e.target.value});
}
@@ -302,6 +328,7 @@ class UserSettingsGeneralTab extends React.Component {
firstName: user.first_name,
lastName: user.last_name,
nickname: user.nickname,
+ position: user.position,
email: user.email,
confirmEmail: '',
picture: null,
@@ -936,6 +963,99 @@ class UserSettingsGeneralTab extends React.Component {
);
}
+ let positionSection;
+ if (this.props.activeSection === 'position') {
+ let extraInfo;
+ let submit = null;
+ if ((this.props.user.auth_service === 'ldap' || this.props.user.auth_service === Constants.SAML_SERVICE) && global.window.mm_config.PositionAttributeSet === 'true') {
+ extraInfo = (
+ <span>
+ <FormattedMessage
+ id='user.settings.general.field_handled_externally'
+ defaultMessage='This field is handled through your login provider. If you want to change it, you need to do so though your login provider.'
+ />
+ </span>
+ );
+ } else {
+ let positionLabel = (
+ <FormattedMessage
+ id='user.settings.general.position'
+ defaultMessage='Position'
+ />
+ );
+ if (Utils.isMobile()) {
+ positionLabel = '';
+ }
+
+ inputs.push(
+ <div
+ key='positionSetting'
+ className='form-group'
+ >
+ <label className='col-sm-5 control-label'>{positionLabel}</label>
+ <div className='col-sm-7'>
+ <input
+ className='form-control'
+ type='text'
+ onChange={this.updatePosition}
+ value={this.state.position}
+ maxLength={Constants.MAX_POSITION_LENGTH}
+ autoCapitalize='off'
+ />
+ </div>
+ </div>
+ );
+
+ extraInfo = (
+ <span>
+ <FormattedMessage
+ id='user.settings.general.positionExtra'
+ defaultMessage='Tell your teammates what you do.'
+ />
+ </span>
+ );
+
+ submit = this.submitPosition;
+ }
+
+ positionSection = (
+ <SettingItemMax
+ title={formatMessage(holders.position)}
+ inputs={inputs}
+ submit={submit}
+ server_error={serverError}
+ client_error={clientError}
+ updateSection={(e) => {
+ this.updateSection('');
+ e.preventDefault();
+ }}
+ extraInfo={extraInfo}
+ />
+ );
+ } else {
+ let describe = '';
+ if (user.position) {
+ describe = user.position;
+ } else {
+ describe = (
+ <FormattedMessage
+ id='user.settings.general.emptyPosition'
+ defaultMessage="Click 'Edit' to add your job title / position"
+ />
+ );
+ }
+
+ positionSection = (
+ <SettingItemMin
+ title={formatMessage(holders.position)}
+ describe={describe}
+ updateSection={() => {
+ this.updateSection('position');
+ }}
+ />
+ );
+ }
+
const emailSection = this.createEmailSection();
let pictureSection;
@@ -1030,6 +1150,8 @@ class UserSettingsGeneralTab extends React.Component {
<div className='divider-light'/>
{nicknameSection}
<div className='divider-light'/>
+ {positionSection}
+ <div className='divider-light'/>
{emailSection}
<div className='divider-light'/>
{pictureSection}