The Blog - Expert Thoughts & Opinions

Allowing Specific Users View Posts In A Private Chatter Group

By default, Salesforce only allows you to make a chatter group public or private. If you decide to make a chatter group private, any users who are not a member of that group cannot see or add posts to that group.

However, sometimes we would like to allow users to see posts in a group but not to add posts to it.

We can achieve this by creating simple custom settings, user groups and a simple trigger code.

The custom settings would link a chatter group to a public users group. Then, only members of this users group would be able to post chatter posts to that chatter group. This will also allow easy administration to add/remove users from the authorised list of users.

When a user will try to post to a group they’re not authorised to do so they will see the following error message that will prevent them from adding a chatter post:

We decided to name our custom settings list object as Chatter_Group_Authorized_Users__c. We added 2 text fields to it called Chatter_Group_Name__c and Group_Name_Of_Authorized_Users__c.

Then we added a trigger code on the Feed Item object: 

 trigger BlockUnauthorisedChatterPosts on FeedItem (before insert) {  
   List newChatterPosts = (List)trigger.new;  
   ChatterPostsValidations.validateUserCanPostToGroup(newChatterPosts);  
 }  

Most of the logic is maintained in a dedicated class. That logic checks if the chatter post is posted under a group, if the chatter group has a group of authorised users associated with it and if the current is a member of that group.

 

 public with sharing class ChatterPostsValidations {  
   private static Map chatterGroups;  
   private static Map chatterGroupNameToAuthorisedUsersGroupName;  
   private static List groupsAndTheirMembers;  
   public static void validateUserCanPostToGroup(List newChatterPosts){  
     chatterGroups = getChatterGroups(newChatterPosts);  
     if(!chatterGroups.isEmpty()){  
       getChatterGroupNameToAuthorisedUsersGroupName();  
       if(!chatterGroupNameToAuthorisedUsersGroupName.isEmpty()){  
         getGroupsAndTheirMembers();  
         for(FeedItem newChatterPost : newChatterPosts){  
           if(userCantCreateChatterPost(newChatterPost)){  
             newChatterPost.addError('You do not have permissions to post to this chatter group');  
           }  
         }  
       }  
     }  
   }  
   private static Map getChatterGroups(List newChatterPosts){  
     Set chatterGroupIds = new Set();  
     for(FeedItem newChatterPost : newChatterPosts){  
       chatterGroupIds.add(newChatterPost.ParentId);  
     }  
     return new Map([SELECT Id, Name FROM CollaborationGroup WHERE Id IN :chatterGroupIds]);  
   }  
   private static void getChatterGroupNameToAuthorisedUsersGroupName(){  
     chatterGroupNameToAuthorisedUsersGroupName = new Map();  
     for(Chatter_Group_Authorized_Users__c c : [SELECT Chatter_Group_Name__c, Group_Name_Of_Authorized_Users__c FROM Chatter_Group_Authorized_Users__c]){  
       chatterGroupNameToAuthorisedUsersGroupName.put(c.Chatter_Group_Name__c, c.Group_Name_Of_Authorized_Users__c);  
     }  
   }  
   private static void getGroupsAndTheirMembers(){  
     groupsAndTheirMembers = [SELECT Name, (SELECT UserOrGroupId FROM GroupMembers)  
                 FROM Group  
                 WHERE Type != 'Queue' AND Name IN :chatterGroupNameToAuthorisedUsersGroupName.values()];  
   }  
   private static Boolean userCantCreateChatterPost(FeedItem newChatterPost){  
     if(chatterGroups.containsKey(newChatterPost.ParentId)){  
       CollaborationGroup chatterGroup = chatterGroups.get(newChatterPost.ParentId);  
       if(chatterGroupNameToAuthorisedUsersGroupName.containsKey(chatterGroup.Name)){  
         String usersGroupName = chatterGroupNameToAuthorisedUsersGroupName.get(chatterGroup.Name);  
         return userIsntMemberOfGroup(usersGroupName);  
       }  
     }  
     return false;  
   }  
   private static Boolean userIsntMemberOfGroup(String usersGroupName){  
     for(Group g : groupsAndTheirMembers){  
       if(g.Name == usersGroupName){  
         for(GroupMember gm : g.GroupMembers){  
           if(UserInfo.getUserId() == gm.UserOrGroupId){  
             return false;  
           }  
         }  
       }  
     }  
     return true;  
   }  
 }  

You can see how we do the SOQL queries only if they’re necessary. First, we check if the new chatter posts were added to chatter groups. Only then we check if there are any settings associated with those chatter groups and at last we get the list of users from the associated groups. We then go over the list of new chatter posts and make sure the current user can add each one of them.

You can find this code with some test methods in our Github.