2
votes

I'm building a custom workflow where all users that are members of a specific role will receive email notifications depending on certain state changes. I've begun fleshing out e-mail templates via Sitecore items with replaceable tokens, but I'm struggling to find a way to allow the setting of the recipient role in Sitecore. I'd like to avoid having users enter a string representation of the role, so a droplink would be ideal if there were a way to populate it with the various roles defined in sitecore. Bonus points if I can filter the roles that populate the droplink.

I'm aware that users/roles/domains aren't defined as items in the content tree, so how exactly does one go about configuring this droplink?

Sitecore 6.5.

2

2 Answers

3
votes

I'm not sure if there is a module for this already made, but you can use this technique: http://newguid.net/sitecore/2013/coded-field-datasources-in-sitecore/

It explains how you can use a class as data source. So you could create a class that lists all user roles.

2
votes

You might want to take a look at http://sitecorejunkie.com/2012/12/28/have-a-field-day-with-custom-sitecore-fields/ which presents a multilist to allow you to select a list of users.

Also take a look at the Workflow Escaltor Module form which you can borrow the AccountSelector control which allows you to select either individual person or roles.

This is the module I previously used to do this exact thing. The following code gets all the unique email addresses of users and only for those users that have read access to the item (it was a multisite implementation, the roles were restricted to each site but the workflow was shared).

protected override List<string> GetRecipientList(WorkflowPipelineArgs args, Item workflowItem)
{
    Field recipientsField = workflowItem.Fields["To"];
    Error.Assert((recipientsField != null || !string.IsNullOrEmpty(recipientsField.Value)), "The 'To' field is not specified in the mail action item: " + workflowItem.Paths.FullPath);

    List<string> recepients = GetEmailsForUsersAndRoles(recipientsField, args);

    if (recepients.Count == 0)
        Log.Info("There are no users with valid email addresses to notify for item submission: " + workflowItem.Paths.FullPath);

    return recepients;
}

//Returns unique email addresses of users that correspond to the selected list of users/roles  
private List<string> GetEmailsForUsersAndRoles(Field field, WorkflowPipelineArgs args)
{
    List<string> emails = new List<string>();
    List<User> allUsers = new List<User>();

    AccountSelectorField accountSelectorField = new AccountSelectorField(field);
    List<Account> selectedRoles = accountSelectorField.GetSelectedAccountsByType(AccountType.Role);
    List<Account> selectedUsers = accountSelectorField.GetSelectedAccountsByType(AccountType.User);

    foreach (var role in selectedRoles)
    {
        var users = RolesInRolesManager.GetUsersInRole(Role.FromName(role.Name), true).ToList();
        if (users.Any()) 
            allUsers.AddRange(users);
    }

    selectedUsers.ForEach(i => allUsers.Add(Sitecore.Security.Accounts.User.FromName(i.Name, false)));

    foreach (var user in allUsers)
    {   
        if (user == null || !args.DataItem.Security.CanRead(user)) continue; //move on if user does not have access to item

        if (!emails.Contains(user.Profile.Email.ToLower()))
        {
            if(user.Profile.Email != null && !string.IsNullOrEmpty(user.Profile.Email.Trim()))
                emails.Add(user.Profile.Email.ToLower());
            else
                Log.Error("No email address setup for user: " + user.Name);

        }
    }

    return emails;
}