Mention group in comments is now possible. Social-util library has been added

git-svn-id: http://svn.research-infrastructures.eu/public/d4science/gcube/trunk/portlets/user/news-feed@128819 82a268e6-3cf1-43bd-a215-b396298e98cf
Feature/26194
Costantino Perciante 8 years ago
parent dc40562897
commit f156300a00

@ -4,12 +4,6 @@
<wb-resource deploy-path="/" source-path="/src/main/webapp" tag="defaultRootSource"/>
<wb-resource deploy-path="/WEB-INF/classes" source-path="/src/main/java"/>
<wb-resource deploy-path="/WEB-INF/classes" source-path="/target/generated-sources/gwt"/>
<dependent-module archiveName="session-checker-1.0.1-SNAPSHOT.jar" deploy-path="/WEB-INF/lib" handle="module:/resource/session-checker/session-checker">
<dependency-type>uses</dependency-type>
</dependent-module>
<dependent-module archiveName="gcube-widgets-2.0.0-SNAPSHOT.jar" deploy-path="/WEB-INF/lib" handle="module:/resource/gcube-widgets/gcube-widgets">
<dependency-type>uses</dependency-type>
</dependent-module>
<property name="java-output-path" value="/${module}/target/www/WEB-INF/classes"/>
<property name="context-root" value="news-feed"/>
</wb-module>

@ -86,6 +86,12 @@
<version>1.0.3</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.gcube.socialnetworking</groupId>
<artifactId>social-util-library</artifactId>
<version>1.0.0-SNAPSHOT</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.gcube.socialnetworking</groupId>
<artifactId>social-data-search-client</artifactId>

@ -3,17 +3,18 @@ package org.gcube.portlets.user.newsfeed.server;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.UUID;
import java.util.Map.Entry;
import javax.servlet.ServletContext;
@ -52,9 +53,11 @@ import org.gcube.portlets.user.newsfeed.shared.NewsConstants;
import org.gcube.portlets.user.newsfeed.shared.OperationResult;
import org.gcube.portlets.user.newsfeed.shared.UserSettings;
import org.gcube.portlets.widgets.pickitem.shared.ItemBean;
import org.gcube.social_networking.socialutillibrary.Utils;
import org.gcube.socialnetworking.social_data_search_client.ElasticSearchClientImpl;
import org.gcube.vomanagement.usermanagement.GroupManager;
import org.gcube.vomanagement.usermanagement.UserManager;
import org.gcube.vomanagement.usermanagement.exception.TeamRetrievalFault;
import org.gcube.vomanagement.usermanagement.exception.UserManagementSystemException;
import org.gcube.vomanagement.usermanagement.exception.UserRetrievalFault;
import org.gcube.vomanagement.usermanagement.impl.LiferayGroupManager;
@ -669,7 +672,7 @@ public class NewsServiceImpl extends RemoteServiceServlet implements NewsService
getASLSession().getScopeName(),
new SocialNetworkingUser(username, user.getEmailaddress(), user.getFullName(), user.getAvatarId()),
APP_ID);
boolean nResult = nm.notifyLikedFeed(feedOwnerId, feedid, escapeHtml(feedText));
boolean nResult = nm.notifyLikedFeed(feedOwnerId, feedid, Utils.escapeHtml(feedText));
_log.trace("Like Notification added? " + nResult);
}
}
@ -756,10 +759,50 @@ public class NewsServiceImpl extends RemoteServiceServlet implements NewsService
//send the notification to the mentioned users, if any
if (mentionedUsers != null && mentionedUsers.size() > 0) {
ArrayList<GenericItemBean> toPass = new ArrayList<GenericItemBean>();
for (ItemBean u : mentionedUsers) {
toPass.add(new GenericItemBean(u.getId(), u.getName(), u.getAlternativeName(), u.getThumbnailURL()));
// among the mentionedUsers there could be groups of people
Map<String, ItemBean> uniqueUsersToNotify = new HashMap<>();
UserManager um = new LiferayUserManager();
for (ItemBean bean : mentionedUsers) {
if(bean.isItemGroup()){
// retrieve the users of this group
try {
List<GCubeUser> teamUsers = um.listUsersByTeam(Long.parseLong(bean.getId()));
for (GCubeUser userTeam : teamUsers) {
if(!uniqueUsersToNotify.containsKey(userTeam.getUsername()))
uniqueUsersToNotify.put(userTeam.getUsername(), new ItemBean(userTeam.getUserId()+"",
userTeam.getUsername(), userTeam.getFullname(), userTeam.getUserAvatarURL()));
}
} catch (NumberFormatException
| UserManagementSystemException
| TeamRetrievalFault | UserRetrievalFault e) {
_log.error("Unable to retrieve team information", e);
}
}else{
// it is a user, just add to the hashmap
if(!uniqueUsersToNotify.containsKey(bean.getName()))
uniqueUsersToNotify.put(bean.getName(), bean);
}
}
Thread thread = new Thread(new MentionNotificationsThread(comment.getFeedid(), commentText, nm, comment.getKey(), toPass));
// iterate over the hashmap
Iterator<Entry<String, ItemBean>> userMapIterator = uniqueUsersToNotify.entrySet().iterator();
while (userMapIterator.hasNext()) {
Map.Entry<String, ItemBean> userEntry = (Map.Entry<String, ItemBean>) userMapIterator
.next();
ItemBean userBean = userEntry.getValue();
toPass.add(new GenericItemBean(userBean.getId(), userBean.getName(), userBean.getAlternativeName(), userBean.getThumbnailURL()));
}
Thread thread = new Thread(new MentionNotificationsThread(comment.getFeedid(), commentText, nm, null, toPass));
thread.start();
}
}
@ -941,7 +984,7 @@ public class NewsServiceImpl extends RemoteServiceServlet implements NewsService
}
@Override
public ArrayList<ItemBean> getOrganizationUsers(String currentScope) {
ArrayList<ItemBean> toReturn = Utils.getOrganizationUsers(currentScope, getASLSession().getUsername(), isWithinPortal());
ArrayList<ItemBean> toReturn = Utils.getDisplayableItemBeans(currentScope, getASLSession().getUsername(), isWithinPortal());
_log.trace("Returning " + toReturn.size() + " users for scope " + currentScope);
return toReturn;
}
@ -966,21 +1009,7 @@ public class NewsServiceImpl extends RemoteServiceServlet implements NewsService
private boolean isUsers(Feed tocheck, String username) {
return (tocheck.getEntityId().equals(username));
}
/**
* Escape an html string. Escaping data received from the client helps to
* prevent cross-site script vulnerabilities.
*
* @param html the html string to escape
* @return the escaped string
*/
private String escapeHtml(String html) {
if (html == null) {
return null;
}
return html.replaceAll("&", "&amp;").replaceAll("<", "&lt;")
.replaceAll(">", "&gt;");
}
/**
*
* @return true if the user is a portal administrator or not
@ -1006,7 +1035,7 @@ public class NewsServiceImpl extends RemoteServiceServlet implements NewsService
if (fullNames == null)
return new ArrayList<ItemBean>();
else {
ArrayList<ItemBean> allUsers = Utils.getOrganizationUsers("/"+PortalContext.getConfiguration().getInfrastructureName(), getASLSession().getUsername(), isWithinPortal());
ArrayList<ItemBean> allUsers = Utils.getDisplayableItemBeans("/"+PortalContext.getConfiguration().getInfrastructureName(), getASLSession().getUsername(), isWithinPortal());
ArrayList<ItemBean> toReturn = new ArrayList<ItemBean>();
for (String fullName : fullNames)
for (ItemBean puser : allUsers) {
@ -1038,36 +1067,6 @@ public class NewsServiceImpl extends RemoteServiceServlet implements NewsService
}
}
/**
* utilty method that convert a URL in a text into a clickable link into the browser
*
* @param text
* @return the text with the clickable url in it
*/
public String transformUrls(String textToCheck) {
StringBuilder sb = new StringBuilder();
// separate input by spaces ( URLs have no spaces )
String [] parts = textToCheck.split("\\s");
// Attempt to convert each item into an URL.
for (int i = 0; i < parts.length; i++) {
if (parts[i].startsWith("http")) {
try {
URL url = new URL(parts[i]);
// If possible then replace with anchor...
sb.append("<a class=\"link\" style=\"font-size:11px;\" href=\"").append(url).append("\" target=\"_blank\">").append(url).append("</a> ");
} catch (MalformedURLException e) {
// If there was an URL then it's not valid
_log.error("MalformedURLException returning... ");
return textToCheck;
}
} else {
sb.append(parts[i]);
sb.append(" ");
}
}
return sb.toString();
}
/**
* read from the property file in /conf the refreshing time and other configurations needed
* @return CustomConfiguration

@ -1,188 +0,0 @@
package org.gcube.portlets.user.newsfeed.server;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.servlet.http.HttpServletRequest;
import org.apache.commons.codec.binary.Base64;
import org.gcube.common.portal.GCubePortalConstants;
import org.gcube.common.portal.PortalContext;
import org.gcube.common.scope.impl.ScopeBean;
import org.gcube.common.scope.impl.ScopeBean.Type;
import org.gcube.portal.databook.client.GCubeSocialNetworking;
import org.gcube.portlets.widgets.pickitem.shared.ItemBean;
import org.gcube.vomanagement.usermanagement.GroupManager;
import org.gcube.vomanagement.usermanagement.UserManager;
import org.gcube.vomanagement.usermanagement.impl.LiferayGroupManager;
import org.gcube.vomanagement.usermanagement.impl.LiferayUserManager;
import org.gcube.vomanagement.usermanagement.model.GCubeUser;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.liferay.portal.kernel.exception.PortalException;
import com.liferay.portal.kernel.exception.SystemException;
import com.liferay.portal.kernel.management.PortalManager;
public class Utils {
private static final Logger _log = LoggerFactory.getLogger(Utils.class);
/**
*
* @param session the Asl Session
* @param withinPortal true when is on Liferay portal
* @return the users belonging to the current organization (scope)
*/
public static ArrayList<ItemBean> getOrganizationUsers(String scope, String currUser, boolean withinPortal) {
ArrayList<ItemBean> portalUsers = new ArrayList<ItemBean>();
try {
if (withinPortal) {
UserManager um = new LiferayUserManager();
GroupManager gm = new LiferayGroupManager();
ScopeBean sb = new ScopeBean(scope);
List<GCubeUser> users = null;
if (sb.is(Type.INFRASTRUCTURE))
users = um.listUsersByGroup(gm.getRootVO().getGroupId());
else if (sb.is(Type.VRE)) { //must be in VRE
//get the name from the scope
String orgName = scope.substring(scope.lastIndexOf("/")+1, scope.length());
//ask the users
users = um.listUsersByGroup(gm.getGroupId(orgName));
}
else {
_log.error("Error, you must be in SCOPE VRE OR INFRASTURCTURE, you are in VO SCOPE returning no users");
return portalUsers;
}
for (GCubeUser user : users) {
if (user.getUsername().compareTo("test.user") != 0 && user.getUsername().compareTo(currUser) != 0) { //skip test.user & current user
portalUsers.add(new ItemBean(user.getUserId()+"", user.getUsername(), user.getFullname(), user.getUserAvatarURL()));
}
}
}
else { //test users
portalUsers.add(new ItemBean("12111", "massimiliano.assante", "Test User #1", ""));
portalUsers.add(new ItemBean("14111", "massimiliano.assante", "Test Second User #2", ""));
portalUsers.add(new ItemBean("11511", "massimiliano.assante", "Test Third User", ""));
portalUsers.add(new ItemBean("11611", "massimiliano.assante", "Test Fourth User", ""));
portalUsers.add(new ItemBean("11711", "massimiliano.assante", "Test Fifth User", ""));
portalUsers.add(new ItemBean("11811", "massimiliano.assante", "Test Sixth User", ""));
portalUsers.add(new ItemBean("15811", "massimiliano.assante", "Ninth Testing User", ""));
portalUsers.add(new ItemBean("15811", "massimiliano.assante", "Eighth Testing User", ""));
portalUsers.add(new ItemBean("11211", "giogio.giorgi", "Seventh Test User", ""));
portalUsers.add(new ItemBean("2222", "pino.pinetti", "Tenth Testing User", ""));
}
} catch (Exception e) {
_log.error("Error in server get all contacts ", e);
}
return portalUsers;
}
/**
* utility method that extract the hashtags from a text
* @param postText
* @return the list of hashtags present in the text
*/
protected static List<String> getHashTags(String postText) {
List<String> hashtags = new ArrayList<>();
Pattern MY_PATTERN = Pattern.compile("^#\\w+|\\s#\\w+");
Matcher matcher = MY_PATTERN.matcher(postText);
while (matcher.find()) {
hashtags.add("#"+matcher.group().replace(" ", "").replace("#", ""));
}
return hashtags;
}
/**
* Escape an html string. Escaping data received from the client helps to
* prevent cross-site script vulnerabilities.
*
* @param html the html string to escape
* @return the escaped string
*/
protected static String escapeHtmlAndTransformUrl(String html) {
if (html == null) {
return null;
}
String toReturn = html.replaceAll("&", "&amp;").replaceAll("<", "&lt;")
.replaceAll(">", "&gt;");
// replace all the line breaks by <br/>
toReturn = toReturn.replaceAll("(\r\n|\n)"," <br/> ");
//transfrom the URL in a clickable URL
toReturn = transformUrls(toReturn);
// then replace all the double spaces by the html version &nbsp;
toReturn = toReturn.replaceAll("\\s\\s","&nbsp;&nbsp;");
return toReturn;
}
/**
* utility method that convert a url ina text in a clickable url by the browser
* and if the user has just pasted a link, converts the link in: shared a link
* @param feedText
* @return the text with the clickable url in it
*/
protected static String transformUrls(String feedText) {
StringBuilder sb = new StringBuilder();
// separate input by spaces ( URLs have no spaces )
String [] parts = feedText.split("\\s");
// Attempt to convert each item into an URL.
for (int i = 0; i < parts.length; i++) {
String toCheck = getHttpToken(parts[i]);
if (toCheck != null) {
try {
URL url = new URL(toCheck);
if (i == 0 && parts.length == 1) //then he shared just a link
return sb.append("<span style=\"color:gray; font-size:12px;\">shared </span><a class=\"link\" href=\"").append(url).append("\" target=\"_blank\">").append("a link.").append("</a> ").toString();
// If possible then replace with anchor...
sb.append("<a class=\"link\" href=\"").append(url).append("\" target=\"_blank\">").append(url).append("</a> ");
} catch (MalformedURLException e) {
// If there was an URL then it's not valid
_log.error("MalformedURLException returning... ");
return feedText;
}
} else {
sb.append(parts[i]);
sb.append(" ");
}
}
return sb.toString();
}
/**
* convert the mentioned people in HTML anchor and also Encode the params Base64
* @param escapedFeedText
* @param taggedPeople
* @return
*/
protected static String convertMentionPeopleAnchorHTML(String escapedFeedText, ArrayList<ItemBean> taggedPeople, HttpServletRequest request) {
String userProfilePageURL = "";
userProfilePageURL = PortalContext.getConfiguration().getSiteLandingPagePath(request)+GCubePortalConstants.USER_PROFILE_FRIENDLY_URL;
for (ItemBean tagged : taggedPeople) {
String taggedHTML = "<a class=\"link\" href=\""+userProfilePageURL
+"?"+
new String(Base64.encodeBase64(GCubeSocialNetworking.USER_PROFILE_OID.getBytes()))+"="+
new String(Base64.encodeBase64(tagged.getName().getBytes()))+"\">"+tagged.getAlternativeName()+"</a> ";
escapedFeedText = escapedFeedText.replace(tagged.getAlternativeName(), taggedHTML);
}
return escapedFeedText;
}
/**
* check the tokens of a pasted text and see if there's any http link in it
* @param item a text token
* @return the actual http link
*/
private static String getHttpToken(String item) {
if (item.startsWith("http") || item.startsWith("www") || item.startsWith("(www") || item.startsWith("(http")) {
if (item.startsWith("("))
item = item.substring(1, item.length());
if (item.endsWith(".") || item.endsWith(")")) { //sometimes people write the url and close the phrase with a .
item = item.substring(0, item.length()-1);
}
item = item.startsWith("www") ? "http://"+item : item;
//System.out.println("getHttpToken returns -> " + item);
return item;
}
return null;
}
}
Loading…
Cancel
Save