Join GitHub today
GitHub is home to over 40 million developers working together to host and review code, manage projects, and build software together.Sign up
[dev.icinga.com #173] fix duplicate entries in table servicechecks (mysql) #82
This issue has been migrated from Redmine: https://dev.icinga.com/issues/173
Created by mfriedrich on 2009-11-03 11:37:31 +00:00
my comment from nagios-devel
Øyvind Nordang wrote:
I've noticed that myself and that seems to be a bug. Maybe it concerns the unique constraint where the UPDATE should happen. But it could also be that some data is sent incorrectly and therefore no matching can be done.
Also the creation of "buf1" is interesting. The approach of building the query buffer for both INSERT and UPDATE might lead into a real error too. The only difference is that the INSERT statement gets command_object_id, command_args and command_line
The defined keys in db/mysql.sql
KEY `instance_id` (`instance_id`),
Kind of strange, no unique definition ... but let's step further into analysis.
Problem regarding that routine is, that the constraint never matches.
I've run several tests with Postgres and Oracle, and regarding especially right now Oracle, the defined constraint also matches and entries do not get duplicated. Postgres also works fine.
The reason why this is happening is quite simple - the queries point exactly to the unique constraint.
Conclusion to that is that it is a MySQL problem regarding the defined keys and the ON DUPLICATE KEY statement.
To step further into that, I've only selected the columns which are necessary to see the difference::
mysql> select servicecheck_id, service_object_id, start_time, start_time_usec, end_time, end_time_usec, command_object_id, execution_time from icinga_servicechecks;
This block should be have been updated e.g.
But it doesn't, you can see the INSERT statements right after a while in the history.
Let's focus on service_object_id=6421 (i've cleared the IP address)
The first query generates the entry where end_time is 0 ... FROM_UNIXTIME(0), 0 ... start_time is 1257240898 (= 2009-11-03 10:34:58 GMT+1)
[1257240916.978113] [002.0] [pid=2673] INSERT INTO icinga_servicechecks (instance_id, service_object_id, check_type, current_check_attempt, max_check_attempts, state, state_type, start_time, start_time_usec, end_time, end_time_usec, timeout, early_timeout, execution_time, latency, return_code, output, long_output, perfdata, command_object_id, command_args, command_line) VALUES (1, 6421, 0, 1, 3, 0, 1, FROM_UNIXTIME(1257240898), 245848, FROM_UNIXTIME(0), 0, 60, 0, 0.000000, 0.245000, 0, 'PING OK - Packet loss = 0, RTA = 17\.43 ms', '', '', 6193, '100\.0,20!500\.0,60', '/opt/icinga/libexec/check_ping -H 1\.2\.3\.4 -w 100\.0,20 -c 500\.0,60% -p 5
For that check, we are waiting for end_time and end_time_usec and truly need the UPDATE condition, the INSERT will create this faulty and duplicate entry (short version!).
[1257240917.081916] [002.0] [pid=2673] INSERT INTO icinga_servicechecks (instance_id, service_object_id, check_type, current_check_attempt, max_check_attempts, state, state_type, start_time, start_time_usec, end_time, end_time_usec, timeout, early_timeout, execution_time, latency, return_code, output, long_output, perfdata, command_object_id, command_args, command_line) VALUES (1, 6421, 0, 1, 3, 0, 1, FROM_UNIXTIME(1257240898), 245848, FROM_UNIXTIME(1257240902), 798210, 60, 0, 4.552360, 0.245000, 0, 'PING OK - Packet loss = 0, RTA = 75\.77 ms', '', '', 0, '', '') ON DUPLICATE KEY UPDATE check_type='0', current_check_attempt='1', max_check_attempts='3', state='0', state_type='1', start_time=FROM_UNIXTIME(1257240898), start_time_usec='245848', end_time=FROM_UNIXTIME(1257240902), end_time_usec='798210', timeout='60', early_timeout='0', execution_time='4.552360', latency='0.245000', return_code='0', output='PING OK - Packet loss = 0, RTA = 75\.77 ms', long_output='', perfdata=''
As you may see on a full output on that row, the INSERT puts empty command_line, empty command_object_id etc into the DB which is wrong.
Now let's compare on the unique constraint, where ON DUPLICATE KEY shoud trigger on the UPDATE statement:
instance_id - same!
Well regarding the fact that the unique constraint is missing and instead normal keys are defined, let's turn the other way around - why are the hostchecks running fine without duplicate entries? Hmmm, because the unique key is defined in a correct manner.
Whoever did that to the SQL-Statement during table creation......
Correct way of getting that to work will be defining a real unique key and then ON DUPLICATE KEY will trigger the UPDATE statement.
I will work on a patch and provide it when finished testing.
Updated by mfriedrich on 2009-11-03 12:01:07 +00:00
resolution is by defining the unique key instead of the keys.
then getting those queries
this one updates only endtime and so on.
and here we go:
modified in mysql.sql and added mysql-upgrade-1.0.sql with the ALTER statements (to prepare for stable release).
already pushed to master!