@golemio/flow 1.2.4 → 1.2.5-dev.957761714
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/db/migrations/postgresql/20230803101255-update-detections-data.js +53 -0
- package/db/migrations/postgresql/sqls/20230803101255-update-detections-data-down.sql +125 -0
- package/db/migrations/postgresql/sqls/20230803101255-update-detections-data-up.sql +118 -0
- package/dist/output-gateway/models/PedestriansMeasurementsModel.js +5 -4
- package/dist/output-gateway/models/PedestriansMeasurementsModel.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var dbm;
|
|
4
|
+
var type;
|
|
5
|
+
var seed;
|
|
6
|
+
var fs = require('fs');
|
|
7
|
+
var path = require('path');
|
|
8
|
+
var Promise;
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* We receive the dbmigrate dependency from dbmigrate initially.
|
|
12
|
+
* This enables us to not have to rely on NODE_PATH.
|
|
13
|
+
*/
|
|
14
|
+
exports.setup = function(options, seedLink) {
|
|
15
|
+
dbm = options.dbmigrate;
|
|
16
|
+
type = dbm.dataType;
|
|
17
|
+
seed = seedLink;
|
|
18
|
+
Promise = options.Promise;
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
exports.up = function(db) {
|
|
22
|
+
var filePath = path.join(__dirname, 'sqls', '20230803101255-update-detections-data-up.sql');
|
|
23
|
+
return new Promise( function( resolve, reject ) {
|
|
24
|
+
fs.readFile(filePath, {encoding: 'utf-8'}, function(err,data){
|
|
25
|
+
if (err) return reject(err);
|
|
26
|
+
console.log('received data: ' + data);
|
|
27
|
+
|
|
28
|
+
resolve(data);
|
|
29
|
+
});
|
|
30
|
+
})
|
|
31
|
+
.then(function(data) {
|
|
32
|
+
return db.runSql(data);
|
|
33
|
+
});
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
exports.down = function(db) {
|
|
37
|
+
var filePath = path.join(__dirname, 'sqls', '20230803101255-update-detections-data-down.sql');
|
|
38
|
+
return new Promise( function( resolve, reject ) {
|
|
39
|
+
fs.readFile(filePath, {encoding: 'utf-8'}, function(err,data){
|
|
40
|
+
if (err) return reject(err);
|
|
41
|
+
console.log('received data: ' + data);
|
|
42
|
+
|
|
43
|
+
resolve(data);
|
|
44
|
+
});
|
|
45
|
+
})
|
|
46
|
+
.then(function(data) {
|
|
47
|
+
return db.runSql(data);
|
|
48
|
+
});
|
|
49
|
+
};
|
|
50
|
+
|
|
51
|
+
exports._meta = {
|
|
52
|
+
"version": 1
|
|
53
|
+
};
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
-- update_detections_data procedure definition
|
|
2
|
+
|
|
3
|
+
CREATE OR replace procedure update_detections_data()
|
|
4
|
+
LANGUAGE plpgsql
|
|
5
|
+
AS $$
|
|
6
|
+
declare
|
|
7
|
+
lastupdatetimestamp timestamptz;
|
|
8
|
+
lastupdateunix bigint;
|
|
9
|
+
begin
|
|
10
|
+
select
|
|
11
|
+
case
|
|
12
|
+
when flowmax.max_measured_from is not null
|
|
13
|
+
then flowmax.max_measured_from
|
|
14
|
+
else to_timestamp(0)
|
|
15
|
+
end as max_measured_from into lastupdatetimestamp
|
|
16
|
+
from (select max(measured_from) - interval '1 hours' as max_measured_from from flow.pedestrians_detections_api) flowMax;
|
|
17
|
+
|
|
18
|
+
lastupdateunix := extract ('epoch' from lastupdatetimestamp) * 1000;
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
insert into flow.pedestrians_detections_api
|
|
22
|
+
with wifi as (
|
|
23
|
+
select
|
|
24
|
+
pedestrians_wifi.location_id,
|
|
25
|
+
pedestrians_wifi.direction_id,
|
|
26
|
+
date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval as measured_from,
|
|
27
|
+
date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval + '00:15:00'::interval as measured_to,
|
|
28
|
+
sum(pedestrians_wifi.value) as value,
|
|
29
|
+
count(pedestrians_wifi.value) as count_n,
|
|
30
|
+
3 as quantity
|
|
31
|
+
from
|
|
32
|
+
flow.pedestrians_wifi
|
|
33
|
+
group by
|
|
34
|
+
pedestrians_wifi.location_id,
|
|
35
|
+
pedestrians_wifi.direction_id,
|
|
36
|
+
(date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval),
|
|
37
|
+
(date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval + '00:15:00'::interval)
|
|
38
|
+
) SELECT wifi.measured_from,
|
|
39
|
+
wifi.measured_to,
|
|
40
|
+
wifi.location_id,
|
|
41
|
+
wifi.direction_id,
|
|
42
|
+
wifi.value,
|
|
43
|
+
wifi.count_n::numeric / wifi.quantity::numeric AS quality
|
|
44
|
+
FROM wifi
|
|
45
|
+
where wifi.measured_from > lastupdatetimestamp
|
|
46
|
+
ON CONFLICT (location_id,direction_id,measured_from,measured_to)
|
|
47
|
+
DO update
|
|
48
|
+
SET value = EXCLUDED.value,
|
|
49
|
+
quality = EXCLUDED.quality;
|
|
50
|
+
|
|
51
|
+
insert into flow.pedestrians_detections_api
|
|
52
|
+
with pyro as (
|
|
53
|
+
select
|
|
54
|
+
cd.locations_id as location_id,
|
|
55
|
+
cd.directions_id as direction_id,
|
|
56
|
+
to_timestamp((cd.measured_from / 1000)::double precision) as measured_from,
|
|
57
|
+
to_timestamp((cd.measured_from / 1000)::double precision) + '00:15:00'::interval as measured_to,
|
|
58
|
+
sum(cd.value) as value,
|
|
59
|
+
1 as count_n,
|
|
60
|
+
1 as quantity
|
|
61
|
+
from flow.counters_detections cd
|
|
62
|
+
where
|
|
63
|
+
cd.category::text = 'pedestrian'::text
|
|
64
|
+
and (cd.directions_id::text in (select distinct pedestrians_directions_api.direction_id from flow.pedestrians_directions_api))
|
|
65
|
+
group by
|
|
66
|
+
cd.locations_id,
|
|
67
|
+
cd.directions_id,
|
|
68
|
+
(to_timestamp((cd.measured_from / 1000)::double precision)),
|
|
69
|
+
(to_timestamp((cd.measured_from / 1000)::double precision) + '00:15:00'::interval)
|
|
70
|
+
)
|
|
71
|
+
select
|
|
72
|
+
pyro.measured_from,
|
|
73
|
+
pyro.measured_to,
|
|
74
|
+
pyro.location_id,
|
|
75
|
+
pyro.direction_id,
|
|
76
|
+
pyro.value,
|
|
77
|
+
pyro.count_n::numeric / pyro.quantity::numeric as quality
|
|
78
|
+
from pyro
|
|
79
|
+
where pyro.measured_from > lastupdatetimestamp
|
|
80
|
+
ON CONFLICT (location_id,direction_id,measured_from,measured_to)
|
|
81
|
+
DO update
|
|
82
|
+
SET value = EXCLUDED.value,
|
|
83
|
+
quality = EXCLUDED.quality;
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
insert into flow.pedestrians_detections_api
|
|
87
|
+
with vyber as (
|
|
88
|
+
select * from flow.flow_measurements where flow_measurements.start_timestamp > lastupdateunix and category::text = 'pedestrian'::text
|
|
89
|
+
), flow as (
|
|
90
|
+
select
|
|
91
|
+
vyber.cube_id::character varying(50) as location_id,
|
|
92
|
+
vyber.sink_id::character varying(50) as direction_id,
|
|
93
|
+
date_trunc('hour'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision)) + (date_part('minute'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision))::integer / 15)::double precision * '00:15:00'::interval as measured_from,
|
|
94
|
+
date_trunc('hour'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision)) + (date_part('minute'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision))::integer / 15)::double precision * '00:15:00'::interval + '00:15:00'::interval as measured_to,
|
|
95
|
+
sum(vyber.value) as value,
|
|
96
|
+
count(vyber.value) as count_n,
|
|
97
|
+
3 as quantity
|
|
98
|
+
from
|
|
99
|
+
vyber
|
|
100
|
+
where
|
|
101
|
+
((vyber.cube_id::character varying(50)::text,
|
|
102
|
+
vyber.sink_id::character varying(50)::text) in (
|
|
103
|
+
select distinct
|
|
104
|
+
pedestrians_directions_api.cube_id as location_id,
|
|
105
|
+
pedestrians_directions_api.direction_id
|
|
106
|
+
from
|
|
107
|
+
flow.pedestrians_directions_api))
|
|
108
|
+
group by 1,2,3,4
|
|
109
|
+
) select
|
|
110
|
+
flow.measured_from,
|
|
111
|
+
flow.measured_to,
|
|
112
|
+
flow.location_id,
|
|
113
|
+
flow.direction_id,
|
|
114
|
+
flow.value,
|
|
115
|
+
flow.count_n::numeric / flow.quantity::numeric as quality
|
|
116
|
+
from flow
|
|
117
|
+
where flow.measured_from > lastupdatetimestamp
|
|
118
|
+
ON CONFLICT (location_id,direction_id,measured_from,measured_to)
|
|
119
|
+
DO update
|
|
120
|
+
SET value = EXCLUDED.value,
|
|
121
|
+
quality = EXCLUDED.quality;
|
|
122
|
+
end;
|
|
123
|
+
$$;
|
|
124
|
+
|
|
125
|
+
-- ^^
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
-- update_detections_data procedure definition
|
|
2
|
+
|
|
3
|
+
CREATE OR replace procedure update_detections_data()
|
|
4
|
+
LANGUAGE plpgsql
|
|
5
|
+
AS $$
|
|
6
|
+
declare
|
|
7
|
+
lastupdatetimestamp timestamptz;
|
|
8
|
+
lastupdateunix bigint;
|
|
9
|
+
begin
|
|
10
|
+
select
|
|
11
|
+
case
|
|
12
|
+
when flowmax.max_measured_from is not null
|
|
13
|
+
then flowmax.max_measured_from
|
|
14
|
+
else to_timestamp(0)
|
|
15
|
+
end as max_measured_from into lastupdatetimestamp
|
|
16
|
+
from (select max(measured_from) - interval '1 hours' as max_measured_from from flow.pedestrians_detections_api) flowMax;
|
|
17
|
+
|
|
18
|
+
lastupdateunix := extract ('epoch' from lastupdatetimestamp) * 1000;
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
insert into flow.pedestrians_detections_api
|
|
22
|
+
with wifi as (
|
|
23
|
+
select
|
|
24
|
+
pedestrians_wifi.location_id,
|
|
25
|
+
pedestrians_wifi.direction_id,
|
|
26
|
+
date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval as measured_from,
|
|
27
|
+
date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval + '00:15:00'::interval as measured_to,
|
|
28
|
+
sum(pedestrians_wifi.value) as value,
|
|
29
|
+
count(pedestrians_wifi.value) as count_n,
|
|
30
|
+
3 as quantity
|
|
31
|
+
from
|
|
32
|
+
flow.pedestrians_wifi
|
|
33
|
+
group by
|
|
34
|
+
pedestrians_wifi.location_id,
|
|
35
|
+
pedestrians_wifi.direction_id,
|
|
36
|
+
(date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval),
|
|
37
|
+
(date_trunc('hour'::text, pedestrians_wifi.measured_from) + (date_part('minute'::text, pedestrians_wifi.measured_from)::integer / 15)::double precision * '00:15:00'::interval + '00:15:00'::interval)
|
|
38
|
+
) SELECT wifi.measured_from,
|
|
39
|
+
wifi.measured_to,
|
|
40
|
+
wifi.location_id,
|
|
41
|
+
wifi.direction_id,
|
|
42
|
+
wifi.value,
|
|
43
|
+
wifi.count_n::numeric / wifi.quantity::numeric AS quality
|
|
44
|
+
FROM wifi
|
|
45
|
+
where wifi.measured_from > lastupdatetimestamp
|
|
46
|
+
ON CONFLICT (location_id,direction_id,measured_from,measured_to)
|
|
47
|
+
DO update
|
|
48
|
+
SET value = EXCLUDED.value,
|
|
49
|
+
quality = EXCLUDED.quality;
|
|
50
|
+
|
|
51
|
+
insert into flow.pedestrians_detections_api
|
|
52
|
+
with pyro as (
|
|
53
|
+
select
|
|
54
|
+
cd.locations_id as location_id,
|
|
55
|
+
cd.directions_id as direction_id,
|
|
56
|
+
to_timestamp((cd.measured_from / 1000)::double precision) as measured_from,
|
|
57
|
+
to_timestamp((cd.measured_from / 1000)::double precision) + '00:15:00'::interval as measured_to,
|
|
58
|
+
sum(cd.value) as value,
|
|
59
|
+
1 as count_n,
|
|
60
|
+
1 as quantity
|
|
61
|
+
from flow.counters_detections cd
|
|
62
|
+
where
|
|
63
|
+
cd.category::text = 'pedestrian'::text
|
|
64
|
+
and (cd.directions_id::text in (select distinct pedestrians_directions_api.direction_id from flow.pedestrians_directions_api))
|
|
65
|
+
group by
|
|
66
|
+
cd.locations_id,
|
|
67
|
+
cd.directions_id,
|
|
68
|
+
(to_timestamp((cd.measured_from / 1000)::double precision)),
|
|
69
|
+
(to_timestamp((cd.measured_from / 1000)::double precision) + '00:15:00'::interval)
|
|
70
|
+
)
|
|
71
|
+
select
|
|
72
|
+
pyro.measured_from,
|
|
73
|
+
pyro.measured_to,
|
|
74
|
+
pyro.location_id,
|
|
75
|
+
pyro.direction_id,
|
|
76
|
+
pyro.value,
|
|
77
|
+
pyro.count_n::numeric / pyro.quantity::numeric as quality
|
|
78
|
+
from pyro
|
|
79
|
+
where pyro.measured_from > lastupdatetimestamp
|
|
80
|
+
ON CONFLICT (location_id,direction_id,measured_from,measured_to)
|
|
81
|
+
DO update
|
|
82
|
+
SET value = EXCLUDED.value,
|
|
83
|
+
quality = EXCLUDED.quality;
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
insert into flow.pedestrians_detections_api
|
|
87
|
+
with vyber as (
|
|
88
|
+
select * from flow.flow_measurements where flow_measurements.start_timestamp > lastupdateunix and category::text = 'pedestrian'::text
|
|
89
|
+
), flow as (
|
|
90
|
+
select
|
|
91
|
+
pdi.location_id::character varying(50) as location_id,
|
|
92
|
+
vyber.sink_id::character varying(50) as direction_id,
|
|
93
|
+
date_trunc('hour'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision)) + (date_part('minute'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision))::integer / 15)::double precision * '00:15:00'::interval as measured_from,
|
|
94
|
+
date_trunc('hour'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision)) + (date_part('minute'::text, to_timestamp((vyber.start_timestamp / 1000)::double precision))::integer / 15)::double precision * '00:15:00'::interval + '00:15:00'::interval as measured_to,
|
|
95
|
+
sum(vyber.value) as value,
|
|
96
|
+
count(vyber.value) as count_n,
|
|
97
|
+
3 as quantity
|
|
98
|
+
from vyber
|
|
99
|
+
join flow.pedestrians_directions_api pdi
|
|
100
|
+
on vyber.cube_id::text = pdi.cube_id and vyber.sink_id::text = pdi.direction_id
|
|
101
|
+
group by 1,2,3,4
|
|
102
|
+
) select
|
|
103
|
+
flow.measured_from,
|
|
104
|
+
flow.measured_to,
|
|
105
|
+
flow.location_id,
|
|
106
|
+
flow.direction_id,
|
|
107
|
+
flow.value,
|
|
108
|
+
flow.count_n::numeric / flow.quantity::numeric as quality
|
|
109
|
+
from flow
|
|
110
|
+
where flow.measured_from > lastupdatetimestamp
|
|
111
|
+
ON CONFLICT (location_id,direction_id,measured_from,measured_to)
|
|
112
|
+
DO update
|
|
113
|
+
SET value = EXCLUDED.value,
|
|
114
|
+
quality = EXCLUDED.quality;
|
|
115
|
+
end;
|
|
116
|
+
$$;
|
|
117
|
+
|
|
118
|
+
-- ^^
|
|
@@ -41,10 +41,12 @@ class PedestriansMeasurementsModel extends models_1.SequelizeModel {
|
|
|
41
41
|
const where = {
|
|
42
42
|
[and]: [],
|
|
43
43
|
};
|
|
44
|
-
if (locationId)
|
|
44
|
+
if (locationId) {
|
|
45
45
|
where[and].push({ location_id: locationId });
|
|
46
|
-
|
|
46
|
+
}
|
|
47
|
+
if (directionId) {
|
|
47
48
|
where[and].push({ direction_id: directionId });
|
|
49
|
+
}
|
|
48
50
|
if (from) {
|
|
49
51
|
where[and].push({
|
|
50
52
|
measured_from: {
|
|
@@ -61,7 +63,7 @@ class PedestriansMeasurementsModel extends models_1.SequelizeModel {
|
|
|
61
63
|
}
|
|
62
64
|
const attributes = ["measured_from", "measured_to", "location_id", "direction_id", "value", "quality"];
|
|
63
65
|
order.push(["location_id", "DESC"]);
|
|
64
|
-
|
|
66
|
+
return yield this.sequelizeModel.findAll({
|
|
65
67
|
attributes,
|
|
66
68
|
limit,
|
|
67
69
|
offset,
|
|
@@ -69,7 +71,6 @@ class PedestriansMeasurementsModel extends models_1.SequelizeModel {
|
|
|
69
71
|
raw: true,
|
|
70
72
|
where,
|
|
71
73
|
});
|
|
72
|
-
return pedestriansMeasurementsFromDB;
|
|
73
74
|
}
|
|
74
75
|
catch (err) {
|
|
75
76
|
throw new golemio_errors_1.GeneralError("Database error", "PedestriansMeasurementsModel", err, 500);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"PedestriansMeasurementsModel.js","sourceRoot":"","sources":["../../../src/output-gateway/models/PedestriansMeasurementsModel.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,oFAA4D;AAC5D,6EAAwE;AACxE,qEAA0E;AAC1E,0DAAkC;AAElC,MAAa,4BAA6B,SAAQ,uBAAc;IAC5D;QACI,KAAK,CACD,YAAI,CAAC,0BAA0B,CAAC,IAAI,EACpC,YAAI,CAAC,0BAA0B,CAAC,WAAW,EAC3C,YAAI,CAAC,0BAA0B,CAAC,yBAAyB,EACzD;YACI,MAAM,EAAE,YAAI,CAAC,QAAQ;SACxB,CACJ,CAAC;QAGN;;;;;;;;;WASG;
|
|
1
|
+
{"version":3,"file":"PedestriansMeasurementsModel.js","sourceRoot":"","sources":["../../../src/output-gateway/models/PedestriansMeasurementsModel.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,oFAA4D;AAC5D,6EAAwE;AACxE,qEAA0E;AAC1E,0DAAkC;AAElC,MAAa,4BAA6B,SAAQ,uBAAc;IAC5D;QACI,KAAK,CACD,YAAI,CAAC,0BAA0B,CAAC,IAAI,EACpC,YAAI,CAAC,0BAA0B,CAAC,WAAW,EAC3C,YAAI,CAAC,0BAA0B,CAAC,yBAAyB,EACzD;YACI,MAAM,EAAE,YAAI,CAAC,QAAQ;SACxB,CACJ,CAAC;QAGN;;;;;;;;;WASG;QACI,WAAM,GAAG,CACZ,UAOI,EAAE,EACM,EAAE;YACd,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,UAAU,EAAE,WAAW,EAAE,IAAI,EAAE,EAAE,EAAE,GAAG,OAAO,CAAC;YACrE,IAAI;gBACA,wCAAwC;gBACxC,MAAM,GAAG,GAAW,mBAAS,CAAC,EAAE,CAAC,GAAG,CAAC;gBACrC,MAAM,KAAK,GAAU,EAAE,CAAC;gBACxB,MAAM,KAAK,GAAQ;oBACf,CAAC,GAAG,CAAC,EAAE,EAAE;iBACZ,CAAC;gBAEF,IAAI,UAAU,EAAE;oBACZ,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,WAAW,EAAE,UAAU,EAAE,CAAC,CAAC;iBAChD;gBAED,IAAI,WAAW,EAAE;oBACb,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,YAAY,EAAE,WAAW,EAAE,CAAC,CAAC;iBAClD;gBAED,IAAI,IAAI,EAAE;oBACN,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC;wBACZ,aAAa,EAAE;4BACX,CAAC,mBAAS,CAAC,EAAE,CAAC,GAAG,CAAC,EAAE,IAAI;yBAC3B;qBACJ,CAAC,CAAC;iBACN;gBAED,IAAI,EAAE,EAAE;oBACJ,KAAK,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC;wBACZ,WAAW,EAAE;4BACT,CAAC,mBAAS,CAAC,EAAE,CAAC,GAAG,CAAC,EAAE,EAAE;yBACzB;qBACJ,CAAC,CAAC;iBACN;gBAED,MAAM,UAAU,GAAa,CAAC,eAAe,EAAE,aAAa,EAAE,aAAa,EAAE,cAAc,EAAE,OAAO,EAAE,SAAS,CAAC,CAAC;gBAEjH,KAAK,CAAC,IAAI,CAAC,CAAC,aAAa,EAAE,MAAM,CAAC,CAAC,CAAC;gBAEpC,OAAO,MAAM,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC;oBACrC,UAAU;oBACV,KAAK;oBACL,MAAM;oBACN,KAAK;oBACL,GAAG,EAAE,IAAI;oBACT,KAAK;iBACR,CAAC,CAAC;aACN;YAAC,OAAO,GAAG,EAAE;gBACV,MAAM,IAAI,6BAAY,CAAC,gBAAgB,EAAE,8BAA8B,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC;aACtF;QACL,CAAC,CAAA,CAAC;QAEK,WAAM,GAAG,CAAO,EAAU,EAA0B,EAAE;YACzD,OAAO,IAAI,CAAC;QAChB,CAAC,CAAA,CAAC;IA1EF,CAAC;CA2EJ;AArFD,oEAqFC"}
|