I have a system composed of two main components, sensors and triggers.
The system is responsible for recording information sent from the sensors, and reporting to users the times when certain triggers went active or inactive.
A few pieces of information about sensors:
Triggers:
Sensors are assigned to triggers on a many to many basis.
The problem I have relates to tracking "when" the triggers went active or inactive.
for example, for a trigger checking value > 1
sensor_id | reading | value | trigger_value
1 2011-04-25T20:09:00 0 false
1 2011-04-25T20:11:00 1 false
1 2011-04-25T20:13:00 4 true
1 2011-04-25T20:15:00 5 true
1 2011-04-25T20:17:00 3 true
1 2011-04-25T20:19:00 6 true
1 2011-04-25T20:21:00 1 false
it might return:
sensor_id | reading | event
1 2011-04-25T20:13:00 1 -- 'went active'
1 2011-04-25T20:21:00 0 -- 'went in-active'
My current approach involves recording the current state of the set of triggers for each sensor. When the next input comes in for a sensor, and the triggers are evaluated, it compares this with the list of current trigger states for that sensor. For each change in state the 'activation' or 'de-activation' is recorded.
This approach is quite simple, but it generates data about state changes that is "already there" in the database; however the data isn't in a single tuple, it resides in the relationship between tuples (in the same table).
So, the question is:
Do I change my approach because the data is 'already there'; by changing the schema to make it less dependent on the relationship between tuples, or creating views / stored procs to analyse it apon request
OR
Do I keep with this system because it solves the problem and hides the fact there is a temporal relationship between tuples in the same table (which I know is bad).
In a more general form:
How do you store time based statistics / data in tables, and analyse the differences between consecutive statistics without bastardising RDBMS.
Example of current implementation structure:
-- log incoming sensor data, keyed by sensor and when it was recorded
create table sensor_log (
sensor_id integer references sensors (sensor_id),
reading timestamp,
data_point_a integer NOT NULL, -- example name only
data_point_b integer NOT NULL,
-- ... various other data points
primary key(sensor_id, reading)
);
-- data storage for trigger configuration
create table triggers (
trigger_id integer,
-- ... configuration for the triggers
primary key(trigger_id)
);
-- associate triggers with particular sensors on a many to many basis
create table sensor_triggers (
sensor_id integer references sensors (sensor_id),
trigger_id integer references triggers (trigger_id),
-- ... configuration for the triggers
primary key(sensor_id, trigger_id)
);
-- record which triggers were active for a particular sensor input
-- not necessary, unless to save on recomputing past trigger activations
create table sensor_trigger_activations (
sensor_id integer,
reading timestamp,
trigger_id integer references triggers (trigger_id),
primary key (sensor_id, reading, trigger_id),
foreign key (sensor_id, reading) references sensor_log (sensor_id, reading)
);
-- record trigger 'activations' & 'deactivations'
-- activation: active state preceded by in-active state (for a particular trigger)
-- deactivation: in-active state preceded by an active state ""
-- absense
create table sensor_trigger_events (
sensor_id integer,
reading timestamp,
trigger_id integer,
event_type smallint CHECK (event_type = 0 OR event_type = 1), -- 0 = deactivation, 1 = activation
primary_key (sensor_id, reading, trigger_id),
foreign key (sensor_id, reading) references sensor_log (sensor_id, reading)
);
First, I don't think a temporal relationship between tuples in the same table is necessarily bad. It isn't really direct and so hiding it is ok.
I don't really see much that can be improved given your set of requirements.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.