Syncing user between two servers instances with different authentication methods

Originally asked by Ziad Qadora on 03 August 2020 (original question)


Hello,

I’m syncing issues between two server instances of Jira(Server(source) and DC(target)). We user Azure to authenticate the users in the server instance using an external corporate email for username. The users do exist on the DC instance, but they are assigned user ids as the username that is used to authenticate using LDAP . The user email in the DC profile is a different email than the one used in the Azure email essentially making them different users.

We are using the latest version of Exalate in both side of the integration. I have added two custom fields to populate the user info as below, but the field is getting populated.

Outgoing sync

replica.assignee = issue.assignee
replica.reporter = issue.reporter

Incoming Sync

issue.customFields.“External Assignee”.value = nodeHelper.getUserByUsername(replica.assignee?.username)
issue.customFields.“External Reporter”.value = nodeHelper.getUserByUsername(replica.reporter?.username)

Any idea why these custom fields are getting populated? Any recommendation on how to map the users in a more efficient way. Eventually we will have to manually re-assign the users to match the actual users specified in the source.


Answer by Francis Martens (Exalate) on 03 August 2020

Hi Ziad Qadora

What is the type of the customfields (External Assignee, External Reporter)?

the nodeHelper,getUserByUsername returns an user object, and the custom field needs to be a user customfield to accept user objects.

Alternative is that if ‘Esternal Assignee’ is a text field, you can do something like

issue.customFields."External Assignee".value = nodeHelper,getUserByUsername(replica.assignee?.username)?.displayName ?: replica.assignee?.displayName

Let me know


Answer by Ziad Qadora on 04 August 2020

Hi,

Instead of populating the custom text field, when possible to construct the username from the remote issue information then we can use that instead. Below is an example of constructing the information using the displayName and populating the assignee with that information.

def assigneeUser = replica.assignee?.displayName

if(assigneeUser){
String str;
str = assigneeUser.split(’ ');
def firstName = str[0].toLowerCase();
def lastName = str[1].toLowerCase();
def lastInitial = lastName.take(1);
def username = firstName.concat(lastInitial);
issue.assignee = nodeHelper.getUserByUsername(username);
}

If anyone has used a more efficient way, then please let me know


Comments:

Francis Martens (Exalate) commented on 04 August 2020

A small optimization is by using a regexp, but this is rather style than anything else (and me bragging)

def name = replica.assignee?.displayName
def matcher =  name =~ /(.*) (.)/
if (name && matcher.groupCount() == 2) {
   def username = (matcher[0][1] + matcher[0][2]).toLowerCase()
   issue.assignee = nodeHelper.getUserByUsername(username)
}

It is always a good thing to try this first in a groovy web console

https://groovyconsole.appspot.com/

Answer by Ziad Qadora on 03 August 2020

Hi,

using issue.customFields.“External Assignee”.value = replica.assignee?.displayName has worked.


Answer by Ziad Qadora on 03 August 2020

Hi Francis,

You are correct that the custom fields are single line text field.

I have used the suggested code and the custom field for the external assignee and reporter are not getting populated getting updated still.


Comments:

Francis Martens (Exalate) commented on 04 August 2020

Oops - had a mistake in my suggestion - fixed in the mean time.