Browse Source

Notification settings for rules

pull/8819/head
ViacheslavKlimov 3 years ago
parent
commit
d49a6c3e92
  1. 4
      application/src/main/java/org/thingsboard/server/controller/NotificationController.java
  2. 8
      application/src/main/java/org/thingsboard/server/service/notification/DefaultNotificationCenter.java
  3. 2
      common/dao-api/src/main/java/org/thingsboard/server/dao/notification/NotificationSettingsService.java
  4. 54
      common/data/src/main/java/org/thingsboard/server/common/data/notification/settings/UserNotificationSettings.java
  5. 2
      common/data/src/main/java/org/thingsboard/server/common/data/page/SortOrder.java
  6. 52
      dao/src/main/java/org/thingsboard/server/dao/notification/DefaultNotificationSettingsService.java

4
application/src/main/java/org/thingsboard/server/controller/NotificationController.java

@ -298,7 +298,7 @@ public class NotificationController extends BaseController {
if (targetType == NotificationTargetType.PLATFORM_USERS) {
PageData<User> recipients = notificationTargetService.findRecipientsForNotificationTargetConfig(user.getTenantId(),
(PlatformUsersNotificationTargetConfig) target.getConfiguration(), new PageLink(recipientsPreviewSize, 0, null,
new SortOrder("createdTime", SortOrder.Direction.DESC)));
SortOrder.byCreatedTimeDesc));
recipientsCount = (int) recipients.getTotalElements();
recipientsPart = recipients.getData().stream().map(r -> (NotificationRecipient) r).collect(Collectors.toList());
} else {
@ -451,7 +451,7 @@ public class NotificationController extends BaseController {
@PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')")
public UserNotificationSettings getUserNotificationSettings(@AuthenticationPrincipal SecurityUser user) {
return notificationSettingsService.getUserNotificationSettings(user.getTenantId(),
userService.findUserById(user.getTenantId(), user.getId()));
userService.findUserById(user.getTenantId(), user.getId()), true);
}
}

8
application/src/main/java/org/thingsboard/server/service/notification/DefaultNotificationCenter.java

@ -37,7 +37,6 @@ import org.thingsboard.server.common.data.notification.NotificationRequestConfig
import org.thingsboard.server.common.data.notification.NotificationRequestStats;
import org.thingsboard.server.common.data.notification.NotificationRequestStatus;
import org.thingsboard.server.common.data.notification.NotificationStatus;
import org.thingsboard.server.common.data.notification.NotificationType;
import org.thingsboard.server.common.data.notification.info.RuleOriginatedNotificationInfo;
import org.thingsboard.server.common.data.notification.settings.NotificationSettings;
import org.thingsboard.server.common.data.notification.settings.UserNotificationSettings;
@ -240,10 +239,9 @@ public class DefaultNotificationCenter extends AbstractSubscriptionService imple
if (ctx.getStats().contains(deliveryMethod, recipient.getId())) {
throw new AlreadySentException();
}
if (recipient instanceof User) {
NotificationType notificationType = ctx.getNotificationTemplate().getNotificationType();
UserNotificationSettings settings = notificationSettingsService.getUserNotificationSettings(ctx.getTenantId(), (User) recipient);
Set<NotificationDeliveryMethod> enabledDeliveryMethods = settings.getEnabledDeliveryMethods(notificationType);
if (recipient instanceof User && ctx.getRequest().getRuleId() != null) {
UserNotificationSettings settings = notificationSettingsService.getUserNotificationSettings(ctx.getTenantId(), (User) recipient, false);
Set<NotificationDeliveryMethod> enabledDeliveryMethods = settings.getEnabledDeliveryMethods(ctx.getRequest().getRuleId());
if (!enabledDeliveryMethods.contains(deliveryMethod)) {
throw new RuntimeException("User disabled " + deliveryMethod.getName() + " notifications of this type");
}

2
common/dao-api/src/main/java/org/thingsboard/server/dao/notification/NotificationSettingsService.java

@ -29,7 +29,7 @@ public interface NotificationSettingsService {
void saveUserNotificationSettings(TenantId tenantId, UserId userId, UserNotificationSettings settings);
UserNotificationSettings getUserNotificationSettings(TenantId tenantId, User user);
UserNotificationSettings getUserNotificationSettings(TenantId tenantId, User user, boolean format);
void createDefaultNotificationConfigs(TenantId tenantId);

54
common/data/src/main/java/org/thingsboard/server/common/data/notification/settings/UserNotificationSettings.java

@ -18,47 +18,55 @@ package org.thingsboard.server.common.data.notification.settings;
import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;
import org.thingsboard.server.common.data.id.NotificationRuleId;
import org.thingsboard.server.common.data.notification.NotificationDeliveryMethod;
import org.thingsboard.server.common.data.notification.NotificationType;
import org.thingsboard.server.common.data.util.CollectionsUtil;
import org.thingsboard.server.common.data.notification.rule.NotificationRule;
import javax.validation.Valid;
import javax.validation.constraints.NotNull;
import java.util.Collections;
import java.util.Map;
import java.util.List;
import java.util.Set;
import java.util.UUID;
@Data
public class UserNotificationSettings {
private final Map<NotificationType, NotificationTypePrefs> prefs;
@NotNull
@Valid
private final List<NotificationPref> prefs;
public static final UserNotificationSettings DEFAULT = new UserNotificationSettings(Collections.emptyList());
@JsonCreator
public UserNotificationSettings(@JsonProperty("prefs") Map<NotificationType, NotificationTypePrefs> prefs) {
public UserNotificationSettings(@JsonProperty("prefs") List<NotificationPref> prefs) {
this.prefs = prefs;
}
public static final UserNotificationSettings DEFAULT = new UserNotificationSettings(Collections.emptyMap());
public Set<NotificationDeliveryMethod> getEnabledDeliveryMethods(NotificationType notificationType) {
NotificationTypePrefs prefs;
if (this.prefs == null || (prefs = this.prefs.get(notificationType)) == null) {
return NotificationDeliveryMethod.values;
}
if (prefs.isEnabled()) {
Set<NotificationDeliveryMethod> deliveryMethods = prefs.getEnabledDeliveryMethods();
if (CollectionsUtil.isNotEmpty(deliveryMethods)) {
return deliveryMethods;
} else {
return NotificationDeliveryMethod.values;
}
} else {
return Collections.emptySet();
}
public Set<NotificationDeliveryMethod> getEnabledDeliveryMethods(NotificationRuleId ruleId) {
return prefs.stream()
.filter(pref -> pref.getRuleId().equals(ruleId.getId())).findFirst()
.map(pref -> pref.isEnabled() ? pref.getEnabledDeliveryMethods() : Collections.<NotificationDeliveryMethod>emptySet())
.orElse(NotificationDeliveryMethod.values);
}
@Data
public static class NotificationTypePrefs {
public static class NotificationPref {
@NotNull
private UUID ruleId;
private String ruleName;
private boolean enabled;
@NotNull
private Set<NotificationDeliveryMethod> enabledDeliveryMethods;
public static NotificationPref createDefault(NotificationRule rule) {
NotificationPref pref = new NotificationPref();
pref.setRuleId(rule.getUuidId());
pref.setRuleName(rule.getName());
pref.setEnabled(true);
pref.setEnabledDeliveryMethods(NotificationDeliveryMethod.values);
return pref;
}
}
}

2
common/data/src/main/java/org/thingsboard/server/common/data/page/SortOrder.java

@ -36,4 +36,6 @@ public class SortOrder {
ASC, DESC
}
public static final SortOrder byCreatedTimeDesc = new SortOrder("createdTime", Direction.DESC);
}

52
dao/src/main/java/org/thingsboard/server/dao/notification/DefaultNotificationSettingsService.java

@ -20,6 +20,7 @@ import com.fasterxml.jackson.databind.node.ObjectNode;
import lombok.RequiredArgsConstructor;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
@ -30,8 +31,10 @@ import org.thingsboard.server.common.data.User;
import org.thingsboard.server.common.data.id.TenantId;
import org.thingsboard.server.common.data.id.UserId;
import org.thingsboard.server.common.data.notification.NotificationType;
import org.thingsboard.server.common.data.notification.rule.NotificationRule;
import org.thingsboard.server.common.data.notification.settings.NotificationSettings;
import org.thingsboard.server.common.data.notification.settings.UserNotificationSettings;
import org.thingsboard.server.common.data.notification.settings.UserNotificationSettings.NotificationPref;
import org.thingsboard.server.common.data.notification.targets.NotificationTarget;
import org.thingsboard.server.common.data.notification.targets.platform.AffectedTenantAdministratorsFilter;
import org.thingsboard.server.common.data.notification.targets.platform.AffectedUserFilter;
@ -43,12 +46,19 @@ import org.thingsboard.server.common.data.notification.targets.platform.TenantAd
import org.thingsboard.server.common.data.notification.targets.platform.UsersFilter;
import org.thingsboard.server.common.data.notification.targets.platform.UsersFilterType;
import org.thingsboard.server.common.data.page.PageLink;
import org.thingsboard.server.common.data.page.SortOrder;
import org.thingsboard.server.dao.settings.AdminSettingsService;
import org.thingsboard.server.dao.user.UserService;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.UUID;
import static java.util.function.Predicate.not;
@Service
@RequiredArgsConstructor
@ -57,6 +67,7 @@ public class DefaultNotificationSettingsService implements NotificationSettingsS
private final AdminSettingsService adminSettingsService;
private final NotificationTargetService notificationTargetService;
private final NotificationTemplateService notificationTemplateService;
private final NotificationRuleService notificationRuleService;
private final DefaultNotifications defaultNotifications;
private final UserService userService;
@ -98,13 +109,42 @@ public class DefaultNotificationSettingsService implements NotificationSettingsS
}
@Override
public UserNotificationSettings getUserNotificationSettings(TenantId tenantId, User user) {
// TODO: decide whether to use user_settings or store it in the additionalInfo not to make more DB requests
JsonNode notificationSettings = user.getAdditionalInfo().get("notificationSettings");
if (notificationSettings == null || notificationSettings.isNull()) {
return UserNotificationSettings.DEFAULT;
public UserNotificationSettings getUserNotificationSettings(TenantId tenantId, User user, boolean format) {
UserNotificationSettings settings = Optional.ofNullable(user.getAdditionalInfo().get("notificationSettings"))
.filter(not(JsonNode::isNull))
.map(json -> JacksonUtil.treeToValue(json, UserNotificationSettings.class))
.orElse(null);
if (!format) {
if (settings != null) {
return settings;
} else {
return UserNotificationSettings.DEFAULT;
}
}
Map<UUID, NotificationRule> rules = new HashMap<>();
notificationRuleService.findNotificationRulesByTenantId(tenantId, new PageLink(Integer.MAX_VALUE, 0,null, SortOrder.byCreatedTimeDesc))
.getData().forEach(rule -> rules.put(rule.getUuidId(), rule));
List<NotificationPref> prefs = new ArrayList<>();
if (settings == null) {
rules.values().forEach(rule -> {
prefs.add(NotificationPref.createDefault(rule));
});
} else {
settings.getPrefs().forEach(pref -> {
NotificationRule rule = rules.remove(pref.getRuleId());
if (rule == null) {
return;
}
pref.setRuleName(rule.getName());
prefs.add(pref);
});
rules.values().forEach(rule -> {
prefs.add(NotificationPref.createDefault(rule));
});
}
return JacksonUtil.treeToValue(notificationSettings, UserNotificationSettings.class);
return new UserNotificationSettings(prefs);
}
@Transactional(propagation = Propagation.NOT_SUPPORTED) // so that parent transaction is not aborted on method failure

Loading…
Cancel
Save