001    /**
002     * Copyright (c) 2000-2011 Liferay, Inc. All rights reserved.
003     *
004     * The contents of this file are subject to the terms of the Liferay Enterprise
005     * Subscription License ("License"). You may not use this file except in
006     * compliance with the License. You can obtain a copy of the License by
007     * contacting Liferay, Inc. See the License for the specific language governing
008     * permissions and limitations under the License, including but not limited to
009     * distribution rights of the Software.
010     *
011     *
012     *
013     */
014    
015    package com.liferay.portlet.social.service.impl;
016    
017    import com.liferay.portal.kernel.dao.orm.QueryUtil;
018    import com.liferay.portal.kernel.exception.PortalException;
019    import com.liferay.portal.kernel.exception.SystemException;
020    import com.liferay.portal.kernel.transaction.Propagation;
021    import com.liferay.portal.kernel.transaction.Transactional;
022    import com.liferay.portal.kernel.util.Tuple;
023    import com.liferay.portal.model.Group;
024    import com.liferay.portal.model.User;
025    import com.liferay.portal.util.PortalUtil;
026    import com.liferay.portlet.asset.model.AssetEntry;
027    import com.liferay.portlet.social.NoSuchActivityCounterException;
028    import com.liferay.portlet.social.model.SocialAchievement;
029    import com.liferay.portlet.social.model.SocialActivity;
030    import com.liferay.portlet.social.model.SocialActivityCounter;
031    import com.liferay.portlet.social.model.SocialActivityCounterConstants;
032    import com.liferay.portlet.social.model.SocialActivityCounterDefinition;
033    import com.liferay.portlet.social.model.SocialActivityDefinition;
034    import com.liferay.portlet.social.model.SocialActivityLimit;
035    import com.liferay.portlet.social.model.SocialActivityProcessor;
036    import com.liferay.portlet.social.service.base.SocialActivityCounterLocalServiceBaseImpl;
037    import com.liferay.portlet.social.service.persistence.SocialActivityCounterFinderUtil;
038    import com.liferay.portlet.social.util.SocialCounterPeriodUtil;
039    
040    import java.util.Arrays;
041    import java.util.Collections;
042    import java.util.HashMap;
043    import java.util.List;
044    import java.util.Map;
045    
046    /**
047     * @author Zsolt Berentey
048     */
049    public class SocialActivityCounterLocalServiceImpl
050            extends SocialActivityCounterLocalServiceBaseImpl {
051    
052            @Transactional(
053                    rollbackFor = SystemException.class,
054                    propagation = Propagation.REQUIRES_NEW)
055            public SocialActivityCounter addActivityCounter(
056                            long groupId, long classNameId, long classPK, String name,
057                            int ownerType, int currentValue, int totalValue)
058                    throws PortalException, SystemException {
059    
060                    Group group = groupPersistence.findByPrimaryKey(groupId);
061    
062                    long activityCounterId = counterLocalService.increment();
063    
064                    SocialActivityCounter activityCounter =
065                            socialActivityCounterPersistence.create(activityCounterId);
066    
067                    activityCounter.setGroupId(groupId);
068                    activityCounter.setCompanyId(group.getCompanyId());
069                    activityCounter.setClassNameId(classNameId);
070                    activityCounter.setClassPK(classPK);
071                    activityCounter.setName(name);
072                    activityCounter.setOwnerType(ownerType);
073                    activityCounter.setCurrentValue(currentValue);
074                    activityCounter.setTotalValue(totalValue);
075                    activityCounter.setStartPeriod(
076                            SocialCounterPeriodUtil.getStartPeriod());
077                    activityCounter.setEndPeriod(
078                            SocialActivityCounterConstants.END_PERIOD_UNDEFINED);
079    
080                    socialActivityCounterPersistence.update(
081                            activityCounter, false);
082    
083                    return activityCounter;
084            }
085    
086            public void addActivityCounters(SocialActivity activity)
087                    throws PortalException, SystemException {
088    
089                    if (!socialActivitySettingLocalService.isEnabled(
090                                    activity.getGroupId(), activity.getClassNameId())) {
091    
092                            return;
093                    }
094    
095                    User user = userPersistence.findByPrimaryKey(activity.getUserId());
096    
097                    SocialActivityDefinition activityDefinition =
098                            socialActivitySettingLocalService.getActivityDefinition(
099                                    activity.getGroupId(), activity.getClassName(),
100                                    activity.getType());
101    
102                    if ((activityDefinition == null) || !activityDefinition.isEnabled()) {
103                            return;
104                    }
105    
106                    SocialActivityProcessor activityProcessor =
107                            activityDefinition.getActivityProcessor();
108    
109                    if (activityProcessor != null) {
110                            activityProcessor.processActivity(activity);
111                    }
112    
113                    for (SocialActivityCounterDefinition activityCounterDefinition :
114                                    activityDefinition.getActivityCounterDefinitions()) {
115    
116                            if (activityCounterDefinition.isEnabled() &&
117                                    (activityCounterDefinition.getIncrement() > 0) &&
118                                    checkActivityLimit(user, activity, activityCounterDefinition)) {
119    
120                                    incrementActivityCounter(
121                                            activity.getGroupId(), user, activity.getAssetEntry(),
122                                            activityCounterDefinition);
123                            }
124                    }
125    
126                    for (SocialAchievement achievement :
127                                    activityDefinition.getAchievements()) {
128    
129                            achievement.processActivity(activity);
130                    }
131    
132                    incrementActivityCounter(
133                            activity.getGroupId(),
134                            PortalUtil.getClassNameId(User.class.getName()),
135                            activity.getUserId(),
136                            SocialActivityCounterConstants.NAME_USER_ACTIVITY,
137                            SocialActivityCounterConstants.TYPE_ACTOR, 1);
138    
139                    incrementActivityCounter(
140                            activity.getGroupId(), activity.getClassNameId(),
141                            activity.getClassPK(),
142                            SocialActivityCounterConstants.NAME_ASSET_ACTIVITY,
143                            SocialActivityCounterConstants.TYPE_ASSET, 1);
144            }
145    
146            public void deleteActivityCounters(AssetEntry assetEntry)
147                    throws PortalException, SystemException {
148    
149                    if (assetEntry == null) {
150                            return;
151                    }
152    
153                    SocialActivityCounter latestContributionActivityCounter =
154                            fetchLatestActivityCounter(
155                                    assetEntry.getGroupId(),
156                                    PortalUtil.getClassNameId(User.class.getName()),
157                                    assetEntry.getUserId(),
158                                    SocialActivityCounterConstants.NAME_CONTRIBUTION,
159                                    SocialActivityCounterConstants.TYPE_CREATOR);
160    
161                    SocialActivityCounter latestPopularityActivityCounter =
162                            fetchLatestActivityCounter(
163                                    assetEntry.getGroupId(), assetEntry.getClassNameId(),
164                                    assetEntry.getClassPK(),
165                                    SocialActivityCounterConstants.NAME_POPULARITY,
166                                    SocialActivityCounterConstants.TYPE_ASSET);
167    
168                    if ((latestContributionActivityCounter != null) &&
169                            (latestPopularityActivityCounter != null)) {
170    
171                            int startPeriod = SocialCounterPeriodUtil.getStartPeriod();
172    
173                            if (latestContributionActivityCounter.getStartPeriod() !=
174                                            startPeriod) {
175    
176                                    latestContributionActivityCounter = addNewPeriod(
177                                            latestContributionActivityCounter);
178                            }
179    
180                            if (latestPopularityActivityCounter.getStartPeriod() ==
181                                            startPeriod) {
182    
183                                    latestContributionActivityCounter.setCurrentValue(
184                                            latestContributionActivityCounter.getCurrentValue() -
185                                                    latestPopularityActivityCounter.getCurrentValue());
186                            }
187    
188                            latestContributionActivityCounter.setTotalValue(
189                                    latestContributionActivityCounter.getTotalValue() -
190                                            latestPopularityActivityCounter.getTotalValue());
191    
192                            socialActivityCounterPersistence.update(
193                                    latestContributionActivityCounter, false);
194                    }
195    
196                    deleteActivityCounters(
197                            assetEntry.getClassNameId(), assetEntry.getClassPK());
198    
199                    socialActivityLimitPersistence.removeByC_C(
200                            assetEntry.getClassNameId(), assetEntry.getClassPK());
201            }
202    
203            public void deleteActivityCounters(long classNameId, long classPK)
204                    throws SystemException {
205    
206                    socialActivityCounterPersistence.removeByC_C(classNameId, classPK);
207            }
208    
209            public SocialActivityCounter fetchLatestActivityCounter(
210                            long groupId, long classNameId, long classPK, String name,
211                            int ownerType)
212                    throws SystemException {
213    
214                    return socialActivityCounterPersistence.fetchByG_C_C_N_O_E(
215                            groupId, classNameId, classPK, name, ownerType,
216                            SocialActivityCounterConstants.END_PERIOD_UNDEFINED);
217            }
218    
219            public List<SocialActivityCounter> getActivityCounterDistribution(
220                            long groupId, String name, int offset,
221                            boolean includeCurrentPeriod)
222                    throws SystemException {
223    
224                    if (includeCurrentPeriod) {
225                            offset = offset - 1;
226                    }
227    
228                    int startPeriod = SocialCounterPeriodUtil.getStartPeriod(-offset);
229    
230                    int endPeriod = SocialActivityCounterConstants.END_PERIOD_UNDEFINED;
231    
232                    if (!includeCurrentPeriod) {
233                            endPeriod = SocialCounterPeriodUtil.getStartPeriod() - 1;
234                    }
235    
236                    return getActivityCounterDistribution(
237                            groupId, name, startPeriod, endPeriod);
238            }
239    
240            public List<SocialActivityCounter> getActivityCounterDistribution(
241                            long groupId, String name, int startPeriod, int endPeriod)
242                    throws SystemException {
243    
244                    return socialActivityCounterFinder.findAC_ByG_N_S_E_2(
245                            groupId, name, startPeriod, endPeriod);
246            }
247    
248            public List<SocialActivityCounter> getActivityCounters(
249                            long groupId, String name, int offset,
250                            boolean includeCurrentPeriod)
251                    throws SystemException {
252    
253                    if (includeCurrentPeriod) {
254                            offset = offset - 1;
255                    }
256    
257                    int startPeriod = SocialCounterPeriodUtil.getStartPeriod(-offset);
258    
259                    int endPeriod = -1;
260    
261                    if (!includeCurrentPeriod) {
262                            endPeriod = SocialCounterPeriodUtil.getStartPeriod() - 1;
263                    }
264    
265                    return getActivityCounters(groupId, name, startPeriod, endPeriod);
266            }
267    
268            public List<SocialActivityCounter> getActivityCounters(
269                            long groupId, String name, int startPeriod, int endPeriod)
270                    throws SystemException {
271    
272                    return socialActivityCounterFinder.findAC_ByG_N_S_E_1(
273                            groupId, name, startPeriod, endPeriod);
274            }
275    
276            public SocialActivityCounter getLatestActivityCounter(
277                            long groupId, long classNameId, long classPK, String name,
278                            int ownerType)
279                    throws NoSuchActivityCounterException, SystemException {
280    
281                    return socialActivityCounterPersistence.findByG_C_C_N_O_E(
282                            groupId, classNameId, classPK, name, ownerType,
283                            SocialActivityCounterConstants.END_PERIOD_UNDEFINED);
284            }
285    
286            public int getUserActivityCounters(long groupId, String[] rankingNames)
287                    throws SystemException {
288    
289                    return SocialActivityCounterFinderUtil.countU_ByG_N(
290                            groupId, rankingNames);
291            }
292    
293            public List<Tuple> getUserActivityCounters(
294                            long groupId, String[] rankingNames, String[] selectedNames,
295                            int start, int end)
296                    throws SystemException {
297    
298                    List<Long> userIds = socialActivityCounterFinder.findU_ByG_N(
299                            groupId, rankingNames, start, end);
300    
301                    if (userIds.isEmpty()) {
302                            return Collections.emptyList();
303                    }
304    
305                    Tuple[] userActivityCounters = new Tuple[userIds.size()];
306    
307                    List<SocialActivityCounter> activityCounters =
308                            SocialActivityCounterFinderUtil.findAC_By_G_C_C_N_S_E(
309                                    groupId, userIds, selectedNames, QueryUtil.ALL_POS,
310                                    QueryUtil.ALL_POS);
311    
312                    long userId = 0;
313                    Map<String, SocialActivityCounter> activityCountersMap = null;
314    
315                    for (SocialActivityCounter activityCounter : activityCounters) {
316                            if (userId != activityCounter.getClassPK()) {
317                                    userId = activityCounter.getClassPK();
318                                    activityCountersMap =
319                                            new HashMap<String, SocialActivityCounter>();
320    
321                                    Tuple userActivityCounter = new Tuple(
322                                            userId, activityCountersMap);
323    
324                                    for (int i = 0; i < userIds.size(); i++) {
325                                            long curUserId = userIds.get(i);
326    
327                                            if (userId == curUserId) {
328                                                    userActivityCounters[i] = userActivityCounter;
329    
330                                                    break;
331                                            }
332                                    }
333                            }
334    
335                            activityCountersMap.put(activityCounter.getName(), activityCounter);
336                    }
337    
338                    return Arrays.asList(userActivityCounters);
339            }
340    
341            public void incrementUserAchievementCounter(long userId, long groupId)
342                    throws PortalException, SystemException {
343    
344                    incrementActivityCounter(
345                            groupId, PortalUtil.getClassNameId(User.class.getName()), userId,
346                            SocialActivityCounterConstants.NAME_USER_ACHIEVEMENT,
347                            SocialActivityCounterConstants.TYPE_ACTOR, 1);
348            }
349    
350            protected SocialActivityCounter addActivityCounter(
351                            long groupId, long classNameId, long classPK, String name,
352                            int ownerType, int overallValue)
353                    throws PortalException, SystemException {
354    
355                    SocialActivityCounter activityCounter = null;
356    
357                    try {
358                            activityCounter = addActivityCounter(
359                                    groupId, classNameId, classPK, name, ownerType, 0,
360                                    overallValue);
361                    }
362                    catch (SystemException se) {
363                            activityCounter = fetchLatestActivityCounter(
364                                    groupId, classNameId, classPK, name, ownerType);
365                    }
366    
367                    return activityCounter;
368            }
369    
370            protected SocialActivityCounter addNewPeriod(
371                            SocialActivityCounter activityCounter)
372                    throws PortalException, SystemException {
373    
374                    if (activityCounter == null) {
375                            return null;
376                    }
377    
378                    activityCounter.setEndPeriod(
379                            SocialCounterPeriodUtil.getStartPeriod() - 1);
380    
381                    socialActivityCounterPersistence.update(activityCounter, false);
382    
383                    return addActivityCounter(
384                            activityCounter.getGroupId(), activityCounter.getClassNameId(),
385                            activityCounter.getClassPK(), activityCounter.getName(),
386                            activityCounter.getOwnerType(), activityCounter.getTotalValue());
387            }
388    
389            protected boolean checkActivityLimit(
390                            User user, SocialActivity activity,
391                            SocialActivityCounterDefinition activityCounterDefinition)
392                    throws PortalException, SystemException {
393    
394                    if (activityCounterDefinition.getLimitValue() == 0) {
395                            return true;
396                    }
397    
398                    SocialActivityLimit activityLimit =
399                            socialActivityLimitPersistence.fetchByG_U_C_C_A_A(
400                                    activity.getGroupId(), user.getUserId(),
401                                    activity.getClassNameId(), activity.getClassPK(),
402                                    activity.getType(), activityCounterDefinition.getName());
403    
404                    if (activityLimit == null) {
405                            try {
406                                    activityLimit =
407                                            socialActivityLimitLocalService.addActivityLimit(
408                                                    user.getUserId(), activity.getGroupId(),
409                                                    activity.getClassNameId(), activity.getClassPK(),
410                                                    activity.getType(), activityCounterDefinition.getName(),
411                                                    activityCounterDefinition.getLimitPeriod());
412                            }
413                            catch (SystemException se) {
414                                    activityLimit =
415                                            socialActivityLimitPersistence.fetchByG_U_C_C_A_A(
416                                                    activity.getGroupId(), user.getUserId(),
417                                                    activity.getClassNameId(), activity.getClassPK(),
418                                                    activity.getType(),
419                                                    activityCounterDefinition.getName());
420    
421                                    if (activityLimit == null) {
422                                            throw se;
423                                    }
424                            }
425                    }
426    
427                    int count = activityLimit.getCount(
428                            activityCounterDefinition.getLimitPeriod());
429    
430                    if (count < activityCounterDefinition.getLimitValue()) {
431                            activityLimit.setCount(
432                                    activityCounterDefinition.getLimitPeriod(), count + 1);
433    
434                            socialActivityLimitPersistence.update(activityLimit, false);
435    
436                            return true;
437                    }
438    
439                    return false;
440            }
441    
442            protected void incrementActivityCounter(
443                            long groupId, long classNameId, long classPK, String name,
444                            int ownerType, int increment)
445                    throws PortalException, SystemException {
446    
447                    SocialActivityCounter activityCounter = fetchLatestActivityCounter(
448                            groupId, classNameId, classPK, name, ownerType);
449    
450                    if (activityCounter == null) {
451                            activityCounter = addActivityCounter(
452                                    groupId, classNameId, classPK, name, ownerType, 0);
453                    }
454    
455                    if (!activityCounter.isActivePeriod()) {
456                            activityCounter = addNewPeriod(activityCounter);
457                    }
458    
459                    activityCounter.setCurrentValue(
460                            activityCounter.getCurrentValue() + increment);
461                    activityCounter.setTotalValue(
462                            activityCounter.getTotalValue() + increment);
463    
464                    socialActivityCounterPersistence.update(activityCounter, false);
465            }
466    
467            protected void incrementActivityCounter(
468                            long groupId, User user, AssetEntry assetEntry,
469                            SocialActivityCounterDefinition activityCounterDefinition)
470                    throws PortalException, SystemException {
471    
472                    int ownerType = activityCounterDefinition.getOwnerType();
473                    long userClassNameId = PortalUtil.getClassNameId(User.class.getName());
474    
475                    if (ownerType == SocialActivityCounterConstants.TYPE_ACTOR) {
476                            incrementActivityCounter(
477                                    groupId, userClassNameId, user.getUserId(),
478                                    activityCounterDefinition.getName(), ownerType,
479                                    activityCounterDefinition.getIncrement());
480                    }
481                    else if (ownerType == SocialActivityCounterConstants.TYPE_ASSET) {
482                            incrementActivityCounter(
483                                    groupId, assetEntry.getClassNameId(), assetEntry.getClassPK(),
484                                    activityCounterDefinition.getName(), ownerType,
485                                    activityCounterDefinition.getIncrement());
486                    }
487                    else {
488                            incrementActivityCounter(
489                                    groupId, userClassNameId, assetEntry.getUserId(),
490                                    activityCounterDefinition.getName(), ownerType,
491                                    activityCounterDefinition.getIncrement());
492                    }
493            }
494    
495    }