001/* 002 * (C) Copyright 2006-2012 Nuxeo SA (http://nuxeo.com/) and others. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 * 016 * Contributors: 017 * Thomas Roger <troger@nuxeo.com> 018 */ 019 020package org.nuxeo.ecm.rating; 021 022import static org.nuxeo.ecm.core.schema.FacetNames.SUPER_SPACE; 023import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.ACTOR_PARAMETER; 024import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.ASPECT_PARAMETER; 025import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.CONTEXT_PARAMETER; 026import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.QUERY_TYPE_PARAMETER; 027import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.RATING_PARAMETER; 028import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.TARGET_OBJECT_PARAMETER; 029import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.QueryType.GET_ACTOR_RATINGS_FOR_OBJECT; 030import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.QueryType.GET_LATEST_RATED_FOR_OBJECT; 031import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.QueryType.GET_RATED_CHILDREN_FOR_CONTEXT; 032import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.QueryType.GET_RATINGS_FOR_CANCEL; 033import static org.nuxeo.ecm.rating.RatingActivityStreamFilter.QueryType.GET_RATINGS_FOR_OBJECT; 034import static org.nuxeo.ecm.rating.api.Constants.RATING_VERB_PREFIX; 035 036import java.io.Serializable; 037import java.util.HashMap; 038import java.util.Map; 039 040import org.apache.commons.lang.exception.ExceptionUtils; 041import org.apache.commons.logging.Log; 042import org.apache.commons.logging.LogFactory; 043import org.nuxeo.ecm.activity.ActivitiesList; 044import org.nuxeo.ecm.activity.Activity; 045import org.nuxeo.ecm.activity.ActivityBuilder; 046import org.nuxeo.ecm.activity.ActivityHelper; 047import org.nuxeo.ecm.activity.ActivityStreamService; 048import org.nuxeo.ecm.core.api.DocumentModel; 049import org.nuxeo.ecm.core.api.IdRef; 050import org.nuxeo.ecm.core.api.UnrestrictedSessionRunner; 051import org.nuxeo.ecm.rating.api.RatingService; 052import org.nuxeo.runtime.api.Framework; 053import org.nuxeo.runtime.model.DefaultComponent; 054 055/** 056 * Default implementation of {@see RatingService}. 057 * 058 * @author <a href="mailto:troger@nuxeo.com">Thomas Roger</a> 059 * @since 5.6 060 */ 061public class RatingServiceImpl extends DefaultComponent implements RatingService { 062 063 private static final Log log = LogFactory.getLog(RatingServiceImpl.class); 064 065 @Override 066 public void rate(String username, int rating, String activityObject, String aspect) { 067 Activity activity = new ActivityBuilder().verb(RATING_VERB_PREFIX + aspect).actor( 068 ActivityHelper.createUserActivityObject(username)).target(activityObject).object(String.valueOf(rating)).build(); 069 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 070 activityStreamService.addActivity(activity); 071 072 addSuperSpaceRate(activity); 073 } 074 075 @Override 076 public void cancelRate(String username, String activityObject, String aspect) { 077 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 078 parameters.put(QUERY_TYPE_PARAMETER, GET_RATINGS_FOR_CANCEL); 079 parameters.put(ACTOR_PARAMETER, ActivityHelper.createUserActivityObject(username)); 080 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 081 parameters.put(ASPECT_PARAMETER, aspect); 082 083 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 084 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 085 activityStreamService.removeActivities(activities); 086 } 087 088 @Override 089 public void cancelRates(String activityObject, String aspect) { 090 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 091 parameters.put(QUERY_TYPE_PARAMETER, GET_RATINGS_FOR_CANCEL); 092 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 093 parameters.put(ASPECT_PARAMETER, aspect); 094 095 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 096 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 097 activityStreamService.removeActivities(activities); 098 } 099 100 @Override 101 public boolean hasUserRated(String username, String activityObject, String aspect) { 102 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 103 parameters.put(QUERY_TYPE_PARAMETER, GET_ACTOR_RATINGS_FOR_OBJECT); 104 parameters.put(ACTOR_PARAMETER, ActivityHelper.createUserActivityObject(username)); 105 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 106 parameters.put(ASPECT_PARAMETER, aspect); 107 108 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 109 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 110 return !activities.isEmpty(); 111 } 112 113 @Override 114 public long getRatesCount(String activityObject, String aspect) { 115 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 116 parameters.put(QUERY_TYPE_PARAMETER, GET_RATINGS_FOR_OBJECT); 117 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 118 parameters.put(ASPECT_PARAMETER, aspect); 119 120 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 121 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 122 return activities.size(); 123 } 124 125 @Override 126 public long getRatesCount(String activityObject, int rating, String aspect) { 127 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 128 parameters.put(QUERY_TYPE_PARAMETER, GET_RATINGS_FOR_OBJECT); 129 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 130 parameters.put(ASPECT_PARAMETER, aspect); 131 parameters.put(RATING_PARAMETER, Integer.valueOf(rating)); 132 133 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 134 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 135 return activities.size(); 136 } 137 138 @Override 139 public long getRatesCountForUser(String username, String activityObject, String aspect) { 140 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 141 parameters.put(QUERY_TYPE_PARAMETER, GET_ACTOR_RATINGS_FOR_OBJECT); 142 parameters.put(ACTOR_PARAMETER, ActivityHelper.createUserActivityObject(username)); 143 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 144 parameters.put(ASPECT_PARAMETER, aspect); 145 146 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 147 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 148 return activities.size(); 149 } 150 151 @Override 152 public long getRatesCountForUser(String username, String activityObject, int rating, String aspect) { 153 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 154 parameters.put(QUERY_TYPE_PARAMETER, GET_ACTOR_RATINGS_FOR_OBJECT); 155 parameters.put(ACTOR_PARAMETER, ActivityHelper.createUserActivityObject(username)); 156 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 157 parameters.put(ASPECT_PARAMETER, aspect); 158 parameters.put(RATING_PARAMETER, Integer.valueOf(rating)); 159 160 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 161 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 162 return activities.size(); 163 } 164 165 @Override 166 public double getAverageRating(String activityObject, String aspect) { 167 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 168 parameters.put(QUERY_TYPE_PARAMETER, GET_RATINGS_FOR_OBJECT); 169 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 170 parameters.put(ASPECT_PARAMETER, aspect); 171 172 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 173 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 174 return computeAverage(activities); 175 } 176 177 @Override 178 public double getAverageRatingForUser(String username, String activityObject, String aspect) { 179 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 180 parameters.put(QUERY_TYPE_PARAMETER, GET_ACTOR_RATINGS_FOR_OBJECT); 181 parameters.put(ACTOR_PARAMETER, ActivityHelper.createUserActivityObject(username)); 182 parameters.put(TARGET_OBJECT_PARAMETER, activityObject); 183 parameters.put(ASPECT_PARAMETER, aspect); 184 185 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 186 ActivitiesList activities = activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 187 return computeAverage(activities); 188 } 189 190 @Override 191 public ActivitiesList getRatedChildren(String activityObject, int rating, String aspect) { 192 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 193 parameters.put(QUERY_TYPE_PARAMETER, GET_RATED_CHILDREN_FOR_CONTEXT); 194 parameters.put(CONTEXT_PARAMETER, activityObject); 195 parameters.put(ASPECT_PARAMETER, aspect); 196 parameters.put(RATING_PARAMETER, Integer.valueOf(rating)); 197 198 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 199 return activityStreamService.query(RatingActivityStreamFilter.ID, parameters); 200 } 201 202 @Override 203 public ActivitiesList getLastestRatedDocByUser(String username, String aspect, int limit) { 204 Map<String, Serializable> parameters = new HashMap<String, Serializable>(); 205 parameters.put(QUERY_TYPE_PARAMETER, GET_LATEST_RATED_FOR_OBJECT); 206 parameters.put(ACTOR_PARAMETER, ActivityHelper.createUserActivityObject(username)); 207 parameters.put(ASPECT_PARAMETER, aspect); 208 209 ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 210 return activityStreamService.query(RatingActivityStreamFilter.ID, parameters, 0, limit); 211 } 212 213 private double computeAverage(ActivitiesList activities) { 214 double average = 0; 215 for (Activity activity : activities) { 216 try { 217 average += Integer.valueOf(activity.getObject()).intValue(); 218 } catch (NumberFormatException e) { 219 log.warn(activity.getObject() + " is not a valid rating"); 220 } 221 } 222 return average / activities.size(); 223 } 224 225 protected void addSuperSpaceRate(final Activity fromActivity) { 226 final String activityObject = fromActivity.getTarget(); 227 if (!ActivityHelper.isDocument(activityObject)) { 228 return; 229 } 230 231 final ActivityStreamService activityStreamService = Framework.getLocalService(ActivityStreamService.class); 232 new UnrestrictedSessionRunner(ActivityHelper.getRepositoryName(activityObject)) { 233 @Override 234 public void run() { 235 IdRef docId = new IdRef(ActivityHelper.getDocumentId(activityObject)); 236 for (DocumentModel parent : session.getParentDocuments(docId)) { 237 if (!parent.hasFacet(SUPER_SPACE)) { 238 continue; 239 } 240 Activity activity = new ActivityBuilder(fromActivity).context( 241 ActivityHelper.createDocumentActivityObject(parent)).build(); 242 activityStreamService.addActivity(activity); 243 } 244 } 245 }.runUnrestricted(); 246 } 247}