Showing
100 changed files
with
896 additions
and
614 deletions
Too many changes to show.
To preserve performance only 100 of 120 files are displayed.
... | ... | @@ -14,33 +14,27 @@ |
14 | 14 | -- limitations under the License. |
15 | 15 | -- |
16 | 16 | |
17 | --- select check_version(); | |
17 | +-- call check_version(); | |
18 | 18 | |
19 | -CREATE OR REPLACE FUNCTION check_version() RETURNS boolean AS $$ | |
19 | +CREATE OR REPLACE PROCEDURE check_version(INOUT valid_version boolean) LANGUAGE plpgsql AS $BODY$ | |
20 | 20 | DECLARE |
21 | 21 | current_version integer; |
22 | - valid_version boolean; | |
23 | 22 | BEGIN |
24 | 23 | RAISE NOTICE 'Check the current installed PostgreSQL version...'; |
25 | 24 | SELECT current_setting('server_version_num') INTO current_version; |
26 | - IF current_version < 100000 THEN | |
27 | - valid_version := FALSE; | |
28 | - ELSE | |
29 | - valid_version := TRUE; | |
30 | - END IF; | |
31 | - IF valid_version = FALSE THEN | |
32 | - RAISE NOTICE 'Postgres version should be at least more than 10!'; | |
33 | - ELSE | |
25 | + IF current_version > 110000 THEN | |
34 | 26 | RAISE NOTICE 'PostgreSQL version is valid!'; |
35 | 27 | RAISE NOTICE 'Schema update started...'; |
28 | + SELECT true INTO valid_version; | |
29 | + ELSE | |
30 | + RAISE NOTICE 'Postgres version should be at least more than 10!'; | |
36 | 31 | END IF; |
37 | - RETURN valid_version; | |
38 | 32 | END; |
39 | -$$ LANGUAGE 'plpgsql'; | |
33 | +$BODY$; | |
40 | 34 | |
41 | --- select create_partition_ts_kv_table(); | |
35 | +-- call create_partition_ts_kv_table(); | |
42 | 36 | |
43 | -CREATE OR REPLACE FUNCTION create_partition_ts_kv_table() RETURNS VOID AS $$ | |
37 | +CREATE OR REPLACE PROCEDURE create_partition_ts_kv_table() LANGUAGE plpgsql AS $$ | |
44 | 38 | |
45 | 39 | BEGIN |
46 | 40 | ALTER TABLE ts_kv |
... | ... | @@ -57,11 +51,11 @@ BEGIN |
57 | 51 | ALTER TABLE ts_kv |
58 | 52 | ALTER COLUMN key TYPE integer USING key::integer; |
59 | 53 | END; |
60 | -$$ LANGUAGE 'plpgsql'; | |
54 | +$$; | |
61 | 55 | |
62 | --- select create_new_ts_kv_latest_table(); | |
56 | +-- call create_new_ts_kv_latest_table(); | |
63 | 57 | |
64 | -CREATE OR REPLACE FUNCTION create_new_ts_kv_latest_table() RETURNS VOID AS $$ | |
58 | +CREATE OR REPLACE PROCEDURE create_new_ts_kv_latest_table() LANGUAGE plpgsql AS $$ | |
65 | 59 | |
66 | 60 | BEGIN |
67 | 61 | ALTER TABLE ts_kv_latest |
... | ... | @@ -81,13 +75,13 @@ BEGIN |
81 | 75 | ALTER TABLE ts_kv_latest |
82 | 76 | ADD CONSTRAINT ts_kv_latest_pkey PRIMARY KEY (entity_id, key); |
83 | 77 | END; |
84 | -$$ LANGUAGE 'plpgsql'; | |
78 | +$$; | |
85 | 79 | |
86 | 80 | |
87 | --- select create_partitions(); | |
81 | +-- call create_partitions(); | |
82 | + | |
83 | +CREATE OR REPLACE PROCEDURE create_partitions() LANGUAGE plpgsql AS $$ | |
88 | 84 | |
89 | -CREATE OR REPLACE FUNCTION create_partitions() RETURNS VOID AS | |
90 | -$$ | |
91 | 85 | DECLARE |
92 | 86 | partition_date varchar; |
93 | 87 | from_ts bigint; |
... | ... | @@ -111,11 +105,11 @@ BEGIN |
111 | 105 | |
112 | 106 | CLOSE key_cursor; |
113 | 107 | END; |
114 | -$$ language 'plpgsql'; | |
108 | +$$; | |
115 | 109 | |
116 | --- select create_ts_kv_dictionary_table(); | |
110 | +-- call create_ts_kv_dictionary_table(); | |
117 | 111 | |
118 | -CREATE OR REPLACE FUNCTION create_ts_kv_dictionary_table() RETURNS VOID AS $$ | |
112 | +CREATE OR REPLACE PROCEDURE create_ts_kv_dictionary_table() LANGUAGE plpgsql AS $$ | |
119 | 113 | |
120 | 114 | BEGIN |
121 | 115 | CREATE TABLE IF NOT EXISTS ts_kv_dictionary |
... | ... | @@ -125,12 +119,12 @@ BEGIN |
125 | 119 | CONSTRAINT ts_key_id_pkey PRIMARY KEY (key) |
126 | 120 | ); |
127 | 121 | END; |
128 | -$$ LANGUAGE 'plpgsql'; | |
122 | +$$; | |
123 | + | |
124 | +-- call insert_into_dictionary(); | |
129 | 125 | |
130 | --- select insert_into_dictionary(); | |
126 | +CREATE OR REPLACE PROCEDURE insert_into_dictionary() LANGUAGE plpgsql AS $$ | |
131 | 127 | |
132 | -CREATE OR REPLACE FUNCTION insert_into_dictionary() RETURNS VOID AS | |
133 | -$$ | |
134 | 128 | DECLARE |
135 | 129 | insert_record RECORD; |
136 | 130 | key_cursor CURSOR FOR SELECT DISTINCT key |
... | ... | @@ -150,28 +144,27 @@ BEGIN |
150 | 144 | END LOOP; |
151 | 145 | CLOSE key_cursor; |
152 | 146 | END; |
153 | -$$ language 'plpgsql'; | |
147 | +$$; | |
154 | 148 | |
155 | --- select insert_into_ts_kv(); | |
149 | +-- call insert_into_ts_kv(); | |
156 | 150 | |
157 | -CREATE OR REPLACE FUNCTION insert_into_ts_kv() RETURNS void AS | |
158 | -$$ | |
151 | +CREATE OR REPLACE PROCEDURE insert_into_ts_kv() LANGUAGE plpgsql AS $$ | |
159 | 152 | DECLARE |
160 | 153 | insert_size CONSTANT integer := 10000; |
161 | 154 | insert_counter integer DEFAULT 0; |
162 | 155 | insert_record RECORD; |
163 | - insert_cursor CURSOR FOR SELECT CONCAT(first_part_uuid, '-', second_part_uuid, '-1', third_part_uuid, '-', fourth_part_uuid, '-', fifth_part_uuid)::uuid AS entity_id, | |
156 | + insert_cursor CURSOR FOR SELECT CONCAT(entity_id_uuid_first_part, '-', entity_id_uuid_second_part, '-1', entity_id_uuid_third_part, '-', entity_id_uuid_fourth_part, '-', entity_id_uuid_fifth_part)::uuid AS entity_id, | |
164 | 157 | ts_kv_records.key AS key, |
165 | 158 | ts_kv_records.ts AS ts, |
166 | 159 | ts_kv_records.bool_v AS bool_v, |
167 | 160 | ts_kv_records.str_v AS str_v, |
168 | 161 | ts_kv_records.long_v AS long_v, |
169 | 162 | ts_kv_records.dbl_v AS dbl_v |
170 | - FROM (SELECT SUBSTRING(entity_id, 8, 8) AS first_part_uuid, | |
171 | - SUBSTRING(entity_id, 4, 4) AS second_part_uuid, | |
172 | - SUBSTRING(entity_id, 1, 3) AS third_part_uuid, | |
173 | - SUBSTRING(entity_id, 16, 4) AS fourth_part_uuid, | |
174 | - SUBSTRING(entity_id, 20) AS fifth_part_uuid, | |
163 | + FROM (SELECT SUBSTRING(entity_id, 8, 8) AS entity_id_uuid_first_part, | |
164 | + SUBSTRING(entity_id, 4, 4) AS entity_id_uuid_second_part, | |
165 | + SUBSTRING(entity_id, 1, 3) AS entity_id_uuid_third_part, | |
166 | + SUBSTRING(entity_id, 16, 4) AS entity_id_uuid_fourth_part, | |
167 | + SUBSTRING(entity_id, 20) AS entity_id_uuid_fifth_part, | |
175 | 168 | key_id AS key, |
176 | 169 | ts, |
177 | 170 | bool_v, |
... | ... | @@ -198,28 +191,27 @@ BEGIN |
198 | 191 | END LOOP; |
199 | 192 | CLOSE insert_cursor; |
200 | 193 | END; |
201 | -$$ LANGUAGE 'plpgsql'; | |
194 | +$$; | |
202 | 195 | |
203 | --- select insert_into_ts_kv_latest(); | |
196 | +-- call insert_into_ts_kv_latest(); | |
204 | 197 | |
205 | -CREATE OR REPLACE FUNCTION insert_into_ts_kv_latest() RETURNS void AS | |
206 | -$$ | |
198 | +CREATE OR REPLACE PROCEDURE insert_into_ts_kv_latest() LANGUAGE plpgsql AS $$ | |
207 | 199 | DECLARE |
208 | 200 | insert_size CONSTANT integer := 10000; |
209 | 201 | insert_counter integer DEFAULT 0; |
210 | 202 | insert_record RECORD; |
211 | - insert_cursor CURSOR FOR SELECT CONCAT(first_part_uuid, '-', second_part_uuid, '-1', third_part_uuid, '-', fourth_part_uuid, '-', fifth_part_uuid)::uuid AS entity_id, | |
203 | + insert_cursor CURSOR FOR SELECT CONCAT(entity_id_uuid_first_part, '-', entity_id_uuid_second_part, '-1', entity_id_uuid_third_part, '-', entity_id_uuid_fourth_part, '-', entity_id_uuid_fifth_part)::uuid AS entity_id, | |
212 | 204 | ts_kv_latest_records.key AS key, |
213 | 205 | ts_kv_latest_records.ts AS ts, |
214 | 206 | ts_kv_latest_records.bool_v AS bool_v, |
215 | 207 | ts_kv_latest_records.str_v AS str_v, |
216 | 208 | ts_kv_latest_records.long_v AS long_v, |
217 | 209 | ts_kv_latest_records.dbl_v AS dbl_v |
218 | - FROM (SELECT SUBSTRING(entity_id, 8, 8) AS first_part_uuid, | |
219 | - SUBSTRING(entity_id, 4, 4) AS second_part_uuid, | |
220 | - SUBSTRING(entity_id, 1, 3) AS third_part_uuid, | |
221 | - SUBSTRING(entity_id, 16, 4) AS fourth_part_uuid, | |
222 | - SUBSTRING(entity_id, 20) AS fifth_part_uuid, | |
210 | + FROM (SELECT SUBSTRING(entity_id, 8, 8) AS entity_id_uuid_first_part, | |
211 | + SUBSTRING(entity_id, 4, 4) AS entity_id_uuid_second_part, | |
212 | + SUBSTRING(entity_id, 1, 3) AS entity_id_uuid_third_part, | |
213 | + SUBSTRING(entity_id, 16, 4) AS entity_id_uuid_fourth_part, | |
214 | + SUBSTRING(entity_id, 20) AS entity_id_uuid_fifth_part, | |
223 | 215 | key_id AS key, |
224 | 216 | ts, |
225 | 217 | bool_v, |
... | ... | @@ -246,6 +238,6 @@ BEGIN |
246 | 238 | END LOOP; |
247 | 239 | CLOSE insert_cursor; |
248 | 240 | END; |
249 | -$$ LANGUAGE 'plpgsql'; | |
241 | +$$; | |
250 | 242 | |
251 | 243 | ... | ... |
... | ... | @@ -14,60 +14,51 @@ |
14 | 14 | -- limitations under the License. |
15 | 15 | -- |
16 | 16 | |
17 | --- select check_version(); | |
17 | +-- call check_version(); | |
18 | + | |
19 | +CREATE OR REPLACE PROCEDURE check_version(INOUT valid_version boolean) LANGUAGE plpgsql AS $BODY$ | |
18 | 20 | |
19 | -CREATE OR REPLACE FUNCTION check_version() RETURNS boolean AS $$ | |
20 | 21 | DECLARE |
21 | 22 | current_version integer; |
22 | - valid_version boolean; | |
23 | 23 | BEGIN |
24 | 24 | RAISE NOTICE 'Check the current installed PostgreSQL version...'; |
25 | 25 | SELECT current_setting('server_version_num') INTO current_version; |
26 | - IF current_version < 90600 THEN | |
27 | - valid_version := FALSE; | |
28 | - ELSE | |
29 | - valid_version := TRUE; | |
30 | - END IF; | |
31 | - IF valid_version = FALSE THEN | |
32 | - RAISE NOTICE 'Postgres version should be at least more than 9.6!'; | |
33 | - ELSE | |
26 | + IF current_version > 110000 THEN | |
34 | 27 | RAISE NOTICE 'PostgreSQL version is valid!'; |
35 | 28 | RAISE NOTICE 'Schema update started...'; |
29 | + SELECT true INTO valid_version; | |
30 | + ELSE | |
31 | + RAISE NOTICE 'Postgres version should be at least more than 10!'; | |
36 | 32 | END IF; |
37 | - RETURN valid_version; | |
38 | 33 | END; |
39 | -$$ LANGUAGE 'plpgsql'; | |
34 | +$BODY$; | |
40 | 35 | |
41 | --- select create_new_tenant_ts_kv_table(); | |
36 | +-- call create_new_ts_kv_table(); | |
42 | 37 | |
43 | -CREATE OR REPLACE FUNCTION create_new_tenant_ts_kv_table() RETURNS VOID AS $$ | |
38 | +CREATE OR REPLACE PROCEDURE create_new_ts_kv_table() LANGUAGE plpgsql AS $$ | |
44 | 39 | |
45 | 40 | BEGIN |
46 | 41 | ALTER TABLE tenant_ts_kv |
47 | 42 | RENAME TO tenant_ts_kv_old; |
48 | - CREATE TABLE IF NOT EXISTS tenant_ts_kv | |
43 | + CREATE TABLE IF NOT EXISTS ts_kv | |
49 | 44 | ( |
50 | 45 | LIKE tenant_ts_kv_old |
51 | 46 | ); |
52 | - ALTER TABLE tenant_ts_kv | |
53 | - ALTER COLUMN tenant_id TYPE uuid USING tenant_id::uuid; | |
54 | - ALTER TABLE tenant_ts_kv | |
55 | - ALTER COLUMN entity_id TYPE uuid USING entity_id::uuid; | |
56 | - ALTER TABLE tenant_ts_kv | |
57 | - ALTER COLUMN key TYPE integer USING key::integer; | |
58 | - ALTER TABLE tenant_ts_kv | |
59 | - ADD CONSTRAINT tenant_ts_kv_pkey PRIMARY KEY(tenant_id, entity_id, key, ts); | |
47 | + ALTER TABLE ts_kv ALTER COLUMN entity_id TYPE uuid USING entity_id::uuid; | |
48 | + ALTER TABLE ts_kv ALTER COLUMN key TYPE integer USING key::integer; | |
49 | + ALTER INDEX ts_kv_pkey RENAME TO tenant_ts_kv_pkey_old; | |
60 | 50 | ALTER INDEX idx_tenant_ts_kv RENAME TO idx_tenant_ts_kv_old; |
61 | 51 | ALTER INDEX tenant_ts_kv_ts_idx RENAME TO tenant_ts_kv_ts_idx_old; |
62 | --- PERFORM create_hypertable('tenant_ts_kv', 'ts', chunk_time_interval => 86400000, if_not_exists => true); | |
63 | - CREATE INDEX IF NOT EXISTS idx_tenant_ts_kv ON tenant_ts_kv(tenant_id, entity_id, key, ts); | |
52 | + ALTER TABLE ts_kv ADD CONSTRAINT ts_kv_pkey PRIMARY KEY(entity_id, key, ts); | |
53 | +-- CREATE INDEX IF NOT EXISTS ts_kv_ts_idx ON ts_kv(ts DESC); | |
54 | + ALTER TABLE ts_kv DROP COLUMN IF EXISTS tenant_id; | |
64 | 55 | END; |
65 | -$$ LANGUAGE 'plpgsql'; | |
56 | +$$; | |
66 | 57 | |
67 | 58 | |
68 | --- select create_ts_kv_latest_table(); | |
59 | +-- call create_ts_kv_latest_table(); | |
69 | 60 | |
70 | -CREATE OR REPLACE FUNCTION create_ts_kv_latest_table() RETURNS VOID AS $$ | |
61 | +CREATE OR REPLACE PROCEDURE create_ts_kv_latest_table() LANGUAGE plpgsql AS $$ | |
71 | 62 | |
72 | 63 | BEGIN |
73 | 64 | CREATE TABLE IF NOT EXISTS ts_kv_latest |
... | ... | @@ -82,12 +73,12 @@ BEGIN |
82 | 73 | CONSTRAINT ts_kv_latest_pkey PRIMARY KEY (entity_id, key) |
83 | 74 | ); |
84 | 75 | END; |
85 | -$$ LANGUAGE 'plpgsql'; | |
76 | +$$; | |
86 | 77 | |
87 | 78 | |
88 | --- select create_ts_kv_dictionary_table(); | |
79 | +-- call create_ts_kv_dictionary_table(); | |
89 | 80 | |
90 | -CREATE OR REPLACE FUNCTION create_ts_kv_dictionary_table() RETURNS VOID AS $$ | |
81 | +CREATE OR REPLACE PROCEDURE create_ts_kv_dictionary_table() LANGUAGE plpgsql AS $$ | |
91 | 82 | |
92 | 83 | BEGIN |
93 | 84 | CREATE TABLE IF NOT EXISTS ts_kv_dictionary |
... | ... | @@ -97,12 +88,12 @@ BEGIN |
97 | 88 | CONSTRAINT ts_key_id_pkey PRIMARY KEY (key) |
98 | 89 | ); |
99 | 90 | END; |
100 | -$$ LANGUAGE 'plpgsql'; | |
91 | +$$; | |
101 | 92 | |
102 | --- select insert_into_dictionary(); | |
93 | +-- call insert_into_dictionary(); | |
94 | + | |
95 | +CREATE OR REPLACE PROCEDURE insert_into_dictionary() LANGUAGE plpgsql AS $$ | |
103 | 96 | |
104 | -CREATE OR REPLACE FUNCTION insert_into_dictionary() RETURNS VOID AS | |
105 | -$$ | |
106 | 97 | DECLARE |
107 | 98 | insert_record RECORD; |
108 | 99 | key_cursor CURSOR FOR SELECT DISTINCT key |
... | ... | @@ -122,34 +113,28 @@ BEGIN |
122 | 113 | END LOOP; |
123 | 114 | CLOSE key_cursor; |
124 | 115 | END; |
125 | -$$ language 'plpgsql'; | |
116 | +$$; | |
117 | + | |
118 | +-- call insert_into_ts_kv(); | |
126 | 119 | |
127 | --- select insert_into_tenant_ts_kv(); | |
120 | +CREATE OR REPLACE PROCEDURE insert_into_ts_kv() LANGUAGE plpgsql AS $$ | |
128 | 121 | |
129 | -CREATE OR REPLACE FUNCTION insert_into_tenant_ts_kv() RETURNS void AS | |
130 | -$$ | |
131 | 122 | DECLARE |
132 | 123 | insert_size CONSTANT integer := 10000; |
133 | 124 | insert_counter integer DEFAULT 0; |
134 | 125 | insert_record RECORD; |
135 | - insert_cursor CURSOR FOR SELECT CONCAT(tenant_id_first_part_uuid, '-', tenant_id_second_part_uuid, '-1', tenant_id_third_part_uuid, '-', tenant_id_fourth_part_uuid, '-', tenant_id_fifth_part_uuid)::uuid AS tenant_id, | |
136 | - CONCAT(entity_id_first_part_uuid, '-', entity_id_second_part_uuid, '-1', entity_id_third_part_uuid, '-', entity_id_fourth_part_uuid, '-', entity_id_fifth_part_uuid)::uuid AS entity_id, | |
137 | - tenant_ts_kv_records.key AS key, | |
138 | - tenant_ts_kv_records.ts AS ts, | |
139 | - tenant_ts_kv_records.bool_v AS bool_v, | |
140 | - tenant_ts_kv_records.str_v AS str_v, | |
141 | - tenant_ts_kv_records.long_v AS long_v, | |
142 | - tenant_ts_kv_records.dbl_v AS dbl_v | |
143 | - FROM (SELECT SUBSTRING(tenant_id, 8, 8) AS tenant_id_first_part_uuid, | |
144 | - SUBSTRING(tenant_id, 4, 4) AS tenant_id_second_part_uuid, | |
145 | - SUBSTRING(tenant_id, 1, 3) AS tenant_id_third_part_uuid, | |
146 | - SUBSTRING(tenant_id, 16, 4) AS tenant_id_fourth_part_uuid, | |
147 | - SUBSTRING(tenant_id, 20) AS tenant_id_fifth_part_uuid, | |
148 | - SUBSTRING(entity_id, 8, 8) AS entity_id_first_part_uuid, | |
149 | - SUBSTRING(entity_id, 4, 4) AS entity_id_second_part_uuid, | |
150 | - SUBSTRING(entity_id, 1, 3) AS entity_id_third_part_uuid, | |
151 | - SUBSTRING(entity_id, 16, 4) AS entity_id_fourth_part_uuid, | |
152 | - SUBSTRING(entity_id, 20) AS entity_id_fifth_part_uuid, | |
126 | + insert_cursor CURSOR FOR SELECT CONCAT(entity_id_uuid_first_part, '-', entity_id_uuid_second_part, '-1', entity_id_uuid_third_part, '-', entity_id_uuid_fourth_part, '-', entity_id_uuid_fifth_part)::uuid AS entity_id, | |
127 | + new_ts_kv_records.key AS key, | |
128 | + new_ts_kv_records.ts AS ts, | |
129 | + new_ts_kv_records.bool_v AS bool_v, | |
130 | + new_ts_kv_records.str_v AS str_v, | |
131 | + new_ts_kv_records.long_v AS long_v, | |
132 | + new_ts_kv_records.dbl_v AS dbl_v | |
133 | + FROM (SELECT SUBSTRING(entity_id, 8, 8) AS entity_id_uuid_first_part, | |
134 | + SUBSTRING(entity_id, 4, 4) AS entity_id_uuid_second_part, | |
135 | + SUBSTRING(entity_id, 1, 3) AS entity_id_uuid_third_part, | |
136 | + SUBSTRING(entity_id, 16, 4) AS entity_id_uuid_fourth_part, | |
137 | + SUBSTRING(entity_id, 20) AS entity_id_uuid_fifth_part, | |
153 | 138 | key_id AS key, |
154 | 139 | ts, |
155 | 140 | bool_v, |
... | ... | @@ -157,31 +142,31 @@ DECLARE |
157 | 142 | long_v, |
158 | 143 | dbl_v |
159 | 144 | FROM tenant_ts_kv_old |
160 | - INNER JOIN ts_kv_dictionary ON (tenant_ts_kv_old.key = ts_kv_dictionary.key)) AS tenant_ts_kv_records; | |
145 | + INNER JOIN ts_kv_dictionary ON (tenant_ts_kv_old.key = ts_kv_dictionary.key)) AS new_ts_kv_records; | |
161 | 146 | BEGIN |
162 | 147 | OPEN insert_cursor; |
163 | 148 | LOOP |
164 | 149 | insert_counter := insert_counter + 1; |
165 | 150 | FETCH insert_cursor INTO insert_record; |
166 | 151 | IF NOT FOUND THEN |
167 | - RAISE NOTICE '% records have been inserted into the new tenant_ts_kv table!',insert_counter - 1; | |
152 | + RAISE NOTICE '% records have been inserted into the new ts_kv table!',insert_counter - 1; | |
168 | 153 | EXIT; |
169 | 154 | END IF; |
170 | - INSERT INTO tenant_ts_kv(tenant_id, entity_id, key, ts, bool_v, str_v, long_v, dbl_v) | |
171 | - VALUES (insert_record.tenant_id, insert_record.entity_id, insert_record.key, insert_record.ts, insert_record.bool_v, insert_record.str_v, | |
155 | + INSERT INTO ts_kv(entity_id, key, ts, bool_v, str_v, long_v, dbl_v) | |
156 | + VALUES (insert_record.entity_id, insert_record.key, insert_record.ts, insert_record.bool_v, insert_record.str_v, | |
172 | 157 | insert_record.long_v, insert_record.dbl_v); |
173 | 158 | IF MOD(insert_counter, insert_size) = 0 THEN |
174 | - RAISE NOTICE '% records have been inserted into the new tenant_ts_kv table!',insert_counter; | |
159 | + RAISE NOTICE '% records have been inserted into the new ts_kv table!',insert_counter; | |
175 | 160 | END IF; |
176 | 161 | END LOOP; |
177 | 162 | CLOSE insert_cursor; |
178 | 163 | END; |
179 | -$$ LANGUAGE 'plpgsql'; | |
164 | +$$; | |
165 | + | |
166 | +-- call insert_into_ts_kv_latest(); | |
180 | 167 | |
181 | --- select insert_into_ts_kv_latest(); | |
168 | +CREATE OR REPLACE PROCEDURE insert_into_ts_kv_latest() LANGUAGE plpgsql AS $$ | |
182 | 169 | |
183 | -CREATE OR REPLACE FUNCTION insert_into_ts_kv_latest() RETURNS void AS | |
184 | -$$ | |
185 | 170 | DECLARE |
186 | 171 | insert_size CONSTANT integer := 10000; |
187 | 172 | insert_counter integer DEFAULT 0; |
... | ... | @@ -191,7 +176,7 @@ DECLARE |
191 | 176 | latest_records.key AS key, |
192 | 177 | latest_records.entity_id AS entity_id, |
193 | 178 | latest_records.ts AS ts |
194 | - FROM (SELECT DISTINCT key AS key, entity_id AS entity_id, MAX(ts) AS ts FROM tenant_ts_kv GROUP BY key, entity_id) AS latest_records; | |
179 | + FROM (SELECT DISTINCT key AS key, entity_id AS entity_id, MAX(ts) AS ts FROM ts_kv GROUP BY key, entity_id) AS latest_records; | |
195 | 180 | BEGIN |
196 | 181 | OPEN insert_cursor; |
197 | 182 | LOOP |
... | ... | @@ -201,7 +186,7 @@ BEGIN |
201 | 186 | RAISE NOTICE '% records have been inserted into the ts_kv_latest table!',insert_counter - 1; |
202 | 187 | EXIT; |
203 | 188 | END IF; |
204 | - SELECT entity_id AS entity_id, key AS key, ts AS ts, bool_v AS bool_v, str_v AS str_v, long_v AS long_v, dbl_v AS dbl_v INTO insert_record FROM tenant_ts_kv WHERE entity_id = latest_record.entity_id AND key = latest_record.key AND ts = latest_record.ts; | |
189 | + SELECT entity_id AS entity_id, key AS key, ts AS ts, bool_v AS bool_v, str_v AS str_v, long_v AS long_v, dbl_v AS dbl_v INTO insert_record FROM ts_kv WHERE entity_id = latest_record.entity_id AND key = latest_record.key AND ts = latest_record.ts; | |
205 | 190 | INSERT INTO ts_kv_latest(entity_id, key, ts, bool_v, str_v, long_v, dbl_v) |
206 | 191 | VALUES (insert_record.entity_id, insert_record.key, insert_record.ts, insert_record.bool_v, insert_record.str_v, insert_record.long_v, insert_record.dbl_v); |
207 | 192 | IF MOD(insert_counter, insert_size) = 0 THEN |
... | ... | @@ -210,4 +195,4 @@ BEGIN |
210 | 195 | END LOOP; |
211 | 196 | CLOSE insert_cursor; |
212 | 197 | END; |
213 | -$$ LANGUAGE 'plpgsql'; | |
198 | +$$; | ... | ... |
... | ... | @@ -24,6 +24,7 @@ import com.fasterxml.jackson.databind.node.ObjectNode; |
24 | 24 | import com.google.common.util.concurrent.FutureCallback; |
25 | 25 | import com.google.common.util.concurrent.Futures; |
26 | 26 | import com.google.common.util.concurrent.ListenableFuture; |
27 | +import com.google.common.util.concurrent.MoreExecutors; | |
27 | 28 | import com.typesafe.config.Config; |
28 | 29 | import com.typesafe.config.ConfigFactory; |
29 | 30 | import lombok.Getter; |
... | ... | @@ -469,7 +470,7 @@ public class ActorSystemContext { |
469 | 470 | public void onFailure(Throwable th) { |
470 | 471 | log.error("Could not save debug Event for Node", th); |
471 | 472 | } |
472 | - }); | |
473 | + }, MoreExecutors.directExecutor()); | |
473 | 474 | } catch (IOException ex) { |
474 | 475 | log.warn("Failed to persist rule node debug message", ex); |
475 | 476 | } |
... | ... | @@ -522,7 +523,7 @@ public class ActorSystemContext { |
522 | 523 | public void onFailure(Throwable th) { |
523 | 524 | log.error("Could not save debug Event for Rule Chain", th); |
524 | 525 | } |
525 | - }); | |
526 | + }, MoreExecutors.directExecutor()); | |
526 | 527 | } |
527 | 528 | |
528 | 529 | public static Exception toException(Throwable error) { | ... | ... |
... | ... | @@ -20,9 +20,9 @@ import com.datastax.driver.core.utils.UUIDs; |
20 | 20 | import com.google.common.util.concurrent.FutureCallback; |
21 | 21 | import com.google.common.util.concurrent.Futures; |
22 | 22 | import com.google.common.util.concurrent.ListenableFuture; |
23 | +import com.google.common.util.concurrent.MoreExecutors; | |
23 | 24 | import com.google.gson.Gson; |
24 | 25 | import com.google.gson.JsonObject; |
25 | -import com.google.gson.JsonParser; | |
26 | 26 | import com.google.protobuf.InvalidProtocolBufferException; |
27 | 27 | import lombok.extern.slf4j.Slf4j; |
28 | 28 | import org.apache.commons.collections.CollectionUtils; |
... | ... | @@ -292,7 +292,7 @@ class DeviceActorMessageProcessor extends AbstractContextAwareMsgProcessor { |
292 | 292 | .build(); |
293 | 293 | sendToTransport(responseMsg, sessionInfo); |
294 | 294 | } |
295 | - }); | |
295 | + }, MoreExecutors.directExecutor()); | |
296 | 296 | } |
297 | 297 | |
298 | 298 | private ListenableFuture<List<List<AttributeKvEntry>>> getAttributesKvEntries(GetAttributeRequestMsg request) { | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.controller; |
18 | 18 | import com.google.common.util.concurrent.FutureCallback; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import org.springframework.http.HttpStatus; |
22 | 23 | import org.springframework.http.ResponseEntity; |
23 | 24 | import org.springframework.security.access.prepost.PreAuthorize; |
... | ... | @@ -30,7 +31,13 @@ import org.springframework.web.bind.annotation.ResponseBody; |
30 | 31 | import org.springframework.web.bind.annotation.ResponseStatus; |
31 | 32 | import org.springframework.web.bind.annotation.RestController; |
32 | 33 | import org.springframework.web.context.request.async.DeferredResult; |
33 | -import org.thingsboard.server.common.data.*; | |
34 | +import org.thingsboard.server.common.data.ClaimRequest; | |
35 | +import org.thingsboard.server.common.data.Customer; | |
36 | +import org.thingsboard.server.common.data.DataConstants; | |
37 | +import org.thingsboard.server.common.data.Device; | |
38 | +import org.thingsboard.server.common.data.DeviceInfo; | |
39 | +import org.thingsboard.server.common.data.EntitySubtype; | |
40 | +import org.thingsboard.server.common.data.EntityType; | |
34 | 41 | import org.thingsboard.server.common.data.audit.ActionType; |
35 | 42 | import org.thingsboard.server.common.data.device.DeviceSearchQuery; |
36 | 43 | import org.thingsboard.server.common.data.exception.ThingsboardException; |
... | ... | @@ -40,7 +47,6 @@ import org.thingsboard.server.common.data.id.TenantId; |
40 | 47 | import org.thingsboard.server.common.data.page.PageData; |
41 | 48 | import org.thingsboard.server.common.data.page.PageLink; |
42 | 49 | import org.thingsboard.server.common.data.security.DeviceCredentials; |
43 | -import org.thingsboard.server.common.data.ClaimRequest; | |
44 | 50 | import org.thingsboard.server.dao.device.claim.ClaimResponse; |
45 | 51 | import org.thingsboard.server.dao.device.claim.ClaimResult; |
46 | 52 | import org.thingsboard.server.dao.exception.IncorrectParameterException; |
... | ... | @@ -486,11 +492,12 @@ public class DeviceController extends BaseController { |
486 | 492 | deferredResult.setResult(new ResponseEntity<>(HttpStatus.BAD_REQUEST)); |
487 | 493 | } |
488 | 494 | } |
495 | + | |
489 | 496 | @Override |
490 | 497 | public void onFailure(Throwable t) { |
491 | 498 | deferredResult.setErrorResult(t); |
492 | 499 | } |
493 | - }); | |
500 | + }, MoreExecutors.directExecutor()); | |
494 | 501 | return deferredResult; |
495 | 502 | } catch (Exception e) { |
496 | 503 | throw handleException(e); |
... | ... | @@ -527,7 +534,7 @@ public class DeviceController extends BaseController { |
527 | 534 | public void onFailure(Throwable t) { |
528 | 535 | deferredResult.setErrorResult(t); |
529 | 536 | } |
530 | - }); | |
537 | + }, MoreExecutors.directExecutor()); | |
531 | 538 | return deferredResult; |
532 | 539 | } catch (Exception e) { |
533 | 540 | throw handleException(e); | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.controller; |
18 | 18 | import com.google.common.util.concurrent.FutureCallback; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | 23 | import org.springframework.http.HttpStatus; |
23 | 24 | import org.springframework.security.access.prepost.PreAuthorize; |
... | ... | @@ -167,7 +168,7 @@ public class EntityViewController extends BaseController { |
167 | 168 | }); |
168 | 169 | } |
169 | 170 | return null; |
170 | - }); | |
171 | + }, MoreExecutors.directExecutor()); | |
171 | 172 | } else { |
172 | 173 | return Futures.immediateFuture(null); |
173 | 174 | } | ... | ... |
... | ... | @@ -22,6 +22,7 @@ import com.google.common.base.Function; |
22 | 22 | import com.google.common.util.concurrent.FutureCallback; |
23 | 23 | import com.google.common.util.concurrent.Futures; |
24 | 24 | import com.google.common.util.concurrent.ListenableFuture; |
25 | +import com.google.common.util.concurrent.MoreExecutors; | |
25 | 26 | import com.google.gson.JsonElement; |
26 | 27 | import com.google.gson.JsonParseException; |
27 | 28 | import com.google.gson.JsonParser; |
... | ... | @@ -174,7 +175,7 @@ public class TelemetryController extends BaseController { |
174 | 175 | public DeferredResult<ResponseEntity> getTimeseriesKeys( |
175 | 176 | @PathVariable("entityType") String entityType, @PathVariable("entityId") String entityIdStr) throws ThingsboardException { |
176 | 177 | return accessValidator.validateEntityAndCallback(getCurrentUser(), Operation.READ_TELEMETRY, entityType, entityIdStr, |
177 | - (result, tenantId, entityId) -> Futures.addCallback(tsService.findAllLatest(tenantId, entityId), getTsKeysToResponseCallback(result))); | |
178 | + (result, tenantId, entityId) -> Futures.addCallback(tsService.findAllLatest(tenantId, entityId), getTsKeysToResponseCallback(result), MoreExecutors.directExecutor())); | |
178 | 179 | } |
179 | 180 | |
180 | 181 | @PreAuthorize("hasAnyAuthority('SYS_ADMIN', 'TENANT_ADMIN', 'CUSTOMER_USER')") |
... | ... | @@ -210,7 +211,7 @@ public class TelemetryController extends BaseController { |
210 | 211 | List<ReadTsKvQuery> queries = toKeysList(keys).stream().map(key -> new BaseReadTsKvQuery(key, startTs, endTs, interval, limit, agg)) |
211 | 212 | .collect(Collectors.toList()); |
212 | 213 | |
213 | - Futures.addCallback(tsService.findAll(tenantId, entityId, queries), getTsKvListCallback(result, useStrictDataTypes)); | |
214 | + Futures.addCallback(tsService.findAll(tenantId, entityId, queries), getTsKvListCallback(result, useStrictDataTypes), MoreExecutors.directExecutor()); | |
214 | 215 | }); |
215 | 216 | } |
216 | 217 | |
... | ... | @@ -462,7 +463,7 @@ public class TelemetryController extends BaseController { |
462 | 463 | } else { |
463 | 464 | future = tsService.findLatest(user.getTenantId(), entityId, toKeysList(keys)); |
464 | 465 | } |
465 | - Futures.addCallback(future, getTsKvListCallback(result, useStrictDataTypes)); | |
466 | + Futures.addCallback(future, getTsKvListCallback(result, useStrictDataTypes), MoreExecutors.directExecutor()); | |
466 | 467 | } |
467 | 468 | |
468 | 469 | private void getAttributeValuesCallback(@Nullable DeferredResult<ResponseEntity> result, SecurityUser user, EntityId entityId, String scope, String keys) { |
... | ... | @@ -470,9 +471,9 @@ public class TelemetryController extends BaseController { |
470 | 471 | FutureCallback<List<AttributeKvEntry>> callback = getAttributeValuesToResponseCallback(result, user, scope, entityId, keyList); |
471 | 472 | if (!StringUtils.isEmpty(scope)) { |
472 | 473 | if (keyList != null && !keyList.isEmpty()) { |
473 | - Futures.addCallback(attributesService.find(user.getTenantId(), entityId, scope, keyList), callback); | |
474 | + Futures.addCallback(attributesService.find(user.getTenantId(), entityId, scope, keyList), callback, MoreExecutors.directExecutor()); | |
474 | 475 | } else { |
475 | - Futures.addCallback(attributesService.findAll(user.getTenantId(), entityId, scope), callback); | |
476 | + Futures.addCallback(attributesService.findAll(user.getTenantId(), entityId, scope), callback, MoreExecutors.directExecutor()); | |
476 | 477 | } |
477 | 478 | } else { |
478 | 479 | List<ListenableFuture<List<AttributeKvEntry>>> futures = new ArrayList<>(); |
... | ... | @@ -486,12 +487,12 @@ public class TelemetryController extends BaseController { |
486 | 487 | |
487 | 488 | ListenableFuture<List<AttributeKvEntry>> future = mergeAllAttributesFutures(futures); |
488 | 489 | |
489 | - Futures.addCallback(future, callback); | |
490 | + Futures.addCallback(future, callback, MoreExecutors.directExecutor()); | |
490 | 491 | } |
491 | 492 | } |
492 | 493 | |
493 | 494 | private void getAttributeKeysCallback(@Nullable DeferredResult<ResponseEntity> result, TenantId tenantId, EntityId entityId, String scope) { |
494 | - Futures.addCallback(attributesService.findAll(tenantId, entityId, scope), getAttributeKeysToResponseCallback(result)); | |
495 | + Futures.addCallback(attributesService.findAll(tenantId, entityId, scope), getAttributeKeysToResponseCallback(result), MoreExecutors.directExecutor()); | |
495 | 496 | } |
496 | 497 | |
497 | 498 | private void getAttributeKeysCallback(@Nullable DeferredResult<ResponseEntity> result, TenantId tenantId, EntityId entityId) { |
... | ... | @@ -502,7 +503,7 @@ public class TelemetryController extends BaseController { |
502 | 503 | |
503 | 504 | ListenableFuture<List<AttributeKvEntry>> future = mergeAllAttributesFutures(futures); |
504 | 505 | |
505 | - Futures.addCallback(future, getAttributeKeysToResponseCallback(result)); | |
506 | + Futures.addCallback(future, getAttributeKeysToResponseCallback(result), MoreExecutors.directExecutor()); | |
506 | 507 | } |
507 | 508 | |
508 | 509 | private FutureCallback<List<TsKvEntry>> getTsKeysToResponseCallback(final DeferredResult<ResponseEntity> response) { | ... | ... |
... | ... | @@ -22,38 +22,21 @@ import org.springframework.beans.factory.annotation.Value; |
22 | 22 | import java.nio.charset.StandardCharsets; |
23 | 23 | import java.nio.file.Files; |
24 | 24 | import java.nio.file.Path; |
25 | -import java.sql.CallableStatement; | |
26 | 25 | import java.sql.Connection; |
26 | +import java.sql.ResultSet; | |
27 | 27 | import java.sql.SQLException; |
28 | 28 | import java.sql.SQLWarning; |
29 | -import java.sql.Types; | |
29 | +import java.sql.Statement; | |
30 | 30 | |
31 | 31 | @Slf4j |
32 | 32 | public abstract class AbstractSqlTsDatabaseUpgradeService { |
33 | 33 | |
34 | 34 | protected static final String CALL_REGEX = "call "; |
35 | - protected static final String CHECK_VERSION = "check_version()"; | |
35 | + protected static final String CHECK_VERSION = "check_version(false)"; | |
36 | + protected static final String CHECK_VERSION_TO_DELETE = "check_version(INOUT valid_version boolean)"; | |
36 | 37 | protected static final String DROP_TABLE = "DROP TABLE "; |
37 | - protected static final String DROP_FUNCTION_IF_EXISTS = "DROP FUNCTION IF EXISTS "; | |
38 | - | |
39 | - private static final String CALL_CHECK_VERSION = CALL_REGEX + CHECK_VERSION; | |
40 | - | |
41 | - | |
42 | - private static final String FUNCTION = "function: {}"; | |
43 | - private static final String DROP_STATEMENT = "drop statement: {}"; | |
44 | - private static final String QUERY = "query: {}"; | |
45 | - private static final String SUCCESSFULLY_EXECUTED = "Successfully executed "; | |
46 | - private static final String FAILED_TO_EXECUTE = "Failed to execute "; | |
47 | - private static final String FAILED_DUE_TO = " due to: {}"; | |
48 | - | |
49 | - protected static final String SUCCESSFULLY_EXECUTED_FUNCTION = SUCCESSFULLY_EXECUTED + FUNCTION; | |
50 | - protected static final String FAILED_TO_EXECUTE_FUNCTION_DUE_TO = FAILED_TO_EXECUTE + FUNCTION + FAILED_DUE_TO; | |
51 | - | |
52 | - protected static final String SUCCESSFULLY_EXECUTED_DROP_STATEMENT = SUCCESSFULLY_EXECUTED + DROP_STATEMENT; | |
53 | - protected static final String FAILED_TO_EXECUTE_DROP_STATEMENT = FAILED_TO_EXECUTE + DROP_STATEMENT + FAILED_DUE_TO; | |
54 | - | |
55 | - protected static final String SUCCESSFULLY_EXECUTED_QUERY = SUCCESSFULLY_EXECUTED + QUERY; | |
56 | - protected static final String FAILED_TO_EXECUTE_QUERY = FAILED_TO_EXECUTE + QUERY + FAILED_DUE_TO; | |
38 | + protected static final String DROP_PROCEDURE_IF_EXISTS = "DROP PROCEDURE IF EXISTS "; | |
39 | + protected static final String DROP_PROCEDURE_CHECK_VERSION = DROP_PROCEDURE_IF_EXISTS + CHECK_VERSION_TO_DELETE; | |
57 | 40 | |
58 | 41 | @Value("${spring.datasource.url}") |
59 | 42 | protected String dbUrl; |
... | ... | @@ -78,23 +61,22 @@ public abstract class AbstractSqlTsDatabaseUpgradeService { |
78 | 61 | log.info("Check the current PostgreSQL version..."); |
79 | 62 | boolean versionValid = false; |
80 | 63 | try { |
81 | - CallableStatement callableStatement = conn.prepareCall("{? = " + CALL_CHECK_VERSION + " }"); | |
82 | - callableStatement.registerOutParameter(1, Types.BOOLEAN); | |
83 | - callableStatement.execute(); | |
84 | - versionValid = callableStatement.getBoolean(1); | |
85 | - callableStatement.close(); | |
64 | + Statement statement = conn.createStatement(); | |
65 | + ResultSet resultSet = statement.executeQuery(CALL_REGEX + CHECK_VERSION); | |
66 | + resultSet.next(); | |
67 | + versionValid = resultSet.getBoolean(1); | |
68 | + statement.close(); | |
86 | 69 | } catch (Exception e) { |
87 | 70 | log.info("Failed to check current PostgreSQL version due to: {}", e.getMessage()); |
88 | 71 | } |
89 | 72 | return versionValid; |
90 | 73 | } |
91 | 74 | |
92 | - protected void executeFunction(Connection conn, String query) { | |
93 | - log.info("{} ... ", query); | |
75 | + protected void executeQuery(Connection conn, String query) { | |
94 | 76 | try { |
95 | - CallableStatement callableStatement = conn.prepareCall("{" + query + "}"); | |
96 | - callableStatement.execute(); | |
97 | - SQLWarning warnings = callableStatement.getWarnings(); | |
77 | + Statement statement = conn.createStatement(); | |
78 | + statement.execute(query); //NOSONAR, ignoring because method used to execute thingsboard database upgrade script | |
79 | + SQLWarning warnings = statement.getWarnings(); | |
98 | 80 | if (warnings != null) { |
99 | 81 | log.info("{}", warnings.getMessage()); |
100 | 82 | SQLWarning nextWarning = warnings.getNextWarning(); |
... | ... | @@ -103,31 +85,10 @@ public abstract class AbstractSqlTsDatabaseUpgradeService { |
103 | 85 | nextWarning = nextWarning.getNextWarning(); |
104 | 86 | } |
105 | 87 | } |
106 | - callableStatement.close(); | |
107 | - log.info(SUCCESSFULLY_EXECUTED_FUNCTION, query.replace(CALL_REGEX, "")); | |
108 | - Thread.sleep(2000); | |
109 | - } catch (Exception e) { | |
110 | - log.info(FAILED_TO_EXECUTE_FUNCTION_DUE_TO, query, e.getMessage()); | |
111 | - } | |
112 | - } | |
113 | - | |
114 | - protected void executeDropStatement(Connection conn, String query) { | |
115 | - try { | |
116 | - conn.createStatement().execute(query); //NOSONAR, ignoring because method used to execute thingsboard database upgrade script | |
117 | - log.info(SUCCESSFULLY_EXECUTED_DROP_STATEMENT, query); | |
118 | - Thread.sleep(5000); | |
119 | - } catch (InterruptedException | SQLException e) { | |
120 | - log.info(FAILED_TO_EXECUTE_DROP_STATEMENT, query, e.getMessage()); | |
121 | - } | |
122 | - } | |
123 | - | |
124 | - protected void executeQuery(Connection conn, String query) { | |
125 | - try { | |
126 | - conn.createStatement().execute(query); //NOSONAR, ignoring because method used to execute thingsboard database upgrade script | |
127 | - log.info(SUCCESSFULLY_EXECUTED_QUERY, query); | |
128 | 88 | Thread.sleep(5000); |
89 | + log.info("Successfully executed query: {}", query); | |
129 | 90 | } catch (InterruptedException | SQLException e) { |
130 | - log.info(FAILED_TO_EXECUTE_QUERY, query, e.getMessage()); | |
91 | + log.info("Failed to execute query: {} due to: {}", query, e.getMessage()); | |
131 | 92 | } |
132 | 93 | } |
133 | 94 | ... | ... |
... | ... | @@ -57,14 +57,13 @@ public class PsqlTsDatabaseUpgradeService extends AbstractSqlTsDatabaseUpgradeSe |
57 | 57 | private static final String DROP_TABLE_TS_KV_OLD = DROP_TABLE + TS_KV_OLD; |
58 | 58 | private static final String DROP_TABLE_TS_KV_LATEST_OLD = DROP_TABLE + TS_KV_LATEST_OLD; |
59 | 59 | |
60 | - private static final String DROP_FUNCTION_CHECK_VERSION = DROP_FUNCTION_IF_EXISTS + CHECK_VERSION; | |
61 | - private static final String DROP_FUNCTION_CREATE_PARTITION_TS_KV_TABLE = DROP_FUNCTION_IF_EXISTS + CREATE_PARTITION_TS_KV_TABLE; | |
62 | - private static final String DROP_FUNCTION_CREATE_NEW_TS_KV_LATEST_TABLE = DROP_FUNCTION_IF_EXISTS + CREATE_NEW_TS_KV_LATEST_TABLE; | |
63 | - private static final String DROP_FUNCTION_CREATE_PARTITIONS = DROP_FUNCTION_IF_EXISTS + CREATE_PARTITIONS; | |
64 | - private static final String DROP_FUNCTION_CREATE_TS_KV_DICTIONARY_TABLE = DROP_FUNCTION_IF_EXISTS + CREATE_TS_KV_DICTIONARY_TABLE; | |
65 | - private static final String DROP_FUNCTION_INSERT_INTO_DICTIONARY = DROP_FUNCTION_IF_EXISTS + INSERT_INTO_DICTIONARY; | |
66 | - private static final String DROP_FUNCTION_INSERT_INTO_TS_KV = DROP_FUNCTION_IF_EXISTS + INSERT_INTO_TS_KV; | |
67 | - private static final String DROP_FUNCTION_INSERT_INTO_TS_KV_LATEST = DROP_FUNCTION_IF_EXISTS + INSERT_INTO_TS_KV_LATEST; | |
60 | + private static final String DROP_PROCEDURE_CREATE_PARTITION_TS_KV_TABLE = DROP_PROCEDURE_IF_EXISTS + CREATE_PARTITION_TS_KV_TABLE; | |
61 | + private static final String DROP_PROCEDURE_CREATE_NEW_TS_KV_LATEST_TABLE = DROP_PROCEDURE_IF_EXISTS + CREATE_NEW_TS_KV_LATEST_TABLE; | |
62 | + private static final String DROP_PROCEDURE_CREATE_PARTITIONS = DROP_PROCEDURE_IF_EXISTS + CREATE_PARTITIONS; | |
63 | + private static final String DROP_PROCEDURE_CREATE_TS_KV_DICTIONARY_TABLE = DROP_PROCEDURE_IF_EXISTS + CREATE_TS_KV_DICTIONARY_TABLE; | |
64 | + private static final String DROP_PROCEDURE_INSERT_INTO_DICTIONARY = DROP_PROCEDURE_IF_EXISTS + INSERT_INTO_DICTIONARY; | |
65 | + private static final String DROP_PROCEDURE_INSERT_INTO_TS_KV = DROP_PROCEDURE_IF_EXISTS + INSERT_INTO_TS_KV; | |
66 | + private static final String DROP_PROCEDURE_INSERT_INTO_TS_KV_LATEST = DROP_PROCEDURE_IF_EXISTS + INSERT_INTO_TS_KV_LATEST; | |
68 | 67 | |
69 | 68 | @Override |
70 | 69 | public void upgradeDatabase(String fromVersion) throws Exception { |
... | ... | @@ -76,30 +75,30 @@ public class PsqlTsDatabaseUpgradeService extends AbstractSqlTsDatabaseUpgradeSe |
76 | 75 | loadSql(conn); |
77 | 76 | boolean versionValid = checkVersion(conn); |
78 | 77 | if (!versionValid) { |
79 | - log.info("PostgreSQL version should be at least more than 10!"); | |
78 | + log.info("PostgreSQL version should be at least more than 11!"); | |
80 | 79 | log.info("Please upgrade your PostgreSQL and restart the script!"); |
81 | 80 | } else { |
82 | 81 | log.info("PostgreSQL version is valid!"); |
83 | 82 | log.info("Updating schema ..."); |
84 | - executeFunction(conn, CALL_CREATE_PARTITION_TS_KV_TABLE); | |
85 | - executeFunction(conn, CALL_CREATE_PARTITIONS); | |
86 | - executeFunction(conn, CALL_CREATE_TS_KV_DICTIONARY_TABLE); | |
87 | - executeFunction(conn, CALL_INSERT_INTO_DICTIONARY); | |
88 | - executeFunction(conn, CALL_INSERT_INTO_TS_KV); | |
89 | - executeFunction(conn, CALL_CREATE_NEW_TS_KV_LATEST_TABLE); | |
90 | - executeFunction(conn, CALL_INSERT_INTO_TS_KV_LATEST); | |
83 | + executeQuery(conn, CALL_CREATE_PARTITION_TS_KV_TABLE); | |
84 | + executeQuery(conn, CALL_CREATE_PARTITIONS); | |
85 | + executeQuery(conn, CALL_CREATE_TS_KV_DICTIONARY_TABLE); | |
86 | + executeQuery(conn, CALL_INSERT_INTO_DICTIONARY); | |
87 | + executeQuery(conn, CALL_INSERT_INTO_TS_KV); | |
88 | + executeQuery(conn, CALL_CREATE_NEW_TS_KV_LATEST_TABLE); | |
89 | + executeQuery(conn, CALL_INSERT_INTO_TS_KV_LATEST); | |
91 | 90 | |
92 | - executeDropStatement(conn, DROP_TABLE_TS_KV_OLD); | |
93 | - executeDropStatement(conn, DROP_TABLE_TS_KV_LATEST_OLD); | |
91 | + executeQuery(conn, DROP_TABLE_TS_KV_OLD); | |
92 | + executeQuery(conn, DROP_TABLE_TS_KV_LATEST_OLD); | |
94 | 93 | |
95 | - executeDropStatement(conn, DROP_FUNCTION_CHECK_VERSION); | |
96 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_PARTITION_TS_KV_TABLE); | |
97 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_PARTITIONS); | |
98 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_TS_KV_DICTIONARY_TABLE); | |
99 | - executeDropStatement(conn, DROP_FUNCTION_INSERT_INTO_DICTIONARY); | |
100 | - executeDropStatement(conn, DROP_FUNCTION_INSERT_INTO_TS_KV); | |
101 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_NEW_TS_KV_LATEST_TABLE); | |
102 | - executeDropStatement(conn, DROP_FUNCTION_INSERT_INTO_TS_KV_LATEST); | |
94 | + executeQuery(conn, DROP_PROCEDURE_CHECK_VERSION); | |
95 | + executeQuery(conn, DROP_PROCEDURE_CREATE_PARTITION_TS_KV_TABLE); | |
96 | + executeQuery(conn, DROP_PROCEDURE_CREATE_PARTITIONS); | |
97 | + executeQuery(conn, DROP_PROCEDURE_CREATE_TS_KV_DICTIONARY_TABLE); | |
98 | + executeQuery(conn, DROP_PROCEDURE_INSERT_INTO_DICTIONARY); | |
99 | + executeQuery(conn, DROP_PROCEDURE_INSERT_INTO_TS_KV); | |
100 | + executeQuery(conn, DROP_PROCEDURE_CREATE_NEW_TS_KV_LATEST_TABLE); | |
101 | + executeQuery(conn, DROP_PROCEDURE_INSERT_INTO_TS_KV_LATEST); | |
103 | 102 | |
104 | 103 | executeQuery(conn, "ALTER TABLE ts_kv ADD COLUMN json_v json;"); |
105 | 104 | executeQuery(conn, "ALTER TABLE ts_kv_latest ADD COLUMN json_v json;"); | ... | ... |
... | ... | @@ -45,13 +45,13 @@ public class TimescaleTsDatabaseSchemaService extends SqlAbstractDatabaseSchemaS |
45 | 45 | private long chunkTimeInterval; |
46 | 46 | |
47 | 47 | public TimescaleTsDatabaseSchemaService() { |
48 | - super("schema-timescale.sql", "schema-timescale-idx.sql"); | |
48 | + super("schema-timescale.sql", null); | |
49 | 49 | } |
50 | 50 | |
51 | 51 | @Override |
52 | 52 | public void createDatabaseSchema() throws Exception { |
53 | 53 | super.createDatabaseSchema(); |
54 | - executeQuery("SELECT create_hypertable('tenant_ts_kv', 'ts', chunk_time_interval => " + chunkTimeInterval + ", if_not_exists => true);"); | |
54 | + executeQuery("SELECT create_hypertable('ts_kv', 'ts', chunk_time_interval => " + chunkTimeInterval + ", if_not_exists => true);"); | |
55 | 55 | } |
56 | 56 | |
57 | 57 | private void executeQuery(String query) { | ... | ... |
... | ... | @@ -43,27 +43,27 @@ public class TimescaleTsDatabaseUpgradeService extends AbstractSqlTsDatabaseUpgr |
43 | 43 | private static final String TENANT_TS_KV_OLD_TABLE = "tenant_ts_kv_old;"; |
44 | 44 | |
45 | 45 | private static final String CREATE_TS_KV_LATEST_TABLE = "create_ts_kv_latest_table()"; |
46 | - private static final String CREATE_NEW_TENANT_TS_KV_TABLE = "create_new_tenant_ts_kv_table()"; | |
46 | + private static final String CREATE_NEW_TS_KV_TABLE = "create_new_ts_kv_table()"; | |
47 | 47 | private static final String CREATE_TS_KV_DICTIONARY_TABLE = "create_ts_kv_dictionary_table()"; |
48 | 48 | private static final String INSERT_INTO_DICTIONARY = "insert_into_dictionary()"; |
49 | - private static final String INSERT_INTO_TENANT_TS_KV = "insert_into_tenant_ts_kv()"; | |
49 | + private static final String INSERT_INTO_TS_KV = "insert_into_ts_kv()"; | |
50 | 50 | private static final String INSERT_INTO_TS_KV_LATEST = "insert_into_ts_kv_latest()"; |
51 | 51 | |
52 | 52 | private static final String CALL_CREATE_TS_KV_LATEST_TABLE = CALL_REGEX + CREATE_TS_KV_LATEST_TABLE; |
53 | - private static final String CALL_CREATE_NEW_TENANT_TS_KV_TABLE = CALL_REGEX + CREATE_NEW_TENANT_TS_KV_TABLE; | |
53 | + private static final String CALL_CREATE_NEW_TENANT_TS_KV_TABLE = CALL_REGEX + CREATE_NEW_TS_KV_TABLE; | |
54 | 54 | private static final String CALL_CREATE_TS_KV_DICTIONARY_TABLE = CALL_REGEX + CREATE_TS_KV_DICTIONARY_TABLE; |
55 | 55 | private static final String CALL_INSERT_INTO_DICTIONARY = CALL_REGEX + INSERT_INTO_DICTIONARY; |
56 | - private static final String CALL_INSERT_INTO_TS_KV = CALL_REGEX + INSERT_INTO_TENANT_TS_KV; | |
56 | + private static final String CALL_INSERT_INTO_TS_KV = CALL_REGEX + INSERT_INTO_TS_KV; | |
57 | 57 | private static final String CALL_INSERT_INTO_TS_KV_LATEST = CALL_REGEX + INSERT_INTO_TS_KV_LATEST; |
58 | 58 | |
59 | 59 | private static final String DROP_OLD_TENANT_TS_KV_TABLE = DROP_TABLE + TENANT_TS_KV_OLD_TABLE; |
60 | 60 | |
61 | - private static final String DROP_FUNCTION_CREATE_TS_KV_LATEST_TABLE = DROP_FUNCTION_IF_EXISTS + CREATE_TS_KV_LATEST_TABLE; | |
62 | - private static final String DROP_FUNCTION_CREATE_TENANT_TS_KV_TABLE_COPY = DROP_FUNCTION_IF_EXISTS + CREATE_NEW_TENANT_TS_KV_TABLE; | |
63 | - private static final String DROP_FUNCTION_CREATE_TS_KV_DICTIONARY_TABLE = DROP_FUNCTION_IF_EXISTS + CREATE_TS_KV_DICTIONARY_TABLE; | |
64 | - private static final String DROP_FUNCTION_INSERT_INTO_DICTIONARY = DROP_FUNCTION_IF_EXISTS + INSERT_INTO_DICTIONARY; | |
65 | - private static final String DROP_FUNCTION_INSERT_INTO_TENANT_TS_KV = DROP_FUNCTION_IF_EXISTS + INSERT_INTO_TENANT_TS_KV; | |
66 | - private static final String DROP_FUNCTION_INSERT_INTO_TS_KV_LATEST = DROP_FUNCTION_IF_EXISTS + INSERT_INTO_TS_KV_LATEST; | |
61 | + private static final String DROP_PROCEDURE_CREATE_TS_KV_LATEST_TABLE = DROP_PROCEDURE_IF_EXISTS + CREATE_TS_KV_LATEST_TABLE; | |
62 | + private static final String DROP_PROCEDURE_CREATE_TENANT_TS_KV_TABLE_COPY = DROP_PROCEDURE_IF_EXISTS + CREATE_NEW_TS_KV_TABLE; | |
63 | + private static final String DROP_PROCEDURE_CREATE_TS_KV_DICTIONARY_TABLE = DROP_PROCEDURE_IF_EXISTS + CREATE_TS_KV_DICTIONARY_TABLE; | |
64 | + private static final String DROP_PROCEDURE_INSERT_INTO_DICTIONARY = DROP_PROCEDURE_IF_EXISTS + INSERT_INTO_DICTIONARY; | |
65 | + private static final String DROP_PROCEDURE_INSERT_INTO_TENANT_TS_KV = DROP_PROCEDURE_IF_EXISTS + INSERT_INTO_TS_KV; | |
66 | + private static final String DROP_PROCEDURE_INSERT_INTO_TS_KV_LATEST = DROP_PROCEDURE_IF_EXISTS + INSERT_INTO_TS_KV_LATEST; | |
67 | 67 | |
68 | 68 | @Autowired |
69 | 69 | private InstallScripts installScripts; |
... | ... | @@ -78,33 +78,31 @@ public class TimescaleTsDatabaseUpgradeService extends AbstractSqlTsDatabaseUpgr |
78 | 78 | loadSql(conn); |
79 | 79 | boolean versionValid = checkVersion(conn); |
80 | 80 | if (!versionValid) { |
81 | - log.info("PostgreSQL version should be at least more than 9.6!"); | |
81 | + log.info("PostgreSQL version should be at least more than 11!"); | |
82 | 82 | log.info("Please upgrade your PostgreSQL and restart the script!"); |
83 | 83 | } else { |
84 | 84 | log.info("PostgreSQL version is valid!"); |
85 | 85 | log.info("Updating schema ..."); |
86 | - executeFunction(conn, CALL_CREATE_TS_KV_LATEST_TABLE); | |
87 | - executeFunction(conn, CALL_CREATE_NEW_TENANT_TS_KV_TABLE); | |
86 | + executeQuery(conn, CALL_CREATE_TS_KV_LATEST_TABLE); | |
87 | + executeQuery(conn, CALL_CREATE_NEW_TENANT_TS_KV_TABLE); | |
88 | 88 | |
89 | - executeQuery(conn, "SELECT create_hypertable('tenant_ts_kv', 'ts', chunk_time_interval => " + chunkTimeInterval + ", if_not_exists => true);"); | |
89 | + executeQuery(conn, "SELECT create_hypertable('ts_kv', 'ts', chunk_time_interval => " + chunkTimeInterval + ", if_not_exists => true);"); | |
90 | 90 | |
91 | - executeFunction(conn, CALL_CREATE_TS_KV_DICTIONARY_TABLE); | |
92 | - executeFunction(conn, CALL_INSERT_INTO_DICTIONARY); | |
93 | - executeFunction(conn, CALL_INSERT_INTO_TS_KV); | |
94 | - executeFunction(conn, CALL_INSERT_INTO_TS_KV_LATEST); | |
91 | + executeQuery(conn, CALL_CREATE_TS_KV_DICTIONARY_TABLE); | |
92 | + executeQuery(conn, CALL_INSERT_INTO_DICTIONARY); | |
93 | + executeQuery(conn, CALL_INSERT_INTO_TS_KV); | |
94 | + executeQuery(conn, CALL_INSERT_INTO_TS_KV_LATEST); | |
95 | 95 | |
96 | - //executeQuery(conn, "SELECT set_chunk_time_interval('tenant_ts_kv', " + chunkTimeInterval +");"); | |
96 | + executeQuery(conn, DROP_OLD_TENANT_TS_KV_TABLE); | |
97 | 97 | |
98 | - executeDropStatement(conn, DROP_OLD_TENANT_TS_KV_TABLE); | |
98 | + executeQuery(conn, DROP_PROCEDURE_CREATE_TS_KV_LATEST_TABLE); | |
99 | + executeQuery(conn, DROP_PROCEDURE_CREATE_TENANT_TS_KV_TABLE_COPY); | |
100 | + executeQuery(conn, DROP_PROCEDURE_CREATE_TS_KV_DICTIONARY_TABLE); | |
101 | + executeQuery(conn, DROP_PROCEDURE_INSERT_INTO_DICTIONARY); | |
102 | + executeQuery(conn, DROP_PROCEDURE_INSERT_INTO_TENANT_TS_KV); | |
103 | + executeQuery(conn, DROP_PROCEDURE_INSERT_INTO_TS_KV_LATEST); | |
99 | 104 | |
100 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_TS_KV_LATEST_TABLE); | |
101 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_TENANT_TS_KV_TABLE_COPY); | |
102 | - executeDropStatement(conn, DROP_FUNCTION_CREATE_TS_KV_DICTIONARY_TABLE); | |
103 | - executeDropStatement(conn, DROP_FUNCTION_INSERT_INTO_DICTIONARY); | |
104 | - executeDropStatement(conn, DROP_FUNCTION_INSERT_INTO_TENANT_TS_KV); | |
105 | - executeDropStatement(conn, DROP_FUNCTION_INSERT_INTO_TS_KV_LATEST); | |
106 | - | |
107 | - executeQuery(conn, "ALTER TABLE tenant_ts_kv ADD COLUMN json_v json;"); | |
105 | + executeQuery(conn, "ALTER TABLE ts_kv ADD COLUMN json_v json;"); | |
108 | 106 | executeQuery(conn, "ALTER TABLE ts_kv_latest ADD COLUMN json_v json;"); |
109 | 107 | |
110 | 108 | log.info("schema timeseries updated!"); | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.service.script; |
18 | 18 | import com.google.common.util.concurrent.FutureCallback; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import delight.nashornsandbox.NashornSandbox; |
22 | 23 | import delight.nashornsandbox.NashornSandboxes; |
23 | 24 | import jdk.nashorn.api.scripting.NashornScriptEngineFactory; |
... | ... | @@ -28,20 +29,17 @@ import org.springframework.beans.factory.annotation.Value; |
28 | 29 | import org.springframework.scheduling.annotation.Scheduled; |
29 | 30 | import org.thingsboard.common.util.ThingsBoardThreadFactory; |
30 | 31 | |
31 | -import javax.annotation.Nullable; | |
32 | 32 | import javax.annotation.PostConstruct; |
33 | 33 | import javax.annotation.PreDestroy; |
34 | 34 | import javax.script.Invocable; |
35 | 35 | import javax.script.ScriptEngine; |
36 | 36 | import javax.script.ScriptException; |
37 | 37 | import java.util.UUID; |
38 | -import java.util.concurrent.Callable; | |
39 | 38 | import java.util.concurrent.ExecutionException; |
40 | 39 | import java.util.concurrent.ExecutorService; |
41 | 40 | import java.util.concurrent.Executors; |
42 | 41 | import java.util.concurrent.ScheduledExecutorService; |
43 | 42 | import java.util.concurrent.TimeUnit; |
44 | -import java.util.concurrent.TimeoutException; | |
45 | 43 | import java.util.concurrent.atomic.AtomicInteger; |
46 | 44 | |
47 | 45 | @Slf4j |
... | ... | @@ -140,7 +138,7 @@ public abstract class AbstractNashornJsInvokeService extends AbstractJsInvokeSer |
140 | 138 | if (maxRequestsTimeout > 0) { |
141 | 139 | result = Futures.withTimeout(result, maxRequestsTimeout, TimeUnit.MILLISECONDS, timeoutExecutorService); |
142 | 140 | } |
143 | - Futures.addCallback(result, evalCallback); | |
141 | + Futures.addCallback(result, evalCallback, MoreExecutors.directExecutor()); | |
144 | 142 | return result; |
145 | 143 | } |
146 | 144 | |
... | ... | @@ -163,7 +161,7 @@ public abstract class AbstractNashornJsInvokeService extends AbstractJsInvokeSer |
163 | 161 | if (maxRequestsTimeout > 0) { |
164 | 162 | result = Futures.withTimeout(result, maxRequestsTimeout, TimeUnit.MILLISECONDS, timeoutExecutorService); |
165 | 163 | } |
166 | - Futures.addCallback(result, invokeCallback); | |
164 | + Futures.addCallback(result, invokeCallback, MoreExecutors.directExecutor()); | |
167 | 165 | return result; |
168 | 166 | } |
169 | 167 | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.service.script; |
18 | 18 | import com.google.common.util.concurrent.FutureCallback; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import lombok.Getter; |
22 | 23 | import lombok.extern.slf4j.Slf4j; |
23 | 24 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -40,7 +41,6 @@ import java.util.UUID; |
40 | 41 | import java.util.concurrent.ConcurrentHashMap; |
41 | 42 | import java.util.concurrent.TimeoutException; |
42 | 43 | import java.util.concurrent.atomic.AtomicInteger; |
43 | -import java.util.concurrent.atomic.AtomicLong; | |
44 | 44 | |
45 | 45 | @Slf4j |
46 | 46 | @ConditionalOnProperty(prefix = "js", value = "evaluator", havingValue = "remote", matchIfMissing = true) |
... | ... | @@ -166,7 +166,7 @@ public class RemoteJsInvokeService extends AbstractJsInvokeService { |
166 | 166 | } |
167 | 167 | kafkaFailedMsgs.incrementAndGet(); |
168 | 168 | } |
169 | - }); | |
169 | + }, MoreExecutors.directExecutor()); | |
170 | 170 | return Futures.transform(future, response -> { |
171 | 171 | JsInvokeProtos.JsCompileResponse compilationResult = response.getCompileResponse(); |
172 | 172 | UUID compiledScriptId = new UUID(compilationResult.getScriptIdMSB(), compilationResult.getScriptIdLSB()); |
... | ... | @@ -178,7 +178,7 @@ public class RemoteJsInvokeService extends AbstractJsInvokeService { |
178 | 178 | log.debug("[{}] Failed to compile script due to [{}]: {}", compiledScriptId, compilationResult.getErrorCode().name(), compilationResult.getErrorDetails()); |
179 | 179 | throw new RuntimeException(compilationResult.getErrorDetails()); |
180 | 180 | } |
181 | - }); | |
181 | + }, MoreExecutors.directExecutor()); | |
182 | 182 | } |
183 | 183 | |
184 | 184 | @Override |
... | ... | @@ -217,7 +217,7 @@ public class RemoteJsInvokeService extends AbstractJsInvokeService { |
217 | 217 | } |
218 | 218 | kafkaFailedMsgs.incrementAndGet(); |
219 | 219 | } |
220 | - }); | |
220 | + }, MoreExecutors.directExecutor()); | |
221 | 221 | return Futures.transform(future, response -> { |
222 | 222 | JsInvokeProtos.JsInvokeResponse invokeResult = response.getInvokeResponse(); |
223 | 223 | if (invokeResult.getSuccess()) { |
... | ... | @@ -226,7 +226,7 @@ public class RemoteJsInvokeService extends AbstractJsInvokeService { |
226 | 226 | log.debug("[{}] Failed to compile script due to [{}]: {}", scriptId, invokeResult.getErrorCode().name(), invokeResult.getErrorDetails()); |
227 | 227 | throw new RuntimeException(invokeResult.getErrorDetails()); |
228 | 228 | } |
229 | - }); | |
229 | + }, MoreExecutors.directExecutor()); | |
230 | 230 | } |
231 | 231 | |
232 | 232 | @Override | ... | ... |
... | ... | @@ -21,6 +21,7 @@ import com.fasterxml.jackson.databind.ObjectMapper; |
21 | 21 | import com.google.common.collect.Sets; |
22 | 22 | import com.google.common.util.concurrent.Futures; |
23 | 23 | import com.google.common.util.concurrent.ListenableFuture; |
24 | +import com.google.common.util.concurrent.MoreExecutors; | |
24 | 25 | import lombok.extern.slf4j.Slf4j; |
25 | 26 | import org.apache.commons.lang3.StringUtils; |
26 | 27 | import org.thingsboard.server.common.data.id.EntityId; |
... | ... | @@ -121,7 +122,7 @@ public class RuleNodeJsScriptEngine implements org.thingsboard.rule.engine.api.S |
121 | 122 | } else { |
122 | 123 | return Futures.immediateFuture(unbindMsg(json, msg)); |
123 | 124 | } |
124 | - }); | |
125 | + }, MoreExecutors.directExecutor()); | |
125 | 126 | } |
126 | 127 | |
127 | 128 | @Override |
... | ... | @@ -174,7 +175,7 @@ public class RuleNodeJsScriptEngine implements org.thingsboard.rule.engine.api.S |
174 | 175 | } else { |
175 | 176 | return Futures.immediateFuture(json.asBoolean()); |
176 | 177 | } |
177 | - }); | |
178 | + }, MoreExecutors.directExecutor()); | |
178 | 179 | } |
179 | 180 | |
180 | 181 | @Override |
... | ... | @@ -232,7 +233,7 @@ public class RuleNodeJsScriptEngine implements org.thingsboard.rule.engine.api.S |
232 | 233 | return Futures.immediateFailedFuture(new ScriptException(e)); |
233 | 234 | } |
234 | 235 | } |
235 | - }); | |
236 | + }, MoreExecutors.directExecutor()); | |
236 | 237 | } |
237 | 238 | |
238 | 239 | public void destroy() { | ... | ... |
... | ... | @@ -64,14 +64,26 @@ import org.thingsboard.server.service.telemetry.TelemetrySubscriptionService; |
64 | 64 | import javax.annotation.Nullable; |
65 | 65 | import javax.annotation.PostConstruct; |
66 | 66 | import javax.annotation.PreDestroy; |
67 | -import java.util.*; | |
67 | +import java.util.ArrayList; | |
68 | +import java.util.Arrays; | |
69 | +import java.util.Collections; | |
70 | +import java.util.HashSet; | |
71 | +import java.util.List; | |
72 | +import java.util.Optional; | |
73 | +import java.util.Random; | |
74 | +import java.util.Set; | |
75 | +import java.util.UUID; | |
68 | 76 | import java.util.concurrent.ConcurrentHashMap; |
69 | 77 | import java.util.concurrent.ConcurrentMap; |
70 | 78 | import java.util.concurrent.ExecutionException; |
71 | 79 | import java.util.concurrent.Executors; |
72 | 80 | import java.util.concurrent.TimeUnit; |
73 | 81 | |
74 | -import static org.thingsboard.server.common.data.DataConstants.*; | |
82 | +import static org.thingsboard.server.common.data.DataConstants.ACTIVITY_EVENT; | |
83 | +import static org.thingsboard.server.common.data.DataConstants.CONNECT_EVENT; | |
84 | +import static org.thingsboard.server.common.data.DataConstants.DISCONNECT_EVENT; | |
85 | +import static org.thingsboard.server.common.data.DataConstants.INACTIVITY_EVENT; | |
86 | +import static org.thingsboard.server.common.data.DataConstants.SERVER_SCOPE; | |
75 | 87 | |
76 | 88 | /** |
77 | 89 | * Created by ashvayka on 01.05.18. |
... | ... | @@ -401,7 +413,7 @@ public class DefaultDeviceStateService implements DeviceStateService { |
401 | 413 | public void onFailure(Throwable t) { |
402 | 414 | log.warn("Failed to register device to the state service", t); |
403 | 415 | } |
404 | - }); | |
416 | + }, MoreExecutors.directExecutor()); | |
405 | 417 | } else { |
406 | 418 | sendDeviceEvent(device.getTenantId(), device.getId(), address.get(), true, false, false); |
407 | 419 | } |
... | ... | @@ -456,10 +468,10 @@ public class DefaultDeviceStateService implements DeviceStateService { |
456 | 468 | private ListenableFuture<DeviceStateData> fetchDeviceState(Device device) { |
457 | 469 | if (persistToTelemetry) { |
458 | 470 | ListenableFuture<List<TsKvEntry>> tsData = tsService.findLatest(TenantId.SYS_TENANT_ID, device.getId(), PERSISTENT_ATTRIBUTES); |
459 | - return Futures.transform(tsData, extractDeviceStateData(device)); | |
471 | + return Futures.transform(tsData, extractDeviceStateData(device), MoreExecutors.directExecutor()); | |
460 | 472 | } else { |
461 | 473 | ListenableFuture<List<AttributeKvEntry>> attrData = attributesService.find(TenantId.SYS_TENANT_ID, device.getId(), DataConstants.SERVER_SCOPE, PERSISTENT_ATTRIBUTES); |
462 | - return Futures.transform(attrData, extractDeviceStateData(device)); | |
474 | + return Futures.transform(attrData, extractDeviceStateData(device), MoreExecutors.directExecutor()); | |
463 | 475 | } |
464 | 476 | } |
465 | 477 | ... | ... |
... | ... | @@ -21,6 +21,7 @@ import com.google.common.base.Function; |
21 | 21 | import com.google.common.util.concurrent.FutureCallback; |
22 | 22 | import com.google.common.util.concurrent.Futures; |
23 | 23 | import com.google.common.util.concurrent.ListenableFuture; |
24 | +import com.google.common.util.concurrent.MoreExecutors; | |
24 | 25 | import lombok.extern.slf4j.Slf4j; |
25 | 26 | import org.springframework.beans.factory.annotation.Autowired; |
26 | 27 | import org.springframework.beans.factory.annotation.Value; |
... | ... | @@ -54,9 +55,6 @@ import org.thingsboard.server.service.telemetry.cmd.SubscriptionCmd; |
54 | 55 | import org.thingsboard.server.service.telemetry.cmd.TelemetryPluginCmd; |
55 | 56 | import org.thingsboard.server.service.telemetry.cmd.TelemetryPluginCmdsWrapper; |
56 | 57 | import org.thingsboard.server.service.telemetry.cmd.TimeseriesSubscriptionCmd; |
57 | -import org.thingsboard.server.service.telemetry.exception.AccessDeniedException; | |
58 | -import org.thingsboard.server.service.telemetry.exception.EntityNotFoundException; | |
59 | -import org.thingsboard.server.service.telemetry.exception.InternalErrorException; | |
60 | 58 | import org.thingsboard.server.service.telemetry.exception.UnauthorizedException; |
61 | 59 | import org.thingsboard.server.service.telemetry.sub.SubscriptionErrorCode; |
62 | 60 | import org.thingsboard.server.service.telemetry.sub.SubscriptionState; |
... | ... | @@ -70,12 +68,14 @@ import java.util.ArrayList; |
70 | 68 | import java.util.Collections; |
71 | 69 | import java.util.HashMap; |
72 | 70 | import java.util.HashSet; |
73 | -import java.util.Iterator; | |
74 | 71 | import java.util.List; |
75 | 72 | import java.util.Map; |
76 | 73 | import java.util.Optional; |
77 | 74 | import java.util.Set; |
78 | -import java.util.concurrent.*; | |
75 | +import java.util.concurrent.ConcurrentHashMap; | |
76 | +import java.util.concurrent.ConcurrentMap; | |
77 | +import java.util.concurrent.ExecutorService; | |
78 | +import java.util.concurrent.Executors; | |
79 | 79 | import java.util.function.Consumer; |
80 | 80 | import java.util.stream.Collectors; |
81 | 81 | |
... | ... | @@ -616,7 +616,7 @@ public class DefaultTelemetryWebSocketService implements TelemetryWebSocketServi |
616 | 616 | } |
617 | 617 | |
618 | 618 | ListenableFuture<List<AttributeKvEntry>> future = mergeAllAttributesFutures(futures); |
619 | - Futures.addCallback(future, callback); | |
619 | + Futures.addCallback(future, callback, MoreExecutors.directExecutor()); | |
620 | 620 | } |
621 | 621 | |
622 | 622 | @Override |
... | ... | @@ -630,7 +630,7 @@ public class DefaultTelemetryWebSocketService implements TelemetryWebSocketServi |
630 | 630 | return new FutureCallback<ValidationResult>() { |
631 | 631 | @Override |
632 | 632 | public void onSuccess(@Nullable ValidationResult result) { |
633 | - Futures.addCallback(attributesService.find(tenantId, entityId, scope, keys), callback); | |
633 | + Futures.addCallback(attributesService.find(tenantId, entityId, scope, keys), callback, MoreExecutors.directExecutor()); | |
634 | 634 | } |
635 | 635 | |
636 | 636 | @Override |
... | ... | @@ -650,7 +650,7 @@ public class DefaultTelemetryWebSocketService implements TelemetryWebSocketServi |
650 | 650 | } |
651 | 651 | |
652 | 652 | ListenableFuture<List<AttributeKvEntry>> future = mergeAllAttributesFutures(futures); |
653 | - Futures.addCallback(future, callback); | |
653 | + Futures.addCallback(future, callback, MoreExecutors.directExecutor()); | |
654 | 654 | } |
655 | 655 | |
656 | 656 | @Override |
... | ... | @@ -664,7 +664,7 @@ public class DefaultTelemetryWebSocketService implements TelemetryWebSocketServi |
664 | 664 | return new FutureCallback<ValidationResult>() { |
665 | 665 | @Override |
666 | 666 | public void onSuccess(@Nullable ValidationResult result) { |
667 | - Futures.addCallback(attributesService.findAll(tenantId, entityId, scope), callback); | |
667 | + Futures.addCallback(attributesService.findAll(tenantId, entityId, scope), callback, MoreExecutors.directExecutor()); | |
668 | 668 | } |
669 | 669 | |
670 | 670 | @Override | ... | ... |
... | ... | @@ -19,10 +19,9 @@ import com.fasterxml.jackson.core.JsonProcessingException; |
19 | 19 | import com.fasterxml.jackson.databind.ObjectMapper; |
20 | 20 | import com.google.common.util.concurrent.Futures; |
21 | 21 | import com.google.common.util.concurrent.ListenableFuture; |
22 | +import com.google.common.util.concurrent.MoreExecutors; | |
22 | 23 | import lombok.extern.slf4j.Slf4j; |
23 | 24 | import org.springframework.beans.factory.annotation.Autowired; |
24 | -import org.springframework.beans.factory.annotation.Value; | |
25 | -import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; | |
26 | 25 | import org.springframework.stereotype.Service; |
27 | 26 | import org.springframework.util.StringUtils; |
28 | 27 | import org.thingsboard.server.common.data.Device; |
... | ... | @@ -42,19 +41,10 @@ import org.thingsboard.server.gen.transport.TransportProtos.TransportApiResponse |
42 | 41 | import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceCredentialsResponseMsg; |
43 | 42 | import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceTokenRequestMsg; |
44 | 43 | import org.thingsboard.server.gen.transport.TransportProtos.ValidateDeviceX509CertRequestMsg; |
45 | -import org.thingsboard.server.kafka.TBKafkaConsumerTemplate; | |
46 | -import org.thingsboard.server.kafka.TBKafkaProducerTemplate; | |
47 | -import org.thingsboard.server.kafka.TbKafkaResponseTemplate; | |
48 | -import org.thingsboard.server.kafka.TbKafkaSettings; | |
49 | -import org.thingsboard.server.service.cluster.discovery.DiscoveryService; | |
50 | 44 | import org.thingsboard.server.service.executors.DbCallbackExecutorService; |
51 | 45 | import org.thingsboard.server.service.state.DeviceStateService; |
52 | 46 | |
53 | -import javax.annotation.PostConstruct; | |
54 | -import javax.annotation.PreDestroy; | |
55 | 47 | import java.util.UUID; |
56 | -import java.util.concurrent.ExecutorService; | |
57 | -import java.util.concurrent.Executors; | |
58 | 48 | import java.util.concurrent.locks.ReentrantLock; |
59 | 49 | |
60 | 50 | /** |
... | ... | @@ -145,7 +135,7 @@ public class LocalTransportApiService implements TransportApiService { |
145 | 135 | try { |
146 | 136 | ValidateDeviceCredentialsResponseMsg.Builder builder = ValidateDeviceCredentialsResponseMsg.newBuilder(); |
147 | 137 | builder.setDeviceInfo(getDeviceInfoProto(device)); |
148 | - if(!StringUtils.isEmpty(credentials.getCredentialsValue())){ | |
138 | + if (!StringUtils.isEmpty(credentials.getCredentialsValue())) { | |
149 | 139 | builder.setCredentialsBody(credentials.getCredentialsValue()); |
150 | 140 | } |
151 | 141 | return TransportApiResponseMsg.newBuilder() |
... | ... | @@ -154,7 +144,7 @@ public class LocalTransportApiService implements TransportApiService { |
154 | 144 | log.warn("[{}] Failed to lookup device by id", deviceId, e); |
155 | 145 | return getEmptyTransportApiResponse(); |
156 | 146 | } |
157 | - }); | |
147 | + }, MoreExecutors.directExecutor()); | |
158 | 148 | } |
159 | 149 | |
160 | 150 | private DeviceInfoProto getDeviceInfoProto(Device device) throws JsonProcessingException { | ... | ... |
... | ... | @@ -2,8 +2,8 @@ |
2 | 2 | |
3 | 3 | set -e |
4 | 4 | |
5 | -chown -R ${pkg.name}: ${pkg.logFolder} | |
6 | -chown -R ${pkg.name}: ${pkg.installFolder} | |
5 | +chown -R ${pkg.user}: ${pkg.logFolder} | |
6 | +chown -R ${pkg.user}: ${pkg.installFolder} | |
7 | 7 | systemctl --no-reload enable ${pkg.name}.service >/dev/null 2>&1 || : |
8 | 8 | |
9 | 9 | exit 0 | ... | ... |
... | ... | @@ -2,21 +2,21 @@ |
2 | 2 | |
3 | 3 | set -e |
4 | 4 | |
5 | -if ! getent group ${pkg.name} >/dev/null; then | |
6 | - addgroup --system ${pkg.name} | |
5 | +if ! getent group ${pkg.user} >/dev/null; then | |
6 | + addgroup --system ${pkg.user} | |
7 | 7 | fi |
8 | 8 | |
9 | -if ! getent passwd ${pkg.name} >/dev/null; then | |
9 | +if ! getent passwd ${pkg.user} >/dev/null; then | |
10 | 10 | adduser --quiet \ |
11 | 11 | --system \ |
12 | - --ingroup ${pkg.name} \ | |
12 | + --ingroup ${pkg.user} \ | |
13 | 13 | --quiet \ |
14 | 14 | --disabled-login \ |
15 | 15 | --disabled-password \ |
16 | 16 | --home ${pkg.installFolder} \ |
17 | 17 | --no-create-home \ |
18 | 18 | -gecos "Thingsboard application" \ |
19 | - ${pkg.name} | |
19 | + ${pkg.user} | |
20 | 20 | fi |
21 | 21 | |
22 | 22 | exit 0 |
\ No newline at end of file | ... | ... |
... | ... | @@ -44,7 +44,7 @@ installDir=${pkg.installFolder}/data |
44 | 44 | |
45 | 45 | source "${CONF_FOLDER}/${configfile}" |
46 | 46 | |
47 | -run_user=${pkg.name} | |
47 | +run_user=${pkg.user} | |
48 | 48 | |
49 | 49 | su -s /bin/sh -c "java -cp ${jarfile} $JAVA_OPTS -Dloader.main=org.thingsboard.server.ThingsboardInstallApplication \ |
50 | 50 | -Dinstall.data_dir=${installDir} \ | ... | ... |
... | ... | @@ -43,7 +43,7 @@ installDir=${pkg.installFolder}/data |
43 | 43 | |
44 | 44 | source "${CONF_FOLDER}/${configfile}" |
45 | 45 | |
46 | -run_user=${pkg.name} | |
46 | +run_user=${pkg.user} | |
47 | 47 | |
48 | 48 | su -s /bin/sh -c "java -cp ${jarfile} $JAVA_OPTS -Dloader.main=org.thingsboard.server.ThingsboardInstallApplication \ |
49 | 49 | -Dinstall.data_dir=${installDir} \ | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.kafka; |
18 | 18 | import com.google.common.util.concurrent.FutureCallback; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | |
22 | 23 | import java.util.concurrent.Executor; |
23 | 24 | import java.util.concurrent.ScheduledExecutorService; |
... | ... | @@ -59,7 +60,7 @@ public class AsyncCallbackTemplate { |
59 | 60 | if (executor != null) { |
60 | 61 | Futures.addCallback(future, callback, executor); |
61 | 62 | } else { |
62 | - Futures.addCallback(future, callback); | |
63 | + Futures.addCallback(future, callback, MoreExecutors.directExecutor()); | |
63 | 64 | } |
64 | 65 | } |
65 | 66 | ... | ... |
... | ... | @@ -18,19 +18,20 @@ package org.thingsboard.common.util; |
18 | 18 | import com.google.common.util.concurrent.FutureCallback; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | |
22 | 23 | import java.util.concurrent.Executor; |
23 | 24 | import java.util.function.Consumer; |
24 | 25 | |
25 | 26 | public class DonAsynchron { |
26 | 27 | |
27 | - public static <T> void withCallback(ListenableFuture<T> future, Consumer<T> onSuccess, | |
28 | - Consumer<Throwable> onFailure) { | |
28 | + public static <T> void withCallback(ListenableFuture<T> future, Consumer<T> onSuccess, | |
29 | + Consumer<Throwable> onFailure) { | |
29 | 30 | withCallback(future, onSuccess, onFailure, null); |
30 | 31 | } |
31 | 32 | |
32 | - public static <T> void withCallback(ListenableFuture<T> future, Consumer<T> onSuccess, | |
33 | - Consumer<Throwable> onFailure, Executor executor) { | |
33 | + public static <T> void withCallback(ListenableFuture<T> future, Consumer<T> onSuccess, | |
34 | + Consumer<Throwable> onFailure, Executor executor) { | |
34 | 35 | FutureCallback<T> callback = new FutureCallback<T>() { |
35 | 36 | @Override |
36 | 37 | public void onSuccess(T result) { |
... | ... | @@ -49,7 +50,7 @@ public class DonAsynchron { |
49 | 50 | if (executor != null) { |
50 | 51 | Futures.addCallback(future, callback, executor); |
51 | 52 | } else { |
52 | - Futures.addCallback(future, callback); | |
53 | + Futures.addCallback(future, callback, MoreExecutors.directExecutor()); | |
53 | 54 | } |
54 | 55 | } |
55 | 56 | } | ... | ... |
... | ... | @@ -20,6 +20,7 @@ import com.fasterxml.jackson.databind.JsonNode; |
20 | 20 | import com.google.common.base.Function; |
21 | 21 | import com.google.common.util.concurrent.Futures; |
22 | 22 | import com.google.common.util.concurrent.ListenableFuture; |
23 | +import com.google.common.util.concurrent.MoreExecutors; | |
23 | 24 | import lombok.extern.slf4j.Slf4j; |
24 | 25 | import org.springframework.beans.factory.annotation.Autowired; |
25 | 26 | import org.springframework.stereotype.Service; |
... | ... | @@ -53,7 +54,6 @@ import javax.annotation.Nullable; |
53 | 54 | import javax.annotation.PostConstruct; |
54 | 55 | import javax.annotation.PreDestroy; |
55 | 56 | import java.util.ArrayList; |
56 | -import java.util.Collections; | |
57 | 57 | import java.util.Comparator; |
58 | 58 | import java.util.List; |
59 | 59 | import java.util.Set; |
... | ... | @@ -264,9 +264,8 @@ public class BaseAlarmService extends AbstractEntityService implements AlarmServ |
264 | 264 | entityService.fetchEntityNameAsync(tenantId, alarmInfo.getOriginator()), originatorName -> { |
265 | 265 | alarmInfo.setOriginatorName(originatorName); |
266 | 266 | return alarmInfo; |
267 | - } | |
268 | - ); | |
269 | - }); | |
267 | + }, MoreExecutors.directExecutor()); | |
268 | + }, MoreExecutors.directExecutor()); | |
270 | 269 | } |
271 | 270 | |
272 | 271 | @Override |
... | ... | @@ -282,12 +281,12 @@ public class BaseAlarmService extends AbstractEntityService implements AlarmServ |
282 | 281 | } |
283 | 282 | alarmInfo.setOriginatorName(originatorName); |
284 | 283 | return alarmInfo; |
285 | - } | |
284 | + }, MoreExecutors.directExecutor() | |
286 | 285 | )); |
287 | 286 | } |
288 | - return Futures.transform(Futures.successfulAsList(alarmFutures), alarmInfos -> { | |
289 | - return new PageData(alarmInfos, alarms.getTotalPages(), alarms.getTotalElements(), alarms.hasNext()); | |
290 | - }); | |
287 | + return Futures.transform(Futures.successfulAsList(alarmFutures), | |
288 | + alarmInfos -> new PageData(alarmInfos, alarms.getTotalPages(), alarms.getTotalElements(), | |
289 | + alarms.hasNext()), MoreExecutors.directExecutor()); | |
291 | 290 | } |
292 | 291 | return Futures.immediateFuture(alarms); |
293 | 292 | } | ... | ... |
... | ... | @@ -16,9 +16,9 @@ |
16 | 16 | package org.thingsboard.server.dao.asset; |
17 | 17 | |
18 | 18 | |
19 | -import com.google.common.base.Function; | |
20 | 19 | import com.google.common.util.concurrent.Futures; |
21 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
22 | 22 | import lombok.extern.slf4j.Slf4j; |
23 | 23 | import org.hibernate.exception.ConstraintViolationException; |
24 | 24 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -29,7 +29,6 @@ import org.springframework.cache.annotation.Cacheable; |
29 | 29 | import org.springframework.stereotype.Service; |
30 | 30 | import org.springframework.util.StringUtils; |
31 | 31 | import org.thingsboard.server.common.data.Customer; |
32 | -import org.thingsboard.server.common.data.Device; | |
33 | 32 | import org.thingsboard.server.common.data.EntitySubtype; |
34 | 33 | import org.thingsboard.server.common.data.EntityType; |
35 | 34 | import org.thingsboard.server.common.data.EntityView; |
... | ... | @@ -63,7 +62,10 @@ import java.util.stream.Collectors; |
63 | 62 | import static org.thingsboard.server.common.data.CacheConstants.ASSET_CACHE; |
64 | 63 | import static org.thingsboard.server.dao.DaoUtil.toUUIDs; |
65 | 64 | import static org.thingsboard.server.dao.model.ModelConstants.NULL_UUID; |
66 | -import static org.thingsboard.server.dao.service.Validator.*; | |
65 | +import static org.thingsboard.server.dao.service.Validator.validateId; | |
66 | +import static org.thingsboard.server.dao.service.Validator.validateIds; | |
67 | +import static org.thingsboard.server.dao.service.Validator.validatePageLink; | |
68 | +import static org.thingsboard.server.dao.service.Validator.validateString; | |
67 | 69 | |
68 | 70 | @Service |
69 | 71 | @Slf4j |
... | ... | @@ -298,9 +300,9 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ |
298 | 300 | } |
299 | 301 | } |
300 | 302 | return Futures.successfulAsList(futures); |
301 | - }); | |
303 | + }, MoreExecutors.directExecutor()); | |
302 | 304 | assets = Futures.transform(assets, assetList -> |
303 | - assetList == null ? Collections.emptyList() : assetList.stream().filter(asset -> query.getAssetTypes().contains(asset.getType())).collect(Collectors.toList()) | |
305 | + assetList == null ? Collections.emptyList() : assetList.stream().filter(asset -> query.getAssetTypes().contains(asset.getType())).collect(Collectors.toList()), MoreExecutors.directExecutor() | |
304 | 306 | ); |
305 | 307 | return assets; |
306 | 308 | } |
... | ... | @@ -314,7 +316,7 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ |
314 | 316 | assetTypes -> { |
315 | 317 | assetTypes.sort(Comparator.comparing(EntitySubtype::getType)); |
316 | 318 | return assetTypes; |
317 | - }); | |
319 | + }, MoreExecutors.directExecutor()); | |
318 | 320 | } |
319 | 321 | |
320 | 322 | private DataValidator<Asset> assetValidator = |
... | ... | @@ -375,18 +377,18 @@ public class BaseAssetService extends AbstractEntityService implements AssetServ |
375 | 377 | }; |
376 | 378 | |
377 | 379 | private PaginatedRemover<TenantId, Asset> tenantAssetsRemover = |
378 | - new PaginatedRemover<TenantId, Asset>() { | |
380 | + new PaginatedRemover<TenantId, Asset>() { | |
379 | 381 | |
380 | - @Override | |
381 | - protected PageData<Asset> findEntities(TenantId tenantId, TenantId id, PageLink pageLink) { | |
382 | - return assetDao.findAssetsByTenantId(id.getId(), pageLink); | |
383 | - } | |
382 | + @Override | |
383 | + protected PageData<Asset> findEntities(TenantId tenantId, TenantId id, PageLink pageLink) { | |
384 | + return assetDao.findAssetsByTenantId(id.getId(), pageLink); | |
385 | + } | |
384 | 386 | |
385 | - @Override | |
386 | - protected void removeEntity(TenantId tenantId, Asset entity) { | |
387 | - deleteAsset(tenantId, new AssetId(entity.getId().getId())); | |
388 | - } | |
389 | - }; | |
387 | + @Override | |
388 | + protected void removeEntity(TenantId tenantId, Asset entity) { | |
389 | + deleteAsset(tenantId, new AssetId(entity.getId().getId())); | |
390 | + } | |
391 | + }; | |
390 | 392 | |
391 | 393 | private PaginatedRemover<CustomerId, Asset> customerAssetsUnasigner = new PaginatedRemover<CustomerId, Asset>() { |
392 | 394 | ... | ... |
... | ... | @@ -15,8 +15,6 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.dao.dashboard; |
17 | 17 | |
18 | -import com.google.common.base.Function; | |
19 | -import com.google.common.util.concurrent.Futures; | |
20 | 18 | import com.google.common.util.concurrent.ListenableFuture; |
21 | 19 | import lombok.extern.slf4j.Slf4j; |
22 | 20 | import org.apache.commons.lang3.StringUtils; |
... | ... | @@ -31,7 +29,6 @@ import org.thingsboard.server.common.data.id.DashboardId; |
31 | 29 | import org.thingsboard.server.common.data.id.TenantId; |
32 | 30 | import org.thingsboard.server.common.data.page.PageData; |
33 | 31 | import org.thingsboard.server.common.data.page.PageLink; |
34 | -import org.thingsboard.server.common.data.page.TimePageLink; | |
35 | 32 | import org.thingsboard.server.common.data.relation.EntityRelation; |
36 | 33 | import org.thingsboard.server.common.data.relation.RelationTypeGroup; |
37 | 34 | import org.thingsboard.server.dao.customer.CustomerDao; |
... | ... | @@ -39,12 +36,9 @@ import org.thingsboard.server.dao.entity.AbstractEntityService; |
39 | 36 | import org.thingsboard.server.dao.exception.DataValidationException; |
40 | 37 | import org.thingsboard.server.dao.service.DataValidator; |
41 | 38 | import org.thingsboard.server.dao.service.PaginatedRemover; |
42 | -import org.thingsboard.server.dao.service.TimePaginatedRemover; | |
43 | 39 | import org.thingsboard.server.dao.service.Validator; |
44 | 40 | import org.thingsboard.server.dao.tenant.TenantDao; |
45 | 41 | |
46 | -import javax.annotation.Nullable; | |
47 | -import java.util.List; | |
48 | 42 | import java.util.concurrent.ExecutionException; |
49 | 43 | |
50 | 44 | import static org.thingsboard.server.dao.service.Validator.validateId; |
... | ... | @@ -63,7 +57,7 @@ public class DashboardServiceImpl extends AbstractEntityService implements Dashb |
63 | 57 | |
64 | 58 | @Autowired |
65 | 59 | private TenantDao tenantDao; |
66 | - | |
60 | + | |
67 | 61 | @Autowired |
68 | 62 | private CustomerDao customerDao; |
69 | 63 | |
... | ... | @@ -101,7 +95,7 @@ public class DashboardServiceImpl extends AbstractEntityService implements Dashb |
101 | 95 | dashboardValidator.validate(dashboard, DashboardInfo::getTenantId); |
102 | 96 | return dashboardDao.save(dashboard.getTenantId(), dashboard); |
103 | 97 | } |
104 | - | |
98 | + | |
105 | 99 | @Override |
106 | 100 | public Dashboard assignDashboardToCustomer(TenantId tenantId, DashboardId dashboardId, CustomerId customerId) { |
107 | 101 | Dashboard dashboard = findDashboardById(tenantId, dashboardId); |
... | ... | @@ -234,11 +228,11 @@ public class DashboardServiceImpl extends AbstractEntityService implements Dashb |
234 | 228 | } |
235 | 229 | } |
236 | 230 | } |
237 | - }; | |
238 | - | |
231 | + }; | |
232 | + | |
239 | 233 | private PaginatedRemover<TenantId, DashboardInfo> tenantDashboardsRemover = |
240 | 234 | new PaginatedRemover<TenantId, DashboardInfo>() { |
241 | - | |
235 | + | |
242 | 236 | @Override |
243 | 237 | protected PageData<DashboardInfo> findEntities(TenantId tenantId, TenantId id, PageLink pageLink) { |
244 | 238 | return dashboardInfoDao.findDashboardsByTenantId(id.getId(), pageLink); |
... | ... | @@ -267,7 +261,7 @@ public class DashboardServiceImpl extends AbstractEntityService implements Dashb |
267 | 261 | protected void removeEntity(TenantId tenantId, DashboardInfo entity) { |
268 | 262 | unassignDashboardFromCustomer(customer.getTenantId(), new DashboardId(entity.getUuidId()), this.customer.getId()); |
269 | 263 | } |
270 | - | |
264 | + | |
271 | 265 | } |
272 | 266 | |
273 | 267 | private class CustomerDashboardsUpdater extends PaginatedRemover<Customer, DashboardInfo> { | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.dao.device; |
18 | 18 | import com.fasterxml.jackson.databind.ObjectMapper; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | 23 | import org.springframework.beans.factory.annotation.Autowired; |
23 | 24 | import org.springframework.beans.factory.annotation.Value; |
... | ... | @@ -97,9 +98,9 @@ public class ClaimDevicesServiceImpl implements ClaimDevicesService { |
97 | 98 | } |
98 | 99 | log.warn("Failed to find claimingAllowed attribute for device or it is already claimed![{}]", device.getName()); |
99 | 100 | throw new IllegalArgumentException(); |
100 | - }); | |
101 | + }, MoreExecutors.directExecutor()); | |
101 | 102 | } |
102 | - }); | |
103 | + }, MoreExecutors.directExecutor()); | |
103 | 104 | } |
104 | 105 | |
105 | 106 | private ClaimDataInfo getClaimData(Cache cache, Device device) throws ExecutionException, InterruptedException { |
... | ... | @@ -138,9 +139,9 @@ public class ClaimDevicesServiceImpl implements ClaimDevicesService { |
138 | 139 | if (device.getCustomerId().getId().equals(ModelConstants.NULL_UUID)) { |
139 | 140 | device.setCustomerId(customerId); |
140 | 141 | Device savedDevice = deviceService.saveDevice(device); |
141 | - return Futures.transform(removeClaimingSavedData(cache, claimData, device), result -> new ClaimResult(savedDevice, ClaimResponse.SUCCESS)); | |
142 | + return Futures.transform(removeClaimingSavedData(cache, claimData, device), result -> new ClaimResult(savedDevice, ClaimResponse.SUCCESS), MoreExecutors.directExecutor()); | |
142 | 143 | } |
143 | - return Futures.transform(removeClaimingSavedData(cache, claimData, device), result -> new ClaimResult(null, ClaimResponse.CLAIMED)); | |
144 | + return Futures.transform(removeClaimingSavedData(cache, claimData, device), result -> new ClaimResult(null, ClaimResponse.CLAIMED), MoreExecutors.directExecutor()); | |
144 | 145 | } |
145 | 146 | } else { |
146 | 147 | log.warn("Failed to find the device's claiming message![{}]", device.getName()); | ... | ... |
... | ... | @@ -18,6 +18,7 @@ package org.thingsboard.server.dao.device; |
18 | 18 | import com.google.common.base.Function; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | 23 | import org.apache.commons.lang3.RandomStringUtils; |
23 | 24 | import org.hibernate.exception.ConstraintViolationException; |
... | ... | @@ -28,7 +29,13 @@ import org.springframework.cache.annotation.CacheEvict; |
28 | 29 | import org.springframework.cache.annotation.Cacheable; |
29 | 30 | import org.springframework.stereotype.Service; |
30 | 31 | import org.springframework.util.StringUtils; |
31 | -import org.thingsboard.server.common.data.*; | |
32 | +import org.thingsboard.server.common.data.Customer; | |
33 | +import org.thingsboard.server.common.data.Device; | |
34 | +import org.thingsboard.server.common.data.DeviceInfo; | |
35 | +import org.thingsboard.server.common.data.EntitySubtype; | |
36 | +import org.thingsboard.server.common.data.EntityType; | |
37 | +import org.thingsboard.server.common.data.EntityView; | |
38 | +import org.thingsboard.server.common.data.Tenant; | |
32 | 39 | import org.thingsboard.server.common.data.device.DeviceSearchQuery; |
33 | 40 | import org.thingsboard.server.common.data.id.CustomerId; |
34 | 41 | import org.thingsboard.server.common.data.id.DeviceId; |
... | ... | @@ -325,7 +332,7 @@ public class DeviceServiceImpl extends AbstractEntityService implements DeviceSe |
325 | 332 | } |
326 | 333 | } |
327 | 334 | return Futures.successfulAsList(futures); |
328 | - }); | |
335 | + }, MoreExecutors.directExecutor()); | |
329 | 336 | |
330 | 337 | devices = Futures.transform(devices, new Function<List<Device>, List<Device>>() { |
331 | 338 | @Nullable |
... | ... | @@ -333,7 +340,7 @@ public class DeviceServiceImpl extends AbstractEntityService implements DeviceSe |
333 | 340 | public List<Device> apply(@Nullable List<Device> deviceList) { |
334 | 341 | return deviceList == null ? Collections.emptyList() : deviceList.stream().filter(device -> query.getDeviceTypes().contains(device.getType())).collect(Collectors.toList()); |
335 | 342 | } |
336 | - }); | |
343 | + }, MoreExecutors.directExecutor()); | |
337 | 344 | |
338 | 345 | return devices; |
339 | 346 | } |
... | ... | @@ -347,7 +354,7 @@ public class DeviceServiceImpl extends AbstractEntityService implements DeviceSe |
347 | 354 | deviceTypes -> { |
348 | 355 | deviceTypes.sort(Comparator.comparing(EntitySubtype::getType)); |
349 | 356 | return deviceTypes; |
350 | - }); | |
357 | + }, MoreExecutors.directExecutor()); | |
351 | 358 | } |
352 | 359 | |
353 | 360 | private DataValidator<Device> deviceValidator = |
... | ... | @@ -408,18 +415,18 @@ public class DeviceServiceImpl extends AbstractEntityService implements DeviceSe |
408 | 415 | }; |
409 | 416 | |
410 | 417 | private PaginatedRemover<TenantId, Device> tenantDevicesRemover = |
411 | - new PaginatedRemover<TenantId, Device>() { | |
418 | + new PaginatedRemover<TenantId, Device>() { | |
412 | 419 | |
413 | - @Override | |
414 | - protected PageData<Device> findEntities(TenantId tenantId, TenantId id, PageLink pageLink) { | |
415 | - return deviceDao.findDevicesByTenantId(id.getId(), pageLink); | |
416 | - } | |
420 | + @Override | |
421 | + protected PageData<Device> findEntities(TenantId tenantId, TenantId id, PageLink pageLink) { | |
422 | + return deviceDao.findDevicesByTenantId(id.getId(), pageLink); | |
423 | + } | |
417 | 424 | |
418 | - @Override | |
419 | - protected void removeEntity(TenantId tenantId, Device entity) { | |
420 | - deleteDevice(tenantId, new DeviceId(entity.getUuidId())); | |
421 | - } | |
422 | - }; | |
425 | + @Override | |
426 | + protected void removeEntity(TenantId tenantId, Device entity) { | |
427 | + deleteDevice(tenantId, new DeviceId(entity.getUuidId())); | |
428 | + } | |
429 | + }; | |
423 | 430 | |
424 | 431 | private PaginatedRemover<CustomerId, Device> customerDeviceUnasigner = new PaginatedRemover<CustomerId, Device>() { |
425 | 432 | ... | ... |
... | ... | @@ -18,12 +18,21 @@ package org.thingsboard.server.dao.entity; |
18 | 18 | import com.google.common.base.Function; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | 23 | import org.springframework.beans.factory.annotation.Autowired; |
23 | 24 | import org.springframework.stereotype.Service; |
24 | 25 | import org.thingsboard.server.common.data.HasName; |
25 | 26 | import org.thingsboard.server.common.data.alarm.AlarmId; |
26 | -import org.thingsboard.server.common.data.id.*; | |
27 | +import org.thingsboard.server.common.data.id.AssetId; | |
28 | +import org.thingsboard.server.common.data.id.CustomerId; | |
29 | +import org.thingsboard.server.common.data.id.DashboardId; | |
30 | +import org.thingsboard.server.common.data.id.DeviceId; | |
31 | +import org.thingsboard.server.common.data.id.EntityId; | |
32 | +import org.thingsboard.server.common.data.id.EntityViewId; | |
33 | +import org.thingsboard.server.common.data.id.RuleChainId; | |
34 | +import org.thingsboard.server.common.data.id.TenantId; | |
35 | +import org.thingsboard.server.common.data.id.UserId; | |
27 | 36 | import org.thingsboard.server.dao.alarm.AlarmService; |
28 | 37 | import org.thingsboard.server.dao.asset.AssetService; |
29 | 38 | import org.thingsboard.server.dao.customer.CustomerService; |
... | ... | @@ -109,7 +118,7 @@ public class BaseEntityService extends AbstractEntityService implements EntitySe |
109 | 118 | default: |
110 | 119 | throw new IllegalStateException("Not Implemented!"); |
111 | 120 | } |
112 | - entityName = Futures.transform(hasName, (Function<HasName, String>) hasName1 -> hasName1 != null ? hasName1.getName() : null ); | |
121 | + entityName = Futures.transform(hasName, (Function<HasName, String>) hasName1 -> hasName1 != null ? hasName1.getName() : null, MoreExecutors.directExecutor()); | |
113 | 122 | return entityName; |
114 | 123 | } |
115 | 124 | ... | ... |
... | ... | @@ -19,6 +19,7 @@ import com.google.common.base.Function; |
19 | 19 | import com.google.common.util.concurrent.FutureCallback; |
20 | 20 | import com.google.common.util.concurrent.Futures; |
21 | 21 | import com.google.common.util.concurrent.ListenableFuture; |
22 | +import com.google.common.util.concurrent.MoreExecutors; | |
22 | 23 | import lombok.extern.slf4j.Slf4j; |
23 | 24 | import org.apache.commons.lang3.StringUtils; |
24 | 25 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -238,7 +239,7 @@ public class EntityViewServiceImpl extends AbstractEntityService implements Enti |
238 | 239 | } |
239 | 240 | } |
240 | 241 | return Futures.successfulAsList(futures); |
241 | - }); | |
242 | + }, MoreExecutors.directExecutor()); | |
242 | 243 | |
243 | 244 | entityViews = Futures.transform(entityViews, new Function<List<EntityView>, List<EntityView>>() { |
244 | 245 | @Nullable |
... | ... | @@ -246,7 +247,7 @@ public class EntityViewServiceImpl extends AbstractEntityService implements Enti |
246 | 247 | public List<EntityView> apply(@Nullable List<EntityView> entityViewList) { |
247 | 248 | return entityViewList == null ? Collections.emptyList() : entityViewList.stream().filter(entityView -> query.getEntityViewTypes().contains(entityView.getType())).collect(Collectors.toList()); |
248 | 249 | } |
249 | - }); | |
250 | + }, MoreExecutors.directExecutor()); | |
250 | 251 | |
251 | 252 | return entityViews; |
252 | 253 | } |
... | ... | @@ -285,7 +286,7 @@ public class EntityViewServiceImpl extends AbstractEntityService implements Enti |
285 | 286 | public void onFailure(Throwable t) { |
286 | 287 | log.error("Error while finding entity views by tenantId and entityId", t); |
287 | 288 | } |
288 | - }); | |
289 | + }, MoreExecutors.directExecutor()); | |
289 | 290 | return entityViewsFuture; |
290 | 291 | } |
291 | 292 | } |
... | ... | @@ -318,7 +319,7 @@ public class EntityViewServiceImpl extends AbstractEntityService implements Enti |
318 | 319 | entityViewTypes -> { |
319 | 320 | entityViewTypes.sort(Comparator.comparing(EntitySubtype::getType)); |
320 | 321 | return entityViewTypes; |
321 | - }); | |
322 | + }, MoreExecutors.directExecutor()); | |
322 | 323 | } |
323 | 324 | |
324 | 325 | private DataValidator<EntityView> entityViewValidator = | ... | ... |
... | ... | @@ -36,6 +36,7 @@ import static org.thingsboard.server.dao.model.ModelConstants.BOOLEAN_VALUE_COLU |
36 | 36 | import static org.thingsboard.server.dao.model.ModelConstants.DOUBLE_VALUE_COLUMN; |
37 | 37 | import static org.thingsboard.server.dao.model.ModelConstants.ENTITY_ID_COLUMN; |
38 | 38 | import static org.thingsboard.server.dao.model.ModelConstants.JSON_VALUE_COLUMN; |
39 | +import static org.thingsboard.server.dao.model.ModelConstants.KEY_COLUMN; | |
39 | 40 | import static org.thingsboard.server.dao.model.ModelConstants.LONG_VALUE_COLUMN; |
40 | 41 | import static org.thingsboard.server.dao.model.ModelConstants.STRING_VALUE_COLUMN; |
41 | 42 | import static org.thingsboard.server.dao.model.ModelConstants.TS_COLUMN; |
... | ... | @@ -54,6 +55,10 @@ public abstract class AbstractTsKvEntity implements ToData<TsKvEntry> { |
54 | 55 | protected UUID entityId; |
55 | 56 | |
56 | 57 | @Id |
58 | + @Column(name = KEY_COLUMN) | |
59 | + protected int key; | |
60 | + | |
61 | + @Id | |
57 | 62 | @Column(name = TS_COLUMN) |
58 | 63 | protected Long ts; |
59 | 64 | ... | ... |
... | ... | @@ -69,10 +69,6 @@ import static org.thingsboard.server.dao.model.ModelConstants.KEY_COLUMN; |
69 | 69 | }) |
70 | 70 | public final class TsKvLatestEntity extends AbstractTsKvEntity { |
71 | 71 | |
72 | - @Id | |
73 | - @Column(name = KEY_COLUMN) | |
74 | - private int key; | |
75 | - | |
76 | 72 | @Override |
77 | 73 | public boolean isNotEmpty() { |
78 | 74 | return strValue != null || longValue != null || doubleValue != null || booleanValue != null || jsonValue != null; | ... | ... |
... | ... | @@ -18,25 +18,18 @@ package org.thingsboard.server.dao.model.sqlts.timescale.ts; |
18 | 18 | import lombok.Data; |
19 | 19 | import lombok.EqualsAndHashCode; |
20 | 20 | import org.springframework.util.StringUtils; |
21 | -import org.thingsboard.server.common.data.kv.TsKvEntry; | |
22 | -import org.thingsboard.server.dao.model.ToData; | |
23 | 21 | import org.thingsboard.server.dao.model.sql.AbstractTsKvEntity; |
24 | 22 | |
25 | -import javax.persistence.Column; | |
26 | 23 | import javax.persistence.ColumnResult; |
27 | 24 | import javax.persistence.ConstructorResult; |
28 | 25 | import javax.persistence.Entity; |
29 | -import javax.persistence.Id; | |
30 | 26 | import javax.persistence.IdClass; |
31 | 27 | import javax.persistence.NamedNativeQueries; |
32 | 28 | import javax.persistence.NamedNativeQuery; |
33 | 29 | import javax.persistence.SqlResultSetMapping; |
34 | 30 | import javax.persistence.SqlResultSetMappings; |
35 | 31 | import javax.persistence.Table; |
36 | -import java.util.UUID; | |
37 | 32 | |
38 | -import static org.thingsboard.server.dao.model.ModelConstants.KEY_COLUMN; | |
39 | -import static org.thingsboard.server.dao.model.ModelConstants.TENANT_ID_COLUMN; | |
40 | 33 | import static org.thingsboard.server.dao.sqlts.timescale.AggregationRepository.FIND_AVG; |
41 | 34 | import static org.thingsboard.server.dao.sqlts.timescale.AggregationRepository.FIND_AVG_QUERY; |
42 | 35 | import static org.thingsboard.server.dao.sqlts.timescale.AggregationRepository.FIND_COUNT; |
... | ... | @@ -52,7 +45,7 @@ import static org.thingsboard.server.dao.sqlts.timescale.AggregationRepository.F |
52 | 45 | @Data |
53 | 46 | @EqualsAndHashCode(callSuper = true) |
54 | 47 | @Entity |
55 | -@Table(name = "tenant_ts_kv") | |
48 | +@Table(name = "ts_kv") | |
56 | 49 | @IdClass(TimescaleTsKvCompositeKey.class) |
57 | 50 | @SqlResultSetMappings({ |
58 | 51 | @SqlResultSetMapping( |
... | ... | @@ -116,15 +109,7 @@ import static org.thingsboard.server.dao.sqlts.timescale.AggregationRepository.F |
116 | 109 | resultSetMapping = "timescaleCountMapping" |
117 | 110 | ) |
118 | 111 | }) |
119 | -public final class TimescaleTsKvEntity extends AbstractTsKvEntity implements ToData<TsKvEntry> { | |
120 | - | |
121 | - @Id | |
122 | - @Column(name = TENANT_ID_COLUMN, columnDefinition = "uuid") | |
123 | - private UUID tenantId; | |
124 | - | |
125 | - @Id | |
126 | - @Column(name = KEY_COLUMN) | |
127 | - private int key; | |
112 | +public final class TimescaleTsKvEntity extends AbstractTsKvEntity { | |
128 | 113 | |
129 | 114 | public TimescaleTsKvEntity() { |
130 | 115 | } | ... | ... |
... | ... | @@ -32,10 +32,6 @@ import static org.thingsboard.server.dao.model.ModelConstants.KEY_COLUMN; |
32 | 32 | @IdClass(TsKvCompositeKey.class) |
33 | 33 | public final class TsKvEntity extends AbstractTsKvEntity { |
34 | 34 | |
35 | - @Id | |
36 | - @Column(name = KEY_COLUMN) | |
37 | - private int key; | |
38 | - | |
39 | 35 | public TsKvEntity() { |
40 | 36 | } |
41 | 37 | ... | ... |
... | ... | @@ -22,6 +22,7 @@ import com.datastax.driver.core.Statement; |
22 | 22 | import com.google.common.util.concurrent.FutureCallback; |
23 | 23 | import com.google.common.util.concurrent.Futures; |
24 | 24 | import com.google.common.util.concurrent.ListenableFuture; |
25 | +import com.google.common.util.concurrent.MoreExecutors; | |
25 | 26 | import com.google.common.util.concurrent.Uninterruptibles; |
26 | 27 | import org.thingsboard.server.dao.exception.BufferLimitException; |
27 | 28 | import org.thingsboard.server.dao.util.AsyncRateLimiter; |
... | ... | @@ -44,9 +45,9 @@ public class RateLimitedResultSetFuture implements ResultSetFuture { |
44 | 45 | rateLimiter.release(); |
45 | 46 | } |
46 | 47 | return Futures.immediateFailedFuture(t); |
47 | - }); | |
48 | + }, MoreExecutors.directExecutor()); | |
48 | 49 | this.originalFuture = Futures.transform(rateLimitFuture, |
49 | - i -> executeAsyncWithRelease(rateLimiter, session, statement)); | |
50 | + i -> executeAsyncWithRelease(rateLimiter, session, statement), MoreExecutors.directExecutor()); | |
50 | 51 | |
51 | 52 | } |
52 | 53 | |
... | ... | @@ -145,7 +146,7 @@ public class RateLimitedResultSetFuture implements ResultSetFuture { |
145 | 146 | public void onFailure(Throwable t) { |
146 | 147 | rateLimiter.release(); |
147 | 148 | } |
148 | - }); | |
149 | + }, MoreExecutors.directExecutor()); | |
149 | 150 | return resultSetFuture; |
150 | 151 | } catch (RuntimeException re) { |
151 | 152 | rateLimiter.release(); | ... | ... |
... | ... | @@ -16,7 +16,10 @@ |
16 | 16 | package org.thingsboard.server.dao.relation; |
17 | 17 | |
18 | 18 | import com.google.common.base.Function; |
19 | -import com.google.common.util.concurrent.*; | |
19 | +import com.google.common.util.concurrent.FutureCallback; | |
20 | +import com.google.common.util.concurrent.Futures; | |
21 | +import com.google.common.util.concurrent.ListenableFuture; | |
22 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 23 | import lombok.extern.slf4j.Slf4j; |
21 | 24 | import org.springframework.beans.factory.annotation.Autowired; |
22 | 25 | import org.springframework.cache.Cache; |
... | ... | @@ -206,17 +209,20 @@ public class BaseRelationService implements RelationService { |
206 | 209 | relations -> { |
207 | 210 | List<ListenableFuture<Boolean>> results = deleteRelationGroupsAsync(tenantId, relations, cache, true); |
208 | 211 | return Futures.allAsList(results); |
209 | - }); | |
212 | + }, MoreExecutors.directExecutor()); | |
210 | 213 | |
211 | 214 | ListenableFuture<List<Boolean>> outboundDeletions = Futures.transformAsync(outboundRelations, |
212 | 215 | relations -> { |
213 | 216 | List<ListenableFuture<Boolean>> results = deleteRelationGroupsAsync(tenantId, relations, cache, false); |
214 | 217 | return Futures.allAsList(results); |
215 | - }); | |
218 | + }, MoreExecutors.directExecutor()); | |
216 | 219 | |
217 | 220 | ListenableFuture<List<List<Boolean>>> deletionsFuture = Futures.allAsList(inboundDeletions, outboundDeletions); |
218 | 221 | |
219 | - return Futures.transform(Futures.transformAsync(deletionsFuture, (deletions) -> relationDao.deleteOutboundRelationsAsync(tenantId, entityId)), result -> null); | |
222 | + return Futures.transform(Futures.transformAsync(deletionsFuture, | |
223 | + (deletions) -> relationDao.deleteOutboundRelationsAsync(tenantId, entityId), | |
224 | + MoreExecutors.directExecutor()), | |
225 | + result -> null, MoreExecutors.directExecutor()); | |
220 | 226 | } |
221 | 227 | |
222 | 228 | private List<ListenableFuture<Boolean>> deleteRelationGroupsAsync(TenantId tenantId, List<List<EntityRelation>> relations, Cache cache, boolean deleteFromDb) { |
... | ... | @@ -306,9 +312,11 @@ public class BaseRelationService implements RelationService { |
306 | 312 | public void onSuccess(@Nullable List<EntityRelation> result) { |
307 | 313 | cache.putIfAbsent(fromAndTypeGroup, result); |
308 | 314 | } |
315 | + | |
309 | 316 | @Override |
310 | - public void onFailure(Throwable t) {} | |
311 | - }); | |
317 | + public void onFailure(Throwable t) { | |
318 | + } | |
319 | + }, MoreExecutors.directExecutor()); | |
312 | 320 | return relationsFuture; |
313 | 321 | } |
314 | 322 | } |
... | ... | @@ -328,7 +336,7 @@ public class BaseRelationService implements RelationService { |
328 | 336 | EntityRelationInfo::setToName)) |
329 | 337 | ); |
330 | 338 | return Futures.successfulAsList(futures); |
331 | - }); | |
339 | + }, MoreExecutors.directExecutor()); | |
332 | 340 | } |
333 | 341 | |
334 | 342 | @Cacheable(cacheNames = RELATIONS_CACHE, key = "{#from, #relationType, #typeGroup, 'FROM'}") |
... | ... | @@ -385,9 +393,11 @@ public class BaseRelationService implements RelationService { |
385 | 393 | public void onSuccess(@Nullable List<EntityRelation> result) { |
386 | 394 | cache.putIfAbsent(toAndTypeGroup, result); |
387 | 395 | } |
396 | + | |
388 | 397 | @Override |
389 | - public void onFailure(Throwable t) {} | |
390 | - }); | |
398 | + public void onFailure(Throwable t) { | |
399 | + } | |
400 | + }, MoreExecutors.directExecutor()); | |
391 | 401 | return relationsFuture; |
392 | 402 | } |
393 | 403 | } |
... | ... | @@ -407,7 +417,7 @@ public class BaseRelationService implements RelationService { |
407 | 417 | EntityRelationInfo::setFromName)) |
408 | 418 | ); |
409 | 419 | return Futures.successfulAsList(futures); |
410 | - }); | |
420 | + }, MoreExecutors.directExecutor()); | |
411 | 421 | } |
412 | 422 | |
413 | 423 | private ListenableFuture<EntityRelationInfo> fetchRelationInfoAsync(TenantId tenantId, EntityRelation relation, |
... | ... | @@ -418,7 +428,7 @@ public class BaseRelationService implements RelationService { |
418 | 428 | EntityRelationInfo entityRelationInfo1 = new EntityRelationInfo(relation); |
419 | 429 | entityNameSetter.accept(entityRelationInfo1, entityName1); |
420 | 430 | return entityRelationInfo1; |
421 | - }); | |
431 | + }, MoreExecutors.directExecutor()); | |
422 | 432 | } |
423 | 433 | |
424 | 434 | @Cacheable(cacheNames = RELATIONS_CACHE, key = "{#to, #relationType, #typeGroup, 'TO'}") |
... | ... | @@ -466,7 +476,7 @@ public class BaseRelationService implements RelationService { |
466 | 476 | } |
467 | 477 | } |
468 | 478 | return relations; |
469 | - }); | |
479 | + }, MoreExecutors.directExecutor()); | |
470 | 480 | } catch (Exception e) { |
471 | 481 | log.warn("Failed to query relations: [{}]", query, e); |
472 | 482 | throw new RuntimeException(e); |
... | ... | @@ -493,7 +503,7 @@ public class BaseRelationService implements RelationService { |
493 | 503 | })) |
494 | 504 | ); |
495 | 505 | return Futures.successfulAsList(futures); |
496 | - }); | |
506 | + }, MoreExecutors.directExecutor()); | |
497 | 507 | } |
498 | 508 | |
499 | 509 | protected void validate(EntityRelation relation) { |
... | ... | @@ -600,7 +610,7 @@ public class BaseRelationService implements RelationService { |
600 | 610 | } |
601 | 611 | //TODO: try to remove this blocking operation |
602 | 612 | List<Set<EntityRelation>> relations = Futures.successfulAsList(futures).get(); |
603 | - if (fetchLastLevelOnly && lvl > 0){ | |
613 | + if (fetchLastLevelOnly && lvl > 0) { | |
604 | 614 | children.clear(); |
605 | 615 | } |
606 | 616 | relations.forEach(r -> r.forEach(children::add)); | ... | ... |
... | ... | @@ -15,14 +15,12 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.dao.sql.alarm; |
17 | 17 | |
18 | -import com.google.common.util.concurrent.Futures; | |
19 | 18 | import com.google.common.util.concurrent.ListenableFuture; |
20 | 19 | import lombok.extern.slf4j.Slf4j; |
21 | 20 | import org.springframework.beans.factory.annotation.Autowired; |
22 | 21 | import org.springframework.data.domain.PageRequest; |
23 | 22 | import org.springframework.data.repository.CrudRepository; |
24 | 23 | import org.springframework.stereotype.Component; |
25 | -import org.thingsboard.server.common.data.EntityType; | |
26 | 24 | import org.thingsboard.server.common.data.UUIDConverter; |
27 | 25 | import org.thingsboard.server.common.data.alarm.Alarm; |
28 | 26 | import org.thingsboard.server.common.data.alarm.AlarmInfo; |
... | ... | @@ -31,8 +29,6 @@ import org.thingsboard.server.common.data.alarm.AlarmSearchStatus; |
31 | 29 | import org.thingsboard.server.common.data.id.EntityId; |
32 | 30 | import org.thingsboard.server.common.data.id.TenantId; |
33 | 31 | import org.thingsboard.server.common.data.page.PageData; |
34 | -import org.thingsboard.server.common.data.relation.EntityRelation; | |
35 | -import org.thingsboard.server.common.data.relation.RelationTypeGroup; | |
36 | 32 | import org.thingsboard.server.dao.DaoUtil; |
37 | 33 | import org.thingsboard.server.dao.alarm.AlarmDao; |
38 | 34 | import org.thingsboard.server.dao.alarm.BaseAlarmService; |
... | ... | @@ -41,7 +37,6 @@ import org.thingsboard.server.dao.relation.RelationDao; |
41 | 37 | import org.thingsboard.server.dao.sql.JpaAbstractDao; |
42 | 38 | import org.thingsboard.server.dao.util.SqlDao; |
43 | 39 | |
44 | -import java.util.ArrayList; | |
45 | 40 | import java.util.List; |
46 | 41 | import java.util.Objects; |
47 | 42 | import java.util.UUID; | ... | ... |
... | ... | @@ -15,23 +15,14 @@ |
15 | 15 | */ |
16 | 16 | package org.thingsboard.server.dao.sql.dashboard; |
17 | 17 | |
18 | -import com.google.common.util.concurrent.Futures; | |
19 | -import com.google.common.util.concurrent.ListenableFuture; | |
20 | 18 | import lombok.extern.slf4j.Slf4j; |
21 | 19 | import org.springframework.beans.factory.annotation.Autowired; |
22 | -import org.springframework.data.domain.PageRequest; | |
23 | 20 | import org.springframework.data.repository.CrudRepository; |
24 | 21 | import org.springframework.stereotype.Component; |
25 | 22 | import org.thingsboard.server.common.data.DashboardInfo; |
26 | -import org.thingsboard.server.common.data.EntityType; | |
27 | 23 | import org.thingsboard.server.common.data.UUIDConverter; |
28 | -import org.thingsboard.server.common.data.id.CustomerId; | |
29 | -import org.thingsboard.server.common.data.id.TenantId; | |
30 | 24 | import org.thingsboard.server.common.data.page.PageData; |
31 | 25 | import org.thingsboard.server.common.data.page.PageLink; |
32 | -import org.thingsboard.server.common.data.page.TimePageLink; | |
33 | -import org.thingsboard.server.common.data.relation.EntityRelation; | |
34 | -import org.thingsboard.server.common.data.relation.RelationTypeGroup; | |
35 | 26 | import org.thingsboard.server.dao.DaoUtil; |
36 | 27 | import org.thingsboard.server.dao.dashboard.DashboardInfoDao; |
37 | 28 | import org.thingsboard.server.dao.model.sql.DashboardInfoEntity; |
... | ... | @@ -39,13 +30,9 @@ import org.thingsboard.server.dao.relation.RelationDao; |
39 | 30 | import org.thingsboard.server.dao.sql.JpaAbstractSearchTextDao; |
40 | 31 | import org.thingsboard.server.dao.util.SqlDao; |
41 | 32 | |
42 | -import java.util.ArrayList; | |
43 | -import java.util.List; | |
44 | 33 | import java.util.Objects; |
45 | 34 | import java.util.UUID; |
46 | 35 | |
47 | -import static org.thingsboard.server.dao.model.ModelConstants.NULL_UUID_STR; | |
48 | - | |
49 | 36 | /** |
50 | 37 | * Created by Valerii Sosliuk on 5/6/2017. |
51 | 38 | */ | ... | ... |
dao/src/main/java/org/thingsboard/server/dao/sql/relation/AbstractRelationInsertRepository.java
0 → 100644
1 | +/** | |
2 | + * Copyright © 2016-2020 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.dao.sql.relation; | |
17 | + | |
18 | +import lombok.extern.slf4j.Slf4j; | |
19 | +import org.springframework.data.jpa.repository.Modifying; | |
20 | +import org.thingsboard.server.dao.model.sql.RelationEntity; | |
21 | + | |
22 | +import javax.persistence.EntityManager; | |
23 | +import javax.persistence.PersistenceContext; | |
24 | +import javax.persistence.Query; | |
25 | + | |
26 | +@Slf4j | |
27 | +public abstract class AbstractRelationInsertRepository implements RelationInsertRepository { | |
28 | + | |
29 | + @PersistenceContext | |
30 | + protected EntityManager entityManager; | |
31 | + | |
32 | + protected Query getQuery(RelationEntity entity, String query) { | |
33 | + Query nativeQuery = entityManager.createNativeQuery(query, RelationEntity.class); | |
34 | + if (entity.getAdditionalInfo() == null) { | |
35 | + nativeQuery.setParameter("additionalInfo", null); | |
36 | + } else { | |
37 | + nativeQuery.setParameter("additionalInfo", entity.getAdditionalInfo().toString()); | |
38 | + } | |
39 | + return nativeQuery | |
40 | + .setParameter("fromId", entity.getFromId()) | |
41 | + .setParameter("fromType", entity.getFromType()) | |
42 | + .setParameter("toId", entity.getToId()) | |
43 | + .setParameter("toType", entity.getToType()) | |
44 | + .setParameter("relationTypeGroup", entity.getRelationTypeGroup()) | |
45 | + .setParameter("relationType", entity.getRelationType()); | |
46 | + } | |
47 | + | |
48 | + @Modifying | |
49 | + protected abstract RelationEntity processSaveOrUpdate(RelationEntity entity); | |
50 | + | |
51 | +} | |
\ No newline at end of file | ... | ... |
dao/src/main/java/org/thingsboard/server/dao/sql/relation/HsqlRelationInsertRepository.java
0 → 100644
1 | +/** | |
2 | + * Copyright © 2016-2020 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.dao.sql.relation; | |
17 | + | |
18 | +import org.springframework.stereotype.Repository; | |
19 | +import org.springframework.transaction.annotation.Transactional; | |
20 | +import org.thingsboard.server.dao.model.sql.RelationCompositeKey; | |
21 | +import org.thingsboard.server.dao.model.sql.RelationEntity; | |
22 | +import org.thingsboard.server.dao.util.HsqlDao; | |
23 | +import org.thingsboard.server.dao.util.SqlDao; | |
24 | + | |
25 | +@HsqlDao | |
26 | +@SqlDao | |
27 | +@Repository | |
28 | +@Transactional | |
29 | +public class HsqlRelationInsertRepository extends AbstractRelationInsertRepository implements RelationInsertRepository { | |
30 | + | |
31 | + private static final String INSERT_ON_CONFLICT_DO_UPDATE = "MERGE INTO relation USING (VALUES :fromId, :fromType, :toId, :toType, :relationTypeGroup, :relationType, :additionalInfo) R " + | |
32 | + "(from_id, from_type, to_id, to_type, relation_type_group, relation_type, additional_info) " + | |
33 | + "ON (relation.from_id = R.from_id AND relation.from_type = R.from_type AND relation.relation_type_group = R.relation_type_group AND relation.relation_type = R.relation_type AND relation.to_id = R.to_id AND relation.to_type = R.to_type) " + | |
34 | + "WHEN MATCHED THEN UPDATE SET relation.additional_info = R.additional_info " + | |
35 | + "WHEN NOT MATCHED THEN INSERT (from_id, from_type, to_id, to_type, relation_type_group, relation_type, additional_info) VALUES (R.from_id, R.from_type, R.to_id, R.to_type, R.relation_type_group, R.relation_type, R.additional_info)"; | |
36 | + | |
37 | + @Override | |
38 | + public RelationEntity saveOrUpdate(RelationEntity entity) { | |
39 | + return processSaveOrUpdate(entity); | |
40 | + } | |
41 | + | |
42 | + @Override | |
43 | + protected RelationEntity processSaveOrUpdate(RelationEntity entity) { | |
44 | + getQuery(entity, INSERT_ON_CONFLICT_DO_UPDATE).executeUpdate(); | |
45 | + return entityManager.find(RelationEntity.class, new RelationCompositeKey(entity.toData())); | |
46 | + } | |
47 | +} | ... | ... |
... | ... | @@ -58,6 +58,9 @@ public class JpaRelationDao extends JpaAbstractDaoListeningExecutorService imple |
58 | 58 | @Autowired |
59 | 59 | private RelationRepository relationRepository; |
60 | 60 | |
61 | + @Autowired | |
62 | + private RelationInsertRepository relationInsertRepository; | |
63 | + | |
61 | 64 | @Override |
62 | 65 | public ListenableFuture<List<EntityRelation>> findAllByFrom(TenantId tenantId, EntityId from, RelationTypeGroup typeGroup) { |
63 | 66 | return service.submit(() -> DaoUtil.convertDataList( |
... | ... | @@ -119,12 +122,12 @@ public class JpaRelationDao extends JpaAbstractDaoListeningExecutorService imple |
119 | 122 | |
120 | 123 | @Override |
121 | 124 | public boolean saveRelation(TenantId tenantId, EntityRelation relation) { |
122 | - return relationRepository.save(new RelationEntity(relation)) != null; | |
125 | + return relationInsertRepository.saveOrUpdate(new RelationEntity(relation)) != null; | |
123 | 126 | } |
124 | 127 | |
125 | 128 | @Override |
126 | 129 | public ListenableFuture<Boolean> saveRelationAsync(TenantId tenantId, EntityRelation relation) { |
127 | - return service.submit(() -> relationRepository.save(new RelationEntity(relation)) != null); | |
130 | + return service.submit(() -> relationInsertRepository.saveOrUpdate(new RelationEntity(relation)) != null); | |
128 | 131 | } |
129 | 132 | |
130 | 133 | @Override | ... | ... |
dao/src/main/java/org/thingsboard/server/dao/sql/relation/PsqlRelationInsertRepository.java
0 → 100644
1 | +/** | |
2 | + * Copyright © 2016-2020 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.dao.sql.relation; | |
17 | + | |
18 | +import org.springframework.stereotype.Repository; | |
19 | +import org.springframework.transaction.annotation.Transactional; | |
20 | +import org.thingsboard.server.dao.model.sql.RelationEntity; | |
21 | +import org.thingsboard.server.dao.util.PsqlDao; | |
22 | +import org.thingsboard.server.dao.util.SqlDao; | |
23 | + | |
24 | +@PsqlDao | |
25 | +@SqlDao | |
26 | +@Repository | |
27 | +@Transactional | |
28 | +public class PsqlRelationInsertRepository extends AbstractRelationInsertRepository implements RelationInsertRepository { | |
29 | + | |
30 | + private static final String INSERT_ON_CONFLICT_DO_UPDATE = "INSERT INTO relation (from_id, from_type, to_id, to_type, relation_type_group, relation_type, additional_info)" + | |
31 | + " VALUES (:fromId, :fromType, :toId, :toType, :relationTypeGroup, :relationType, :additionalInfo) " + | |
32 | + "ON CONFLICT (from_id, from_type, relation_type_group, relation_type, to_id, to_type) DO UPDATE SET additional_info = :additionalInfo returning *"; | |
33 | + | |
34 | + @Override | |
35 | + public RelationEntity saveOrUpdate(RelationEntity entity) { | |
36 | + return processSaveOrUpdate(entity); | |
37 | + } | |
38 | + | |
39 | + @Override | |
40 | + protected RelationEntity processSaveOrUpdate(RelationEntity entity) { | |
41 | + return (RelationEntity) getQuery(entity, INSERT_ON_CONFLICT_DO_UPDATE).getSingleResult(); | |
42 | + } | |
43 | +} | ... | ... |
1 | +/** | |
2 | + * Copyright © 2016-2020 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.server.dao.sql.relation; | |
17 | + | |
18 | +import org.thingsboard.server.dao.model.sql.RelationEntity; | |
19 | + | |
20 | +public interface RelationInsertRepository { | |
21 | + | |
22 | + RelationEntity saveOrUpdate(RelationEntity entity); | |
23 | + | |
24 | +} | |
\ No newline at end of file | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.server.dao.sqlts; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import com.google.common.util.concurrent.SettableFuture; |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | 23 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -95,7 +96,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
95 | 96 | |
96 | 97 | @Override |
97 | 98 | public ListenableFuture<Void> removeLatest(TenantId tenantId, EntityId entityId, DeleteTsKvQuery query) { |
98 | - return getRemoveLatestFuture(tenantId, entityId, query); | |
99 | + return getRemoveLatestFuture(entityId, query); | |
99 | 100 | } |
100 | 101 | |
101 | 102 | @Override |
... | ... | @@ -124,9 +125,9 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
124 | 125 | } |
125 | 126 | |
126 | 127 | @Override |
127 | - protected ListenableFuture<List<TsKvEntry>> findAllAsync(TenantId tenantId, EntityId entityId, ReadTsKvQuery query) { | |
128 | + protected ListenableFuture<List<TsKvEntry>> findAllAsync(EntityId entityId, ReadTsKvQuery query) { | |
128 | 129 | if (query.getAggregation() == Aggregation.NONE) { |
129 | - return findAllAsyncWithLimit(tenantId, entityId, query); | |
130 | + return findAllAsyncWithLimit(entityId, query); | |
130 | 131 | } else { |
131 | 132 | long stepTs = query.getStartTs(); |
132 | 133 | List<ListenableFuture<Optional<TsKvEntry>>> futures = new ArrayList<>(); |
... | ... | @@ -134,7 +135,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
134 | 135 | long startTs = stepTs; |
135 | 136 | long endTs = stepTs + query.getInterval(); |
136 | 137 | long ts = startTs + (endTs - startTs) / 2; |
137 | - futures.add(findAndAggregateAsync(tenantId, entityId, query.getKey(), startTs, endTs, ts, query.getAggregation())); | |
138 | + futures.add(findAndAggregateAsync(entityId, query.getKey(), startTs, endTs, ts, query.getAggregation())); | |
138 | 139 | stepTs = endTs; |
139 | 140 | } |
140 | 141 | return getTskvEntriesFuture(Futures.allAsList(futures)); |
... | ... | @@ -142,7 +143,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
142 | 143 | } |
143 | 144 | |
144 | 145 | @Override |
145 | - protected ListenableFuture<List<TsKvEntry>> findAllAsyncWithLimit(TenantId tenantId, EntityId entityId, ReadTsKvQuery query) { | |
146 | + protected ListenableFuture<List<TsKvEntry>> findAllAsyncWithLimit(EntityId entityId, ReadTsKvQuery query) { | |
146 | 147 | Integer keyId = getOrSaveKeyId(query.getKey()); |
147 | 148 | List<TsKvEntity> tsKvEntities = tsKvRepository.findAllWithLimit( |
148 | 149 | entityId.getId(), |
... | ... | @@ -156,9 +157,9 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
156 | 157 | return Futures.immediateFuture(DaoUtil.convertDataList(tsKvEntities)); |
157 | 158 | } |
158 | 159 | |
159 | - protected ListenableFuture<Optional<TsKvEntry>> findAndAggregateAsync(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, long ts, Aggregation aggregation) { | |
160 | + private ListenableFuture<Optional<TsKvEntry>> findAndAggregateAsync(EntityId entityId, String key, long startTs, long endTs, long ts, Aggregation aggregation) { | |
160 | 161 | List<CompletableFuture<TsKvEntity>> entitiesFutures = new ArrayList<>(); |
161 | - switchAggregation(tenantId, entityId, key, startTs, endTs, aggregation, entitiesFutures); | |
162 | + switchAggregation(entityId, key, startTs, endTs, aggregation, entitiesFutures); | |
162 | 163 | return Futures.transform(setFutures(entitiesFutures), entity -> { |
163 | 164 | if (entity != null && entity.isNotEmpty()) { |
164 | 165 | entity.setEntityId(entityId.getId()); |
... | ... | @@ -168,32 +169,32 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
168 | 169 | } else { |
169 | 170 | return Optional.empty(); |
170 | 171 | } |
171 | - }); | |
172 | + }, MoreExecutors.directExecutor()); | |
172 | 173 | } |
173 | 174 | |
174 | - protected void switchAggregation(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, Aggregation aggregation, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
175 | + protected void switchAggregation(EntityId entityId, String key, long startTs, long endTs, Aggregation aggregation, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
175 | 176 | switch (aggregation) { |
176 | 177 | case AVG: |
177 | - findAvg(tenantId, entityId, key, startTs, endTs, entitiesFutures); | |
178 | + findAvg(entityId, key, startTs, endTs, entitiesFutures); | |
178 | 179 | break; |
179 | 180 | case MAX: |
180 | - findMax(tenantId, entityId, key, startTs, endTs, entitiesFutures); | |
181 | + findMax(entityId, key, startTs, endTs, entitiesFutures); | |
181 | 182 | break; |
182 | 183 | case MIN: |
183 | - findMin(tenantId, entityId, key, startTs, endTs, entitiesFutures); | |
184 | + findMin(entityId, key, startTs, endTs, entitiesFutures); | |
184 | 185 | break; |
185 | 186 | case SUM: |
186 | - findSum(tenantId, entityId, key, startTs, endTs, entitiesFutures); | |
187 | + findSum(entityId, key, startTs, endTs, entitiesFutures); | |
187 | 188 | break; |
188 | 189 | case COUNT: |
189 | - findCount(tenantId, entityId, key, startTs, endTs, entitiesFutures); | |
190 | + findCount(entityId, key, startTs, endTs, entitiesFutures); | |
190 | 191 | break; |
191 | 192 | default: |
192 | 193 | throw new IllegalArgumentException("Not supported aggregation type: " + aggregation); |
193 | 194 | } |
194 | 195 | } |
195 | 196 | |
196 | - protected void findCount(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
197 | + protected void findCount(EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
197 | 198 | Integer keyId = getOrSaveKeyId(key); |
198 | 199 | entitiesFutures.add(tsKvRepository.findCount( |
199 | 200 | entityId.getId(), |
... | ... | @@ -202,7 +203,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
202 | 203 | endTs)); |
203 | 204 | } |
204 | 205 | |
205 | - protected void findSum(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
206 | + protected void findSum(EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
206 | 207 | Integer keyId = getOrSaveKeyId(key); |
207 | 208 | entitiesFutures.add(tsKvRepository.findSum( |
208 | 209 | entityId.getId(), |
... | ... | @@ -211,7 +212,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
211 | 212 | endTs)); |
212 | 213 | } |
213 | 214 | |
214 | - protected void findMin(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
215 | + protected void findMin(EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
215 | 216 | Integer keyId = getOrSaveKeyId(key); |
216 | 217 | entitiesFutures.add(tsKvRepository.findStringMin( |
217 | 218 | entityId.getId(), |
... | ... | @@ -225,7 +226,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
225 | 226 | endTs)); |
226 | 227 | } |
227 | 228 | |
228 | - protected void findMax(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
229 | + protected void findMax(EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
229 | 230 | Integer keyId = getOrSaveKeyId(key); |
230 | 231 | entitiesFutures.add(tsKvRepository.findStringMax( |
231 | 232 | entityId.getId(), |
... | ... | @@ -239,7 +240,7 @@ public abstract class AbstractChunkedAggregationTimeseriesDao extends AbstractSq |
239 | 240 | endTs)); |
240 | 241 | } |
241 | 242 | |
242 | - protected void findAvg(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
243 | + protected void findAvg(EntityId entityId, String key, long startTs, long endTs, List<CompletableFuture<TsKvEntity>> entitiesFutures) { | |
243 | 244 | Integer keyId = getOrSaveKeyId(key); |
244 | 245 | entitiesFutures.add(tsKvRepository.findAvg( |
245 | 246 | entityId.getId(), | ... | ... |
... | ... | @@ -20,6 +20,7 @@ import com.google.common.collect.Lists; |
20 | 20 | import com.google.common.util.concurrent.FutureCallback; |
21 | 21 | import com.google.common.util.concurrent.Futures; |
22 | 22 | import com.google.common.util.concurrent.ListenableFuture; |
23 | +import com.google.common.util.concurrent.MoreExecutors; | |
23 | 24 | import lombok.extern.slf4j.Slf4j; |
24 | 25 | import org.hibernate.exception.ConstraintViolationException; |
25 | 26 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -126,7 +127,7 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
126 | 127 | protected ListenableFuture<List<TsKvEntry>> processFindAllAsync(TenantId tenantId, EntityId entityId, List<ReadTsKvQuery> queries) { |
127 | 128 | List<ListenableFuture<List<TsKvEntry>>> futures = queries |
128 | 129 | .stream() |
129 | - .map(query -> findAllAsync(tenantId, entityId, query)) | |
130 | + .map(query -> findAllAsync(entityId, query)) | |
130 | 131 | .collect(Collectors.toList()); |
131 | 132 | return Futures.transform(Futures.allAsList(futures), new Function<List<List<TsKvEntry>>, List<TsKvEntry>>() { |
132 | 133 | @Nullable |
... | ... | @@ -143,9 +144,9 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
143 | 144 | }, service); |
144 | 145 | } |
145 | 146 | |
146 | - protected abstract ListenableFuture<List<TsKvEntry>> findAllAsync(TenantId tenantId, EntityId entityId, ReadTsKvQuery query); | |
147 | + protected abstract ListenableFuture<List<TsKvEntry>> findAllAsync(EntityId entityId, ReadTsKvQuery query); | |
147 | 148 | |
148 | - protected abstract ListenableFuture<List<TsKvEntry>> findAllAsyncWithLimit(TenantId tenantId, EntityId entityId, ReadTsKvQuery query); | |
149 | + protected abstract ListenableFuture<List<TsKvEntry>> findAllAsyncWithLimit(EntityId entityId, ReadTsKvQuery query); | |
149 | 150 | |
150 | 151 | protected ListenableFuture<List<TsKvEntry>> getTskvEntriesFuture(ListenableFuture<List<Optional<TsKvEntry>>> future) { |
151 | 152 | return Futures.transform(future, new Function<List<Optional<TsKvEntry>>, List<TsKvEntry>>() { |
... | ... | @@ -163,12 +164,12 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
163 | 164 | }, service); |
164 | 165 | } |
165 | 166 | |
166 | - protected ListenableFuture<List<TsKvEntry>> findNewLatestEntryFuture(TenantId tenantId, EntityId entityId, DeleteTsKvQuery query) { | |
167 | + protected ListenableFuture<List<TsKvEntry>> findNewLatestEntryFuture(EntityId entityId, DeleteTsKvQuery query) { | |
167 | 168 | long startTs = 0; |
168 | 169 | long endTs = query.getStartTs() - 1; |
169 | 170 | ReadTsKvQuery findNewLatestQuery = new BaseReadTsKvQuery(query.getKey(), startTs, endTs, endTs - startTs, 1, |
170 | 171 | Aggregation.NONE, DESC_ORDER); |
171 | - return findAllAsync(tenantId, entityId, findNewLatestQuery); | |
172 | + return findAllAsync(entityId, findNewLatestQuery); | |
172 | 173 | } |
173 | 174 | |
174 | 175 | protected ListenableFuture<TsKvEntry> getFindLatestFuture(EntityId entityId, String key) { |
... | ... | @@ -188,7 +189,7 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
188 | 189 | return Futures.immediateFuture(result); |
189 | 190 | } |
190 | 191 | |
191 | - protected ListenableFuture<Void> getRemoveLatestFuture(TenantId tenantId, EntityId entityId, DeleteTsKvQuery query) { | |
192 | + protected ListenableFuture<Void> getRemoveLatestFuture(EntityId entityId, DeleteTsKvQuery query) { | |
192 | 193 | ListenableFuture<TsKvEntry> latestFuture = getFindLatestFuture(entityId, query.getKey()); |
193 | 194 | |
194 | 195 | ListenableFuture<Boolean> booleanFuture = Futures.transform(latestFuture, tsKvEntry -> { |
... | ... | @@ -216,7 +217,7 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
216 | 217 | if (query.getRewriteLatestIfDeleted()) { |
217 | 218 | ListenableFuture<Void> savedLatestFuture = Futures.transformAsync(booleanFuture, isRemove -> { |
218 | 219 | if (isRemove) { |
219 | - return getNewLatestEntryFuture(tenantId, entityId, query); | |
220 | + return getNewLatestEntryFuture(entityId, query); | |
220 | 221 | } |
221 | 222 | return Futures.immediateFuture(null); |
222 | 223 | }, service); |
... | ... | @@ -235,7 +236,7 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
235 | 236 | public void onFailure(Throwable t) { |
236 | 237 | log.warn("[{}] Failed to process remove of the latest value", entityId, t); |
237 | 238 | } |
238 | - }); | |
239 | + }, MoreExecutors.directExecutor()); | |
239 | 240 | return resultFuture; |
240 | 241 | } |
241 | 242 | |
... | ... | @@ -295,8 +296,8 @@ public abstract class AbstractSqlTimeseriesDao extends JpaAbstractDaoListeningEx |
295 | 296 | return keyId; |
296 | 297 | } |
297 | 298 | |
298 | - private ListenableFuture<Void> getNewLatestEntryFuture(TenantId tenantId, EntityId entityId, DeleteTsKvQuery query) { | |
299 | - ListenableFuture<List<TsKvEntry>> future = findNewLatestEntryFuture(tenantId, entityId, query); | |
299 | + private ListenableFuture<Void> getNewLatestEntryFuture(EntityId entityId, DeleteTsKvQuery query) { | |
300 | + ListenableFuture<List<TsKvEntry>> future = findNewLatestEntryFuture(entityId, query); | |
300 | 301 | return Futures.transformAsync(future, entryList -> { |
301 | 302 | if (entryList.size() == 1) { |
302 | 303 | return getSaveLatestFuture(entityId, entryList.get(0)); | ... | ... |
dao/src/main/java/org/thingsboard/server/dao/sqlts/insert/timescale/TimescaleInsertTsRepository.java
... | ... | @@ -37,8 +37,8 @@ import java.util.List; |
37 | 37 | public class TimescaleInsertTsRepository extends AbstractInsertRepository implements InsertTsRepository<TimescaleTsKvEntity> { |
38 | 38 | |
39 | 39 | private static final String INSERT_OR_UPDATE = |
40 | - "INSERT INTO tenant_ts_kv (tenant_id, entity_id, key, ts, bool_v, str_v, long_v, dbl_v, json_v) VALUES(?, ?, ?, ?, ?, ?, ?, ?, cast(? AS json)) " + | |
41 | - "ON CONFLICT (tenant_id, entity_id, key, ts) DO UPDATE SET bool_v = ?, str_v = ?, long_v = ?, dbl_v = ?, json_v = cast(? AS json);"; | |
40 | + "INSERT INTO ts_kv (entity_id, key, ts, bool_v, str_v, long_v, dbl_v, json_v) VALUES(?, ?, ?, ?, ?, ?, ?, cast(? AS json)) " + | |
41 | + "ON CONFLICT (entity_id, key, ts) DO UPDATE SET bool_v = ?, str_v = ?, long_v = ?, dbl_v = ?, json_v = cast(? AS json);"; | |
42 | 42 | |
43 | 43 | @Override |
44 | 44 | public void saveOrUpdate(List<EntityContainer<TimescaleTsKvEntity>> entities) { |
... | ... | @@ -46,41 +46,40 @@ public class TimescaleInsertTsRepository extends AbstractInsertRepository implem |
46 | 46 | @Override |
47 | 47 | public void setValues(PreparedStatement ps, int i) throws SQLException { |
48 | 48 | TimescaleTsKvEntity tsKvEntity = entities.get(i).getEntity(); |
49 | - ps.setObject(1, tsKvEntity.getTenantId()); | |
50 | - ps.setObject(2, tsKvEntity.getEntityId()); | |
51 | - ps.setInt(3, tsKvEntity.getKey()); | |
52 | - ps.setLong(4, tsKvEntity.getTs()); | |
49 | + ps.setObject(1, tsKvEntity.getEntityId()); | |
50 | + ps.setInt(2, tsKvEntity.getKey()); | |
51 | + ps.setLong(3, tsKvEntity.getTs()); | |
53 | 52 | |
54 | 53 | if (tsKvEntity.getBooleanValue() != null) { |
55 | - ps.setBoolean(5, tsKvEntity.getBooleanValue()); | |
56 | - ps.setBoolean(10, tsKvEntity.getBooleanValue()); | |
54 | + ps.setBoolean(4, tsKvEntity.getBooleanValue()); | |
55 | + ps.setBoolean(9, tsKvEntity.getBooleanValue()); | |
57 | 56 | } else { |
58 | - ps.setNull(5, Types.BOOLEAN); | |
59 | - ps.setNull(10, Types.BOOLEAN); | |
57 | + ps.setNull(4, Types.BOOLEAN); | |
58 | + ps.setNull(9, Types.BOOLEAN); | |
60 | 59 | } |
61 | 60 | |
62 | - ps.setString(6, replaceNullChars(tsKvEntity.getStrValue())); | |
63 | - ps.setString(11, replaceNullChars(tsKvEntity.getStrValue())); | |
61 | + ps.setString(5, replaceNullChars(tsKvEntity.getStrValue())); | |
62 | + ps.setString(10, replaceNullChars(tsKvEntity.getStrValue())); | |
64 | 63 | |
65 | 64 | |
66 | 65 | if (tsKvEntity.getLongValue() != null) { |
67 | - ps.setLong(7, tsKvEntity.getLongValue()); | |
68 | - ps.setLong(12, tsKvEntity.getLongValue()); | |
66 | + ps.setLong(6, tsKvEntity.getLongValue()); | |
67 | + ps.setLong(11, tsKvEntity.getLongValue()); | |
69 | 68 | } else { |
70 | - ps.setNull(7, Types.BIGINT); | |
71 | - ps.setNull(12, Types.BIGINT); | |
69 | + ps.setNull(6, Types.BIGINT); | |
70 | + ps.setNull(11, Types.BIGINT); | |
72 | 71 | } |
73 | 72 | |
74 | 73 | if (tsKvEntity.getDoubleValue() != null) { |
75 | - ps.setDouble(8, tsKvEntity.getDoubleValue()); | |
76 | - ps.setDouble(13, tsKvEntity.getDoubleValue()); | |
74 | + ps.setDouble(7, tsKvEntity.getDoubleValue()); | |
75 | + ps.setDouble(12, tsKvEntity.getDoubleValue()); | |
77 | 76 | } else { |
78 | - ps.setNull(8, Types.DOUBLE); | |
79 | - ps.setNull(13, Types.DOUBLE); | |
77 | + ps.setNull(7, Types.DOUBLE); | |
78 | + ps.setNull(12, Types.DOUBLE); | |
80 | 79 | } |
81 | 80 | |
82 | - ps.setString(9, replaceNullChars(tsKvEntity.getJsonValue())); | |
83 | - ps.setString(14, replaceNullChars(tsKvEntity.getJsonValue())); | |
81 | + ps.setString(8, replaceNullChars(tsKvEntity.getJsonValue())); | |
82 | + ps.setString(13, replaceNullChars(tsKvEntity.getJsonValue())); | |
84 | 83 | } |
85 | 84 | |
86 | 85 | @Override | ... | ... |
... | ... | @@ -36,7 +36,7 @@ public class AggregationRepository { |
36 | 36 | public static final String FIND_SUM = "findSum"; |
37 | 37 | public static final String FIND_COUNT = "findCount"; |
38 | 38 | |
39 | - public static final String FROM_WHERE_CLAUSE = "FROM tenant_ts_kv tskv WHERE tskv.tenant_id = cast(:tenantId AS uuid) AND tskv.entity_id = cast(:entityId AS uuid) AND tskv.key= cast(:entityKey AS int) AND tskv.ts > :startTs AND tskv.ts <= :endTs GROUP BY tskv.tenant_id, tskv.entity_id, tskv.key, tsBucket ORDER BY tskv.tenant_id, tskv.entity_id, tskv.key, tsBucket"; | |
39 | + public static final String FROM_WHERE_CLAUSE = "FROM ts_kv tskv WHERE tskv.entity_id = cast(:entityId AS uuid) AND tskv.key= cast(:entityKey AS int) AND tskv.ts > :startTs AND tskv.ts <= :endTs GROUP BY tskv.entity_id, tskv.key, tsBucket ORDER BY tskv.entity_id, tskv.key, tsBucket"; | |
40 | 40 | |
41 | 41 | public static final String FIND_AVG_QUERY = "SELECT time_bucket(:timeBucket, tskv.ts) AS tsBucket, :timeBucket AS interval, SUM(COALESCE(tskv.long_v, 0)) AS longValue, SUM(COALESCE(tskv.dbl_v, 0.0)) AS doubleValue, SUM(CASE WHEN tskv.long_v IS NULL THEN 0 ELSE 1 END) AS longCountValue, SUM(CASE WHEN tskv.dbl_v IS NULL THEN 0 ELSE 1 END) AS doubleCountValue, null AS strValue, 'AVG' AS aggType "; |
42 | 42 | |
... | ... | @@ -52,43 +52,42 @@ public class AggregationRepository { |
52 | 52 | private EntityManager entityManager; |
53 | 53 | |
54 | 54 | @Async |
55 | - public CompletableFuture<List<TimescaleTsKvEntity>> findAvg(UUID tenantId, UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
55 | + public CompletableFuture<List<TimescaleTsKvEntity>> findAvg(UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
56 | 56 | @SuppressWarnings("unchecked") |
57 | - List<TimescaleTsKvEntity> resultList = getResultList(tenantId, entityId, entityKey, timeBucket, startTs, endTs, FIND_AVG); | |
57 | + List<TimescaleTsKvEntity> resultList = getResultList(entityId, entityKey, timeBucket, startTs, endTs, FIND_AVG); | |
58 | 58 | return CompletableFuture.supplyAsync(() -> resultList); |
59 | 59 | } |
60 | 60 | |
61 | 61 | @Async |
62 | - public CompletableFuture<List<TimescaleTsKvEntity>> findMax(UUID tenantId, UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
62 | + public CompletableFuture<List<TimescaleTsKvEntity>> findMax(UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
63 | 63 | @SuppressWarnings("unchecked") |
64 | - List<TimescaleTsKvEntity> resultList = getResultList(tenantId, entityId, entityKey, timeBucket, startTs, endTs, FIND_MAX); | |
64 | + List<TimescaleTsKvEntity> resultList = getResultList(entityId, entityKey, timeBucket, startTs, endTs, FIND_MAX); | |
65 | 65 | return CompletableFuture.supplyAsync(() -> resultList); |
66 | 66 | } |
67 | 67 | |
68 | 68 | @Async |
69 | - public CompletableFuture<List<TimescaleTsKvEntity>> findMin(UUID tenantId, UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
69 | + public CompletableFuture<List<TimescaleTsKvEntity>> findMin(UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
70 | 70 | @SuppressWarnings("unchecked") |
71 | - List<TimescaleTsKvEntity> resultList = getResultList(tenantId, entityId, entityKey, timeBucket, startTs, endTs, FIND_MIN); | |
71 | + List<TimescaleTsKvEntity> resultList = getResultList(entityId, entityKey, timeBucket, startTs, endTs, FIND_MIN); | |
72 | 72 | return CompletableFuture.supplyAsync(() -> resultList); |
73 | 73 | } |
74 | 74 | |
75 | 75 | @Async |
76 | - public CompletableFuture<List<TimescaleTsKvEntity>> findSum(UUID tenantId, UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
76 | + public CompletableFuture<List<TimescaleTsKvEntity>> findSum(UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
77 | 77 | @SuppressWarnings("unchecked") |
78 | - List<TimescaleTsKvEntity> resultList = getResultList(tenantId, entityId, entityKey, timeBucket, startTs, endTs, FIND_SUM); | |
78 | + List<TimescaleTsKvEntity> resultList = getResultList(entityId, entityKey, timeBucket, startTs, endTs, FIND_SUM); | |
79 | 79 | return CompletableFuture.supplyAsync(() -> resultList); |
80 | 80 | } |
81 | 81 | |
82 | 82 | @Async |
83 | - public CompletableFuture<List<TimescaleTsKvEntity>> findCount(UUID tenantId, UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
83 | + public CompletableFuture<List<TimescaleTsKvEntity>> findCount(UUID entityId, int entityKey, long timeBucket, long startTs, long endTs) { | |
84 | 84 | @SuppressWarnings("unchecked") |
85 | - List<TimescaleTsKvEntity> resultList = getResultList(tenantId, entityId, entityKey, timeBucket, startTs, endTs, FIND_COUNT); | |
85 | + List<TimescaleTsKvEntity> resultList = getResultList(entityId, entityKey, timeBucket, startTs, endTs, FIND_COUNT); | |
86 | 86 | return CompletableFuture.supplyAsync(() -> resultList); |
87 | 87 | } |
88 | 88 | |
89 | - private List getResultList(UUID tenantId, UUID entityId, int entityKey, long timeBucket, long startTs, long endTs, String query) { | |
89 | + private List getResultList(UUID entityId, int entityKey, long timeBucket, long startTs, long endTs, String query) { | |
90 | 90 | return entityManager.createNamedQuery(query) |
91 | - .setParameter("tenantId", tenantId) | |
92 | 91 | .setParameter("entityId", entityId) |
93 | 92 | .setParameter("entityKey", entityKey) |
94 | 93 | .setParameter("timeBucket", timeBucket) | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.server.dao.sqlts.timescale; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import com.google.common.util.concurrent.SettableFuture; |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | 23 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -87,24 +88,23 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
87 | 88 | } |
88 | 89 | |
89 | 90 | @Override |
90 | - protected ListenableFuture<List<TsKvEntry>> findAllAsync(TenantId tenantId, EntityId entityId, ReadTsKvQuery query) { | |
91 | + protected ListenableFuture<List<TsKvEntry>> findAllAsync(EntityId entityId, ReadTsKvQuery query) { | |
91 | 92 | if (query.getAggregation() == Aggregation.NONE) { |
92 | - return findAllAsyncWithLimit(tenantId, entityId, query); | |
93 | + return findAllAsyncWithLimit(entityId, query); | |
93 | 94 | } else { |
94 | 95 | long startTs = query.getStartTs(); |
95 | 96 | long endTs = query.getEndTs(); |
96 | 97 | long timeBucket = query.getInterval(); |
97 | - ListenableFuture<List<Optional<TsKvEntry>>> future = findAllAndAggregateAsync(tenantId, entityId, query.getKey(), startTs, endTs, timeBucket, query.getAggregation()); | |
98 | + ListenableFuture<List<Optional<TsKvEntry>>> future = findAllAndAggregateAsync(entityId, query.getKey(), startTs, endTs, timeBucket, query.getAggregation()); | |
98 | 99 | return getTskvEntriesFuture(future); |
99 | 100 | } |
100 | 101 | } |
101 | 102 | |
102 | 103 | @Override |
103 | - protected ListenableFuture<List<TsKvEntry>> findAllAsyncWithLimit(TenantId tenantId, EntityId entityId, ReadTsKvQuery query) { | |
104 | + protected ListenableFuture<List<TsKvEntry>> findAllAsyncWithLimit(EntityId entityId, ReadTsKvQuery query) { | |
104 | 105 | String strKey = query.getKey(); |
105 | 106 | Integer keyId = getOrSaveKeyId(strKey); |
106 | 107 | List<TimescaleTsKvEntity> timescaleTsKvEntities = tsKvRepository.findAllWithLimit( |
107 | - tenantId.getId(), | |
108 | 108 | entityId.getId(), |
109 | 109 | keyId, |
110 | 110 | query.getStartTs(), |
... | ... | @@ -116,8 +116,8 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
116 | 116 | return Futures.immediateFuture(DaoUtil.convertDataList(timescaleTsKvEntities)); |
117 | 117 | } |
118 | 118 | |
119 | - private ListenableFuture<List<Optional<TsKvEntry>>> findAllAndAggregateAsync(TenantId tenantId, EntityId entityId, String key, long startTs, long endTs, long timeBucket, Aggregation aggregation) { | |
120 | - CompletableFuture<List<TimescaleTsKvEntity>> listCompletableFuture = switchAggregation(key, startTs, endTs, timeBucket, aggregation, entityId.getId(), tenantId.getId()); | |
119 | + private ListenableFuture<List<Optional<TsKvEntry>>> findAllAndAggregateAsync(EntityId entityId, String key, long startTs, long endTs, long timeBucket, Aggregation aggregation) { | |
120 | + CompletableFuture<List<TimescaleTsKvEntity>> listCompletableFuture = switchAggregation(key, startTs, endTs, timeBucket, aggregation, entityId.getId()); | |
121 | 121 | SettableFuture<List<TimescaleTsKvEntity>> listenableFuture = SettableFuture.create(); |
122 | 122 | listCompletableFuture.whenComplete((timescaleTsKvEntities, throwable) -> { |
123 | 123 | if (throwable != null) { |
... | ... | @@ -132,7 +132,6 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
132 | 132 | timescaleTsKvEntities.forEach(entity -> { |
133 | 133 | if (entity != null && entity.isNotEmpty()) { |
134 | 134 | entity.setEntityId(entityId.getId()); |
135 | - entity.setTenantId(tenantId.getId()); | |
136 | 135 | entity.setStrKey(key); |
137 | 136 | result.add(Optional.of(DaoUtil.getData(entity))); |
138 | 137 | } else { |
... | ... | @@ -143,7 +142,7 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
143 | 142 | } else { |
144 | 143 | return Collections.emptyList(); |
145 | 144 | } |
146 | - }); | |
145 | + }, MoreExecutors.directExecutor()); | |
147 | 146 | } |
148 | 147 | |
149 | 148 | @Override |
... | ... | @@ -166,7 +165,6 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
166 | 165 | String strKey = tsKvEntry.getKey(); |
167 | 166 | Integer keyId = getOrSaveKeyId(strKey); |
168 | 167 | TimescaleTsKvEntity entity = new TimescaleTsKvEntity(); |
169 | - entity.setTenantId(tenantId.getId()); | |
170 | 168 | entity.setEntityId(entityId.getId()); |
171 | 169 | entity.setTs(tsKvEntry.getTs()); |
172 | 170 | entity.setKey(keyId); |
... | ... | @@ -196,7 +194,6 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
196 | 194 | Integer keyId = getOrSaveKeyId(strKey); |
197 | 195 | return service.submit(() -> { |
198 | 196 | tsKvRepository.delete( |
199 | - tenantId.getId(), | |
200 | 197 | entityId.getId(), |
201 | 198 | keyId, |
202 | 199 | query.getStartTs(), |
... | ... | @@ -207,7 +204,7 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
207 | 204 | |
208 | 205 | @Override |
209 | 206 | public ListenableFuture<Void> removeLatest(TenantId tenantId, EntityId entityId, DeleteTsKvQuery query) { |
210 | - return getRemoveLatestFuture(tenantId, entityId, query); | |
207 | + return getRemoveLatestFuture(entityId, query); | |
211 | 208 | } |
212 | 209 | |
213 | 210 | @Override |
... | ... | @@ -215,27 +212,26 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
215 | 212 | return service.submit(() -> null); |
216 | 213 | } |
217 | 214 | |
218 | - private CompletableFuture<List<TimescaleTsKvEntity>> switchAggregation(String key, long startTs, long endTs, long timeBucket, Aggregation aggregation, UUID entityId, UUID tenantId) { | |
215 | + private CompletableFuture<List<TimescaleTsKvEntity>> switchAggregation(String key, long startTs, long endTs, long timeBucket, Aggregation aggregation, UUID entityId) { | |
219 | 216 | switch (aggregation) { |
220 | 217 | case AVG: |
221 | - return findAvg(key, startTs, endTs, timeBucket, entityId, tenantId); | |
218 | + return findAvg(key, startTs, endTs, timeBucket, entityId); | |
222 | 219 | case MAX: |
223 | - return findMax(key, startTs, endTs, timeBucket, entityId, tenantId); | |
220 | + return findMax(key, startTs, endTs, timeBucket, entityId); | |
224 | 221 | case MIN: |
225 | - return findMin(key, startTs, endTs, timeBucket, entityId, tenantId); | |
222 | + return findMin(key, startTs, endTs, timeBucket, entityId); | |
226 | 223 | case SUM: |
227 | - return findSum(key, startTs, endTs, timeBucket, entityId, tenantId); | |
224 | + return findSum(key, startTs, endTs, timeBucket, entityId); | |
228 | 225 | case COUNT: |
229 | - return findCount(key, startTs, endTs, timeBucket, entityId, tenantId); | |
226 | + return findCount(key, startTs, endTs, timeBucket, entityId); | |
230 | 227 | default: |
231 | 228 | throw new IllegalArgumentException("Not supported aggregation type: " + aggregation); |
232 | 229 | } |
233 | 230 | } |
234 | 231 | |
235 | - private CompletableFuture<List<TimescaleTsKvEntity>> findCount(String key, long startTs, long endTs, long timeBucket, UUID entityId, UUID tenantId) { | |
232 | + private CompletableFuture<List<TimescaleTsKvEntity>> findCount(String key, long startTs, long endTs, long timeBucket, UUID entityId) { | |
236 | 233 | Integer keyId = getOrSaveKeyId(key); |
237 | 234 | return aggregationRepository.findCount( |
238 | - tenantId, | |
239 | 235 | entityId, |
240 | 236 | keyId, |
241 | 237 | timeBucket, |
... | ... | @@ -243,10 +239,9 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
243 | 239 | endTs); |
244 | 240 | } |
245 | 241 | |
246 | - private CompletableFuture<List<TimescaleTsKvEntity>> findSum(String key, long startTs, long endTs, long timeBucket, UUID entityId, UUID tenantId) { | |
242 | + private CompletableFuture<List<TimescaleTsKvEntity>> findSum(String key, long startTs, long endTs, long timeBucket, UUID entityId) { | |
247 | 243 | Integer keyId = getOrSaveKeyId(key); |
248 | 244 | return aggregationRepository.findSum( |
249 | - tenantId, | |
250 | 245 | entityId, |
251 | 246 | keyId, |
252 | 247 | timeBucket, |
... | ... | @@ -254,10 +249,9 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
254 | 249 | endTs); |
255 | 250 | } |
256 | 251 | |
257 | - private CompletableFuture<List<TimescaleTsKvEntity>> findMin(String key, long startTs, long endTs, long timeBucket, UUID entityId, UUID tenantId) { | |
252 | + private CompletableFuture<List<TimescaleTsKvEntity>> findMin(String key, long startTs, long endTs, long timeBucket, UUID entityId) { | |
258 | 253 | Integer keyId = getOrSaveKeyId(key); |
259 | 254 | return aggregationRepository.findMin( |
260 | - tenantId, | |
261 | 255 | entityId, |
262 | 256 | keyId, |
263 | 257 | timeBucket, |
... | ... | @@ -265,10 +259,9 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
265 | 259 | endTs); |
266 | 260 | } |
267 | 261 | |
268 | - private CompletableFuture<List<TimescaleTsKvEntity>> findMax(String key, long startTs, long endTs, long timeBucket, UUID entityId, UUID tenantId) { | |
262 | + private CompletableFuture<List<TimescaleTsKvEntity>> findMax(String key, long startTs, long endTs, long timeBucket, UUID entityId) { | |
269 | 263 | Integer keyId = getOrSaveKeyId(key); |
270 | 264 | return aggregationRepository.findMax( |
271 | - tenantId, | |
272 | 265 | entityId, |
273 | 266 | keyId, |
274 | 267 | timeBucket, |
... | ... | @@ -276,10 +269,9 @@ public class TimescaleTimeseriesDao extends AbstractSqlTimeseriesDao implements |
276 | 269 | endTs); |
277 | 270 | } |
278 | 271 | |
279 | - private CompletableFuture<List<TimescaleTsKvEntity>> findAvg(String key, long startTs, long endTs, long timeBucket, UUID entityId, UUID tenantId) { | |
272 | + private CompletableFuture<List<TimescaleTsKvEntity>> findAvg(String key, long startTs, long endTs, long timeBucket, UUID entityId) { | |
280 | 273 | Integer keyId = getOrSaveKeyId(key); |
281 | 274 | return aggregationRepository.findAvg( |
282 | - tenantId, | |
283 | 275 | entityId, |
284 | 276 | keyId, |
285 | 277 | timeBucket, | ... | ... |
... | ... | @@ -31,12 +31,10 @@ import java.util.UUID; |
31 | 31 | @TimescaleDBTsDao |
32 | 32 | public interface TsKvTimescaleRepository extends CrudRepository<TimescaleTsKvEntity, TimescaleTsKvCompositeKey> { |
33 | 33 | |
34 | - @Query("SELECT tskv FROM TimescaleTsKvEntity tskv WHERE tskv.tenantId = :tenantId " + | |
35 | - "AND tskv.entityId = :entityId " + | |
34 | + @Query("SELECT tskv FROM TimescaleTsKvEntity tskv WHERE tskv.entityId = :entityId " + | |
36 | 35 | "AND tskv.key = :entityKey " + |
37 | 36 | "AND tskv.ts > :startTs AND tskv.ts <= :endTs") |
38 | 37 | List<TimescaleTsKvEntity> findAllWithLimit( |
39 | - @Param("tenantId") UUID tenantId, | |
40 | 38 | @Param("entityId") UUID entityId, |
41 | 39 | @Param("entityKey") int key, |
42 | 40 | @Param("startTs") long startTs, |
... | ... | @@ -44,12 +42,10 @@ public interface TsKvTimescaleRepository extends CrudRepository<TimescaleTsKvEnt |
44 | 42 | |
45 | 43 | @Transactional |
46 | 44 | @Modifying |
47 | - @Query("DELETE FROM TimescaleTsKvEntity tskv WHERE tskv.tenantId = :tenantId " + | |
48 | - "AND tskv.entityId = :entityId " + | |
45 | + @Query("DELETE FROM TimescaleTsKvEntity tskv WHERE tskv.entityId = :entityId " + | |
49 | 46 | "AND tskv.key = :entityKey " + |
50 | 47 | "AND tskv.ts > :startTs AND tskv.ts <= :endTs") |
51 | - void delete(@Param("tenantId") UUID tenantId, | |
52 | - @Param("entityId") UUID entityId, | |
48 | + void delete(@Param("entityId") UUID entityId, | |
53 | 49 | @Param("entityKey") int key, |
54 | 50 | @Param("startTs") long startTs, |
55 | 51 | @Param("endTs") long endTs); | ... | ... |
... | ... | @@ -28,6 +28,7 @@ import com.google.common.util.concurrent.AsyncFunction; |
28 | 28 | import com.google.common.util.concurrent.FutureCallback; |
29 | 29 | import com.google.common.util.concurrent.Futures; |
30 | 30 | import com.google.common.util.concurrent.ListenableFuture; |
31 | +import com.google.common.util.concurrent.MoreExecutors; | |
31 | 32 | import lombok.extern.slf4j.Slf4j; |
32 | 33 | import org.apache.commons.lang3.StringUtils; |
33 | 34 | import org.springframework.beans.factory.annotation.Autowired; |
... | ... | @@ -330,7 +331,7 @@ public class CassandraBaseTimeseriesDao extends CassandraAbstractAsyncDao implem |
330 | 331 | stmt.setInt(6, (int) ttl); |
331 | 332 | } |
332 | 333 | futures.add(getFuture(executeAsyncWrite(tenantId, stmt), rs -> null)); |
333 | - return Futures.transform(Futures.allAsList(futures), result -> null); | |
334 | + return Futures.transform(Futures.allAsList(futures), result -> null, MoreExecutors.directExecutor()); | |
334 | 335 | } |
335 | 336 | |
336 | 337 | private void processSetNullValues(TenantId tenantId, EntityId entityId, TsKvEntry tsKvEntry, long ttl, List<ListenableFuture<Void>> futures, long partition, DataType type) { |
... | ... | @@ -545,7 +546,7 @@ public class CassandraBaseTimeseriesDao extends CassandraAbstractAsyncDao implem |
545 | 546 | public void onFailure(Throwable t) { |
546 | 547 | log.warn("[{}] Failed to process remove of the latest value", entityId, t); |
547 | 548 | } |
548 | - }); | |
549 | + }, MoreExecutors.directExecutor()); | |
549 | 550 | return resultFuture; |
550 | 551 | } |
551 | 552 | ... | ... |
dao/src/main/resources/sql/schema-timescale-idx.sql
deleted
100644 → 0
1 | --- | |
2 | --- Copyright © 2016-2020 The Thingsboard Authors | |
3 | --- | |
4 | --- Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | --- you may not use this file except in compliance with the License. | |
6 | --- You may obtain a copy of the License at | |
7 | --- | |
8 | --- http://www.apache.org/licenses/LICENSE-2.0 | |
9 | --- | |
10 | --- Unless required by applicable law or agreed to in writing, software | |
11 | --- distributed under the License is distributed on an "AS IS" BASIS, | |
12 | --- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | --- See the License for the specific language governing permissions and | |
14 | --- limitations under the License. | |
15 | --- | |
16 | - | |
17 | -CREATE INDEX IF NOT EXISTS idx_tenant_ts_kv ON tenant_ts_kv(tenant_id, entity_id, key, ts); | |
\ No newline at end of file |
... | ... | @@ -16,8 +16,7 @@ |
16 | 16 | |
17 | 17 | CREATE EXTENSION IF NOT EXISTS timescaledb CASCADE; |
18 | 18 | |
19 | -CREATE TABLE IF NOT EXISTS tenant_ts_kv ( | |
20 | - tenant_id uuid NOT NULL, | |
19 | +CREATE TABLE IF NOT EXISTS ts_kv ( | |
21 | 20 | entity_id uuid NOT NULL, |
22 | 21 | key int NOT NULL, |
23 | 22 | ts bigint NOT NULL, |
... | ... | @@ -26,7 +25,7 @@ CREATE TABLE IF NOT EXISTS tenant_ts_kv ( |
26 | 25 | long_v bigint, |
27 | 26 | dbl_v double precision, |
28 | 27 | json_v json, |
29 | - CONSTRAINT tenant_ts_kv_pkey PRIMARY KEY (tenant_id, entity_id, key, ts) | |
28 | + CONSTRAINT ts_kv_pkey PRIMARY KEY (entity_id, key, ts) | |
30 | 29 | ); |
31 | 30 | |
32 | 31 | CREATE TABLE IF NOT EXISTS ts_kv_dictionary ( | ... | ... |
... | ... | @@ -44,7 +44,7 @@ public class SqlDaoServiceTestSuite { |
44 | 44 | |
45 | 45 | // @ClassRule |
46 | 46 | // public static CustomSqlUnit sqlUnit = new CustomSqlUnit( |
47 | -// Arrays.asList("sql/schema-timescale.sql", "sql/schema-timescale-idx.sql", "sql/schema-entities.sql", "sql/schema-entities-idx.sql", "sql/system-data.sql", "sql/system-test.sql"), | |
47 | +// Arrays.asList("sql/schema-timescale.sql", "sql/schema-entities.sql", "sql/schema-entities-idx.sql", "sql/system-data.sql", "sql/system-test.sql"), | |
48 | 48 | // "sql/timescale/drop-all-tables.sql", |
49 | 49 | // "sql-test.properties" |
50 | 50 | // ); | ... | ... |
... | ... | @@ -119,7 +119,7 @@ public class RateLimitedResultSetFutureTest { |
119 | 119 | |
120 | 120 | resultSetFuture = new RateLimitedResultSetFuture(session, rateLimiter, statement); |
121 | 121 | |
122 | - ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one); | |
122 | + ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one, MoreExecutors.directExecutor()); | |
123 | 123 | Row actualRow = transform.get(); |
124 | 124 | |
125 | 125 | assertSame(row, actualRow); |
... | ... | @@ -132,7 +132,7 @@ public class RateLimitedResultSetFutureTest { |
132 | 132 | when(rateLimiter.acquireAsync()).thenReturn(Futures.immediateFuture(null)); |
133 | 133 | when(session.executeAsync(statement)).thenThrow(new UnsupportedFeatureException(ProtocolVersion.V3, "hjg")); |
134 | 134 | resultSetFuture = new RateLimitedResultSetFuture(session, rateLimiter, statement); |
135 | - ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one); | |
135 | + ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one, MoreExecutors.directExecutor()); | |
136 | 136 | try { |
137 | 137 | transform.get(); |
138 | 138 | fail(); |
... | ... | @@ -156,7 +156,7 @@ public class RateLimitedResultSetFutureTest { |
156 | 156 | |
157 | 157 | when(realFuture.get()).thenThrow(new ExecutionException("Fail", new TimeoutException("timeout"))); |
158 | 158 | resultSetFuture = new RateLimitedResultSetFuture(session, rateLimiter, statement); |
159 | - ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one); | |
159 | + ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one, MoreExecutors.directExecutor()); | |
160 | 160 | try { |
161 | 161 | transform.get(); |
162 | 162 | fail(); |
... | ... | @@ -177,7 +177,7 @@ public class RateLimitedResultSetFutureTest { |
177 | 177 | when(rateLimiter.acquireAsync()).thenReturn(future); |
178 | 178 | resultSetFuture = new RateLimitedResultSetFuture(session, rateLimiter, statement); |
179 | 179 | |
180 | - ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one); | |
180 | + ListenableFuture<Row> transform = Futures.transform(resultSetFuture, ResultSet::one, MoreExecutors.directExecutor()); | |
181 | 181 | // TimeUnit.MILLISECONDS.sleep(200); |
182 | 182 | future.cancel(false); |
183 | 183 | latch.countDown(); | ... | ... |
... | ... | @@ -12,7 +12,7 @@ DROP TABLE IF EXISTS event; |
12 | 12 | DROP TABLE IF EXISTS relation; |
13 | 13 | DROP TABLE IF EXISTS tb_user; |
14 | 14 | DROP TABLE IF EXISTS tenant; |
15 | -DROP TABLE IF EXISTS tenant_ts_kv; | |
15 | +DROP TABLE IF EXISTS ts_kv; | |
16 | 16 | DROP TABLE IF EXISTS ts_kv_latest; |
17 | 17 | DROP TABLE IF EXISTS user_credentials; |
18 | 18 | DROP TABLE IF EXISTS widget_type; | ... | ... |
... | ... | @@ -17,6 +17,13 @@ In order to set database type change the value of `DATABASE` variable in `.env` |
17 | 17 | |
18 | 18 | **NOTE**: According to the database type corresponding docker service will be deployed (see `docker-compose.postgres.yml`, `docker-compose.cassandra.yml` for details). |
19 | 19 | |
20 | +Execute the following command to create log folders for the services and chown of these folders to the docker container users. | |
21 | +To be able to change user, **chown** command is used, which requires sudo permissions (script will request password for a sudo access): | |
22 | + | |
23 | +` | |
24 | +$ ./docker-create-log-folders.sh | |
25 | +` | |
26 | + | |
20 | 27 | Execute the following command to run installation: |
21 | 28 | |
22 | 29 | ` | ... | ... |
docker/docker-create-log-folders.sh
0 → 100755
1 | +#!/bin/bash | |
2 | +# | |
3 | +# Copyright © 2016-2020 The Thingsboard Authors | |
4 | +# | |
5 | +# Licensed under the Apache License, Version 2.0 (the "License"); | |
6 | +# you may not use this file except in compliance with the License. | |
7 | +# You may obtain a copy of the License at | |
8 | +# | |
9 | +# http://www.apache.org/licenses/LICENSE-2.0 | |
10 | +# | |
11 | +# Unless required by applicable law or agreed to in writing, software | |
12 | +# distributed under the License is distributed on an "AS IS" BASIS, | |
13 | +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
14 | +# See the License for the specific language governing permissions and | |
15 | +# limitations under the License. | |
16 | +# | |
17 | + | |
18 | +mkdir -p tb-node/log/ && sudo chown -R 799:799 tb-node/log/ | |
19 | + | |
20 | +mkdir -p tb-transports/coap/log && sudo chown -R 799:799 tb-transports/coap/log | |
21 | + | |
22 | +mkdir -p tb-transports/http/log && sudo chown -R 799:799 tb-transports/http/log | |
23 | + | |
24 | +mkdir -p tb-transports/mqtt/log && sudo chown -R 799:799 tb-transports/mqtt/log | |
\ No newline at end of file | ... | ... |
... | ... | @@ -39,5 +39,5 @@ spec: |
39 | 39 | volumeMounts: |
40 | 40 | - mountPath: /config |
41 | 41 | name: tb-node-config |
42 | - command: ['sh', '-c', 'while [ ! -f /install-finished ]; do sleep 2; done;'] | |
42 | + command: ['sh', '-c', 'while [ ! -f /tmp/install-finished ]; do sleep 2; done;'] | |
43 | 43 | restartPolicy: Never | ... | ... |
... | ... | @@ -15,4 +15,6 @@ |
15 | 15 | # limitations under the License. |
16 | 16 | # |
17 | 17 | |
18 | -kubectl -n thingsboard delete svc,sts,deploy,pv,pvc,cm,po,ing --all | |
18 | +kubectl -n thingsboard delete svc,sts,deploy,cm,po,ing --all | |
19 | + | |
20 | +kubectl -n thingsboard get pvc --no-headers=true | awk '//{print $1}' | xargs kubectl -n thingsboard delete --ignore-not-found=true pvc | |
\ No newline at end of file | ... | ... |
... | ... | @@ -22,7 +22,7 @@ function installTb() { |
22 | 22 | kubectl apply -f tb-node-configmap.yml |
23 | 23 | kubectl apply -f database-setup.yml && |
24 | 24 | kubectl wait --for=condition=Ready pod/tb-db-setup --timeout=120s && |
25 | - kubectl exec tb-db-setup -- sh -c 'export INSTALL_TB=true; export LOAD_DEMO='"$loadDemo"'; start-tb-node.sh; touch /install-finished;' | |
25 | + kubectl exec tb-db-setup -- sh -c 'export INSTALL_TB=true; export LOAD_DEMO='"$loadDemo"'; start-tb-node.sh; touch /tmp/install-finished;' | |
26 | 26 | |
27 | 27 | kubectl delete pod tb-db-setup |
28 | 28 | ... | ... |
... | ... | @@ -38,6 +38,6 @@ fi |
38 | 38 | |
39 | 39 | kubectl apply -f database-setup.yml && |
40 | 40 | kubectl wait --for=condition=Ready pod/tb-db-setup --timeout=120s && |
41 | -kubectl exec tb-db-setup -- sh -c 'export UPGRADE_TB=true; export FROM_VERSION='"$fromVersion"'; start-tb-node.sh; touch /install-finished;' | |
41 | +kubectl exec tb-db-setup -- sh -c 'export UPGRADE_TB=true; export FROM_VERSION='"$fromVersion"'; start-tb-node.sh; touch /tmp/install-finished;' | |
42 | 42 | |
43 | 43 | kubectl delete pod tb-db-setup | ... | ... |
... | ... | @@ -14,7 +14,7 @@ |
14 | 14 | # limitations under the License. |
15 | 15 | # |
16 | 16 | |
17 | -FROM debian:stretch | |
17 | +FROM thingsboard/base | |
18 | 18 | |
19 | 19 | COPY start-js-executor.sh ${pkg.name}.deb /tmp/ |
20 | 20 | |
... | ... | @@ -25,4 +25,6 @@ RUN dpkg -i /tmp/${pkg.name}.deb |
25 | 25 | |
26 | 26 | RUN update-rc.d ${pkg.name} disable |
27 | 27 | |
28 | +USER ${pkg.user} | |
29 | + | |
28 | 30 | CMD ["start-js-executor.sh"] | ... | ... |
... | ... | @@ -36,7 +36,6 @@ |
36 | 36 | <main.dir>${basedir}/../..</main.dir> |
37 | 37 | <pkg.name>tb-js-executor</pkg.name> |
38 | 38 | <docker.name>tb-js-executor</docker.name> |
39 | - <pkg.user>thingsboard</pkg.user> | |
40 | 39 | <pkg.unixLogFolder>/var/log/${pkg.name}</pkg.unixLogFolder> |
41 | 40 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
42 | 41 | <pkg.linux.dist>${project.build.directory}/package/linux</pkg.linux.dist> | ... | ... |
... | ... | @@ -18,12 +18,14 @@ |
18 | 18 | CONF_FOLDER="/config" |
19 | 19 | jarfile=${pkg.installFolder}/bin/${pkg.name}.jar |
20 | 20 | configfile=${pkg.name}.conf |
21 | -run_user=${pkg.name} | |
21 | +run_user=${pkg.user} | |
22 | 22 | |
23 | 23 | source "${CONF_FOLDER}/${configfile}" |
24 | 24 | |
25 | 25 | export LOADER_PATH=/config,${LOADER_PATH} |
26 | 26 | |
27 | +cd ${pkg.installFolder}/bin | |
28 | + | |
27 | 29 | if [ "$INSTALL_TB" == "true" ]; then |
28 | 30 | |
29 | 31 | if [ "$LOAD_DEMO" == "true" ]; then | ... | ... |
... | ... | @@ -36,7 +36,6 @@ |
36 | 36 | <main.dir>${basedir}/../..</main.dir> |
37 | 37 | <pkg.name>thingsboard</pkg.name> |
38 | 38 | <docker.name>tb-node</docker.name> |
39 | - <pkg.user>thingsboard</pkg.user> | |
40 | 39 | <pkg.unixLogFolder>/var/log/${pkg.name}</pkg.unixLogFolder> |
41 | 40 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
42 | 41 | </properties> | ... | ... |
... | ... | @@ -38,7 +38,6 @@ |
38 | 38 | <tb.docker.name>tb</tb.docker.name> |
39 | 39 | <tb-postgres.docker.name>tb-postgres</tb-postgres.docker.name> |
40 | 40 | <tb-cassandra.docker.name>tb-cassandra</tb-cassandra.docker.name> |
41 | - <pkg.user>thingsboard</pkg.user> | |
42 | 41 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
43 | 42 | <pkg.upgradeVersion>2.4.2</pkg.upgradeVersion> |
44 | 43 | </properties> | ... | ... |
... | ... | @@ -25,6 +25,8 @@ export LOADER_PATH=/config,${LOADER_PATH} |
25 | 25 | |
26 | 26 | echo "Starting '${project.name}' ..." |
27 | 27 | |
28 | +cd ${pkg.installFolder}/bin | |
29 | + | |
28 | 30 | exec java -cp ${jarfile} $JAVA_OPTS -Dloader.main=org.thingsboard.server.coap.ThingsboardCoapTransportApplication \ |
29 | 31 | -Dspring.jpa.hibernate.ddl-auto=none \ |
30 | 32 | -Dlogging.config=/config/logback.xml \ | ... | ... |
... | ... | @@ -36,7 +36,6 @@ |
36 | 36 | <main.dir>${basedir}/../../..</main.dir> |
37 | 37 | <pkg.name>tb-coap-transport</pkg.name> |
38 | 38 | <docker.name>tb-coap-transport</docker.name> |
39 | - <pkg.user>thingsboard</pkg.user> | |
40 | 39 | <pkg.logFolder>/var/log/${pkg.name}</pkg.logFolder> |
41 | 40 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
42 | 41 | </properties> | ... | ... |
... | ... | @@ -25,6 +25,8 @@ export LOADER_PATH=/config,${LOADER_PATH} |
25 | 25 | |
26 | 26 | echo "Starting '${project.name}' ..." |
27 | 27 | |
28 | +cd ${pkg.installFolder}/bin | |
29 | + | |
28 | 30 | exec java -cp ${jarfile} $JAVA_OPTS -Dloader.main=org.thingsboard.server.http.ThingsboardHttpTransportApplication \ |
29 | 31 | -Dspring.jpa.hibernate.ddl-auto=none \ |
30 | 32 | -Dlogging.config=/config/logback.xml \ | ... | ... |
... | ... | @@ -36,7 +36,6 @@ |
36 | 36 | <main.dir>${basedir}/../../..</main.dir> |
37 | 37 | <pkg.name>tb-http-transport</pkg.name> |
38 | 38 | <docker.name>tb-http-transport</docker.name> |
39 | - <pkg.user>thingsboard</pkg.user> | |
40 | 39 | <pkg.logFolder>/var/log/${pkg.name}</pkg.logFolder> |
41 | 40 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
42 | 41 | </properties> | ... | ... |
... | ... | @@ -25,6 +25,8 @@ export LOADER_PATH=/config,${LOADER_PATH} |
25 | 25 | |
26 | 26 | echo "Starting '${project.name}' ..." |
27 | 27 | |
28 | +cd ${pkg.installFolder}/bin | |
29 | + | |
28 | 30 | exec java -cp ${jarfile} $JAVA_OPTS -Dloader.main=org.thingsboard.server.mqtt.ThingsboardMqttTransportApplication \ |
29 | 31 | -Dspring.jpa.hibernate.ddl-auto=none \ |
30 | 32 | -Dlogging.config=/config/logback.xml \ | ... | ... |
... | ... | @@ -36,7 +36,6 @@ |
36 | 36 | <main.dir>${basedir}/../../..</main.dir> |
37 | 37 | <pkg.name>tb-mqtt-transport</pkg.name> |
38 | 38 | <docker.name>tb-mqtt-transport</docker.name> |
39 | - <pkg.user>thingsboard</pkg.user> | |
40 | 39 | <pkg.logFolder>/var/log/${pkg.name}</pkg.logFolder> |
41 | 40 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
42 | 41 | </properties> | ... | ... |
... | ... | @@ -14,7 +14,7 @@ |
14 | 14 | # limitations under the License. |
15 | 15 | # |
16 | 16 | |
17 | -FROM debian:stretch | |
17 | +FROM thingsboard/base | |
18 | 18 | |
19 | 19 | COPY start-web-ui.sh ${pkg.name}.deb /tmp/ |
20 | 20 | |
... | ... | @@ -25,4 +25,6 @@ RUN dpkg -i /tmp/${pkg.name}.deb |
25 | 25 | |
26 | 26 | RUN update-rc.d ${pkg.name} disable |
27 | 27 | |
28 | +USER ${pkg.user} | |
29 | + | |
28 | 30 | CMD ["start-web-ui.sh"] | ... | ... |
... | ... | @@ -36,7 +36,6 @@ |
36 | 36 | <main.dir>${basedir}/../..</main.dir> |
37 | 37 | <pkg.name>tb-web-ui</pkg.name> |
38 | 38 | <docker.name>tb-web-ui</docker.name> |
39 | - <pkg.user>thingsboard</pkg.user> | |
40 | 39 | <pkg.unixLogFolder>/var/log/${pkg.name}</pkg.unixLogFolder> |
41 | 40 | <pkg.installFolder>/usr/share/${pkg.name}</pkg.installFolder> |
42 | 41 | <pkg.linux.dist>${project.build.directory}/package/linux</pkg.linux.dist> | ... | ... |
... | ... | @@ -29,6 +29,7 @@ |
29 | 29 | |
30 | 30 | <properties> |
31 | 31 | <main.dir>${basedir}</main.dir> |
32 | + <pkg.user>thingsboard</pkg.user> | |
32 | 33 | <spring-boot.version>2.1.3.RELEASE</spring-boot.version> |
33 | 34 | <spring.version>5.1.5.RELEASE</spring.version> |
34 | 35 | <spring-security.version>5.1.4.RELEASE</spring-security.version> |
... | ... | @@ -44,7 +45,7 @@ |
44 | 45 | <cassandra.version>3.6.0</cassandra.version> |
45 | 46 | <cassandra-unit.version>3.5.0.1</cassandra-unit.version> |
46 | 47 | <takari-cpsuite.version>1.2.7</takari-cpsuite.version> |
47 | - <guava.version>21.0</guava.version> | |
48 | + <guava.version>28.2-jre</guava.version> | |
48 | 49 | <caffeine.version>2.6.1</caffeine.version> |
49 | 50 | <commons-lang3.version>3.4</commons-lang3.version> |
50 | 51 | <commons-validator.version>1.6</commons-validator.version> |
... | ... | @@ -63,7 +64,7 @@ |
63 | 64 | <mail.version>1.4.3</mail.version> |
64 | 65 | <curator.version>4.2.0</curator.version> |
65 | 66 | <zookeeper.version>3.5.5</zookeeper.version> |
66 | - <protobuf.version>3.6.1</protobuf.version> | |
67 | + <protobuf.version>3.11.4</protobuf.version> | |
67 | 68 | <grpc.version>1.22.1</grpc.version> |
68 | 69 | <lombok.version>1.16.18</lombok.version> |
69 | 70 | <paho.client.version>1.1.0</paho.client.version> | ... | ... |
... | ... | @@ -20,6 +20,7 @@ import com.google.common.cache.CacheLoader; |
20 | 20 | import com.google.common.cache.LoadingCache; |
21 | 21 | import com.google.common.util.concurrent.Futures; |
22 | 22 | import com.google.common.util.concurrent.ListenableFuture; |
23 | +import com.google.common.util.concurrent.MoreExecutors; | |
23 | 24 | import lombok.AllArgsConstructor; |
24 | 25 | import lombok.Data; |
25 | 26 | import lombok.NoArgsConstructor; |
... | ... | @@ -54,9 +55,9 @@ import java.util.List; |
54 | 55 | import java.util.Optional; |
55 | 56 | import java.util.concurrent.TimeUnit; |
56 | 57 | |
58 | +import static org.thingsboard.common.util.DonAsynchron.withCallback; | |
57 | 59 | import static org.thingsboard.rule.engine.api.TbRelationTypes.FAILURE; |
58 | 60 | import static org.thingsboard.rule.engine.api.TbRelationTypes.SUCCESS; |
59 | -import static org.thingsboard.common.util.DonAsynchron.withCallback; | |
60 | 61 | |
61 | 62 | @Slf4j |
62 | 63 | public abstract class TbAbstractRelationActionNode<C extends TbAbstractRelationActionNodeConfiguration> implements TbNode { |
... | ... | @@ -86,7 +87,7 @@ public abstract class TbAbstractRelationActionNode<C extends TbAbstractRelationA |
86 | 87 | } |
87 | 88 | |
88 | 89 | protected ListenableFuture<RelationContainer> processEntityRelationAction(TbContext ctx, TbMsg msg) { |
89 | - return Futures.transformAsync(getEntity(ctx, msg), entityContainer -> doProcessEntityRelationAction(ctx, msg, entityContainer)); | |
90 | + return Futures.transformAsync(getEntity(ctx, msg), entityContainer -> doProcessEntityRelationAction(ctx, msg, entityContainer), MoreExecutors.directExecutor()); | |
90 | 91 | } |
91 | 92 | |
92 | 93 | protected abstract boolean createEntityIfNotExists(); | ... | ... |
... | ... | @@ -18,12 +18,13 @@ package org.thingsboard.rule.engine.action; |
18 | 18 | import com.fasterxml.jackson.databind.JsonNode; |
19 | 19 | import com.google.common.util.concurrent.Futures; |
20 | 20 | import com.google.common.util.concurrent.ListenableFuture; |
21 | +import com.google.common.util.concurrent.MoreExecutors; | |
21 | 22 | import lombok.extern.slf4j.Slf4j; |
22 | -import org.thingsboard.rule.engine.api.util.TbNodeUtils; | |
23 | 23 | import org.thingsboard.rule.engine.api.RuleNode; |
24 | 24 | import org.thingsboard.rule.engine.api.TbContext; |
25 | 25 | import org.thingsboard.rule.engine.api.TbNodeConfiguration; |
26 | 26 | import org.thingsboard.rule.engine.api.TbNodeException; |
27 | +import org.thingsboard.rule.engine.api.util.TbNodeUtils; | |
27 | 28 | import org.thingsboard.server.common.data.alarm.Alarm; |
28 | 29 | import org.thingsboard.server.common.data.alarm.AlarmStatus; |
29 | 30 | import org.thingsboard.server.common.data.plugin.ComponentType; |
... | ... | @@ -80,8 +81,8 @@ public class TbClearAlarmNode extends TbAbstractAlarmNode<TbClearAlarmNodeConfig |
80 | 81 | } |
81 | 82 | alarm.setStatus(alarm.getStatus().isAck() ? AlarmStatus.CLEARED_ACK : AlarmStatus.CLEARED_UNACK); |
82 | 83 | return Futures.immediateFuture(new AlarmResult(false, false, true, alarm)); |
83 | - }); | |
84 | - }); | |
84 | + }, MoreExecutors.directExecutor()); | |
85 | + }, MoreExecutors.directExecutor()); | |
85 | 86 | }, ctx.getDbCallbackExecutor()); |
86 | 87 | } |
87 | 88 | } | ... | ... |
... | ... | @@ -20,6 +20,7 @@ import com.fasterxml.jackson.databind.ObjectMapper; |
20 | 20 | import com.google.common.base.Function; |
21 | 21 | import com.google.common.util.concurrent.Futures; |
22 | 22 | import com.google.common.util.concurrent.ListenableFuture; |
23 | +import com.google.common.util.concurrent.MoreExecutors; | |
23 | 24 | import lombok.extern.slf4j.Slf4j; |
24 | 25 | import org.thingsboard.rule.engine.api.RuleNode; |
25 | 26 | import org.thingsboard.rule.engine.api.TbContext; |
... | ... | @@ -108,18 +109,18 @@ public class TbCreateAlarmNode extends TbAbstractAlarmNode<TbCreateAlarmNodeConf |
108 | 109 | private ListenableFuture<AlarmResult> createNewAlarm(TbContext ctx, TbMsg msg, Alarm msgAlarm) { |
109 | 110 | ListenableFuture<Alarm> asyncAlarm; |
110 | 111 | if (msgAlarm != null) { |
111 | - asyncAlarm = Futures.immediateCheckedFuture(msgAlarm); | |
112 | + asyncAlarm = Futures.immediateFuture(msgAlarm); | |
112 | 113 | } else { |
113 | 114 | ctx.logJsEvalRequest(); |
114 | 115 | asyncAlarm = Futures.transform(buildAlarmDetails(ctx, msg, null), |
115 | 116 | details -> { |
116 | 117 | ctx.logJsEvalResponse(); |
117 | 118 | return buildAlarm(msg, details, ctx.getTenantId()); |
118 | - }); | |
119 | + }, MoreExecutors.directExecutor()); | |
119 | 120 | } |
120 | 121 | ListenableFuture<Alarm> asyncCreated = Futures.transform(asyncAlarm, |
121 | 122 | alarm -> ctx.getAlarmService().createOrUpdateAlarm(alarm), ctx.getDbCallbackExecutor()); |
122 | - return Futures.transform(asyncCreated, alarm -> new AlarmResult(true, false, false, alarm)); | |
123 | + return Futures.transform(asyncCreated, alarm -> new AlarmResult(true, false, false, alarm), MoreExecutors.directExecutor()); | |
123 | 124 | } |
124 | 125 | |
125 | 126 | private ListenableFuture<AlarmResult> updateAlarm(TbContext ctx, TbMsg msg, Alarm existingAlarm, Alarm msgAlarm) { |
... | ... | @@ -140,7 +141,7 @@ public class TbCreateAlarmNode extends TbAbstractAlarmNode<TbCreateAlarmNodeConf |
140 | 141 | return ctx.getAlarmService().createOrUpdateAlarm(existingAlarm); |
141 | 142 | }, ctx.getDbCallbackExecutor()); |
142 | 143 | |
143 | - return Futures.transform(asyncUpdated, a -> new AlarmResult(false, true, false, a)); | |
144 | + return Futures.transform(asyncUpdated, a -> new AlarmResult(false, true, false, a), MoreExecutors.directExecutor()); | |
144 | 145 | } |
145 | 146 | |
146 | 147 | private Alarm buildAlarm(TbMsg msg, JsonNode details, TenantId tenantId) { | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.rule.engine.action; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | 22 | import org.thingsboard.rule.engine.api.RuleNode; |
22 | 23 | import org.thingsboard.rule.engine.api.TbContext; |
... | ... | @@ -81,7 +82,7 @@ public class TbCreateRelationNode extends TbAbstractRelationActionNode<TbCreateR |
81 | 82 | } |
82 | 83 | container.setResult(result); |
83 | 84 | return container; |
84 | - }); | |
85 | + }, MoreExecutors.directExecutor()); | |
85 | 86 | } |
86 | 87 | |
87 | 88 | private ListenableFuture<Boolean> createIfAbsent(TbContext ctx, TbMsg msg, EntityContainer entityContainer) { |
... | ... | @@ -120,7 +121,7 @@ public class TbCreateRelationNode extends TbAbstractRelationActionNode<TbCreateR |
120 | 121 | for (EntityRelation relation : entityRelations) { |
121 | 122 | list.add(ctx.getRelationService().deleteRelationAsync(ctx.getTenantId(), relation)); |
122 | 123 | } |
123 | - return Futures.transform(Futures.allAsList(list), result -> false); | |
124 | + return Futures.transform(Futures.allAsList(list), result -> false, MoreExecutors.directExecutor()); | |
124 | 125 | } |
125 | 126 | return Futures.immediateFuture(false); |
126 | 127 | }, ctx.getDbCallbackExecutor()); |
... | ... | @@ -161,7 +162,7 @@ public class TbCreateRelationNode extends TbAbstractRelationActionNode<TbCreateR |
161 | 162 | } else { |
162 | 163 | return Futures.immediateFuture(true); |
163 | 164 | } |
164 | - }); | |
165 | + }, MoreExecutors.directExecutor()); | |
165 | 166 | } |
166 | 167 | |
167 | 168 | private ListenableFuture<Boolean> processAsset(TbContext ctx, EntityContainer entityContainer, SearchDirectionIds sdId) { | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.rule.engine.action; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | 22 | import org.thingsboard.rule.engine.api.RuleNode; |
22 | 23 | import org.thingsboard.rule.engine.api.TbContext; |
... | ... | @@ -66,17 +67,18 @@ public class TbDeleteRelationNode extends TbAbstractRelationActionNode<TbDeleteR |
66 | 67 | |
67 | 68 | @Override |
68 | 69 | protected ListenableFuture<RelationContainer> doProcessEntityRelationAction(TbContext ctx, TbMsg msg, EntityContainer entityContainer) { |
69 | - return Futures.transform(processSingle(ctx, msg, entityContainer), result -> new RelationContainer(msg, result)); | |
70 | + return Futures.transform(processSingle(ctx, msg, entityContainer), result -> new RelationContainer(msg, result), MoreExecutors.directExecutor()); | |
70 | 71 | } |
71 | 72 | |
72 | 73 | private ListenableFuture<RelationContainer> getRelationContainerListenableFuture(TbContext ctx, TbMsg msg) { |
73 | 74 | relationType = processPattern(msg, config.getRelationType()); |
74 | 75 | if (config.isDeleteForSingleEntity()) { |
75 | - return Futures.transformAsync(getEntity(ctx, msg), entityContainer -> doProcessEntityRelationAction(ctx, msg, entityContainer)); | |
76 | + return Futures.transformAsync(getEntity(ctx, msg), entityContainer -> doProcessEntityRelationAction(ctx, msg, entityContainer), MoreExecutors.directExecutor()); | |
76 | 77 | } else { |
77 | - return Futures.transform(processList(ctx, msg), result -> new RelationContainer(msg, result)); | |
78 | + return Futures.transform(processList(ctx, msg), result -> new RelationContainer(msg, result), MoreExecutors.directExecutor()); | |
78 | 79 | } |
79 | 80 | } |
81 | + | |
80 | 82 | private ListenableFuture<Boolean> processList(TbContext ctx, TbMsg msg) { |
81 | 83 | return Futures.transformAsync(processListSearchDirection(ctx, msg), entityRelations -> { |
82 | 84 | if (entityRelations.isEmpty()) { |
... | ... | @@ -93,9 +95,9 @@ public class TbDeleteRelationNode extends TbAbstractRelationActionNode<TbDeleteR |
93 | 95 | } |
94 | 96 | } |
95 | 97 | return Futures.immediateFuture(true); |
96 | - }); | |
98 | + }, MoreExecutors.directExecutor()); | |
97 | 99 | } |
98 | - }); | |
100 | + }, MoreExecutors.directExecutor()); | |
99 | 101 | } |
100 | 102 | |
101 | 103 | private ListenableFuture<Boolean> processSingle(TbContext ctx, TbMsg msg, EntityContainer entityContainer) { |
... | ... | @@ -106,7 +108,7 @@ public class TbDeleteRelationNode extends TbAbstractRelationActionNode<TbDeleteR |
106 | 108 | return processSingleDeleteRelation(ctx, sdId); |
107 | 109 | } |
108 | 110 | return Futures.immediateFuture(true); |
109 | - }); | |
111 | + }, MoreExecutors.directExecutor()); | |
110 | 112 | } |
111 | 113 | |
112 | 114 | private ListenableFuture<Boolean> processSingleDeleteRelation(TbContext ctx, SearchDirectionIds sdId) { | ... | ... |
1 | +/** | |
2 | + * Copyright © 2016-2020 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.rule.engine.filter; | |
17 | + | |
18 | +import com.fasterxml.jackson.databind.ObjectMapper; | |
19 | +import com.google.common.util.concurrent.FutureCallback; | |
20 | +import com.google.common.util.concurrent.Futures; | |
21 | +import com.google.common.util.concurrent.ListenableFuture; | |
22 | +import com.google.common.util.concurrent.MoreExecutors; | |
23 | +import lombok.extern.slf4j.Slf4j; | |
24 | +import org.thingsboard.rule.engine.api.RuleNode; | |
25 | +import org.thingsboard.rule.engine.api.TbContext; | |
26 | +import org.thingsboard.rule.engine.api.TbNode; | |
27 | +import org.thingsboard.rule.engine.api.TbNodeConfiguration; | |
28 | +import org.thingsboard.rule.engine.api.TbNodeException; | |
29 | +import org.thingsboard.rule.engine.api.util.TbNodeUtils; | |
30 | +import org.thingsboard.server.common.data.alarm.Alarm; | |
31 | +import org.thingsboard.server.common.data.alarm.AlarmStatus; | |
32 | +import org.thingsboard.server.common.data.plugin.ComponentType; | |
33 | +import org.thingsboard.server.common.msg.TbMsg; | |
34 | + | |
35 | +import javax.annotation.Nullable; | |
36 | +import java.io.IOException; | |
37 | + | |
38 | +@Slf4j | |
39 | +@RuleNode( | |
40 | + type = ComponentType.FILTER, | |
41 | + name = "checks alarm status", | |
42 | + configClazz = TbCheckAlarmStatusNodeConfig.class, | |
43 | + relationTypes = {"True", "False"}, | |
44 | + nodeDescription = "Checks alarm status.", | |
45 | + nodeDetails = "If the alarm status matches the specified one - msg is success if does not match - msg is failure.", | |
46 | + uiResources = {"static/rulenode/rulenode-core-config.js"}, | |
47 | + configDirective = "tbFilterNodeCheckAlarmStatusConfig") | |
48 | +public class TbCheckAlarmStatusNode implements TbNode { | |
49 | + private TbCheckAlarmStatusNodeConfig config; | |
50 | + private final ObjectMapper mapper = new ObjectMapper(); | |
51 | + | |
52 | + @Override | |
53 | + public void init(TbContext tbContext, TbNodeConfiguration configuration) throws TbNodeException { | |
54 | + this.config = TbNodeUtils.convert(configuration, TbCheckAlarmStatusNodeConfig.class); | |
55 | + } | |
56 | + | |
57 | + @Override | |
58 | + public void onMsg(TbContext ctx, TbMsg msg) throws TbNodeException { | |
59 | + try { | |
60 | + Alarm alarm = mapper.readValue(msg.getData(), Alarm.class); | |
61 | + | |
62 | + ListenableFuture<Alarm> latest = ctx.getAlarmService().findAlarmByIdAsync(ctx.getTenantId(), alarm.getId()); | |
63 | + | |
64 | + Futures.addCallback(latest, new FutureCallback<Alarm>() { | |
65 | + @Override | |
66 | + public void onSuccess(@Nullable Alarm result) { | |
67 | + if (result != null) { | |
68 | + boolean isPresent = false; | |
69 | + for (AlarmStatus alarmStatus : config.getAlarmStatusList()) { | |
70 | + if (alarm.getStatus() == alarmStatus) { | |
71 | + isPresent = true; | |
72 | + break; | |
73 | + } | |
74 | + } | |
75 | + | |
76 | + if (isPresent) { | |
77 | + ctx.tellNext(msg, "True"); | |
78 | + } else { | |
79 | + ctx.tellNext(msg, "False"); | |
80 | + } | |
81 | + } else { | |
82 | + ctx.tellFailure(msg, new TbNodeException("No such Alarm found.")); | |
83 | + } | |
84 | + } | |
85 | + | |
86 | + @Override | |
87 | + public void onFailure(Throwable t) { | |
88 | + ctx.tellFailure(msg, t); | |
89 | + } | |
90 | + }, MoreExecutors.directExecutor()); | |
91 | + } catch (IOException e) { | |
92 | + log.error("Failed to parse alarm: [{}]", msg.getData()); | |
93 | + throw new TbNodeException(e); | |
94 | + } | |
95 | + } | |
96 | + | |
97 | + @Override | |
98 | + public void destroy() { | |
99 | + } | |
100 | +} | ... | ... |
1 | +/** | |
2 | + * Copyright © 2016-2020 The Thingsboard Authors | |
3 | + * | |
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | |
5 | + * you may not use this file except in compliance with the License. | |
6 | + * You may obtain a copy of the License at | |
7 | + * | |
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | |
9 | + * | |
10 | + * Unless required by applicable law or agreed to in writing, software | |
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | |
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
13 | + * See the License for the specific language governing permissions and | |
14 | + * limitations under the License. | |
15 | + */ | |
16 | +package org.thingsboard.rule.engine.filter; | |
17 | + | |
18 | +import lombok.Data; | |
19 | +import org.thingsboard.rule.engine.api.NodeConfiguration; | |
20 | +import org.thingsboard.server.common.data.alarm.AlarmStatus; | |
21 | + | |
22 | +import java.util.Arrays; | |
23 | +import java.util.List; | |
24 | + | |
25 | +@Data | |
26 | +public class TbCheckAlarmStatusNodeConfig implements NodeConfiguration<TbCheckAlarmStatusNodeConfig> { | |
27 | + private List<AlarmStatus> alarmStatusList; | |
28 | + | |
29 | + @Override | |
30 | + public TbCheckAlarmStatusNodeConfig defaultConfiguration() { | |
31 | + TbCheckAlarmStatusNodeConfig config = new TbCheckAlarmStatusNodeConfig(); | |
32 | + config.setAlarmStatusList(Arrays.asList(AlarmStatus.ACTIVE_ACK, AlarmStatus.ACTIVE_UNACK)); | |
33 | + return config; | |
34 | + } | |
35 | +} | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.rule.engine.filter; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | 22 | import org.thingsboard.rule.engine.api.RuleNode; |
22 | 23 | import org.thingsboard.rule.engine.api.TbContext; |
... | ... | @@ -87,10 +88,10 @@ public class TbCheckRelationNode implements TbNode { |
87 | 88 | private ListenableFuture<Boolean> processList(TbContext ctx, TbMsg msg) { |
88 | 89 | if (EntitySearchDirection.FROM.name().equals(config.getDirection())) { |
89 | 90 | return Futures.transformAsync(ctx.getRelationService() |
90 | - .findByToAndTypeAsync(ctx.getTenantId(), msg.getOriginator(), config.getRelationType(), RelationTypeGroup.COMMON), this::isEmptyList); | |
91 | + .findByToAndTypeAsync(ctx.getTenantId(), msg.getOriginator(), config.getRelationType(), RelationTypeGroup.COMMON), this::isEmptyList, MoreExecutors.directExecutor()); | |
91 | 92 | } else { |
92 | 93 | return Futures.transformAsync(ctx.getRelationService() |
93 | - .findByFromAndTypeAsync(ctx.getTenantId(), msg.getOriginator(), config.getRelationType(), RelationTypeGroup.COMMON), this::isEmptyList); | |
94 | + .findByFromAndTypeAsync(ctx.getTenantId(), msg.getOriginator(), config.getRelationType(), RelationTypeGroup.COMMON), this::isEmptyList, MoreExecutors.directExecutor()); | |
94 | 95 | } |
95 | 96 | } |
96 | 97 | ... | ... |
... | ... | @@ -21,6 +21,7 @@ import com.fasterxml.jackson.databind.ObjectMapper; |
21 | 21 | import com.fasterxml.jackson.databind.node.ObjectNode; |
22 | 22 | import com.google.common.util.concurrent.Futures; |
23 | 23 | import com.google.common.util.concurrent.ListenableFuture; |
24 | +import com.google.common.util.concurrent.MoreExecutors; | |
24 | 25 | import com.google.gson.JsonParseException; |
25 | 26 | import org.apache.commons.collections.CollectionUtils; |
26 | 27 | import org.apache.commons.lang3.BooleanUtils; |
... | ... | @@ -122,7 +123,7 @@ public abstract class TbAbstractGetAttributesNode<C extends TbGetAttributesNodeC |
122 | 123 | } |
123 | 124 | } |
124 | 125 | return null; |
125 | - }); | |
126 | + }, MoreExecutors.directExecutor()); | |
126 | 127 | } |
127 | 128 | |
128 | 129 | private ListenableFuture<Void> putLatestTelemetry(TbContext ctx, EntityId entityId, TbMsg msg, String scope, List<String> keys, ConcurrentHashMap<String, List<String>> failuresMap) { |
... | ... | @@ -152,7 +153,7 @@ public abstract class TbAbstractGetAttributesNode<C extends TbGetAttributesNodeC |
152 | 153 | } |
153 | 154 | }); |
154 | 155 | return null; |
155 | - }); | |
156 | + }, MoreExecutors.directExecutor()); | |
156 | 157 | } |
157 | 158 | |
158 | 159 | private void putValueWithTs(TbMsg msg, TsKvEntry r) { | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.rule.engine.metadata; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import com.google.gson.Gson; |
21 | 22 | import com.google.gson.JsonElement; |
22 | 23 | import com.google.gson.JsonObject; |
... | ... | @@ -37,15 +38,16 @@ import org.thingsboard.server.common.msg.TbMsgMetaData; |
37 | 38 | import java.lang.reflect.Type; |
38 | 39 | import java.util.Map; |
39 | 40 | |
40 | -import static org.thingsboard.rule.engine.api.TbRelationTypes.SUCCESS; | |
41 | 41 | import static org.thingsboard.common.util.DonAsynchron.withCallback; |
42 | +import static org.thingsboard.rule.engine.api.TbRelationTypes.SUCCESS; | |
42 | 43 | |
43 | 44 | @Slf4j |
44 | 45 | public abstract class TbAbstractGetEntityDetailsNode<C extends TbAbstractGetEntityDetailsNodeConfiguration> implements TbNode { |
45 | 46 | |
46 | 47 | private static final Gson gson = new Gson(); |
47 | 48 | private static final JsonParser jsonParser = new JsonParser(); |
48 | - private static final Type TYPE = new TypeToken<Map<String, String>>() {}.getType(); | |
49 | + private static final Type TYPE = new TypeToken<Map<String, String>>() { | |
50 | + }.getType(); | |
49 | 51 | |
50 | 52 | protected C config; |
51 | 53 | |
... | ... | @@ -104,7 +106,7 @@ public abstract class TbAbstractGetEntityDetailsNode<C extends TbAbstractGetEnti |
104 | 106 | } else { |
105 | 107 | return Futures.immediateFuture(null); |
106 | 108 | } |
107 | - }); | |
109 | + }, MoreExecutors.directExecutor()); | |
108 | 110 | } |
109 | 111 | |
110 | 112 | private ListenableFuture<JsonElement> addContactProperties(JsonElement data, ListenableFuture<ContactBased> entityFuture, EntityDetails entityDetails, String prefix) { |
... | ... | @@ -114,7 +116,7 @@ public abstract class TbAbstractGetEntityDetailsNode<C extends TbAbstractGetEnti |
114 | 116 | } else { |
115 | 117 | return Futures.immediateFuture(null); |
116 | 118 | } |
117 | - }); | |
119 | + }, MoreExecutors.directExecutor()); | |
118 | 120 | } |
119 | 121 | |
120 | 122 | private JsonElement setProperties(ContactBased entity, JsonElement data, EntityDetails entityDetails, String prefix) { | ... | ... |
... | ... | @@ -17,12 +17,13 @@ package org.thingsboard.rule.engine.metadata; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | -import org.thingsboard.rule.engine.api.util.TbNodeUtils; | |
22 | 22 | import org.thingsboard.rule.engine.api.TbContext; |
23 | 23 | import org.thingsboard.rule.engine.api.TbNode; |
24 | 24 | import org.thingsboard.rule.engine.api.TbNodeConfiguration; |
25 | 25 | import org.thingsboard.rule.engine.api.TbNodeException; |
26 | +import org.thingsboard.rule.engine.api.util.TbNodeUtils; | |
26 | 27 | import org.thingsboard.server.common.data.id.EntityId; |
27 | 28 | import org.thingsboard.server.common.data.kv.AttributeKvEntry; |
28 | 29 | import org.thingsboard.server.common.data.kv.KvEntry; |
... | ... | @@ -60,7 +61,7 @@ public abstract class TbEntityGetAttrNode<T extends EntityId> implements TbNode |
60 | 61 | } |
61 | 62 | |
62 | 63 | private void safeGetAttributes(TbContext ctx, TbMsg msg, T entityId) { |
63 | - if(entityId == null || entityId.isNullUid()) { | |
64 | + if (entityId == null || entityId.isNullUid()) { | |
64 | 65 | ctx.tellNext(msg, FAILURE); |
65 | 66 | return; |
66 | 67 | } |
... | ... | @@ -73,13 +74,13 @@ public abstract class TbEntityGetAttrNode<T extends EntityId> implements TbNode |
73 | 74 | private ListenableFuture<List<KvEntry>> getAttributesAsync(TbContext ctx, EntityId entityId) { |
74 | 75 | ListenableFuture<List<AttributeKvEntry>> latest = ctx.getAttributesService().find(ctx.getTenantId(), entityId, SERVER_SCOPE, config.getAttrMapping().keySet()); |
75 | 76 | return Futures.transform(latest, l -> |
76 | - l.stream().map(i -> (KvEntry) i).collect(Collectors.toList())); | |
77 | + l.stream().map(i -> (KvEntry) i).collect(Collectors.toList()), MoreExecutors.directExecutor()); | |
77 | 78 | } |
78 | 79 | |
79 | 80 | private ListenableFuture<List<KvEntry>> getLatestTelemetry(TbContext ctx, EntityId entityId) { |
80 | 81 | ListenableFuture<List<TsKvEntry>> latest = ctx.getTimeseriesService().findLatest(ctx.getTenantId(), entityId, config.getAttrMapping().keySet()); |
81 | 82 | return Futures.transform(latest, l -> |
82 | - l.stream().map(i -> (KvEntry) i).collect(Collectors.toList())); | |
83 | + l.stream().map(i -> (KvEntry) i).collect(Collectors.toList()), MoreExecutors.directExecutor()); | |
83 | 84 | } |
84 | 85 | |
85 | 86 | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.rule.engine.metadata; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | 22 | import org.thingsboard.rule.engine.api.RuleNode; |
22 | 23 | import org.thingsboard.rule.engine.api.TbContext; |
... | ... | @@ -63,7 +64,7 @@ public class TbGetCustomerDetailsNode extends TbAbstractGetEntityDetailsNode<TbG |
63 | 64 | } else { |
64 | 65 | return Futures.immediateFuture(null); |
65 | 66 | } |
66 | - }); | |
67 | + }, MoreExecutors.directExecutor()); | |
67 | 68 | } |
68 | 69 | |
69 | 70 | private ListenableFuture<Customer> getCustomer(TbContext ctx, TbMsg msg) { |
... | ... | @@ -79,7 +80,7 @@ public class TbGetCustomerDetailsNode extends TbAbstractGetEntityDetailsNode<TbG |
79 | 80 | } else { |
80 | 81 | return Futures.immediateFuture(null); |
81 | 82 | } |
82 | - }); | |
83 | + }, MoreExecutors.directExecutor()); | |
83 | 84 | case ASSET: |
84 | 85 | return Futures.transformAsync(ctx.getAssetService().findAssetByIdAsync(ctx.getTenantId(), new AssetId(msg.getOriginator().getId())), asset -> { |
85 | 86 | if (asset != null) { |
... | ... | @@ -91,7 +92,7 @@ public class TbGetCustomerDetailsNode extends TbAbstractGetEntityDetailsNode<TbG |
91 | 92 | } else { |
92 | 93 | return Futures.immediateFuture(null); |
93 | 94 | } |
94 | - }); | |
95 | + }, MoreExecutors.directExecutor()); | |
95 | 96 | case ENTITY_VIEW: |
96 | 97 | return Futures.transformAsync(ctx.getEntityViewService().findEntityViewByIdAsync(ctx.getTenantId(), new EntityViewId(msg.getOriginator().getId())), entityView -> { |
97 | 98 | if (entityView != null) { |
... | ... | @@ -103,7 +104,7 @@ public class TbGetCustomerDetailsNode extends TbAbstractGetEntityDetailsNode<TbG |
103 | 104 | } else { |
104 | 105 | return Futures.immediateFuture(null); |
105 | 106 | } |
106 | - }); | |
107 | + }, MoreExecutors.directExecutor()); | |
107 | 108 | default: |
108 | 109 | throw new RuntimeException("Entity with entityType '" + msg.getOriginator().getEntityType() + "' is not supported."); |
109 | 110 | } | ... | ... |
... | ... | @@ -17,16 +17,21 @@ package org.thingsboard.rule.engine.metadata; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | -import org.thingsboard.rule.engine.api.*; | |
22 | +import org.thingsboard.rule.engine.api.RuleNode; | |
23 | +import org.thingsboard.rule.engine.api.TbContext; | |
24 | +import org.thingsboard.rule.engine.api.TbNode; | |
25 | +import org.thingsboard.rule.engine.api.TbNodeConfiguration; | |
26 | +import org.thingsboard.rule.engine.api.TbNodeException; | |
22 | 27 | import org.thingsboard.rule.engine.api.util.TbNodeUtils; |
23 | 28 | import org.thingsboard.rule.engine.util.EntitiesFieldsAsyncLoader; |
24 | 29 | import org.thingsboard.server.common.data.id.EntityId; |
25 | 30 | import org.thingsboard.server.common.data.plugin.ComponentType; |
26 | 31 | import org.thingsboard.server.common.msg.TbMsg; |
27 | 32 | |
28 | -import static org.thingsboard.rule.engine.api.TbRelationTypes.SUCCESS; | |
29 | 33 | import static org.thingsboard.common.util.DonAsynchron.withCallback; |
34 | +import static org.thingsboard.rule.engine.api.TbRelationTypes.SUCCESS; | |
30 | 35 | |
31 | 36 | /** |
32 | 37 | * Created by ashvayka on 19.01.18. |
... | ... | @@ -71,7 +76,7 @@ public class TbGetOriginatorFieldsNode implements TbNode { |
71 | 76 | } |
72 | 77 | }); |
73 | 78 | return null; |
74 | - } | |
79 | + }, MoreExecutors.directExecutor() | |
75 | 80 | ); |
76 | 81 | } |
77 | 82 | } | ... | ... |
... | ... | @@ -17,6 +17,7 @@ package org.thingsboard.rule.engine.metadata; |
17 | 17 | |
18 | 18 | import com.google.common.util.concurrent.Futures; |
19 | 19 | import com.google.common.util.concurrent.ListenableFuture; |
20 | +import com.google.common.util.concurrent.MoreExecutors; | |
20 | 21 | import lombok.extern.slf4j.Slf4j; |
21 | 22 | import org.thingsboard.rule.engine.api.RuleNode; |
22 | 23 | import org.thingsboard.rule.engine.api.TbContext; |
... | ... | @@ -59,6 +60,6 @@ public class TbGetTenantDetailsNode extends TbAbstractGetEntityDetailsNode<TbGet |
59 | 60 | } else { |
60 | 61 | return Futures.immediateFuture(null); |
61 | 62 | } |
62 | - }); | |
63 | + }, MoreExecutors.directExecutor()); | |
63 | 64 | } |
64 | 65 | } | ... | ... |