Commit 4d5ad6d882f6c121d0eeee3117c686e7278e068d

Authored by Andrew Shvayka
2 parents 0b13fa2f 4cbacde7

Merge branch 'master' of github.com:thingsboard/thingsboard

@@ -28,7 +28,7 @@ import java.io.Serializable; @@ -28,7 +28,7 @@ import java.io.Serializable;
28 * Created by ashvayka on 19.03.18. 28 * Created by ashvayka on 19.03.18.
29 */ 29 */
30 @Data 30 @Data
31 -final class RemoteToRuleChainTellNextMsg extends RuleNodeToRuleChainTellNextMsg implements TenantAwareMsg, RuleChainAwareMsg, Serializable { 31 +final class RemoteToRuleChainTellNextMsg extends RuleNodeToRuleChainTellNextMsg implements TenantAwareMsg, RuleChainAwareMsg {
32 32
33 private static final long serialVersionUID = 2459605482321657447L; 33 private static final long serialVersionUID = 2459605482321657447L;
34 private final TenantId tenantId; 34 private final TenantId tenantId;
@@ -21,14 +21,16 @@ import org.thingsboard.server.common.msg.MsgType; @@ -21,14 +21,16 @@ import org.thingsboard.server.common.msg.MsgType;
21 import org.thingsboard.server.common.msg.TbActorMsg; 21 import org.thingsboard.server.common.msg.TbActorMsg;
22 import org.thingsboard.server.common.msg.TbMsg; 22 import org.thingsboard.server.common.msg.TbMsg;
23 23
  24 +import java.io.Serializable;
24 import java.util.Set; 25 import java.util.Set;
25 26
26 /** 27 /**
27 * Created by ashvayka on 19.03.18. 28 * Created by ashvayka on 19.03.18.
28 */ 29 */
29 @Data 30 @Data
30 -class RuleNodeToRuleChainTellNextMsg implements TbActorMsg { 31 +class RuleNodeToRuleChainTellNextMsg implements TbActorMsg, Serializable {
31 32
  33 + private static final long serialVersionUID = 4577026446412871820L;
32 private final RuleNodeId originator; 34 private final RuleNodeId originator;
33 private final Set<String> relationTypes; 35 private final Set<String> relationTypes;
34 private final TbMsg msg; 36 private final TbMsg msg;
@@ -291,6 +291,9 @@ caffeine: @@ -291,6 +291,9 @@ caffeine:
291 devices: 291 devices:
292 timeToLiveInMinutes: 1440 292 timeToLiveInMinutes: 1440
293 maxSize: 100000 293 maxSize: 100000
  294 + assets:
  295 + timeToLiveInMinutes: 1440
  296 + maxSize: 100000
294 297
295 redis: 298 redis:
296 # standalone or cluster 299 # standalone or cluster
@@ -19,4 +19,5 @@ public class CacheConstants { @@ -19,4 +19,5 @@ public class CacheConstants {
19 public static final String DEVICE_CREDENTIALS_CACHE = "deviceCredentials"; 19 public static final String DEVICE_CREDENTIALS_CACHE = "deviceCredentials";
20 public static final String RELATIONS_CACHE = "relations"; 20 public static final String RELATIONS_CACHE = "relations";
21 public static final String DEVICE_CACHE = "devices"; 21 public static final String DEVICE_CACHE = "devices";
  22 + public static final String ASSET_CACHE = "assets";
22 } 23 }
@@ -34,7 +34,7 @@ public interface AssetService { @@ -34,7 +34,7 @@ public interface AssetService {
34 34
35 ListenableFuture<Asset> findAssetByIdAsync(AssetId assetId); 35 ListenableFuture<Asset> findAssetByIdAsync(AssetId assetId);
36 36
37 - Optional<Asset> findAssetByTenantIdAndName(TenantId tenantId, String name); 37 + Asset findAssetByTenantIdAndName(TenantId tenantId, String name);
38 38
39 Asset saveAsset(Asset asset); 39 Asset saveAsset(Asset asset);
40 40
@@ -21,6 +21,10 @@ import com.google.common.util.concurrent.Futures; @@ -21,6 +21,10 @@ import com.google.common.util.concurrent.Futures;
21 import com.google.common.util.concurrent.ListenableFuture; 21 import com.google.common.util.concurrent.ListenableFuture;
22 import lombok.extern.slf4j.Slf4j; 22 import lombok.extern.slf4j.Slf4j;
23 import org.springframework.beans.factory.annotation.Autowired; 23 import org.springframework.beans.factory.annotation.Autowired;
  24 +import org.springframework.cache.Cache;
  25 +import org.springframework.cache.CacheManager;
  26 +import org.springframework.cache.annotation.CacheEvict;
  27 +import org.springframework.cache.annotation.Cacheable;
24 import org.springframework.stereotype.Service; 28 import org.springframework.stereotype.Service;
25 import org.springframework.util.StringUtils; 29 import org.springframework.util.StringUtils;
26 import org.thingsboard.server.common.data.Customer; 30 import org.thingsboard.server.common.data.Customer;
@@ -48,15 +52,12 @@ import java.util.ArrayList; @@ -48,15 +52,12 @@ import java.util.ArrayList;
48 import java.util.Collections; 52 import java.util.Collections;
49 import java.util.Comparator; 53 import java.util.Comparator;
50 import java.util.List; 54 import java.util.List;
51 -import java.util.Optional;  
52 import java.util.stream.Collectors; 55 import java.util.stream.Collectors;
53 56
  57 +import static org.thingsboard.server.common.data.CacheConstants.ASSET_CACHE;
54 import static org.thingsboard.server.dao.DaoUtil.toUUIDs; 58 import static org.thingsboard.server.dao.DaoUtil.toUUIDs;
55 import static org.thingsboard.server.dao.model.ModelConstants.NULL_UUID; 59 import static org.thingsboard.server.dao.model.ModelConstants.NULL_UUID;
56 -import static org.thingsboard.server.dao.service.Validator.validateId;  
57 -import static org.thingsboard.server.dao.service.Validator.validateIds;  
58 -import static org.thingsboard.server.dao.service.Validator.validatePageLink;  
59 -import static org.thingsboard.server.dao.service.Validator.validateString; 60 +import static org.thingsboard.server.dao.service.Validator.*;
60 61
61 @Service 62 @Service
62 @Slf4j 63 @Slf4j
@@ -75,6 +76,9 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ @@ -75,6 +76,9 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ
75 @Autowired 76 @Autowired
76 private CustomerDao customerDao; 77 private CustomerDao customerDao;
77 78
  79 + @Autowired
  80 + private CacheManager cacheManager;
  81 +
78 @Override 82 @Override
79 public Asset findAssetById(AssetId assetId) { 83 public Asset findAssetById(AssetId assetId) {
80 log.trace("Executing findAssetById [{}]", assetId); 84 log.trace("Executing findAssetById [{}]", assetId);
@@ -89,13 +93,16 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ @@ -89,13 +93,16 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ
89 return assetDao.findByIdAsync(assetId.getId()); 93 return assetDao.findByIdAsync(assetId.getId());
90 } 94 }
91 95
  96 + @Cacheable(cacheNames = ASSET_CACHE, key = "{#tenantId, #name}")
92 @Override 97 @Override
93 - public Optional<Asset> findAssetByTenantIdAndName(TenantId tenantId, String name) { 98 + public Asset findAssetByTenantIdAndName(TenantId tenantId, String name) {
94 log.trace("Executing findAssetByTenantIdAndName [{}][{}]", tenantId, name); 99 log.trace("Executing findAssetByTenantIdAndName [{}][{}]", tenantId, name);
95 validateId(tenantId, INCORRECT_TENANT_ID + tenantId); 100 validateId(tenantId, INCORRECT_TENANT_ID + tenantId);
96 - return assetDao.findAssetsByTenantIdAndName(tenantId.getId(), name); 101 + return assetDao.findAssetsByTenantIdAndName(tenantId.getId(), name)
  102 + .orElse(null);
97 } 103 }
98 104
  105 + @CacheEvict(cacheNames = ASSET_CACHE, key = "{#asset.tenantId, #asset.name}")
99 @Override 106 @Override
100 public Asset saveAsset(Asset asset) { 107 public Asset saveAsset(Asset asset) {
101 log.trace("Executing saveAsset [{}]", asset); 108 log.trace("Executing saveAsset [{}]", asset);
@@ -122,6 +129,14 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ @@ -122,6 +129,14 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ
122 log.trace("Executing deleteAsset [{}]", assetId); 129 log.trace("Executing deleteAsset [{}]", assetId);
123 validateId(assetId, INCORRECT_ASSET_ID + assetId); 130 validateId(assetId, INCORRECT_ASSET_ID + assetId);
124 deleteEntityRelations(assetId); 131 deleteEntityRelations(assetId);
  132 +
  133 + Cache cache = cacheManager.getCache(ASSET_CACHE);
  134 + Asset asset = assetDao.findById(assetId.getId());
  135 + List<Object> list = new ArrayList<>();
  136 + list.add(asset.getTenantId());
  137 + list.add(asset.getName());
  138 + cache.evict(list);
  139 +
125 assetDao.removeById(assetId.getId()); 140 assetDao.removeById(assetId.getId());
126 } 141 }
127 142
@@ -21,6 +21,9 @@ caffeine.specs.deviceCredentials.maxSize=100000 @@ -21,6 +21,9 @@ caffeine.specs.deviceCredentials.maxSize=100000
21 caffeine.specs.devices.timeToLiveInMinutes=1440 21 caffeine.specs.devices.timeToLiveInMinutes=1440
22 caffeine.specs.devices.maxSize=100000 22 caffeine.specs.devices.maxSize=100000
23 23
  24 +caffeine.specs.assets.timeToLiveInMinutes=1440
  25 +caffeine.specs.assets.maxSize=100000
  26 +
24 caching.specs.devices.timeToLiveInMinutes=1440 27 caching.specs.devices.timeToLiveInMinutes=1440
25 caching.specs.devices.maxSize=100000 28 caching.specs.devices.maxSize=100000
26 29
@@ -498,25 +498,25 @@ @@ -498,25 +498,25 @@
498 "public-link": "Link pubblico", 498 "public-link": "Link pubblico",
499 "copy-public-link": "Copia link pubblico", 499 "copy-public-link": "Copia link pubblico",
500 "public-link-copied-message": "Link pubblico della dashboard copiato negli appunti", 500 "public-link-copied-message": "Link pubblico della dashboard copiato negli appunti",
501 - "manage-states": "Manage dashboard states",  
502 - "states": "Dashboard states",  
503 - "search-states": "Search dashboard states",  
504 - "selected-states": "{ count, plural, 1 {1 dashboard state} other {# dashboard states} } selected",  
505 - "edit-state": "Edit dashboard state",  
506 - "delete-state": "Delete dashboard state",  
507 - "add-state": "Add dashboard state",  
508 - "state": "Dashboard state", 501 + "manage-states": "Gestisci stati dashboard",
  502 + "states": "Stati dashboard",
  503 + "search-states": "Ricerca stati dashboard",
  504 + "selected-states": "{ count, plural, 1 {1 stato dashboard selezionato} other {# stati dashboard selezionati} }",
  505 + "edit-state": "Modifica stato dashboard",
  506 + "delete-state": "Elimina stato dashboard",
  507 + "add-state": "Aggiungi stato dashboard",
  508 + "state": "Stato dashboard",
509 "state-name": "Nome", 509 "state-name": "Nome",
510 - "state-name-required": "Dashboard state name is required.",  
511 - "state-id": "State Id",  
512 - "state-id-required": "Dashboard state id is required.",  
513 - "state-id-exists": "Dashboard state with the same id is already exists.",  
514 - "is-root-state": "Root state",  
515 - "delete-state-title": "Delete dashboard state",  
516 - "delete-state-text": "Are you sure you want delete dashboard state with name '{{stateName}}'?", 510 + "state-name-required": "Nome stato dashboard obbligatorio.",
  511 + "state-id": "Id stato",
  512 + "state-id-required": "Id stato dashboard obbligatorio.",
  513 + "state-id-exists": "Uno stato della dashboard con lo stesso id è già presente.",
  514 + "is-root-state": "Stato radice",
  515 + "delete-state-title": "Elimina stato dashboard",
  516 + "delete-state-text": "Sei sicuro di voler eliminare lo stato della dashboard di nome '{{stateName}}'?",
517 "show-details": "Mostra dettagli", 517 "show-details": "Mostra dettagli",
518 "hide-details": "Nascondi dettagli", 518 "hide-details": "Nascondi dettagli",
519 - "select-state": "Select target state", 519 + "select-state": "Seleziona stato target",
520 "state-controller": "Stato controller" 520 "state-controller": "Stato controller"
521 }, 521 },
522 "datakey": { 522 "datakey": {
@@ -570,7 +570,7 @@ @@ -570,7 +570,7 @@
570 "alias-required": "Alias dispositivo richesto.", 570 "alias-required": "Alias dispositivo richesto.",
571 "remove-alias": "Rimuovi alias dispositivo", 571 "remove-alias": "Rimuovi alias dispositivo",
572 "add-alias": "Aggiungi alias dispositivo", 572 "add-alias": "Aggiungi alias dispositivo",
573 - "name-starts-with": "Dispositivo il cui nome comincia per", 573 + "name-starts-with": "Dispositivo il cui nome inizia per",
574 "device-list": "Lista dispositivi", 574 "device-list": "Lista dispositivi",
575 "use-device-name-filter": "Usa filtro", 575 "use-device-name-filter": "Usa filtro",
576 "device-list-empty": "Nessun dispositivo selezionato.", 576 "device-list-empty": "Nessun dispositivo selezionato.",
@@ -680,7 +680,7 @@ @@ -680,7 +680,7 @@
680 "entity-list-empty": "Nessuna entità selezionata.", 680 "entity-list-empty": "Nessuna entità selezionata.",
681 "entity-type-list-empty": "Nessun tipo di entità selezionato.", 681 "entity-type-list-empty": "Nessun tipo di entità selezionato.",
682 "entity-name-filter-required": "Filtro nome entità obbligatorio.", 682 "entity-name-filter-required": "Filtro nome entità obbligatorio.",
683 - "entity-name-filter-no-entity-matched": "No entities starting with '{{entity}}' were found.", 683 + "entity-name-filter-no-entity-matched": "Nessuna entità che inizia per '{{entity}}' è stata trovata.",
684 "all-subtypes": "Tutte", 684 "all-subtypes": "Tutte",
685 "select-entities": "Seleziona entità", 685 "select-entities": "Seleziona entità",
686 "no-aliases-found": "Nessun alias trovato.", 686 "no-aliases-found": "Nessun alias trovato.",
@@ -733,7 +733,7 @@ @@ -733,7 +733,7 @@
733 "type-rulechains": "Rule chains", 733 "type-rulechains": "Rule chains",
734 "list-of-rulechains": "{ count, plural, 1 {One rule chain} other {List of # rule chains} }", 734 "list-of-rulechains": "{ count, plural, 1 {One rule chain} other {List of # rule chains} }",
735 "rulechain-name-starts-with": "Rule chains whose names start with '{{prefix}}'", 735 "rulechain-name-starts-with": "Rule chains whose names start with '{{prefix}}'",
736 - "type-current-customer": "Current Customer", 736 + "type-current-customer": "Cliente attuale",
737 "search": "Ricerca entità", 737 "search": "Ricerca entità",
738 "selected-entities": "{ count, plural, 1 {1 entità selezionata} other {# entità selezionate} }", 738 "selected-entities": "{ count, plural, 1 {1 entità selezionata} other {# entità selezionate} }",
739 "entity-name": "Nome entità", 739 "entity-name": "Nome entità",
@@ -788,13 +788,13 @@ @@ -788,13 +788,13 @@
788 "delete-extension-text": "Attenzione, dopo la conferma l'estensione e tutti i suoi data non saranno più recuperabili.", 788 "delete-extension-text": "Attenzione, dopo la conferma l'estensione e tutti i suoi data non saranno più recuperabili.",
789 "delete-extensions-title": "Sei sicuro di voler eliminare { count, plural, 1 {1 estensione} other {# estensioni} }?", 789 "delete-extensions-title": "Sei sicuro di voler eliminare { count, plural, 1 {1 estensione} other {# estensioni} }?",
790 "delete-extensions-text": "Attenzione, dopo la conferma tutte le estensioni selezionate saranno eliminate.", 790 "delete-extensions-text": "Attenzione, dopo la conferma tutte le estensioni selezionate saranno eliminate.",
791 - "converters": "Converters",  
792 - "converter-id": "Converter id", 791 + "converters": "Convertitori",
  792 + "converter-id": "Id convertitore",
793 "configuration": "Configurazione", 793 "configuration": "Configurazione",
794 - "converter-configurations": "Converter configurations", 794 + "converter-configurations": "Configurazioni convertitore",
795 "token": "Token di sicurezza", 795 "token": "Token di sicurezza",
796 - "add-converter": "Add converter",  
797 - "add-config": "Add converter configuration", 796 + "add-converter": "Aggiungi convertitore",
  797 + "add-config": "Aggiungi configurazione convertitore",
798 "device-name-expression": "Device name expression", 798 "device-name-expression": "Device name expression",
799 "device-type-expression": "Device type expression", 799 "device-type-expression": "Device type expression",
800 "custom": "Custom", 800 "custom": "Custom",
@@ -828,7 +828,7 @@ @@ -828,7 +828,7 @@
828 "drop-file": "Trascina un file o fai clic per selezionare un file da caricare.", 828 "drop-file": "Trascina un file o fai clic per selezionare un file da caricare.",
829 "mapping": "Mapping", 829 "mapping": "Mapping",
830 "topic-filter": "Filtro topic", 830 "topic-filter": "Filtro topic",
831 - "converter-type": "Converter type", 831 + "converter-type": "Tipo convertitore",
832 "converter-json": "Json", 832 "converter-json": "Json",
833 "json-name-expression": "Device name json expression", 833 "json-name-expression": "Device name json expression",
834 "topic-name-expression": "Device name topic expression", 834 "topic-name-expression": "Device name topic expression",
@@ -847,10 +847,10 @@ @@ -847,10 +847,10 @@
847 "converter-json-required": "Convertitore json obbligatorio.", 847 "converter-json-required": "Convertitore json obbligatorio.",
848 "converter-json-parse": "Unable to parse converter json.", 848 "converter-json-parse": "Unable to parse converter json.",
849 "filter-expression": "Filter expression", 849 "filter-expression": "Filter expression",
850 - "connect-requests": "Connect requests",  
851 - "add-connect-request": "Add connect request",  
852 - "disconnect-requests": "Disconnect requests",  
853 - "add-disconnect-request": "Add disconnect request", 850 + "connect-requests": "Richieste di connessione",
  851 + "add-connect-request": "Aggiungi richiesta di connessione",
  852 + "disconnect-requests": "Richieste di disconnessione",
  853 + "add-disconnect-request": "Aggiungi richiesta di disconnessione",
854 "attribute-requests": "Attribute requests", 854 "attribute-requests": "Attribute requests",
855 "add-attribute-request": "Add attribute request", 855 "add-attribute-request": "Add attribute request",
856 "attribute-updates": "Attribute updates", 856 "attribute-updates": "Attribute updates",
@@ -919,8 +919,8 @@ @@ -919,8 +919,8 @@
919 "not-available": "Non disponibile" 919 "not-available": "Non disponibile"
920 }, 920 },
921 921
922 - "export-extensions-configuration": "Export extensions configuration",  
923 - "import-extensions-configuration": "Import extensions configuration", 922 + "export-extensions-configuration": "Esporta configurazione estensioni",
  923 + "import-extensions-configuration": "Importa configurazione estensioni",
924 "import-extensions": "Importa estensione", 924 "import-extensions": "Importa estensione",
925 "import-extension": "Importa estensione", 925 "import-extension": "Importa estensione",
926 "export-extension": "Esporta estensione", 926 "export-extension": "Esporta estensione",
@@ -928,7 +928,7 @@ @@ -928,7 +928,7 @@
928 "invalid-file-error": "File estensione non valido" 928 "invalid-file-error": "File estensione non valido"
929 }, 929 },
930 "fullscreen": { 930 "fullscreen": {
931 - "expand": "Expand to fullscreen", 931 + "expand": "Espandi a tutto schermo",
932 "exit": "Esci da schermo intero", 932 "exit": "Esci da schermo intero",
933 "toggle": "Commuta modalità schermo intero", 933 "toggle": "Commuta modalità schermo intero",
934 "fullscreen": "Schermo intero" 934 "fullscreen": "Schermo intero"
@@ -937,16 +937,16 @@ @@ -937,16 +937,16 @@
937 "function": "Funzione" 937 "function": "Funzione"
938 }, 938 },
939 "grid": { 939 "grid": {
940 - "delete-item-title": "Are you sure you want to delete this item?",  
941 - "delete-item-text": "Be careful, after the confirmation this item and all related data will become unrecoverable.",  
942 - "delete-items-title": "Are you sure you want to delete { count, plural, 1 {1 item} other {# items} }?",  
943 - "delete-items-action-title": "Delete { count, plural, 1 {1 item} other {# items} }",  
944 - "delete-items-text": "Be careful, after the confirmation all selected items will be removed and all related data will become unrecoverable.",  
945 - "add-item-text": "Add new item",  
946 - "no-items-text": "No items found",  
947 - "item-details": "Item details",  
948 - "delete-item": "Delete Item",  
949 - "delete-items": "Delete Items", 940 + "delete-item-title": "Sei sicuro di voler eliminare questo elemento?",
  941 + "delete-item-text": "Attenzione, dopo la conferma questo elemento e tutti i suoi dati non saranno più recuperabili.",
  942 + "delete-items-title": "Sei sicuro di voler eliminare { count, plural, 1 {1 elemento} other {# elementi} }?",
  943 + "delete-items-action-title": "Elimina { count, plural, 1 {1 elemento} other {# elementi} }",
  944 + "delete-items-text": "Attenzione, dopo la conferma tutti gli elementi selezionati saranno rimossi e i relativi dati non saranno più recuperabili.",
  945 + "add-item-text": "Aggiungi nuovo elemento",
  946 + "no-items-text": "Nessun elemento trovato",
  947 + "item-details": "Dettagli elemento",
  948 + "delete-item": "Elimina elemento",
  949 + "delete-items": "Elimina elementi",
950 "scroll-to-top": "Scroll to top" 950 "scroll-to-top": "Scroll to top"
951 }, 951 },
952 "help": { 952 "help": {
@@ -985,7 +985,7 @@ @@ -985,7 +985,7 @@
985 "settings": "Impostazioni layout", 985 "settings": "Impostazioni layout",
986 "color": "Colore", 986 "color": "Colore",
987 "main": "Main", 987 "main": "Main",
988 - "right": "Right", 988 + "right": "Destra",
989 "select": "Select target layout" 989 "select": "Select target layout"
990 }, 990 },
991 "legend": { 991 "legend": {