Merge branch 'master' of github.com:/ZoneMinder/zoneminder

This commit is contained in:
Isaac Connor 2020-11-04 18:10:55 -05:00
commit 289612a826
64 changed files with 665 additions and 476 deletions

View File

@ -152,13 +152,13 @@ BEGIN
SET
ArchivedEvents = GREATEST(COALESCE(ArchivedEvents,0)-1,0),
ArchivedEventDiskSpace = GREATEST(COALESCE(ArchivedEventDiskSpace,0) - COALESCE(OLD.DiskSpace,0),0)
WHERE Id=OLD.MonitorId;
WHERE Monitors.Id=OLD.MonitorId;
ELSE
IF ( OLD.DiskSpace != NEW.DiskSpace ) THEN
UPDATE Events_Archived SET DiskSpace=NEW.DiskSpace WHERE EventId=NEW.Id;
UPDATE Monitors SET
ArchivedEventDiskSpace = GREATEST(COALESCE(ArchivedEventDiskSpace,0) - COALESCE(OLD.DiskSpace,0) + COALESCE(NEW.DiskSpace,0),0)
WHERE Id=OLD.MonitorId;
WHERE Monitors.Id=OLD.MonitorId;
END IF;
END IF;
ELSEIF ( NEW.Archived AND diff ) THEN
@ -185,10 +185,10 @@ CREATE TRIGGER event_insert_trigger AFTER INSERT ON Events
FOR EACH ROW
BEGIN
INSERT INTO Events_Hour (EventId,MonitorId,StartTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartTime,0);
INSERT INTO Events_Day (EventId,MonitorId,StartTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartTime,0);
INSERT INTO Events_Week (EventId,MonitorId,StartTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartTime,0);
INSERT INTO Events_Month (EventId,MonitorId,StartTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartTime,0);
INSERT INTO Events_Hour (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
INSERT INTO Events_Day (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
INSERT INTO Events_Week (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
INSERT INTO Events_Month (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
UPDATE Monitors SET
HourEvents = COALESCE(HourEvents,0)+1,
DayEvents = COALESCE(DayEvents,0)+1,

View File

@ -189,8 +189,8 @@ CREATE TABLE `Events` (
`SecondaryStorageId` smallint(5) unsigned default 0,
`Name` varchar(64) NOT NULL default '',
`Cause` varchar(32) NOT NULL default '',
`StartTime` datetime default NULL,
`EndTime` datetime default NULL,
`StartDateTime` datetime default NULL,
`EndDateTime` datetime default NULL,
`Width` smallint(5) unsigned NOT NULL default '0',
`Height` smallint(5) unsigned NOT NULL default '0',
`Length` decimal(10,2) NOT NULL default '0.00',
@ -216,52 +216,52 @@ CREATE TABLE `Events` (
PRIMARY KEY (`Id`),
KEY `Events_MonitorId_idx` (`MonitorId`),
KEY `Events_StorageId_idx` (`StorageId`),
KEY `Events_StartTime_idx` (`StartTime`),
KEY `Events_EndTime_DiskSpace` (`EndTime`,`DiskSpace`)
KEY `Events_StartDateTime_idx` (`StartDateTime`),
KEY `Events_EndDateTime_DiskSpace` (`EndDateTime`,`DiskSpace`)
) ENGINE=@ZM_MYSQL_ENGINE@;
DROP TABLE IF EXISTS `Events_Hour`;
CREATE TABLE `Events_Hour` (
`EventId` BIGINT unsigned NOT NULL,
`MonitorId` int(10) unsigned NOT NULL,
`StartTime` datetime default NULL,
`StartDateTime` datetime default NULL,
`DiskSpace` bigint default NULL,
PRIMARY KEY (`EventId`),
KEY `Events_Hour_MonitorId_idx` (`MonitorId`),
KEY `Events_Hour_StartTime_idx` (`StartTime`)
KEY `Events_Hour_StartDateTime_idx` (`StartDateTime`)
) ENGINE=@ZM_MYSQL_ENGINE@;
DROP TABLE IF EXISTS `Events_Day`;
CREATE TABLE `Events_Day` (
`EventId` BIGINT unsigned NOT NULL,
`MonitorId` int(10) unsigned NOT NULL,
`StartTime` datetime default NULL,
`StartDateTime` datetime default NULL,
`DiskSpace` bigint default NULL,
PRIMARY KEY (`EventId`),
KEY `Events_Day_MonitorId_idx` (`MonitorId`),
KEY `Events_Day_StartTime_idx` (`StartTime`)
KEY `Events_Day_StartDateTime_idx` (`StartDateTime`)
) ENGINE=@ZM_MYSQL_ENGINE@;
DROP TABLE IF EXISTS `Events_Week`;
CREATE TABLE `Events_Week` (
`EventId` BIGINT unsigned NOT NULL,
`MonitorId` int(10) unsigned NOT NULL,
`StartTime` datetime default NULL,
`StartDateTime` datetime default NULL,
`DiskSpace` bigint default NULL,
PRIMARY KEY (`EventId`),
KEY `Events_Week_MonitorId_idx` (`MonitorId`),
KEY `Events_Week_StartTime_idx` (`StartTime`)
KEY `Events_Week_StartDateTime_idx` (`StartDateTime`)
) ENGINE=@ZM_MYSQL_ENGINE@;
DROP TABLE IF EXISTS `Events_Month`;
CREATE TABLE `Events_Month` (
`EventId` BIGINT unsigned NOT NULL,
`MonitorId` int(10) unsigned NOT NULL,
`StartTime` datetime default NULL,
`StartDateTime` datetime default NULL,
`DiskSpace` bigint default NULL,
PRIMARY KEY (`EventId`),
KEY `Events_Month_MonitorId_idx` (`MonitorId`),
KEY `Events_Month_StartTime_idx` (`StartTime`)
KEY `Events_Month_StartDateTime_idx` (`StartDateTime`)
) ENGINE=@ZM_MYSQL_ENGINE@;
@ -804,7 +804,7 @@ INSERT INTO `Filters`
VALUES
(
'PurgeWhenFull',
'{"sort_field":"Id","terms":[{"val":0,"attr":"Archived","op":"="},{"cnj":"and","val":95,"attr":"DiskPercent","op":">="}],"limit":100,"sort_asc":1}',
'{"sort_field":"Id","terms":[{"val":0,"attr":"Archived","op":"="},{"cnj":"and","val":95,"attr":"DiskPercent","op":">="},{"cnj":"and","obr":"0","attr":"EndDateTime","op":"IS NOT","val":"NULL","cbr":"0"}],"limit":100,"sort_asc":1}',
0/*AutoArchive*/,
0/*AutoVideo*/,
0/*AutoUpload*/,
@ -848,7 +848,7 @@ INSERT INTO `Filters`
)
VALUES (
'Update DiskSpace',
'{"terms":[{"attr":"DiskSpace","op":"IS","val":"NULL"}]}',
'{"terms":[{"attr":"DiskSpace","op":"IS","val":"NULL"},{"cnj":"and","obr":"0","attr":"EndDateTime","op":"IS NOT","val":"NULL","cbr":"0"}]}',
0/*AutoArchive*/,
0/*AutoVideo*/,
0/*AutoUpload*/,

View File

@ -1,73 +1,91 @@
/* Change Id type to BIGINT. */
SELECT 'Updating Events.Id to BIGINT';
ALTER TABLE Events MODIFY Id bigint unsigned NOT NULL auto_increment;
set @exist := (SELECT count(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_name = 'Events' AND COLUMN_NAME = 'Id' and DATA_TYPE='bigint');
set @sqlstmt := if( @exist = 0, "ALTER TABLE Events MODIFY Id bigint unsigned NOT NULL auto_increment", "SELECT 'Events.Id is already BIGINT'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
/* Add FOREIGN KEYS After deleting lost records */
SELECT 'Adding foreign key for EventId to Frames';
set @exist := (select count(*) FROM information_schema.key_column_usage where table_name='Frames' and column_name='EventId' and referenced_table_name='Events' and referenced_column_name='Id');
set @sqlstmt := if( @exist > 1, "SELECT 'You have more than 1 FOREIGN KEY. Please do manual cleanup'", "SELECT 'Ok'");
set @sqlstmt := if( @exist = 1, "SELECT 'FOREIGN KEY EventId in Frames already exists'", @sqlstmt);
set @sqlstmt := if( @exist = 0, "SELECT 'Adding foreign key for EventId to Frames'", @sqlstmt);
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'FOREIGN KEY for EventId in Frames already exists'", "DELETE FROM Frames WHERE EventId NOT IN (SELECT Id FROM Events)");
set @sqlstmt := if( @exist = 0, "SELECT 'Deleting unlinked Frames'", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'Ok'", "ALTER TABLE Frames ADD FOREIGN KEY (EventId) REFERENCES Events (Id) ON DELETE CASCADE");
set @sqlstmt := if( @exist = 0, "DELETE FROM Frames WHERE EventId NOT IN (SELECT Id FROM Events)", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist = 0, "ALTER TABLE Frames ADD FOREIGN KEY (EventId) REFERENCES Events (Id) ON DELETE CASCADE", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
SELECT 'Adding foreign key for EventId to Stats';
set @exist := (select count(*) FROM information_schema.key_column_usage where table_name='Stats' and column_name='EventId' and referenced_table_name='Events' and referenced_column_name='Id');
set @sqlstmt := if( @exist > 1, "SELECT 'You have more than 1 FOREIGN KEY. Please do manual cleanup'", "SELECT 'Ok'");
set @sqlstmt := if( @exist = 1, "SELECT 'FOREIGN KEY EventId in Stats already exists'", @sqlstmt);
set @sqlstmt := if( @exist = 0, "SELECT 'Adding FOREIGN KEY for EventId to Stats'", @sqlstmt);
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'FOREIGN KEY for EventId in Stats already exists'", "DELETE FROM Stats WHERE EventId NOT IN (SELECT Id FROM Events);");
set @sqlstmt := if( @exist = 0, "SELECT 'Deleting unlinked Stats'", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist = 0, "DELETE FROM Stats WHERE EventId NOT IN (SELECT Id FROM Events);", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'Ok'", "ALTER TABLE Stats ADD FOREIGN KEY (EventId) REFERENCES Events (Id) ON DELETE CASCADE");
set @sqlstmt := if( @exist = 0, "ALTER TABLE Stats ADD FOREIGN KEY (EventId) REFERENCES Events (Id) ON DELETE CASCADE", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
SELECT 'Adding foreign key for MonitorId to Stats';
set @exist := (select count(*) FROM information_schema.key_column_usage where table_name='Stats' and column_name='MonitorId' and referenced_table_name='Monitors' and referenced_column_name='Id');
set @sqlstmt := if( @exist > 1, "SELECT 'You have more than 1 FOREIGN KEY. Please do manual cleanup'", "SELECT 'Ok'");
set @sqlstmt := if( @exist = 1, "SELECT 'FOREIGN KEY for MonitorId in Stats already exists'", @sql_stmt);
set @sqlstmt := if( @exist = 0, "SELECT 'Adding FOREIGN KEY for MonitorId to Stats'", @sqlstmt);
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'FOREIGN KEY for MonitorId in Stats already exists'", "DELETE FROM Stats WHERE MonitorId NOT IN (SELECT Id FROM Monitors);");
set @sqlstmt := if( @exist = 0, "SELECT 'Deleting unlinked Stats'", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist = 0, "DELETE FROM Stats WHERE MonitorId NOT IN (SELECT Id FROM Monitors);", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'Ok'", "ALTER TABLE Stats ADD FOREIGN KEY (MonitorId) REFERENCES Monitors (Id) ON DELETE CASCADE");
set @sqlstmt := if( @exist = 0, "ALTER TABLE Stats ADD FOREIGN KEY (MonitorId) REFERENCES Monitors (Id) ON DELETE CASCADE", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
SELECT 'Adding foreign key for ZoneId to Stats';
set @exist := (select count(*) FROM information_schema.key_column_usage where table_name='Stats' and column_name='ZoneId' and referenced_table_name='Zones' and referenced_column_name='Id');
set @sqlstmt := if( @exist > 1, "SELECT 'You have more than 1 FOREIGN KEY. Please do manual cleanup'", "SELECT 'Ok'");
set @sqlstmt := if( @exist = 1, "SELECT 'FOREIGN KEY for ZoneId in Stats already exists'", @sqlstmt);
set @sqlstmt := if( @exist = 0, "SELECT 'Adding foreign key for ZoneId to Stats'", @sqlstmt);
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'FOREIGN KEY for ZoneId in Stats already exists'", "DELETE FROM Stats WHERE ZoneId NOT IN (SELECT Id FROM Zones);");
set @sqlstmt := if( @exist = 0, "SELECT 'Deleting unlinked Stats'", "SELECT 'Ok'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist > 0, "SELECT 'Ok'", "ALTER TABLE Stats ADD FOREIGN KEY (ZoneId) REFERENCES Zones (Id) ON DELETE CASCADE");
set @sqlstmt := if( @exist = 0, "DELETE FROM Stats WHERE ZoneId NOT IN (SELECT Id FROM Zones);", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist = 0, "ALTER TABLE Stats ADD FOREIGN KEY (ZoneId) REFERENCES Zones (Id) ON DELETE CASCADE", "SELECT '.'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
SELECT 'Adding foreign key for MonitorId to Zones';
set @exist := (select count(*) FROM information_schema.key_column_usage where table_name='Zones' and column_name='MonitorId' and referenced_table_name='Monitors' and referenced_column_name='Id');
set @sqlstmt := if( @exist > 1, "SELECT 'You have more than 1 FOREIGN KEY. Please do manual cleanup'", "SELECT 'Ok'");
PREPARE stmt FROM @sqlstmt;
EXECUTE stmt;
set @sqlstmt := if( @exist = 1, "SELECT 'FOREIGN KEY for MonitorId in Zones already exists'", @sqlstmnt);
set @sqlstmt := if( @exist = 0, "SELECT 'Adding foreign key for MonitorId in Zones'", @sqlstmnt);
set @sqlstmt := if( @exist > 0, "SELECT 'FOREIGN KEY for MonitorId in Zones already exists'", "SELECT 'FOREIGN KEY for MonitorId in Zones does not already exist'");
/*"SELECT 'FOREIGN KEY for MonitorId in Zones does not already exist'");*/
set @badzones := (select count(*) FROM Zones WHERE MonitorId NOT IN (SELECT Id FROM Monitors));
set @sqlstmt := if ( @badzones > 0, "SELECT 'You have Zones with no Monitor record in the Monitors table. Please delete them manually'", "ALTER TABLE Zones ADD FOREIGN KEY (MonitorId) REFERENCES Monitors (Id)");
PREPARE stmt FROM @sqlstmt;

101
db/zm_update-1.35.13.sql Normal file
View File

@ -0,0 +1,101 @@
/* DateTime is invalid and it being set here will cause warnings because it isn't in the dropdown set of values in Filter edit. */
UPDATE Config SET Value='StartDateTime' WHERE Name='ZM_WEB_EVENT_SORT_FIELD' AND Value='DateTime';
SET @s = (SELECT IF(
(SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_schema = DATABASE()
AND table_name = 'Events'
AND column_name = 'StartDateTime'
) > 0,
"SELECT 'Column StartDateTime already exists in Events'",
"ALTER TABLE Events RENAME COLUMN StartTime TO StartDateTime"
));
PREPARE stmt FROM @s;
EXECUTE stmt;
SET @s = (SELECT IF(
(SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_schema = DATABASE()
AND table_name = 'Events'
AND column_name = 'EndDateTime'
) > 0,
"SELECT 'Column EndDateTime already exists in Events'",
"ALTER TABLE Events RENAME COLUMN EndTime TO EndDateTime"
));
PREPARE stmt FROM @s;
EXECUTE stmt;
SET @s = (SELECT IF(
(SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_schema = DATABASE()
AND table_name = 'Events_Hour'
AND column_name = 'StartDateTime'
) > 0,
"SELECT 'Column StartDateTime already exists in Events_Hour'",
"ALTER TABLE Events_Hour RENAME COLUMN StartTime TO StartDateTime"
));
PREPARE stmt FROM @s;
EXECUTE stmt;
SET @s = (SELECT IF(
(SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_schema = DATABASE()
AND table_name = 'Events_Day'
AND column_name = 'StartDateTime'
) > 0,
"SELECT 'Column StartDateTime already exists in Events_Day'",
"ALTER TABLE Events_Day RENAME COLUMN StartTime TO StartDateTime"
));
PREPARE stmt FROM @s;
EXECUTE stmt;
SET @s = (SELECT IF(
(SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_schema = DATABASE()
AND table_name = 'Events_Week'
AND column_name = 'StartDateTime'
) > 0,
"SELECT 'Column StartDateTime already exists in Events_Week'",
"ALTER TABLE Events_Week RENAME COLUMN StartTime TO StartDateTime"
));
PREPARE stmt FROM @s;
EXECUTE stmt;
SET @s = (SELECT IF(
(SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE table_schema = DATABASE()
AND table_name = 'Events_Month'
AND column_name = 'StartDateTime'
) > 0,
"SELECT 'Column StartDateTime already exists in Events_Month'",
"ALTER TABLE Events_Month RENAME COLUMN StartTime TO StartDateTime"
));
PREPARE stmt FROM @s;
EXECUTE stmt;
delimiter //
DROP TRIGGER IF EXISTS event_insert_trigger//
/* The assumption is that when an Event is inserted, it has no size yet, so don't bother updating the DiskSpace, just the count.
* The DiskSpace will get update in the Event Update Trigger
*/
CREATE TRIGGER event_insert_trigger AFTER INSERT ON Events
FOR EACH ROW
BEGIN
INSERT INTO Events_Hour (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
INSERT INTO Events_Day (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
INSERT INTO Events_Week (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
INSERT INTO Events_Month (EventId,MonitorId,StartDateTime,DiskSpace) VALUES (NEW.Id,NEW.MonitorId,NEW.StartDateTime,0);
UPDATE Monitors SET
HourEvents = COALESCE(HourEvents,0)+1,
DayEvents = COALESCE(DayEvents,0)+1,
WeekEvents = COALESCE(WeekEvents,0)+1,
MonthEvents = COALESCE(MonthEvents,0)+1,
TotalEvents = COALESCE(TotalEvents,0)+1
WHERE Id=NEW.MonitorId;
END;
//
delimiter ;

View File

@ -28,7 +28,7 @@
%global _hardened_build 1
Name: zoneminder
Version: 1.35.12
Version: 1.35.13
Release: 1%{?dist}
Summary: A camera monitoring and analysis tool
Group: System Environment/Daemons

View File

@ -68,8 +68,8 @@ $serial = $primary_key = 'Id';
SecondaryStorageId
Name
Cause
StartTime
EndTime
StartDateTime
EndDateTime
Width
Height
Length
@ -111,8 +111,8 @@ sub Time {
$_[0]{Time} = $_[1];
}
if ( ! defined $_[0]{Time} ) {
if ( $_[0]{StartTime} ) {
$_[0]{Time} = Date::Parse::str2time( $_[0]{StartTime} );
if ( $_[0]{StartDateTime} ) {
$_[0]{Time} = Date::Parse::str2time( $_[0]{StartDateTime} );
}
}
return $_[0]{Time};
@ -349,6 +349,10 @@ sub GenerateVideo {
return;
} # end sub GenerateVideo
# Note about transactions, this function may be called with rows locked and hence in a transaction.
# So we will detect if we are in a transaction, and if not, start one. We will NOT do rollback or
# commits unless we started the transaction.
sub delete {
my $event = $_[0];
@ -360,11 +364,11 @@ sub delete {
my $in_zmaudit = ( $0 =~ 'zmaudit.pl$');
if ( ! $in_zmaudit ) {
if ( ! ( $event->{Id} and $event->{MonitorId} and $event->{StartTime} ) ) {
if ( ! ( $event->{Id} and $event->{MonitorId} and $event->{StartDateTime} ) ) {
# zmfilter shouldn't delete anything in an odd situation. zmaudit will though.
my ( $caller, undef, $line ) = caller;
Warning("$0 Can't Delete event $event->{Id} from Monitor $event->{MonitorId} StartTime:".
(defined($event->{StartTime})?$event->{StartTime}:'undef')." from $caller:$line");
Warning("$0 Can't Delete event $event->{Id} from Monitor $event->{MonitorId} StartDateTime:".
(defined($event->{StartDateTime})?$event->{StartDateTime}:'undef')." from $caller:$line");
return;
}
if ( !($event->Storage()->Path() and -e $event->Storage()->Path()) ) {
@ -375,26 +379,28 @@ sub delete {
if ( $$event{Id} ) {
# Need to have an event Id if we are to delete from the db.
Info("Deleting event $event->{Id} from Monitor $event->{MonitorId} StartTime:$event->{StartTime} from ".$event->Path());
Info("Deleting event $event->{Id} from Monitor $event->{MonitorId} StartDateTime:$event->{StartDateTime} from ".$event->Path());
$ZoneMinder::Database::dbh->ping();
$ZoneMinder::Database::dbh->begin_work();
#$event->lock_and_load();
my $in_transaction = $ZoneMinder::Database::dbh->{AutoCommit} ? 0 : 1;
ZoneMinder::Database::zmDbDo('DELETE FROM Frames WHERE EventId=?', $$event{Id});
if ( $ZoneMinder::Database::dbh->errstr() ) {
$ZoneMinder::Database::dbh->commit();
return;
}
$ZoneMinder::Database::dbh->begin_work() if ! $in_transaction;
# Going to delete in order of least value to greatest value. Stats is least and references Frames
ZoneMinder::Database::zmDbDo('DELETE FROM Stats WHERE EventId=?', $$event{Id});
if ( $ZoneMinder::Database::dbh->errstr() ) {
$ZoneMinder::Database::dbh->commit();
$ZoneMinder::Database::dbh->commit() if ! $in_transaction;
return;
}
ZoneMinder::Database::zmDbDo('DELETE FROM Frames WHERE EventId=?', $$event{Id});
if ( $ZoneMinder::Database::dbh->errstr() ) {
$ZoneMinder::Database::dbh->commit() if ! $in_transaction;
return;
}
# Do it individually to avoid locking up the table for new events
ZoneMinder::Database::zmDbDo('DELETE FROM Events WHERE Id=?', $$event{Id});
$ZoneMinder::Database::dbh->commit();
$ZoneMinder::Database::dbh->commit() if ! $in_transaction;
}
if ( ( $in_zmaudit or (!$Config{ZM_OPT_FAST_DELETE})) and $event->Storage()->DoDelete() ) {
@ -814,9 +820,9 @@ sub recover_timestamps {
my $duration = $last_timestamp - $first_timestamp;
$Event->Length($duration);
$Event->StartTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $first_timestamp) );
$Event->EndTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $last_timestamp) );
Debug("From capture Jpegs have duration $duration = $last_timestamp - $first_timestamp : $$Event{StartTime} to $$Event{EndTime}");
$Event->StartDateTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $first_timestamp) );
$Event->EndDateTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $last_timestamp) );
Debug("From capture Jpegs have duration $duration = $last_timestamp - $first_timestamp : $$Event{StartDateTime} to $$Event{EndDateTime}");
$ZoneMinder::Database::dbh->begin_work();
foreach my $jpg ( @capture_jpgs ) {
my ( $id ) = $jpg =~ /^(\d+)\-capture\.jpg$/;
@ -852,8 +858,8 @@ sub recover_timestamps {
}
my $seconds = ($h*60*60)+($m*60)+$s;
$Event->Length($seconds.'.'.$u);
$Event->StartTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $first_timestamp) );
$Event->EndTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $first_timestamp+$seconds) );
$Event->StartDateTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $first_timestamp) );
$Event->EndDateTime( Date::Format::time2str('%Y-%m-%d %H:%M:%S', $first_timestamp+$seconds) );
}
if ( @mp4_files ) {
$Event->DefaultVideo($mp4_files[0]);

View File

@ -149,7 +149,7 @@ sub Sql {
my $filter_expr = ZoneMinder::General::jsonDecode($self->{Query_json});
my $sql = 'SELECT E.*,
unix_timestamp(E.StartTime) as Time,
unix_timestamp(E.StartDateTime) as Time,
M.Name as MonitorName,
M.DefaultRate,
M.DefaultScale
@ -184,27 +184,25 @@ sub Sql {
$self->{Sql} .= $Config{ZM_SERVER_ID};
# StartTime options
} elsif ( $term->{attr} eq 'DateTime' ) {
$self->{Sql} .= 'E.StartTime';
} elsif ( $term->{attr} eq 'StartDateTime' ) {
$self->{Sql} .= 'E.StartTime';
$self->{Sql} .= 'E.StartDateTime';
} elsif ( $term->{attr} eq 'Date' ) {
$self->{Sql} .= 'to_days( E.StartTime )';
$self->{Sql} .= 'to_days( E.StartDateTime )';
} elsif ( $term->{attr} eq 'StartDate' ) {
$self->{Sql} .= 'to_days( E.StartTime )';
$self->{Sql} .= 'to_days( E.StartDateTime )';
} elsif ( $term->{attr} eq 'Time' or $term->{attr} eq 'StartTime' ) {
$self->{Sql} .= 'extract( hour_second from E.StartTime )';
$self->{Sql} .= 'extract( hour_second from E.StartDateTime )';
} elsif ( $term->{attr} eq 'Weekday' or $term->{attr} eq 'StartWeekday' ) {
$self->{Sql} .= 'weekday( E.StartTime )';
$self->{Sql} .= 'weekday( E.StartDateTime )';
# EndTIme options
} elsif ( $term->{attr} eq 'EndDateTime' ) {
$self->{Sql} .= 'E.EndTime';
$self->{Sql} .= 'E.EndDateTime';
} elsif ( $term->{attr} eq 'EndDate' ) {
$self->{Sql} .= 'to_days( E.EndTime )';
} elsif ( $term->{attr} eq 'EndTime' ) {
$self->{Sql} .= 'extract( hour_second from E.EndTime )';
$self->{Sql} .= 'to_days( E.EndDateTime )';
} elsif ( $term->{attr} eq 'EndDateTime' ) {
$self->{Sql} .= 'extract( hour_second from E.EndDateTime )';
} elsif ( $term->{attr} eq 'EndWeekday' ) {
$self->{Sql} .= "weekday( E.EndTime )";
$self->{Sql} .= "weekday( E.EndDateTime )";
} elsif ( $term->{attr} eq 'ExistsInFileSystem' ) {
push @{$self->{PostSQLConditions}}, $term;
$self->{Sql} .= 'TRUE /* ExistsInFileSystem */';
@ -368,7 +366,7 @@ sub Sql {
$sql .= ' AND ( '.join(' or ', @auto_terms).' )';
}
if ( !$filter_expr->{sort_field} ) {
$filter_expr->{sort_field} = 'StartTime';
$filter_expr->{sort_field} = 'StartDateTime';
$filter_expr->{sort_asc} = 0;
}
my $sort_column = '';
@ -378,10 +376,14 @@ sub Sql {
$sort_column = 'M.Name';
} elsif ( $filter_expr->{sort_field} eq 'Name' ) {
$sort_column = 'E.Name';
} elsif ( $filter_expr->{sort_field} eq 'StartDateTime' ) {
$sort_column = 'E.StartDateTime';
} elsif ( $filter_expr->{sort_field} eq 'StartTime' ) {
$sort_column = 'E.StartTime';
$sort_column = 'E.StartDateTime';
} elsif ( $filter_expr->{sort_field} eq 'EndTime' ) {
$sort_column = 'E.EndTime';
$sort_column = 'E.EndDateTime';
} elsif ( $filter_expr->{sort_field} eq 'EndDateTime' ) {
$sort_column = 'E.EndDateTime';
} elsif ( $filter_expr->{sort_field} eq 'Secs' ) {
$sort_column = 'E.Length';
} elsif ( $filter_expr->{sort_field} eq 'Frames' ) {
@ -397,7 +399,7 @@ sub Sql {
} elsif ( $filter_expr->{sort_field} eq 'DiskSpace' ) {
$sort_column = 'E.DiskSpace';
} else {
$sort_column = 'E.StartTime';
$sort_column = 'E.StartDateTime';
}
my $sort_order = $filter_expr->{sort_asc} ? 'ASC' : 'DESC';
$sql .= ' ORDER BY '.$sort_column.' '.$sort_order;

View File

@ -262,21 +262,21 @@ sub createEvent {
}
$frame->{Type} = $frame->{Score}>0?'Alarm':'Normal' unless( $frame->{Type} );
$frame->{Delta} = $lastTimestamp?($frame->{TimeStamp}-$lastTimestamp):0.0;
$event->{StartTime} = $frame->{TimeStamp} unless ( $event->{StartTime} );
$event->{StartDateTime} = $frame->{TimeStamp} unless ( $event->{StartDateTime} );
$event->{TotScore} += $frame->{Score};
$event->{MaxScore} = $frame->{Score} if ( $frame->{Score} > $event->{MaxScore} );
$event->{AlarmFrames}++ if ( $frame->{Type} eq 'Alarm' );
$event->{EndTime} = $frame->{TimeStamp};
$event->{EndDateTime} = $frame->{TimeStamp};
$lastTimestamp = $frame->{TimeStamp};
}
$event->{Width} = $event->{monitor}->{Width} unless( $event->{Width} );
$event->{Height} = $event->{monitor}->{Height} unless( $event->{Height} );
$event->{AvgScore} = $event->{TotScore}/int($event->{AlarmFrames});
$event->{Length} = $event->{EndTime} - $event->{StartTime};
$event->{Length} = $event->{EndDateTime} - $event->{StartDateTime};
my %formats = (
StartTime => 'from_unixtime(?)',
EndTime => 'from_unixtime(?)',
StartDateTime => 'from_unixtime(?)',
EndDateTime => 'from_unixtime(?)',
);
my ( @fields, @formats, @values );
@ -297,7 +297,7 @@ sub createEvent {
$event->{Id} = $dbh->{mysql_insertid};
Info( "Created event ".$event->{Id} );
if ( $event->{EndTime} ) {
if ( $event->{EndDateTime} ) {
$event->{Name} = $event->{monitor}->{EventPrefix}.$event->{Id}
if ( $event->{Name} eq 'New Event' );
my $sql = "update Events set Name = ? where Id = ?";
@ -383,8 +383,8 @@ sub updateEvent {
if ( $event->{Name} eq 'New Event' );
my %formats = (
StartTime => 'from_unixtime(?)',
EndTime => 'from_unixtime(?)',
StartDateTime => 'from_unixtime(?)',
EndDateTime => 'from_unixtime(?)',
);
my ( @values, @sets );

View File

@ -504,9 +504,9 @@ sub openFile {
$LOGFILE->autoflush() if $this->{autoFlush};
my $webUid = (getpwnam($ZoneMinder::Config::Config{ZM_WEB_USER}))[2];
Error("Can't get uid for $ZoneMinder::Config::Config{ZM_WEB_USER}") if ! defined $webUid;
Error('Can\'t get uid for '.$ZoneMinder::Config::Config{ZM_WEB_USER}) if ! defined $webUid;
my $webGid = (getgrnam($ZoneMinder::Config::Config{ZM_WEB_GROUP}))[2];
Error("Can't get gid for $ZoneMinder::Config::Config{ZM_WEB_USER}") if ! defined $webGid;
Error('Can\'t get gid for '.$ZoneMinder::Config::Config{ZM_WEB_USER}) if ! defined $webGid;
if ( $> == 0 ) {
# If we are root, we want to make sure that www-data or whatever owns the file
chown($webUid, $webGid, $this->{logFile} ) or
@ -610,6 +610,7 @@ sub logInit( ;@ ) {
my %options = @_ ? @_ : ();
$logger = ZoneMinder::Logger->new() if !$logger;
$logger->initialise(%options);
logSetSignal();
}
sub logReinit {
@ -626,12 +627,26 @@ sub logHupHandler {
$do_log_rotate = 1;
}
sub logUSR1Handler {
$logger->level($logger->level()+1);
Info('Logger - Level changed to '. $logger->level() . '=>'.$codes{$logger->level()});
}
sub logUSR2Handler {
$logger->level($logger->level()-1);
Info('Logger - Level changed to '. $logger->level() . '=>'.$codes{$logger->level()});
}
sub logSetSignal {
$SIG{HUP} = \&logHupHandler;
$SIG{USR1} = \&logUSR1Handler;
$SIG{USR2} = \&logUSR2Handler;
}
sub logClearSignal {
$SIG{HUP} = 'DEFAULT';
$SIG{USR1} = 'DEFAULT';
$SIG{USR2} = 'DEFAULT';
}
sub logLevel {

View File

@ -205,7 +205,7 @@ MAIN: while( $loop ) {
my $monitorSelectSth = $dbh->prepare_cached( $monitorSelectSql )
or Fatal( "Can't prepare '$monitorSelectSql': ".$dbh->errstr() );
my $eventSelectSql = 'SELECT `Id`, (unix_timestamp() - unix_timestamp(`StartTime`)) AS Age
my $eventSelectSql = 'SELECT `Id`, (unix_timestamp() - unix_timestamp(`StartDateTime`)) AS Age
FROM `Events` WHERE `MonitorId` = ?'.(@Storage_Areas ? ' AND `StorageId` IN ('.join(',',map { '?'} @Storage_Areas).')' : '' ). ' ORDER BY `Id`';
my $eventSelectSth = $dbh->prepare_cached( $eventSelectSql )
or Fatal( "Can't prepare '$eventSelectSql': ".$dbh->errstr() );
@ -397,13 +397,13 @@ MAIN: while( $loop ) {
my ( undef, $year, $month, $day ) = split('/', $day_dir);
$year += 2000;
my ( $hour, $minute, $second ) = split('/', $event_dir);
my $StartTime =sprintf('%.4d-%.2d-%.2d %.2d:%.2d:%.2d', $year, $month, $day, $hour, $minute, $second);
my $StartDateTime =sprintf('%.4d-%.2d-%.2d %.2d:%.2d:%.2d', $year, $month, $day, $hour, $minute, $second);
my $Event = ZoneMinder::Event->find_one(
MonitorId=>$monitor_dir,
StartTime=>$StartTime,
StartDateTime=>$StartDateTime,
);
if ( $Event ) {
Debug("Found event matching starttime on monitor $monitor_dir at $StartTime: " . $Event->to_string());
Debug("Found event matching StartDateTime on monitor $monitor_dir at $StartDateTime: " . $Event->to_string());
next;
}
aud_print("Deleting event directories with no event id information at $day_dir/$event_dir");
@ -440,7 +440,7 @@ MAIN: while( $loop ) {
$Event->Path();
$Event->age();
Debug("Have event $$Event{Id} at $$Event{Path}");
$Event->StartTime(POSIX::strftime('%Y-%m-%d %H:%M:%S', gmtime(time_of_youngest_file($Event->Path()))));
$Event->StartDateTime(POSIX::strftime('%Y-%m-%d %H:%M:%S', gmtime(time_of_youngest_file($Event->Path()))));
} # end foreach event
}
@ -592,7 +592,7 @@ EVENT: while ( my ( $db_event, $age ) = each( %$db_events ) ) {
Warning("Event $$Event{Id} is Archived. Taking no further action on it.");
next;
}
if ( !$Event->StartTime() ) {
if ( !$Event->StartDateTime() ) {
aud_print("Event $$Event{Id} has no start time.");
if ( confirm() ) {
$Event->delete();
@ -600,7 +600,7 @@ EVENT: while ( my ( $db_event, $age ) = each( %$db_events ) ) {
}
next;
}
if ( ! $Event->EndTime() ) {
if ( ! $Event->EndDateTime() ) {
if ( $age > $Config{ZM_AUDIT_MIN_AGE} ) {
aud_print("Event $$Event{Id} has no end time and is $age seconds old. Deleting it.");
if ( confirm() ) {
@ -639,9 +639,9 @@ EVENT: while ( my ( $db_event, $age ) = each( %$db_events ) ) {
Info("Updating storage area on event $$Event{Id} from $$Event{StorageId} to $$fs_events{$db_event}{StorageId}");
$Event->StorageId($$fs_events{$db_event}->StorageId());
}
if ( ! $Event->StartTime() ) {
Info("Updating StartTime on event $$Event{Id} from $$Event{StartTime} to $$fs_events{$db_event}{StartTime}");
$Event->StartTime($$fs_events{$db_event}->StartTime());
if ( ! $Event->StartDateTime() ) {
Info("Updating StartDateTime on event $$Event{Id} from $$Event{StartDateTime} to $$fs_events{$db_event}{StartDateTime}");
$Event->StartDateTime($$fs_events{$db_event}->StartDateTime());
}
$Event->save();
@ -683,12 +683,12 @@ if ( $level > 1 ) {
# Remove empty events (with no frames)
$cleaned = 0;
Debug("Checking for Events with no Frames");
my $selectEmptyEventsSql = 'SELECT `E`.`Id` AS `Id`, `E`.`StartTime`, `F`.`EventId` FROM `Events` AS E LEFT JOIN `Frames` AS F ON (`E`.`Id` = `F`.`EventId`)
WHERE isnull(`F`.`EventId`) AND now() - interval '.$Config{ZM_AUDIT_MIN_AGE}.' second > `E`.`StartTime`';
my $selectEmptyEventsSql = 'SELECT `E`.`Id` AS `Id`, `E`.`StartDateTime`, `F`.`EventId` FROM `Events` AS E LEFT JOIN `Frames` AS F ON (`E`.`Id` = `F`.`EventId`)
WHERE isnull(`F`.`EventId`) AND now() - interval '.$Config{ZM_AUDIT_MIN_AGE}.' second > `E`.`StartDateTime`';
if ( my $selectEmptyEventsSth = $dbh->prepare_cached( $selectEmptyEventsSql ) ) {
if ( $res = $selectEmptyEventsSth->execute() ) {
while( my $event = $selectEmptyEventsSth->fetchrow_hashref() ) {
aud_print("Found empty event with no frame records '$event->{Id}' at $$event{StartTime}");
aud_print("Found empty event with no frame records '$event->{Id}' at $$event{StartDateTime}");
if ( confirm() ) {
if ( $res = $deleteEventSth->execute($event->{Id}) ) {
$cleaned = 1;
@ -750,7 +750,7 @@ if ( $level > 1 ) {
#"SELECT E.Id, ANY_VALUE(E.MonitorId),
#
#max(F.TimeStamp) as EndTime,
#unix_timestamp(max(F.TimeStamp)) - unix_timestamp(E.StartTime) as Length,
#unix_timestamp(max(F.TimeStamp)) - unix_timestamp(E.StartDateTime) as Length,
#max(F.FrameId) as Frames,
#count(if(F.Score>0,1,NULL)) as AlarmFrames,
#sum(F.Score) as TotScore,
@ -760,11 +760,11 @@ if ( $level > 1 ) {
#WHERE isnull(E.Frames) or isnull(E.EndTime)
#GROUP BY E.Id HAVING EndTime < (now() - interval ".$Config{ZM_AUDIT_MIN_AGE}.' second)'
#;
'SELECT *, unix_timestamp(`StartTime`) AS `TimeStamp` FROM `Events` WHERE `EndTime` IS NULL AND `StartTime` < (now() - interval '.$Config{ZM_AUDIT_MIN_AGE}.' second)'.($monitor_id?' AND MonitorId=?':'');
'SELECT *, unix_timestamp(`StartDateTime`) AS `TimeStamp` FROM `Events` WHERE `EndDateTime` IS NULL AND `StartDateTime` < (now() - interval '.$Config{ZM_AUDIT_MIN_AGE}.' second)'.($monitor_id?' AND MonitorId=?':'');
my $selectFrameDataSql = '
SELECT
max(`TimeStamp`) AS `EndTime`,
max(`TimeStamp`) AS `EndDateTime`,
unix_timestamp(max(`TimeStamp`)) AS `EndTimeStamp`,
max(`FrameId`) AS `Frames`,
count(if(`Score`>0,1,NULL)) AS `AlarmFrames`,
@ -779,7 +779,7 @@ FROM `Frames` WHERE `EventId`=?';
my $updateUnclosedEventsSql =
"UPDATE low_priority `Events`
SET `Name` = ?,
`EndTime` = ?,
`EndDateTime` = ?,
`Length` = ?,
`Frames` = ?,
`AlarmFrames` = ?,
@ -794,7 +794,7 @@ FROM `Frames` WHERE `EventId`=?';
$res = $selectUnclosedEventsSth->execute($monitor_id?$monitor_id:())
or Fatal("Can't execute: ".$selectUnclosedEventsSth->errstr());
while( my $event = $selectUnclosedEventsSth->fetchrow_hashref() ) {
aud_print("Found open event '$event->{Id}' on Monitor $event->{MonitorId} at $$event{StartTime}");
aud_print("Found open event '$event->{Id}' on Monitor $event->{MonitorId} at $$event{StartDateTime}");
if ( confirm('close', 'closing') ) {
if ( ! ( $res = $selectFrameDataSth->execute($event->{Id}) ) ) {
Error("Can't execute: $selectFrameDataSql:".$selectFrameDataSth->errstr());
@ -808,7 +808,7 @@ FROM `Frames` WHERE `EventId`=?';
$event->{Id},
RECOVER_TAG
),
$frame->{EndTime},
$frame->{EndDateTime},
$frame->{EndTimeStamp} - $event->{TimeStamp},
$frame->{Frames},
$frame->{AlarmFrames},

View File

@ -704,7 +704,7 @@ sub substituteTags {
$text =~ s/%EN%/$Event->{Name}/g;
$text =~ s/%EC%/$Event->{Cause}/g;
$text =~ s/%ED%/$Event->{Notes}/g;
$text =~ s/%ET%/$Event->{StartTime}/g;
$text =~ s/%ET%/$Event->{StartDateTime}/g;
$text =~ s/%EVF%/$$Event{DefaultVideo}/g; # Event video filename
$text =~ s/%EL%/$Event->{Length}/g;
$text =~ s/%EF%/$Event->{Frames}/g;

View File

@ -231,7 +231,7 @@ Debug("@Monitors");
$Event->Height( $Monitor->Height() );
$Event->Orientation( $Monitor->Orientation() );
$Event->recover_timestamps();
if ( $$Event{StartTime} ) {
if ( $$Event{StartDateTime} ) {
$Event->save({}, 1);
Info("Event resurrected as " . $Event->to_string() );
} else {
@ -294,7 +294,7 @@ Debug("@Monitors");
$Event->StorageId( $Storage->Id() );
$Event->DiskSpace( undef );
$Event->recover_timestamps();
if ( $$Event{StartTime} ) {
if ( $$Event{StartDateTime} ) {
$Event->save({}, 1);
Info("Event resurrected as " . $Event->to_string() );
} else {
@ -309,13 +309,13 @@ Debug("@Monitors");
my ( undef, $year, $month, $day ) = split('/', $day_dir);
$year += 2000;
my ( $hour, $minute, $second ) = split('/', $event_dir);
my $StartTime =sprintf('%.4d-%.2d-%.2d %.2d:%.2d:%.2d', $year, $month, $day, $hour, $minute, $second);
my $StartDateTime =sprintf('%.4d-%.2d-%.2d %.2d:%.2d:%.2d', $year, $month, $day, $hour, $minute, $second);
my $Event = ZoneMinder::Event->find_one(
MonitorId=>$monitor_dir,
StartTime=>$StartTime,
StartDateTime=>$StartDateTime,
);
if ( $Event ) {
Debug("Found event matching starttime on monitor $monitor_dir at $StartTime: " . $Event->to_string());
Debug("Found event matching starttime on monitor $monitor_dir at $StartDateTime: " . $Event->to_string());
next;
}
@ -358,7 +358,7 @@ Debug("@Monitors");
$Event->Orientation( $Monitor->Orientation() );
$Event->StorageId( $Storage->Id() );
$Event->recover_timestamps();
if ( $$Event{StartTime} ) {
if ( $$Event{StartDateTime} ) {
$Event->save({}, 1);
Info("Event resurrected as " . $Event->to_string() );
} else {
@ -400,7 +400,7 @@ Debug("@Monitors");
$Event->Orientation( $Monitor->Orientation() );
$Event->StorageId( $Storage->Id() );
$Event->recover_timestamps();
if ( $$Event{StartTime} ) {
if ( $$Event{StartDateTime} ) {
$Event->save({}, 1);
Info("Event resurrected as " . $Event->to_string() );
} else {

View File

@ -43,10 +43,10 @@ while( 1 ) {
}
}
$dbh->do('DELETE FROM Events_Hour WHERE StartTime < DATE_SUB(NOW(), INTERVAL 1 hour)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Day WHERE StartTime < DATE_SUB(NOW(), INTERVAL 1 day)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Week WHERE StartTime < DATE_SUB(NOW(), INTERVAL 1 week)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Month WHERE StartTime < DATE_SUB(NOW(), INTERVAL 1 month)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Hour WHERE StartDateTime < DATE_SUB(NOW(), INTERVAL 1 hour)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Day WHERE StartDateTime < DATE_SUB(NOW(), INTERVAL 1 day)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Week WHERE StartDateTime < DATE_SUB(NOW(), INTERVAL 1 week)') or Error($dbh->errstr());
$dbh->do('DELETE FROM Events_Month WHERE StartDateTime < DATE_SUB(NOW(), INTERVAL 1 month)') or Error($dbh->errstr());
# Prune the Logs table if required
if ( $Config{ZM_LOG_DATABASE_LIMIT} ) {

View File

@ -201,7 +201,7 @@ if ( $event_id ) {
my $sql = " SELECT (SELECT max(Delta) FROM Frames WHERE EventId=Events.Id)-(SELECT min(Delta) FROM Frames WHERE EventId=Events.Id) as FullLength,
Events.*,
unix_timestamp(Events.StartTime) as Time,
unix_timestamp(Events.StartDateTime) as Time,
M.Name as MonitorName,
M.Palette
FROM Events

View File

@ -49,7 +49,7 @@ protected:
const int &mWd;
protected:
CommsBase( int &rd, int &wd ) : mRd( rd ), mWd( wd ) {
CommsBase(const int &rd, const int &wd) : mRd(rd), mWd(wd) {
}
virtual ~CommsBase() {
}
@ -62,10 +62,10 @@ public:
public:
int getReadDesc() const {
return( mRd );
return mRd;
}
int getWriteDesc() const {
return( mWd );
return mWd;
}
int getMaxDesc() const {
return( mRd>mWd?mRd:mWd );

View File

@ -112,8 +112,9 @@ public:
double DecimalValue() const;
const char *StringValue() const;
ConfigItem &operator=(const ConfigItem item) {
Copy(item);return *this;
ConfigItem &operator=(const ConfigItem &item) {
Copy(item);
return *this;
}
inline operator bool() const {
return BooleanValue();

View File

@ -48,12 +48,12 @@ public:
return( result );
}
inline bool operator==( const Coord &coord ) { return( x == coord.x && y == coord.y ); }
inline bool operator!=( const Coord &coord ) { return( x != coord.x || y != coord.y ); }
inline bool operator>( const Coord &coord ) { return( x > coord.x && y > coord.y ); }
inline bool operator>=( const Coord &coord ) { return( !(operator<(coord)) ); }
inline bool operator<( const Coord &coord ) { return( x < coord.x && y < coord.y ); }
inline bool operator<=( const Coord &coord ) { return( !(operator>(coord)) ); }
inline bool operator==( const Coord &coord ) const { return( x == coord.x && y == coord.y ); }
inline bool operator!=( const Coord &coord ) const { return( x != coord.x || y != coord.y ); }
inline bool operator>( const Coord &coord ) const { return( x > coord.x && y > coord.y ); }
inline bool operator>=( const Coord &coord ) const { return( !(operator<(coord)) ); }
inline bool operator<( const Coord &coord ) const { return( x < coord.x && y < coord.y ); }
inline bool operator<=( const Coord &coord ) const { return( !(operator>(coord)) ); }
inline Coord &operator+=( const Coord &coord ) { x += coord.x; y += coord.y; return( *this ); }
inline Coord &operator-=( const Coord &coord ) { x -= coord.x; y -= coord.y; return( *this ); }

View File

@ -28,7 +28,7 @@ class zmDbRow {
MYSQL_RES *result_set;
MYSQL_ROW row;
public:
zmDbRow() { result_set = nullptr; row = nullptr; };
zmDbRow() : result_set(nullptr), row(nullptr) { };
MYSQL_RES *fetch( const char *query );
zmDbRow( MYSQL_RES *, MYSQL_ROW *row );
~zmDbRow();

View File

@ -71,7 +71,7 @@ Event::Event(
start_time = now;
} else if ( start_time.tv_sec > now.tv_sec ) {
Error(
"StartTime in the future %u.%u > %u.%u",
"StartDateTime in the future %u.%u > %u.%u",
start_time.tv_sec, start_time.tv_usec, now.tv_sec, now.tv_usec
);
start_time = now;
@ -88,7 +88,9 @@ Event::Event(
char sql[ZM_SQL_MED_BUFSIZ];
struct tm *stime = localtime(&start_time.tv_sec);
snprintf(sql, sizeof(sql), "INSERT INTO Events ( MonitorId, StorageId, Name, StartTime, Width, Height, Cause, Notes, StateId, Orientation, Videoed, DefaultVideo, SaveJPEGs, Scheme ) VALUES ( %d, %d, 'New Event', from_unixtime( %ld ), %d, %d, '%s', '%s', %d, %d, %d, '%s', %d, '%s' )",
snprintf(sql, sizeof(sql), "INSERT INTO Events "
"( MonitorId, StorageId, Name, StartDateTime, Width, Height, Cause, Notes, StateId, Orientation, Videoed, DefaultVideo, SaveJPEGs, Scheme )"
" VALUES ( %u, %u, 'New Event', from_unixtime( %ld ), %u, %u, '%s', '%s', %u, %d, %d, '%s', %d, '%s' )",
monitor->Id(),
storage->Id(),
start_time.tv_sec,
@ -104,12 +106,10 @@ Event::Event(
storage->SchemeString().c_str()
);
db_mutex.lock();
if ( mysql_query(&dbconn, sql) ) {
while ( mysql_query(&dbconn, sql) ) {
db_mutex.unlock();
Error("Can't insert event: %s. sql was (%s)", mysql_error(&dbconn), sql);
return;
} else {
Debug(2, "Created new event with %s", sql);
db_mutex.lock();
}
id = mysql_insert_id(&dbconn);
@ -254,6 +254,11 @@ Event::~Event() {
videowriter = nullptr;
}
// endtime is set in AddFrame, so SHOULD be set to the value of the last frame timestamp.
if ( ! end_time.tv_sec ) {
Warning("Empty endtime for event. Should not happen. Setting to now.");
gettimeofday(&end_time, nullptr);
}
struct DeltaTimeval delta_time;
DELTA_TIMEVAL(delta_time, end_time, start_time, DT_PREC_2);
Debug(2, "start_time:%d.%d end_time%d.%d", start_time.tv_sec, start_time.tv_usec, end_time.tv_sec, end_time.tv_usec);
@ -284,7 +289,7 @@ Event::~Event() {
// Should not be static because we might be multi-threaded
char sql[ZM_SQL_LGE_BUFSIZ];
snprintf(sql, sizeof(sql),
"UPDATE Events SET Name='%s%" PRIu64 "', EndTime = from_unixtime(%ld), Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d WHERE Id = %" PRIu64 " AND Name='New Event'",
"UPDATE Events SET Name='%s%" PRIu64 "', EndDateTime = from_unixtime(%ld), Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d WHERE Id = %" PRIu64 " AND Name='New Event'",
monitor->EventPrefix(), id, end_time.tv_sec,
delta_time.positive?"":"-", delta_time.sec, delta_time.fsec,
frames, alarm_frames,
@ -300,7 +305,7 @@ Event::~Event() {
if ( !mysql_affected_rows(&dbconn) ) {
// Name might have been changed during recording, so just do the update without changing the name.
snprintf(sql, sizeof(sql),
"UPDATE Events SET EndTime = from_unixtime(%ld), Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d WHERE Id = %" PRIu64,
"UPDATE Events SET EndDateTime = from_unixtime(%ld), Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d WHERE Id = %" PRIu64,
end_time.tv_sec,
delta_time.positive?"":"-", delta_time.sec, delta_time.fsec,
frames, alarm_frames,
@ -334,7 +339,7 @@ bool Event::WriteFrameImage(
Image *image,
struct timeval timestamp,
const char *event_file,
bool alarm_frame) {
bool alarm_frame) const {
int thisquality =
(alarm_frame && (config.jpeg_alarm_file_quality > config.jpeg_file_quality)) ?
@ -567,10 +572,12 @@ void Event::AddFramesInternal(int n_frames, int start_frame, Image **images, str
} else {
Debug(1, "No valid pre-capture frames to add");
}
end_time = *timestamps[n_frames-1];
} // void Event::AddFramesInternal(int n_frames, int start_frame, Image **images, struct timeval **timestamps)
void Event::WriteDbFrames() {
char *frame_insert_values_ptr = (char *)&frame_insert_sql + 90; // 90 == strlen(frame_insert_sql);
Debug(1, "Inserting %d frames", frame_data.size());
while ( frame_data.size() ) {
Frame *frame = frame_data.front();
frame_data.pop();
@ -586,8 +593,9 @@ void Event::WriteDbFrames() {
frame->score);
delete frame;
}
*(frame_insert_values_ptr-1) = '\0'; // The -2 is for the extra , added for values above
*(frame_insert_values_ptr-1) = '\0'; // The -1 is for the extra , added for values above
db_mutex.lock();
Debug(1, "SQL: %s", frame_insert_sql);
int rc = mysql_query(&dbconn, frame_insert_sql);
db_mutex.unlock();
@ -682,7 +690,6 @@ void Event::AddFrame(Image *image, struct timeval timestamp, int score, Image *a
bool db_frame = ( frame_type != BULK ) || (frames==1) || ((frames%config.bulk_frame_interval)==0) ;
if ( db_frame ) {
static char sql[ZM_SQL_MED_BUFSIZ];
// The idea is to write out 1/sec
frame_data.push(new Frame(id, frames, frame_type, timestamp, delta_time, score));
@ -692,6 +699,7 @@ void Event::AddFrame(Image *image, struct timeval timestamp, int score, Image *a
WriteDbFrames();
last_db_frame = frames;
static char sql[ZM_SQL_MED_BUFSIZ];
snprintf(sql, sizeof(sql),
"UPDATE Events SET Length = %s%ld.%02ld, Frames = %d, AlarmFrames = %d, TotScore = %d, AvgScore = %d, MaxScore = %d WHERE Id = %" PRIu64,
( delta_time.positive?"":"-" ),

View File

@ -113,23 +113,21 @@ class Event {
~Event();
uint64_t Id() const { return id; }
const std::string &Cause() { return cause; }
const std::string &Cause() const { return cause; }
int Frames() const { return frames; }
int AlarmFrames() const { return alarm_frames; }
const struct timeval &StartTime() const { return start_time; }
const struct timeval &EndTime() const { return end_time; }
struct timeval &StartTime() { return start_time; }
struct timeval &EndTime() { return end_time; }
bool SendFrameImage( const Image *image, bool alarm_frame=false );
bool WriteFrameImage( Image *image, struct timeval timestamp, const char *event_file, bool alarm_frame=false );
bool WriteFrameImage( Image *image, struct timeval timestamp, const char *event_file, bool alarm_frame=false ) const;
bool WriteFrameVideo( const Image *image, const struct timeval timestamp, VideoWriter* videow );
void updateNotes( const StringSetMap &stringSetMap );
void AddFrames( int n_frames, Image **images, struct timeval **timestamps );
void AddFrame( Image *image, struct timeval timestamp, int score=0, Image *alarm_frame=nullptr );
void AddFrame( Image *image, struct timeval timestamp, int score=0, Image *alarm_image=nullptr );
private:
void AddFramesInternal( int n_frames, int start_frame, Image **images, struct timeval **timestamps );
@ -146,7 +144,7 @@ class Event {
return Event::getSubPath( localtime( time ) );
}
const char* getEventFile(void) {
const char* getEventFile(void) const {
return video_file.c_str();
}

View File

@ -45,7 +45,7 @@ bool EventStream::loadInitialEventData(int monitor_id, time_t event_time) {
static char sql[ZM_SQL_SML_BUFSIZ];
snprintf(sql, sizeof(sql), "SELECT `Id` FROM `Events` WHERE "
"`MonitorId` = %d AND unix_timestamp(`EndTime`) > %ld "
"`MonitorId` = %d AND unix_timestamp(`EndDateTime`) > %ld "
"ORDER BY `Id` ASC LIMIT 1", monitor_id, event_time);
if ( mysql_query(&dbconn, sql) ) {
@ -116,8 +116,8 @@ bool EventStream::loadEventData(uint64_t event_id) {
static char sql[ZM_SQL_MED_BUFSIZ];
snprintf(sql, sizeof(sql),
"SELECT `MonitorId`, `StorageId`, `Frames`, unix_timestamp( `StartTime` ) AS StartTimestamp, "
"unix_timestamp( `EndTime` ) AS EndTimestamp, "
"SELECT `MonitorId`, `StorageId`, `Frames`, unix_timestamp( `StartDateTime` ) AS StartTimestamp, "
"unix_timestamp( `EndDateTime` ) AS EndTimestamp, "
"(SELECT max(`Delta`)-min(`Delta`) FROM `Frames` WHERE `EventId`=`Events`.`Id`) AS Duration, "
"`DefaultVideo`, `Scheme`, `SaveJPEGs`, `Orientation`+0 FROM `Events` WHERE `Id` = %" PRIu64, event_id);
@ -189,13 +189,13 @@ bool EventStream::loadEventData(uint64_t event_id) {
if ( storage_path[0] == '/' )
snprintf(event_data->path, sizeof(event_data->path),
"%s/%d/%02d/%02d/%02d/%02d/%02d/%02d",
"%s/%u/%02d/%02d/%02d/%02d/%02d/%02d",
storage_path, event_data->monitor_id,
event_time->tm_year-100, event_time->tm_mon+1, event_time->tm_mday,
event_time->tm_hour, event_time->tm_min, event_time->tm_sec);
else
snprintf(event_data->path, sizeof(event_data->path),
"%s/%s/%d/%02d/%02d/%02d/%02d/%02d/%02d",
"%s/%s/%u/%02d/%02d/%02d/%02d/%02d/%02d",
staticConfig.PATH_WEB.c_str(), storage_path, event_data->monitor_id,
event_time->tm_year-100, event_time->tm_mon+1, event_time->tm_mday,
event_time->tm_hour, event_time->tm_min, event_time->tm_sec);
@ -203,23 +203,23 @@ bool EventStream::loadEventData(uint64_t event_id) {
struct tm *event_time = localtime(&event_data->start_time);
if ( storage_path[0] == '/' )
snprintf(event_data->path, sizeof(event_data->path),
"%s/%d/%04d-%02d-%02d/%" PRIu64,
"%s/%u/%04d-%02d-%02d/%" PRIu64,
storage_path, event_data->monitor_id,
event_time->tm_year+1900, event_time->tm_mon+1, event_time->tm_mday,
event_data->event_id);
else
snprintf(event_data->path, sizeof(event_data->path),
"%s/%s/%d/%04d-%02d-%02d/%" PRIu64,
"%s/%s/%u/%04d-%02d-%02d/%" PRIu64,
staticConfig.PATH_WEB.c_str(), storage_path, event_data->monitor_id,
event_time->tm_year+1900, event_time->tm_mon+1, event_time->tm_mday,
event_time->tm_year+1900, event_time->tm_mon+1, event_time->tm_mday,
event_data->event_id);
} else {
if ( storage_path[0] == '/' )
snprintf(event_data->path, sizeof(event_data->path), "%s/%d/%" PRIu64,
snprintf(event_data->path, sizeof(event_data->path), "%s/%u/%" PRIu64,
storage_path, event_data->monitor_id, event_data->event_id);
else
snprintf(event_data->path, sizeof(event_data->path), "%s/%s/%d/%" PRIu64,
snprintf(event_data->path, sizeof(event_data->path), "%s/%s/%u/%" PRIu64,
staticConfig.PATH_WEB.c_str(), storage_path, event_data->monitor_id,
event_data->event_id);
}
@ -424,6 +424,7 @@ void EventStream::processCommand(const CmdMsg *msg) {
switch ( replay_rate ) {
case -1 * ZM_RATE_BASE :
replay_rate = -2 * ZM_RATE_BASE;
break;
case -2 * ZM_RATE_BASE :
replay_rate = -5 * ZM_RATE_BASE;
break;
@ -526,7 +527,7 @@ void EventStream::processCommand(const CmdMsg *msg) {
if ( offset < 0.0 ) {
Warning("Invalid offset, not seeking");
break;
}
}
// This should get us close, but not all frames will have the same duration
curr_frame_id = (int)(event_data->frame_count*offset/event_data->duration)+1;
if ( event_data->frames[curr_frame_id-1].offset > offset ) {
@ -538,10 +539,10 @@ void EventStream::processCommand(const CmdMsg *msg) {
}
if ( curr_frame_id < 1 ) {
curr_frame_id = 1;
} else if ( curr_frame_id > event_data->last_frame_id ) {
} else if ( (unsigned long)curr_frame_id > event_data->last_frame_id ) {
curr_frame_id = event_data->last_frame_id;
}
curr_stream_time = event_data->frames[curr_frame_id-1].timestamp;
Debug(1, "Got SEEK command, to %f (new current frame id: %d offset %f)",
offset, curr_frame_id, event_data->frames[curr_frame_id-1].offset);
@ -794,7 +795,7 @@ bool EventStream::sendFrame(int delta_us) {
Error("Unable to get a frame");
return false;
}
Image *send_image = prepareImage(image);
static unsigned char temp_img_buffer[ZM_MAX_IMAGE_SIZE];
int img_buffer_size = 0;
@ -881,7 +882,7 @@ void EventStream::runStream() {
// If we are streaming and this frame is due to be sent
// frame mod defaults to 1 and if we are going faster than max_fps will get multiplied by 2
// so if it is 2, then we send every other frame, if is it 4 then every fourth frame, etc.
if ( (frame_mod == 1) || (((curr_frame_id-1)%frame_mod) == 0) ) {
send_frame = true;
}
@ -963,7 +964,7 @@ void EventStream::runStream() {
if ( (mode == MODE_SINGLE) && (
(curr_frame_id < 1 )
||
((unsigned int)curr_frame_id >= event_data->frame_count)
((unsigned int)curr_frame_id >= event_data->frame_count)
)
) {
Debug(2, "Have mode==MODE_SINGLE and at end of event, looping back to start");
@ -1054,9 +1055,8 @@ void EventStream::runStream() {
closeComms();
} // end void EventStream::runStream()
bool EventStream::send_file(const char * filepath) {
bool EventStream::send_file(const char *filepath) {
static unsigned char temp_img_buffer[ZM_MAX_IMAGE_SIZE];
int rc;
int img_buffer_size = 0;
uint8_t *img_buffer = temp_img_buffer;
@ -1084,7 +1084,7 @@ bool EventStream::send_file(const char * filepath) {
Info("Unable to send raw frame %u: %s", curr_frame_id, strerror(errno));
return false;
}
rc = zm_sendfile(fileno(stdout), fileno(fdj), 0, (int)filestat.st_size);
int rc = zm_sendfile(fileno(stdout), fileno(fdj), 0, (int)filestat.st_size);
if ( rc == (int)filestat.st_size ) {
// Success
fclose(fdj); /* Close the file handle */

View File

@ -76,7 +76,7 @@ class EventStream : public StreamBase {
StreamMode mode;
bool forceEventChange;
unsigned long curr_frame_id;
long curr_frame_id;
double curr_stream_time;
bool send_frame;
struct timeval start; // clock time when started the event
@ -133,11 +133,11 @@ class EventStream : public StreamBase {
void setStreamMode( StreamMode p_mode ) {
mode = p_mode;
}
void runStream();
void runStream() override;
Image *getImage();
private:
bool send_file( const char *file_path );
bool send_buffer( uint8_t * buffer, int size );
bool send_file(const char *filepath);
bool send_buffer(uint8_t * buffer, int size);
Storage *storage;
FFmpeg_Input *ffmpeg_input;
AVCodecContext *input_codec_context;

View File

@ -22,8 +22,7 @@
#include <string>
class Exception
{
class Exception {
protected:
typedef enum { INFO, WARNING, ERROR, FATAL } Severity;
@ -32,33 +31,28 @@ protected:
Severity mSeverity;
public:
Exception( const std::string &message, Severity severity=ERROR ) : mMessage( message ), mSeverity( severity )
explicit Exception(const std::string &message, const Severity severity=ERROR) :
mMessage(message),
mSeverity(severity)
{
}
public:
const std::string &getMessage() const
{
return( mMessage );
const std::string &getMessage() const {
return mMessage;
}
Severity getSeverity() const
{
return( mSeverity );
Severity getSeverity() const {
return mSeverity;
}
bool isInfo() const
{
return( mSeverity == INFO );
bool isInfo() const {
return mSeverity == INFO;
}
bool isWarning() const
{
bool isWarning() const {
return( mSeverity == WARNING );
}
bool isError() const
{
bool isError() const {
return( mSeverity == ERROR );
}
bool isFatal() const
{
bool isFatal() const {
return( mSeverity == FATAL );
}
};

View File

@ -23,10 +23,10 @@ class FFmpeg_Input {
int Close();
AVFrame *get_frame( int stream_id=-1 );
AVFrame *get_frame( int stream_id, double at );
int get_video_stream_id() {
int get_video_stream_id() const {
return video_stream_id;
}
int get_audio_stream_id() {
int get_audio_stream_id() const {
return audio_stream_id;
}

View File

@ -68,19 +68,26 @@ class FifoStream : public StreamBase {
);
protected:
typedef enum { MJPEG, RAW } StreamType;
typedef enum { UNKNOWN, MJPEG, RAW } StreamType;
StreamType stream_type;
bool sendMJEGFrames();
bool sendRAWFrames();
void processCommand(const CmdMsg *msg) {}
public:
FifoStream() {}
FifoStream() :
stream_path(nullptr),
fd(0),
total_read(0),
bytes_read(0),
frame_count(0),
stream_type(UNKNOWN)
{}
static void fifo_create_if_missing(
const char * path,
bool delete_fake_fifo = true);
void setStreamStart(const char * path);
void setStreamStart(int monitor_id, const char * format);
void runStream();
void runStream() override;
};
#endif // ZM_FIFO_H

View File

@ -153,17 +153,17 @@ public:
int Palette() const { return( palette ); }
int Extras() const { return( extras ); }
int Brightness( int p_brightness=-1 );
int Hue( int p_hue=-1 );
int Colour( int p_colour=-1 );
int Contrast( int p_contrast=-1 );
int Brightness( int p_brightness=-1 ) override;
int Hue( int p_hue=-1 ) override;
int Colour( int p_colour=-1 ) override;
int Contrast( int p_contrast=-1 ) override;
int PrimeCapture();
int PreCapture();
int Capture( Image &image );
int PostCapture();
int CaptureAndRecord( Image &image, timeval recording, char* event_directory ) {return(0);};
int Close() { return 0; };
int PrimeCapture()override ;
int PreCapture()override ;
int Capture( Image &image )override ;
int PostCapture()override ;
int CaptureAndRecord( Image &image, timeval recording, char* event_directory ) override {return(0);};
int Close() override { return 0; };
static bool GetCurrentSettings( const char *device, char *output, int version, bool verbose );
};

View File

@ -43,18 +43,6 @@ Logger *Logger::smInstance = nullptr;
Logger::StringMap Logger::smCodes;
Logger::IntMap Logger::smSyslogPriorities;
#if 0
static void subtractTime( struct timeval * const tp1, struct timeval * const tp2 ) {
tp1->tv_sec -= tp2->tv_sec;
if ( tp1->tv_usec <= tp2->tv_usec ) {
tp1->tv_sec--;
tp1->tv_usec = 1000000 - (tp2->tv_usec - tp1->tv_usec);
} else {
tp1->tv_usec = tp1->tv_usec - tp2->tv_usec;
}
}
#endif
void Logger::usrHandler(int sig) {
Logger *logger = fetch();
if ( sig == SIGUSR1 )

View File

@ -121,7 +121,7 @@ private:
Logger();
~Logger();
int limit(int level) {
int limit(const int level) const {
if ( level > DEBUG9 )
return DEBUG9;
if ( level < NOLOG )
@ -163,7 +163,7 @@ public:
}
Level level(Level=NOOPT);
bool debugOn() {
bool debugOn() const {
return mEffectiveLevel >= DEBUG1;
}

View File

@ -26,7 +26,7 @@
inline void* zm_mallocaligned(unsigned int reqalignment, size_t reqsize) {
uint8_t* retptr;
#if HAVE_POSIX_MEMALIGN
if ( posix_memalign((void**)&retptr,reqalignment,reqsize) != 0 )
if ( posix_memalign((void**)&retptr, reqalignment, reqsize) != 0 )
return nullptr;
return retptr;
@ -39,7 +39,7 @@ inline void* zm_mallocaligned(unsigned int reqalignment, size_t reqsize) {
alloc = retptr + sizeof(void*);
if(((long)alloc % reqalignment) != 0)
if ( ((long)alloc % reqalignment) != 0 )
alloc = alloc + (reqalignment - ((long)alloc % reqalignment));
/* Store a pointer before to the start of the block, just before returned aligned memory */

View File

@ -1613,7 +1613,6 @@ bool Monitor::Analyse() {
} // end if analysis_fps && pre_event_count
shared_data->last_event = event->Id();
//set up video store data
snprintf(video_store_data->event_file, sizeof(video_store_data->event_file), "%s", event->getEventFile());
video_store_data->recording = event->StartTime();
@ -2654,10 +2653,6 @@ bool Monitor::closeEvent() {
if ( !event )
return false;
if ( function == RECORD || function == MOCORD ) {
//FIXME Is this neccessary? ENdTime should be set in the destructor
gettimeofday(&(event->EndTime()), nullptr);
}
if ( event_delete_thread ) {
event_delete_thread->join();
delete event_delete_thread;

View File

@ -444,7 +444,7 @@ public:
inline Function GetFunction() const {
return( function );
}
inline bool Enabled() {
inline bool Enabled() const {
if ( function <= MONITOR )
return false;
return enabled;
@ -452,17 +452,17 @@ public:
inline const char *EventPrefix() const {
return event_prefix;
}
inline bool Ready() {
inline bool Ready() const {
if ( function <= MONITOR )
return false;
return( image_count > ready_count );
}
inline bool Active() {
inline bool Active() const {
if ( function <= MONITOR )
return false;
return( enabled && shared_data->active );
}
inline bool Exif() {
inline bool Exif() const {
return embed_exif;
}
Orientation getOrientation() const;
@ -479,7 +479,7 @@ public:
uint64_t GetVideoWriterEventId() const { return video_store_data->current_event; }
void SetVideoWriterEventId( unsigned long long p_event_id ) { video_store_data->current_event = p_event_id; }
struct timeval GetVideoWriterStartTime() const { return video_store_data->recording; }
void SetVideoWriterStartTime(struct timeval &t) { video_store_data->recording = t; }
void SetVideoWriterStartTime(const struct timeval &t) { video_store_data->recording = t; }
unsigned int GetPreEventCount() const { return pre_event_count; };
struct timeval GetVideoBufferDuration() const { return video_buffer_duration; };
@ -505,7 +505,7 @@ public:
inline time_t getStartupTime() const { return shared_data->startup_time; }
inline void setStartupTime( time_t p_time ) { shared_data->startup_time = p_time; }
int LabelSize() { return label_size; }
int LabelSize() const { return label_size; }
void actionReload();
void actionEnable();

View File

@ -292,7 +292,7 @@ void MonitorStream::processCommand(const CmdMsg *msg) {
if ( (nbytes = sendto(sd, &status_msg, sizeof(status_msg), MSG_DONTWAIT, (sockaddr *)&rem_addr, sizeof(rem_addr))) < 0 ) {
//if ( errno != EAGAIN )
{
Error( "Can't sendto on sd %d: %s", sd, strerror(errno) );
Error("Can't sendto on sd %d: %s", sd, strerror(errno));
//exit( -1 );
}
}
@ -503,7 +503,7 @@ void MonitorStream::runStream() {
const int max_swap_len_suffix = 15;
int swap_path_length = staticConfig.PATH_SWAP.length() + 1; // +1 for NULL terminator
int subfolder1_length = snprintf(nullptr, 0, "/zmswap-m%d", monitor->Id()) + 1;
int subfolder1_length = snprintf(nullptr, 0, "/zmswap-m%u", monitor->Id()) + 1;
int subfolder2_length = snprintf(nullptr, 0, "/zmswap-q%06d", connkey) + 1;
int total_swap_path_length = swap_path_length + subfolder1_length + subfolder2_length;
@ -874,7 +874,7 @@ void MonitorStream::SingleImageRaw(int scale) {
}
fprintf(stdout,
"Content-Length: %d\r\n"
"Content-Length: %u\r\n"
"Content-Type: image/x-rgb\r\n\r\n",
snap_image->Size());
fwrite(snap_image->Buffer(), snap_image->Size(), 1, stdout);

View File

@ -71,7 +71,7 @@ class MonitorStream : public StreamBase {
bool setStreamStart(int monitor_id) {
return loadMonitor(monitor_id);
}
void runStream();
void runStream() override;
};
#endif // ZM_MONITORSTREAM_H

View File

@ -31,7 +31,7 @@ extern "C" {
}
class zm_packetqueue {
public:
zm_packetqueue(int max_stream_id);
explicit zm_packetqueue(int max_stream_id);
virtual ~zm_packetqueue();
bool queuePacket(AVPacket* packet, struct timeval *timestamp);
bool queuePacket(ZMPacket* packet);

View File

@ -29,15 +29,13 @@
bool zm_reload = false;
bool zm_terminate = false;
RETSIGTYPE zm_hup_handler(int signal)
{
RETSIGTYPE zm_hup_handler(int signal) {
// Shouldn't do complex things in signal handlers, logging is complex and can block due to mutexes.
//Info("Got signal %d (%s), reloading", signal, strsignal(signal));
zm_reload = true;
}
RETSIGTYPE zm_term_handler(int signal)
{
RETSIGTYPE zm_term_handler(int signal) {
// Shouldn't do complex things in signal handlers, logging is complex and can block due to mutexes.
//Info("Got signal %d (%s), exiting", signal, strsignal(signal));
zm_terminate = true;
@ -55,8 +53,7 @@ RETSIGTYPE zm_die_handler(int signal)
#if ( HAVE_SIGINFO_T && HAVE_UCONTEXT_T )
void *ip = nullptr;
void *cr2 = nullptr;
if (info && context) {
if ( info && context ) {
Debug(1,
"Signal information: number %d code %d errno %d pid %d uid %d status %d",
signal, info->si_code, info->si_errno, info->si_pid,
@ -79,7 +76,7 @@ RETSIGTYPE zm_die_handler(int signal)
#endif // defined(__x86_64__)
// Print the signal address and instruction pointer if available
if (ip) {
if ( ip ) {
Error("Signal address is %p, from %p", cr2, ip);
} else {
Error("Signal address is %p, no instruction pointer", cr2);
@ -115,8 +112,7 @@ RETSIGTYPE zm_die_handler(int signal)
exit(signal);
}
void zmSetHupHandler(SigHandler * handler)
{
void zmSetHupHandler(SigHandler * handler) {
sigset_t block_set;
sigemptyset(&block_set);
struct sigaction action, old_action;
@ -127,8 +123,7 @@ void zmSetHupHandler(SigHandler * handler)
sigaction(SIGHUP, &action, &old_action);
}
void zmSetTermHandler(SigHandler * handler)
{
void zmSetTermHandler(SigHandler * handler) {
sigset_t block_set;
sigemptyset(&block_set);
struct sigaction action, old_action;
@ -141,8 +136,7 @@ void zmSetTermHandler(SigHandler * handler)
sigaction(SIGQUIT, &action, &old_action);
}
void zmSetDieHandler(SigHandler * handler)
{
void zmSetDieHandler(SigHandler * handler) {
sigset_t block_set;
sigemptyset(&block_set);
struct sigaction action, old_action;
@ -163,19 +157,16 @@ void zmSetDieHandler(SigHandler * handler)
sigaction(SIGFPE, &action, &old_action);
}
void zmSetDefaultHupHandler()
{
void zmSetDefaultHupHandler() {
zmSetHupHandler((SigHandler *) zm_hup_handler);
}
void zmSetDefaultTermHandler()
{
void zmSetDefaultTermHandler() {
zmSetTermHandler((SigHandler *) zm_term_handler);
}
void zmSetDefaultDieHandler()
{
if (config.dump_cores) {
void zmSetDefaultDieHandler() {
if ( config.dump_cores ) {
// Do nothing
} else {
zmSetDieHandler((SigHandler *) zm_die_handler);

View File

@ -76,7 +76,9 @@ struct DeltaTimeval
#define USEC_PER_SEC 1000000
#define MSEC_PER_SEC 1000
/*
extern struct timeval tv;
*/
inline int tvDiffUsec( struct timeval first, struct timeval last )
{

View File

@ -46,7 +46,7 @@ class User {
User();
explicit User(const MYSQL_ROW &dbrow);
~User();
User(User &u) { Copy(u); }
User(const User &u) { Copy(u); }
void Copy(const User &u);
User& operator=(const User &u) {
Copy(u); return *this;

View File

@ -216,7 +216,7 @@ int X264MP4Writer::Open() {
int X264MP4Writer::Close() {
/* Flush all pending frames */
for ( int i = (x264_encoder_delayed_frames(x264enc) + 1); i > 0; i-- ) {
Debug(1,"Encoding delayed frame");
Debug(1, "Encoding delayed frame");
if ( x264encodeloop(true) < 0 )
break;
}
@ -227,7 +227,7 @@ Debug(1,"Encoding delayed frame");
/* Close MP4 handle */
MP4Close(mp4h);
Debug(1,"Optimising");
Debug(1, "Optimising");
/* Required for proper HTTP streaming */
MP4Optimize((path + ".incomplete").c_str(), path.c_str());

View File

@ -95,91 +95,92 @@ int main(int argc, const char *argv[], char **envp) {
}
const char *query = getenv("QUERY_STRING");
if ( query ) {
Debug(1, "Query: %s", query);
char temp_query[1024];
strncpy(temp_query, query, sizeof(temp_query)-1);
char *q_ptr = temp_query;
char *parms[16]; // Shouldn't be more than this
int parm_no = 0;
while ( (parm_no < 16) && (parms[parm_no] = strtok(q_ptr, "&")) ) {
parm_no++;
q_ptr = nullptr;
}
for ( int p = 0; p < parm_no; p++ ) {
char *name = strtok(parms[p], "=");
char const *value = strtok(nullptr, "=");
if ( !value )
value = "";
if ( !strcmp(name, "source") ) {
source = !strcmp(value, "event")?ZMS_EVENT:ZMS_MONITOR;
if ( !strcmp(value, "fifo") )
source = ZMS_FIFO;
} else if ( !strcmp(name, "mode") ) {
mode = !strcmp(value, "jpeg")?ZMS_JPEG:ZMS_MPEG;
mode = !strcmp(value, "raw")?ZMS_RAW:mode;
mode = !strcmp(value, "zip")?ZMS_ZIP:mode;
mode = !strcmp(value, "single")?ZMS_SINGLE:mode;
} else if ( !strcmp(name, "format") ) {
strncpy( format, value, sizeof(format) );
} else if ( !strcmp(name, "monitor") ) {
monitor_id = atoi(value);
if ( source == ZMS_UNKNOWN )
source = ZMS_MONITOR;
} else if ( !strcmp(name, "time") ) {
event_time = atoi(value);
} else if ( !strcmp(name, "event") ) {
event_id = strtoull(value, nullptr, 10);
source = ZMS_EVENT;
} else if ( !strcmp(name, "frame") ) {
frame_id = strtoull(value, nullptr, 10);
source = ZMS_EVENT;
} else if ( !strcmp(name, "scale") ) {
scale = atoi(value);
} else if ( !strcmp(name, "rate") ) {
rate = atoi(value);
} else if ( !strcmp(name, "maxfps") ) {
maxfps = atof(value);
} else if ( !strcmp(name, "bitrate") ) {
bitrate = atoi(value);
} else if ( !strcmp(name, "ttl") ) {
ttl = atoi(value);
} else if ( !strcmp(name, "replay") ) {
if ( !strcmp(value, "gapless") ) {
replay = EventStream::MODE_ALL_GAPLESS;
} else if ( !strcmp(value, "all") ) {
replay = EventStream::MODE_ALL;
} else if ( !strcmp(value, "none") ) {
replay = EventStream::MODE_NONE;
} else if ( !strcmp(value, "single") ) {
replay = EventStream::MODE_SINGLE;
} else {
Error("Unsupported value %s for replay, defaulting to none", value);
}
} else if ( !strcmp(name, "connkey") ) {
connkey = atoi(value);
} else if ( !strcmp(name, "buffer") ) {
playback_buffer = atoi(value);
} else if ( !strcmp(name, "auth") ) {
strncpy(auth, value, sizeof(auth)-1);
} else if ( !strcmp(name, "token") ) {
jwt_token_str = value;
Debug(1, "ZMS: JWT token found: %s", jwt_token_str.c_str());
} else if ( !strcmp(name, "user") ) {
username = UriDecode(value);
} else if ( !strcmp(name, "pass") ) {
password = UriDecode(value);
Debug(1, "Have %s for password", password.c_str());
} else {
Debug(1, "Unknown parameter passed to zms %s=%s", name, value);
} // end if possible parameter names
} // end foreach parm
} else {
if ( query == nullptr ) {
Fatal("No query string.");
return 0;
} // end if query
Debug(1, "Query: %s", query);
char temp_query[1024];
strncpy(temp_query, query, sizeof(temp_query)-1);
char *q_ptr = temp_query;
char *parms[16]; // Shouldn't be more than this
int parm_no = 0;
while ( (parm_no < 16) && (parms[parm_no] = strtok(q_ptr, "&")) ) {
parm_no++;
q_ptr = nullptr;
}
for ( int p = 0; p < parm_no; p++ ) {
char *name = strtok(parms[p], "=");
char const *value = strtok(nullptr, "=");
if ( !value )
value = "";
if ( !strcmp(name, "source") ) {
source = !strcmp(value, "event")?ZMS_EVENT:ZMS_MONITOR;
if ( !strcmp(value, "fifo") )
source = ZMS_FIFO;
} else if ( !strcmp(name, "mode") ) {
mode = !strcmp(value, "jpeg")?ZMS_JPEG:ZMS_MPEG;
mode = !strcmp(value, "raw")?ZMS_RAW:mode;
mode = !strcmp(value, "zip")?ZMS_ZIP:mode;
mode = !strcmp(value, "single")?ZMS_SINGLE:mode;
} else if ( !strcmp(name, "format") ) {
strncpy(format, value, sizeof(format)-1);
} else if ( !strcmp(name, "monitor") ) {
monitor_id = atoi(value);
if ( source == ZMS_UNKNOWN )
source = ZMS_MONITOR;
} else if ( !strcmp(name, "time") ) {
event_time = atoi(value);
} else if ( !strcmp(name, "event") ) {
event_id = strtoull(value, nullptr, 10);
source = ZMS_EVENT;
} else if ( !strcmp(name, "frame") ) {
frame_id = strtoull(value, nullptr, 10);
source = ZMS_EVENT;
} else if ( !strcmp(name, "scale") ) {
scale = atoi(value);
} else if ( !strcmp(name, "rate") ) {
rate = atoi(value);
} else if ( !strcmp(name, "maxfps") ) {
maxfps = atof(value);
} else if ( !strcmp(name, "bitrate") ) {
bitrate = atoi(value);
} else if ( !strcmp(name, "ttl") ) {
ttl = atoi(value);
} else if ( !strcmp(name, "replay") ) {
if ( !strcmp(value, "gapless") ) {
replay = EventStream::MODE_ALL_GAPLESS;
} else if ( !strcmp(value, "all") ) {
replay = EventStream::MODE_ALL;
} else if ( !strcmp(value, "none") ) {
replay = EventStream::MODE_NONE;
} else if ( !strcmp(value, "single") ) {
replay = EventStream::MODE_SINGLE;
} else {
Error("Unsupported value %s for replay, defaulting to none", value);
}
} else if ( !strcmp(name, "connkey") ) {
connkey = atoi(value);
} else if ( !strcmp(name, "buffer") ) {
playback_buffer = atoi(value);
} else if ( !strcmp(name, "auth") ) {
strncpy(auth, value, sizeof(auth)-1);
} else if ( !strcmp(name, "token") ) {
jwt_token_str = value;
Debug(1, "ZMS: JWT token found: %s", jwt_token_str.c_str());
} else if ( !strcmp(name, "user") ) {
username = UriDecode(value);
} else if ( !strcmp(name, "pass") ) {
password = UriDecode(value);
Debug(1, "Have %s for password", password.c_str());
} else {
Debug(1, "Unknown parameter passed to zms %s=%s", name, value);
} // end if possible parameter names
} // end foreach parm
if ( monitor_id ) {
snprintf(log_id_string, sizeof(log_id_string), "zms_m%d", monitor_id);
} else {

View File

@ -482,7 +482,7 @@ int main(int argc, char *argv[]) {
} // end if ! MONITOR
if ( verbose ) {
printf("Monitor %d(%s)\n", monitor->Id(), monitor->Name());
printf("Monitor %u(%s)\n", monitor->Id(), monitor->Name());
}
if ( !monitor->connect() ) {
Error("Can't connect to capture daemon: %d %s", monitor->Id(), monitor->Name());
@ -521,19 +521,19 @@ int main(int argc, char *argv[]) {
}
if ( function & ZMU_READ_IDX ) {
if ( verbose )
printf("Last read index: %d\n", monitor->GetLastReadIndex());
printf("Last read index: %u\n", monitor->GetLastReadIndex());
else {
if ( have_output ) fputc(separator, stdout);
printf("%d", monitor->GetLastReadIndex());
printf("%u", monitor->GetLastReadIndex());
have_output = true;
}
}
if ( function & ZMU_WRITE_IDX ) {
if ( verbose ) {
printf("Last write index: %d\n", monitor->GetLastWriteIndex());
printf("Last write index: %u\n", monitor->GetLastWriteIndex());
} else {
if ( have_output ) fputc(separator, stdout);
printf("%d", monitor->GetLastWriteIndex());
printf("%u", monitor->GetLastWriteIndex());
have_output = true;
}
}
@ -558,9 +558,9 @@ int main(int argc, char *argv[]) {
if ( function & ZMU_IMAGE ) {
if ( verbose ) {
if ( image_idx == -1 )
printf("Dumping last image captured to Monitor%d.jpg", monitor->Id());
printf("Dumping last image captured to Monitor%u.jpg", monitor->Id());
else
printf("Dumping buffer image %d to Monitor%d.jpg", image_idx, monitor->Id());
printf("Dumping buffer image %d to Monitor%u.jpg", image_idx, monitor->Id());
if ( scale != -1 )
printf(", scaling by %d%%", scale);
printf("\n");
@ -569,7 +569,7 @@ int main(int argc, char *argv[]) {
}
if ( function & ZMU_ZONES ) {
if ( verbose )
printf("Dumping zone image to Zones%d.jpg\n", monitor->Id());
printf("Dumping zone image to Zones%u.jpg\n", monitor->Id());
monitor->DumpZoneImage(zoneString);
}
if ( function & ZMU_ALARM ) {
@ -735,17 +735,17 @@ int main(int argc, char *argv[]) {
Debug(1, "Got %d monitors", mysql_num_rows(result));
printf("%4s%5s%6s%9s%14s%6s%6s%8s%8s\n", "Id", "Func", "State", "TrgState", "LastImgTim", "RdIdx", "WrIdx", "LastEvt", "FrmRate");
for( int i = 0; MYSQL_ROW dbrow = mysql_fetch_row(result); i++ ) {
int mon_id = atoi(dbrow[0]);
int function = atoi(dbrow[1]);
if ( !user || user->canAccess(mon_id) ) {
if ( function > 1 ) {
Monitor *monitor = Monitor::Load(mon_id, false, Monitor::QUERY);
for ( int i = 0; MYSQL_ROW dbrow = mysql_fetch_row(result); i++ ) {
int monitor_id = atoi(dbrow[0]);
int monitor_function = atoi(dbrow[1]);
if ( !user || user->canAccess(monitor_id) ) {
if ( monitor_function > 1 ) {
Monitor *monitor = Monitor::Load(monitor_id, false, Monitor::QUERY);
if ( monitor && monitor->connect() ) {
struct timeval tv = monitor->GetTimestamp();
printf( "%4d%5d%6d%9d%11ld.%02ld%6d%6d%8" PRIu64 "%8.2f\n",
monitor->Id(),
function,
monitor_function,
monitor->GetState(),
monitor->GetTriggerState(),
tv.tv_sec, tv.tv_usec/10000,

View File

@ -1 +1 @@
1.35.12
1.35.13

View File

@ -39,7 +39,7 @@ $search = isset($_REQUEST['search']) ? $_REQUEST['search'] : '';
$advsearch = isset($_REQUEST['advsearch']) ? json_decode($_REQUEST['advsearch'], JSON_OBJECT_AS_ARRAY) : array();
// Sort specifies the name of the column to sort on
$sort = 'StartTime';
$sort = 'StartDateTime';
if ( isset($_REQUEST['sort']) ) {
$sort = $_REQUEST['sort'];
}
@ -133,7 +133,7 @@ function queryRequest($filter, $search, $advsearch, $sort, $offset, $order, $lim
$table = 'Events';
// The names of the dB columns in the events table we are interested in
$columns = array('Id', 'MonitorId', 'StorageId', 'Name', 'Cause', 'StartTime', 'EndTime', 'Length', 'Frames', 'AlarmFrames', 'TotScore', 'AvgScore', 'MaxScore', 'Archived', 'Emailed', 'Notes', 'DiskSpace');
$columns = array('Id', 'MonitorId', 'StorageId', 'Name', 'Cause', 'StartDateTime', 'EndDateTime', 'Length', 'Frames', 'AlarmFrames', 'TotScore', 'AvgScore', 'MaxScore', 'Archived', 'Emailed', 'Notes', 'DiskSpace');
// The names of columns shown in the event view that are NOT dB columns in the database
$col_alt = array('Monitor', 'Storage');
@ -212,19 +212,24 @@ function queryRequest($filter, $search, $advsearch, $sort, $offset, $order, $lim
$row['Archived'] = $row['Archived'] ? translate('Yes') : translate('No');
$row['Emailed'] = $row['Emailed'] ? translate('Yes') : translate('No');
$row['Cause'] = validHtmlStr($row['Cause']);
$row['StartTime'] = strftime(STRF_FMT_DATETIME_SHORTER, strtotime($row['StartTime']));
$row['EndTime'] = strftime(STRF_FMT_DATETIME_SHORTER, strtotime($row['EndTime']));
$row['StartDateTime'] = strftime(STRF_FMT_DATETIME_SHORTER, strtotime($row['StartDateTime']));
$row['EndDateTime'] = $row['EndDateTime'] ? strftime(STRF_FMT_DATETIME_SHORTER, strtotime($row['EndDateTime'])) : null;
$row['Length'] = gmdate('H:i:s', $row['Length'] );
$row['Storage'] = ( $row['StorageId'] and isset($StorageById[$row['StorageId']]) ) ? $StorageById[$row['StorageId']]->Name() : 'Default';
$row['Notes'] = htmlspecialchars($row['Notes']);
$row['Notes'] = nl2br(htmlspecialchars($row['Notes']));
$row['DiskSpace'] = human_filesize($event->DiskSpace());
$rows[] = $row;
}
$data['rows'] = $rows;
# total has to be the # of available rows. Not sure what totalNotFiltered is actually used for yet.
$data['totalNotFiltered'] = $data['total'] = dbFetchOne('SELECT count(*) AS Total FROM ' .$table. ' AS E'. ($filter->sql() ? ' WHERE '.$filter->sql():''), 'Total');
#$data['total'] = count($rows);
# totalNotFiltered must equal total, except when either search bar has been used
$data['totalNotFiltered'] = dbFetchOne('SELECT count(*) AS Total FROM Events AS E INNER JOIN Monitors AS M ON E.MonitorId = M.Id'. ($filter->sql() ? ' WHERE '.$filter->sql():''), 'Total');
if ( $search != '' || count($advsearch) ) {
$data['total'] = dbFetchOne('SELECT count(*) AS Total FROM Events AS E INNER JOIN Monitors AS M ON E.MonitorId = M.Id'.$where , 'Total', $wherevalues);
} else {
$data['total'] = $data['totalNotFiltered'];
}
return $data;
}
?>

View File

@ -14,8 +14,8 @@ class Event extends ZM_Object {
'StorageId' => null,
'SecondaryStorageId' => null,
'Cause' => '',
'StartTime' => null,
'EndTime' => null,
'StartDateTime' => null,
'EndDateTime' => null,
'Width' => null,
'Height' => null,
'Length' => null,
@ -93,7 +93,7 @@ class Event extends ZM_Object {
public function Time() {
if ( ! isset($this->{'Time'}) ) {
$this->{'Time'} = strtotime($this->{'StartTime'});
$this->{'Time'} = strtotime($this->{'StartDateTime'});
}
return $this->{'Time'};
}
@ -153,9 +153,9 @@ class Event extends ZM_Object {
if ( $this->{'Scheme'} == 'Deep' ) {
# Assumption: All events have a start time
$start_date = date_parse($this->{'StartTime'});
$start_date = date_parse($this->{'StartDateTime'});
if ( ! $start_date ) {
throw new Exception('Unable to parse start time for event ' . $this->{'Id'} . ' not deleting files.');
throw new Exception('Unable to parse start date time for event ' . $this->{'Id'} . ' not deleting files.');
}
$start_date['year'] = $start_date['year'] % 100;
@ -279,7 +279,7 @@ class Event extends ZM_Object {
}
if ( (!property_exists($this, 'DiskSpace')) or (null === $this->{'DiskSpace'}) ) {
$this->{'DiskSpace'} = folder_size($this->Path());
if ( $this->{'EndTime'} ) {
if ( $this->{'EndDateTime'} ) {
# Finished events shouldn't grow in size much so we can commit it to the db.
dbQuery('UPDATE Events SET DiskSpace=? WHERE Id=?', array($this->{'DiskSpace'}, $this->{'Id'}));
}
@ -606,7 +606,7 @@ class Event extends ZM_Object {
if ( $this->Archived() ) {
return false;
}
if ( !$this->EndTime() ) {
if ( !$this->EndDateTime() ) {
return false;
}
if ( !canEdit('Events') ) {
@ -619,7 +619,7 @@ class Event extends ZM_Object {
public function cant_delete_reason() {
if ( $this->Archived() ) {
return 'You cannot delete an archived event. Unarchive it first.';
} else if ( ! $this->EndTime() ) {
} else if ( ! $this->EndDateTime() ) {
return 'You cannot delete an event while it is being recorded. Wait for it to finish.';
} else if ( ! canEdit('Events') ) {
return 'You do not have rights to edit Events.';

View File

@ -1,6 +1,7 @@
<?php
namespace ZM;
require_once('Object.php');
require_once('FilterTerm.php');
class Filter extends ZM_Object {
protected static $table = 'Filters';
@ -60,7 +61,7 @@ class Filter extends ZM_Object {
$this->_querystring .= $term->querystring($objectname, $separator);
} # end foreach term
if ( $this->Id() ) {
$this->_querystring .= $separator.$objectname.'[Id]='.$this->Id();
$this->_querystring .= $separator.$objectname.urlencode('[Id]=').$this->Id();
}
}
return $this->_querystring;
@ -391,35 +392,35 @@ class Filter extends ZM_Object {
break;
case 'DateTime':
case 'StartDateTime':
$sqlValue = 'E.StartTime';
$sqlValue = 'E.StartDateTime';
$dtAttr = true;
break;
case 'Date':
case 'StartDate':
$sqlValue = 'to_days(E.StartTime)';
$sqlValue = 'to_days(E.StartDateTime)';
$dtAttr = true;
break;
case 'Time':
case 'StartTime':
$sqlValue = 'extract(hour_second from E.StartTime)';
$sqlValue = 'extract(hour_second from E.StartDateTime)';
break;
case 'Weekday':
case 'StartWeekday':
$sqlValue = 'weekday(E.StartTime)';
$sqlValue = 'weekday(E.StartDateTime)';
break;
case 'EndDateTime':
$sqlValue = 'E.EndTime';
$sqlValue = 'E.EndDateTime';
$dtAttr = true;
break;
case 'EndDate':
$sqlValue = 'to_days(E.EndTime)';
$sqlValue = 'to_days(E.EndDateTime)';
$dtAttr = true;
break;
case 'EndTime':
$sqlValue = 'extract(hour_second from E.EndTime)';
$sqlValue = 'extract(hour_second from E.EndDateTime)';
break;
case 'EndWeekday':
$sqlValue = 'weekday(E.EndTime)';
$sqlValue = 'weekday(E.EndDateTime)';
break;
case 'Id':
case 'Name':
@ -632,6 +633,11 @@ class Filter extends ZM_Object {
function addTerm($term=false, $position=null) {
if ( !FilterTerm::is_valid_attr($term['attr']) ) {
Error('Unsupported filter attribute ' . $term['attr']);
return $this;
}
$terms = $this->terms();
if ( (!isset($position)) or ($position > count($terms)) )
@ -650,5 +656,12 @@ class Filter extends ZM_Object {
return $this;
} # end function addTerm
function addTerms($terms, $options=null) {
foreach ( $terms as $term ) {
$this->addTerm($term);
}
return $this;
}
} # end class Filter
?>

View File

@ -13,6 +13,7 @@ function getFilterQueryConjunctionTypes() {
return $validConjunctionTypes;
}
class FilterTerm {
public $filter;
public $index;
@ -35,7 +36,7 @@ class FilterTerm {
$this->val = $term['val'];
if ( isset($term['cnj']) ) {
if ( array_key_exists($term['cnj'], $validConjunctionTypes) ) {
$this->cnj = $term['cnj'];
$this->cnj = $term['cnj'];
} else {
Warning('Invalid cnj ' . $term['cnj'].' in '.print_r($term, true));
}
@ -65,7 +66,8 @@ class FilterTerm {
return $values;
}
foreach ( preg_split('/["\'\s]*?,["\'\s]*?/', preg_replace('/^["\']+?(.+)["\']+?$/', '$1', $this->val)) as $value ) {
$vals = is_array($this->val) ? $this->val : preg_split('/["\'\s]*?,["\'\s]*?/', preg_replace('/^["\']+?(.+)["\']+?$/', '$1', $this->val));
foreach ( $vals as $value ) {
switch ( $this->attr ) {
@ -75,7 +77,7 @@ class FilterTerm {
case 'ExistsInFileSystem':
$value = '';
break;
case 'DiskSpace':
case 'DiskPercent':
$value = '';
break;
case 'MonitorName':
@ -83,7 +85,7 @@ class FilterTerm {
case 'Name':
case 'Cause':
case 'Notes':
if ( $this->op == 'LIKE' || $this->op == 'NOT LIKE' ) {
if ( strstr($this->op, 'LIKE') and ! strstr($this->val, '%' ) ) {
$value = '%'.$value.'%';
}
$value = dbEscape($value);
@ -145,7 +147,7 @@ class FilterTerm {
case 'AlarmZoneId':
return ' EXISTS ';
case 'ExistsInFileSystem':
case 'DiskSpace':
case 'DiskPercent':
return '';
}
@ -202,7 +204,7 @@ class FilterTerm {
switch ( $this->attr ) {
case 'ExistsInFileSystem':
case 'DiskSpace':
case 'DiskPercent':
$sql .= 'TRUE /*'.$this->attr.'*/';
break;
case 'MonitorName':
@ -220,49 +222,50 @@ class FilterTerm {
break;
# Unspecified start or end, so assume start, this is to support legacy filters
case 'DateTime':
$sql .= 'E.StartTime';
$sql .= 'E.StartDateTime';
break;
case 'Date':
$sql .= 'to_days(E.StartTime)';
$sql .= 'to_days(E.StartDateTime)';
break;
case 'Time':
$sql .= 'extract(hour_second FROM E.StartTime)';
$sql .= 'extract(hour_second FROM E.StartDateTime)';
break;
case 'Weekday':
$sql .= 'weekday(E.StartTime)';
$sql .= 'weekday(E.StartDateTime)';
break;
# Starting Time
case 'StartDateTime':
$sql .= 'E.StartTime';
$sql .= 'E.StartDateTime';
break;
case 'FramesEventId':
$sql .= 'F.EventId';
break;
case 'StartDate':
$sql .= 'to_days(E.StartTime)';
$sql .= 'to_days(E.StartDateTime)';
break;
case 'StartTime':
$sql .= 'extract(hour_second FROM E.StartTime)';
$sql .= 'extract(hour_second FROM E.StartDateTime)';
break;
case 'StartWeekday':
$sql .= 'weekday(E.StartTime)';
$sql .= 'weekday(E.StartDateTime)';
break;
# Ending Time
case 'EndDateTime':
$sql .= 'E.EndTime';
$sql .= 'E.EndDateTime';
break;
case 'EndDate':
$sql .= 'to_days(E.EndTime)';
$sql .= 'to_days(E.EndDateTime)';
break;
case 'EndTime':
$sql .= 'extract(hour_second FROM E.EndTime)';
$sql .= 'extract(hour_second FROM E.EndDateTime)';
break;
case 'EndWeekday':
$sql .= 'weekday(E.EndTime)';
$sql .= 'weekday(E.EndDateTime)';
break;
case 'Emailed':
case 'Id':
case 'Name':
case 'EventDiskSpace':
case 'DiskSpace':
case 'MonitorId':
case 'StorageId':
case 'SecondaryStorageId':
@ -400,21 +403,63 @@ class FilterTerm {
}
public function is_pre_sql() {
if ( $this->attr == 'DiskPercent' ) {
if ( $this->attr == 'DiskPercent' )
return true;
if ( $this->attr == 'DiskBlocks' )
return true;
}
return false;
}
public function is_post_sql() {
if ( $this->attr == 'ExistsInFileSystem' ) {
return true;
} else if ( $this->attr == 'DiskPercent' ) {
return true;
}
return false;
}
public static function is_valid_attr($attr) {
$attrs = array(
'ExistsInFileSystem',
'Emailed',
'DiskSpace',
'DiskPercent',
'DiskBlocks',
'MonitorName',
'ServerId',
'MonitorServerId',
'StorageServerId',
'FilterServerId',
'DateTime',
'Date',
'Time',
'Weekday',
'StartDateTime',
'FramesEventId',
'StartDate',
'StartTime',
'StartWeekday',
'EndDateTime',
'EndDate',
'EndTime',
'EndWeekday',
'Id',
'Name',
'MonitorId',
'StorageId',
'SecondaryStorageId',
'Length',
'Frames',
'AlarmFrames',
'TotScore',
'AvgScore',
'MaxScore',
'Cause',
'Notes',
'StateId',
'Archived'
);
return in_array($attr, $attrs);
}
} # end class FilterTerm
?>

View File

@ -95,7 +95,7 @@ if ( isset($_REQUEST['object']) and ( $_REQUEST['object'] == 'filter' ) ) {
} else if ( $filter->Background() ) {
$filter->control('start');
}
$redirect = '?view=filter&Id='.$filter->Id();
$redirect = '?view=filter'.$filter->querystring();
} else if ( $action == 'control' ) {
if ( $_REQUEST['command'] == 'start'

View File

@ -121,7 +121,8 @@ if ( $action == 'save' ) {
}
$saferNewName = basename($_REQUEST['newMonitor']['Name']);
$link_path = $NewStorage->Path().'/'.$saferNewName;
if ( !symlink($NewStorage->Path().'/'.$mid, $link_path) ) {
// Use a relative path for the target so the link continues to work from backups or directory changes.
if ( !symlink($mid, $link_path) ) {
if ( ! ( file_exists($link_path) and is_link($link_path) ) ) {
ZM\Warning('Unable to symlink ' . $NewStorage->Path().'/'.$mid . ' to ' . $NewStorage->Path().'/'.$saferNewName);
}

View File

@ -996,26 +996,19 @@ function parseSort($saveToSession=false, $querySep='&amp;') {
$sortColumn = 'E.Cause';
break;
case 'DateTime' :
$sortColumn = 'E.StartTime';
$_REQUEST['sort_field'] = 'StartTime';
$sortColumn = 'E.StartDateTime';
$_REQUEST['sort_field'] = 'StartDateTime';
break;
case 'DiskSpace' :
$sortColumn = 'E.DiskSpace';
break;
case 'StartTime' :
$sortColumn = 'E.StartTime';
break;
case 'StartDateTime' :
// Fix for systems with EVENT_SORT_ORDER set to erroneous StartDateTime.
$_REQUEST['sort_field'] = 'StartTime';
$sortColumn = 'E.StartTime';
$sortColumn = 'E.StartDateTime';
break;
case 'EndTime' :
$sortColumn = 'E.EndTime';
break;
case 'EndDateTime' :
$_REQUEST['sort_field'] = 'EndTime';
$sortColumn = 'E.EndTime';
$sortColumn = 'E.EndDateTime';
break;
case 'Length' :
$sortColumn = 'E.Length';
@ -1051,7 +1044,7 @@ function parseSort($saveToSession=false, $querySep='&amp;') {
$sortColumn = 'F.Score';
break;
default:
$sortColumn = 'E.StartTime';
$sortColumn = 'E.StartDateTime';
break;
}
if ( !isset($_REQUEST['sort_asc']) )

View File

@ -123,7 +123,7 @@ table th:last-child{
a:link {
color: #3498db;
color: #0fbcf9;
text-decoration: none;
}

View File

@ -145,7 +145,7 @@ if ( !$Event->Id() ) {
<span id="dataId" title="<?php echo translate('Id') ?>"><?php echo $Event->Id() ?></span>
<span id="dataMonitor" title="<?php echo translate('Monitor') ?>"><?php echo $Monitor->Id().' '.validHtmlStr($Monitor->Name()) ?></span>
<span id="dataCause" title="<?php echo $Event->Notes()?validHtmlStr($Event->Notes()):translate('AttrCause') ?>"><?php echo validHtmlStr($Event->Cause()) ?></span>
<span id="dataTime" title="<?php echo translate('Time') ?>"><?php echo strftime(STRF_FMT_DATETIME_SHORT, strtotime($Event->StartTime())) ?></span>
<span id="dataTime" title="<?php echo translate('Time') ?>"><?php echo strftime(STRF_FMT_DATETIME_SHORT, strtotime($Event->StartDateTime())) ?></span>
<span id="dataDuration" title="<?php echo translate('Duration') ?>"><?php echo $Event->Length().'s' ?></span>
<span id="dataFrames" title="<?php echo translate('AttrFrames').'/'.translate('AttrAlarmFrames') ?>"><?php echo $Event->Frames() ?>/<?php echo $Event->AlarmFrames() ?></span>
<span id="dataScore" title="<?php echo translate('AttrTotalScore').'/'.translate('AttrAvgScore').'/'.translate('AttrMaxScore') ?>"><?php echo $Event->TotScore() ?>/<?php echo $Event->AvgScore() ?>/<?php echo $Event->MaxScore() ?></span>

View File

@ -104,8 +104,8 @@ getBodyTopHTML();
<th data-sortable="true" data-field="Emailed"><?php echo translate('Emailed') ?></th>
<th data-sortable="true" data-field="Monitor"><?php echo translate('Monitor') ?></th>
<th data-sortable="true" data-field="Cause"><?php echo translate('Cause') ?></th>
<th data-sortable="true" data-field="StartTime"><?php echo translate('AttrStartTime') ?></th>
<th data-sortable="true" data-field="EndTime"><?php echo translate('AttrEndTime') ?></th>
<th data-sortable="true" data-field="StartDateTime"><?php echo translate('AttrStartTime') ?></th>
<th data-sortable="true" data-field="EndDateTime"><?php echo translate('AttrEndTime') ?></th>
<th data-sortable="true" data-field="Length"><?php echo translate('Duration') ?></th>
<th data-sortable="true" data-field="Frames"><?php echo translate('Frames') ?></th>
<th data-sortable="true" data-field="AlarmFrames"><?php echo translate('AlarmBrFrames') ?></th>

View File

@ -152,8 +152,8 @@ while ( $event_row = dbFetchNext($results) ) {
<td class="colName"><a href="?view=event&amp;eid=<?php echo $event->Id().$filterQuery.$sortQuery ?>&amp;page=1"><?php echo validHtmlStr($event->Name()).($event->Archived()?'*':'') ?></a></td>
<td class="colMonitorName"><?php echo makeLink( '?view=monitor&amp;mid='.$event->MonitorId(), $event->MonitorName(), canEdit( 'Monitors' ) ) ?></td>
<td class="colCause"><?php echo makeLink( '#', validHtmlStr($event->Cause()), canEdit( 'Events' ), 'title="' .htmlspecialchars($event->Notes()). '" class="eDetailLink" data-eid=' .$event->Id(). '"') ?></td>
<td class="colTime"><?php echo strftime(STRF_FMT_DATETIME_SHORTER, strtotime($event->StartTime())) .
( $event->EndTime() ? ' until ' . strftime(STRF_FMT_DATETIME_SHORTER, strtotime($event->EndTime()) ) : '' ) ?>
<td class="colTime"><?php echo strftime(STRF_FMT_DATETIME_SHORTER, strtotime($event->StartDateTime())) .
( $event->EndDateTime() ? ' until ' . strftime(STRF_FMT_DATETIME_SHORTER, strtotime($event->EndDateTime()) ) : '' ) ?>
</td>
<td class="colDuration"><?php echo gmdate("H:i:s", $event->Length() ) ?></td>
<td class="colFrames"><?php echo makeLink( '?view=frames&amp;eid='.$event->Id(), $event->Frames() ) ?></td>

View File

@ -35,13 +35,12 @@ $filterNames = array(''=>translate('ChooseFilter'));
$filter = NULL;
$fid = 0;
if ( isset($_REQUEST['Id']) ) {
if ( isset($_REQUEST['Id']) and $_REQUEST['Id'] ) {
$fid = validInt($_REQUEST['Id']);
} else if ( isset($_REQUEST['filter[Id]']) ) {
$fid = validInt($_REQUEST['filter[Id]']);
ZM\Warning("got fid by object id $fid");
}
$filter = null;
foreach ( ZM\Filter::find(null,array('order'=>'lower(Name)')) as $Filter ) {
$filterNames[$Filter->Id()] = $Filter->Id() . ' ' . $Filter->Name();
if ( $Filter->Background() )
@ -53,17 +52,17 @@ foreach ( ZM\Filter::find(null,array('order'=>'lower(Name)')) as $Filter ) {
$filter = $Filter;
}
}
if ( !$filter ) {
if ( !$filter ) {
$filter = new ZM\Filter();
if ( isset($_REQUEST['filter']) ) {
# Update our filter object with whatever changes we have made before saving
$filter->set($_REQUEST['filter']);
}
} else {
ZM\Debug('filter: ' . print_r($filter,true));
}
if ( isset($_REQUEST['filter']) ) {
# Update our filter object with whatever changes we have made before saving
$filter->set($_REQUEST['filter']);
ZM\Debug("Setting filter from " . print_r($_REQUEST['filter'], true));
}
ZM\Debug('filter: ' . print_r($filter,true));
$conjunctionTypes = ZM\getFilterQueryConjunctionTypes();
$obracketTypes = array();
$cbracketTypes = array();
@ -89,8 +88,8 @@ $attrTypes = array(
'Cause' => translate('AttrCause'),
'DiskBlocks' => translate('AttrDiskBlocks'),
'DiskPercent' => translate('AttrDiskPercent'),
'DiskSpace' => translate('AttrDiskSpace'),
'EventDiskSpace' => translate('AttrEventDiskSpace'),
#'StorageDiskSpace' => translate('AttrStorageDiskSpace'),
'DiskSpace' => translate('AttrEventDiskSpace'),
'EndDateTime' => translate('AttrEndDateTime'),
'EndDate' => translate('AttrEndDate'),
'EndTime' => translate('AttrEndTime'),

View File

@ -16,7 +16,7 @@ function vjsReplay() {
var overLaid = $j("#videoobj");
overLaid.append('<p class="vjsMessage" style="height: '+overLaid.height()+'px; line-height: '+overLaid.height()+'px;">No more events</p>');
} else {
var endTime = (Date.parse(eventData.EndTime)).getTime();
var endTime = (Date.parse(eventData.EndDateTime)).getTime();
var nextStartTime = nextEventStartTime.getTime(); //nextEventStartTime.getTime() is a mootools workaround, highjacks Date.parse
if ( nextStartTime <= endTime ) {
streamNext(true);
@ -584,7 +584,7 @@ function getEventResponse(respObj, respText) {
$('dataCause').setProperty( 'title', causeString );
}
$('dataCause').set( 'text', eventData.Cause );
$('dataTime').set( 'text', eventData.StartTime );
$('dataTime').set( 'text', eventData.StartDateTime );
$('dataDuration').set( 'text', eventData.Length );
$('dataFrames').set( 'text', eventData.Frames+"/"+eventData.AlarmFrames );
$('dataScore').set( 'text', eventData.TotScore+"/"+eventData.AvgScore+"/"+eventData.MaxScore );
@ -606,7 +606,7 @@ function getEventResponse(respObj, respText) {
vid.src({type: 'video/mp4', src: CurEventDefVideoPath}); //Currently mp4 is all we use
console.log('getEventResponse');
initialAlarmCues(eventData.Id);//ajax and render, new event
addVideoTimingTrack(vid, LabelFormat, eventData.MonitorName, eventData.Length, eventData.StartTime);
addVideoTimingTrack(vid, LabelFormat, eventData.MonitorName, eventData.Length, eventData.StartDateTime);
CurEventDefVideoPath = null;
$j('#modeValue').html('Replay');
$j('#zoomValue').html('1');
@ -1088,7 +1088,7 @@ function initPage() {
//FIXME prevent blocking...not sure what is happening or best way to unblock
if ( $j('#videoobj').length ) {
vid = videojs('videoobj');
addVideoTimingTrack(vid, LabelFormat, eventData.MonitorName, eventData.Length, eventData.StartTime);
addVideoTimingTrack(vid, LabelFormat, eventData.MonitorName, eventData.Length, eventData.StartDateTime);
$j('.vjs-progress-control').append('<div class="alarmCue"></div>');//add a place for videojs only on first load
vid.on('ended', vjsReplay);
vid.on('play', vjsPlay);

View File

@ -44,8 +44,8 @@ var eventData = {
Width: '<?php echo $Event->Width() ?>',
Height: '<?php echo $Event->Height() ?>',
Length: '<?php echo $Event->Length() ?>',
StartTime: '<?php echo $Event->StartTime() ?>',
EndTime: '<?php echo $Event->EndTime() ?>',
StartDateTime: '<?php echo $Event->StartDateTime() ?>',
EndDateTime: '<?php echo $Event->EndDateTime() ?>',
Frames: '<?php echo $Event->Frames() ?>',
MonitorName: '<?php echo validJsStr($Monitor->Name()) ?>'
};

View File

@ -17,14 +17,14 @@ var params =
"data":
{
"search":"some search text",
"sort":"StartTime",
"sort":"StartDateTime",
"order":"asc",
"offset":0,
"limit":25
"filter":
{
"Name":"some advanced search text"
"StartTime":"some more advanced search text"
"StartDateTime":"some more advanced search text"
}
},
"cache":true,
@ -68,7 +68,7 @@ function processRows(rows) {
row.Frames = '<a href="?view=frames&amp;eid=' + eid + '">' + row.Frames + '</a>';
row.AlarmFrames = '<a href="?view=frames&amp;eid=' + eid + '">' + row.AlarmFrames + '</a>';
row.MaxScore = '<a href="?view=frame&amp;eid=' + eid + '&amp;fid=0">' + row.MaxScore + '</a>';
row.Thumbnail = '<a href="?view=event&amp;eid=' + eid + filterQuery + sortQuery + '&amp;page=1">' + row.imgHtml + '</a>';
if ( WEB_LIST_THUMBS ) row.Thumbnail = '<a href="?view=event&amp;eid=' + eid + filterQuery + sortQuery + '&amp;page=1">' + row.imgHtml + '</a>';
});
return rows;
@ -161,6 +161,9 @@ function getEventDetailModal(eid) {
}
function initPage() {
// Remove the thumbnail column from the DOM if thumbnails are off globally
if ( !WEB_LIST_THUMBS ) $j('th[data-field="Thumbnail"]').remove();
// Load the delete confirmation modal into the DOM
getDelConfirmModal();

View File

@ -11,3 +11,4 @@ var archivedString = "<?php echo translate('Archived') ?>";
var emailedString = "<?php echo translate('Emailed') ?>";
var yesString = "<?php echo translate('Yes') ?>";
var noString = "<?php echo translate('No') ?>";
var WEB_LIST_THUMBS = <?php echo ZM_WEB_LIST_THUMBS?'true':'false' ?>;

View File

@ -76,7 +76,7 @@ if ( !$liveMode ) {
if ( !isset($event['FramesById']) ) {
// Please note that this is the last frame as we sort DESC
$event['FramesById'] = array();
$frame['NextTimeStampSecs'] = $event['EndTime'];
$frame['NextTimeStampSecs'] = $event['EndTimeSecs'];
} else {
$frame['NextTimeStampSecs'] = $next_frames[$frame['EventId']]['TimeStampSecs'];
$frame['NextFrameId'] = $next_frames[$frame['EventId']]['Id'];

View File

@ -24,7 +24,7 @@ function createEventHtml(zm_event, frame) {
new Element('p').inject(eventHtml).set('text', monitors[zm_event.MonitorId].Name);
new Element('p').inject(eventHtml).set('text', zm_event.Name+(frame?('('+frame.FrameId+')'):''));
new Element('p').inject(eventHtml).set('text', zm_event.StartTime+' - '+zm_event.Length+'s');
new Element('p').inject(eventHtml).set('text', zm_event.StartDateTime+' - '+zm_event.Length+'s');
new Element('p').inject(eventHtml).set('text', zm_event.Cause);
if ( zm_event.Notes ) {
new Element('p').inject(eventHtml).set('text', zm_event.Notes);
@ -90,7 +90,7 @@ function showEventData(eventId, frameId) {
showEventDetail( zm_event['frames'][frameId]['html'] );
var imagePath = 'index.php?view=image&eid='+eventId+'&fid='+frameId;
var videoName = zm_event.DefaultVideo;
loadEventImage( imagePath, eventId, frameId, zm_event.Width, zm_event.Height, zm_event.Frames/zm_event.Length, videoName, zm_event.Length, zm_event.StartTime, monitors[zm_event.MonitorId]);
loadEventImage( imagePath, eventId, frameId, zm_event.Width, zm_event.Height, zm_event.Frames/zm_event.Length, videoName, zm_event.Length, zm_event.StartDateTime, monitors[zm_event.MonitorId]);
return;
} else {
console.log('No frames for ' + frameId);

View File

@ -603,7 +603,7 @@ function getEventCmdResponse( respObj, respText ) {
link.set('text', zm_event.Name);
link.inject(row.getElement('td.colName'));
row.getElement('td.colTime').set('text', zm_event.StartTime);
row.getElement('td.colTime').set('text', zm_event.StartDateTime);
row.getElement('td.colSecs').set('text', zm_event.Length);
link = new Element('a', {'href': '#', 'events': {'click': openFrames.pass( [zm_event.Id] )}});
@ -946,7 +946,8 @@ function initPage() {
});
// Only enable the settings button for local cameras
settingsBtn.prop('disabled', !(monitorType == 'Local' && canViewControl));
settingsBtn.prop('disabled', !canViewControl);
if ( monitorType != 'Local' ) settingsBtn.hide();
} // initPage
// Kick everything off

View File

@ -114,19 +114,19 @@ if ( count($filter) ) {
$eventsSql = 'SELECT
E.Id,E.Name,E.StorageId,
E.StartTime AS StartTime,UNIX_TIMESTAMP(E.StartTime) AS StartTimeSecs,
CASE WHEN E.EndTime IS NULL THEN (SELECT NOW()) ELSE E.EndTime END AS EndTime,
UNIX_TIMESTAMP(EndTime) AS EndTimeSecs,
E.StartDateTime AS StartDateTime,UNIX_TIMESTAMP(E.StartDateTime) AS StartTimeSecs,
CASE WHEN E.EndDateTime IS NULL THEN (SELECT NOW()) ELSE E.EndDateTime END AS EndDateTime,
UNIX_TIMESTAMP(EndDateTime) AS EndTimeSecs,
E.Length, E.Frames, E.MaxScore,E.Cause,E.Notes,E.Archived,E.MonitorId
FROM Events AS E
WHERE 1 > 0
';
// select E.Id,E.Name,UNIX_TIMESTAMP(E.StartTime) as StartTimeSecs,UNIX_TIMESTAMP(max(DATE_ADD(E.StartTime, Interval Delta+0.5 Second))) as CalcEndTimeSecs, E.Length,max(F.FrameId) as Frames,E.MaxScore,E.Cause,E.Notes,E.Archived,E.MonitorId
// select E.Id,E.Name,UNIX_TIMESTAMP(E.StartDateTime) as StartTimeSecs,UNIX_TIMESTAMP(max(DATE_ADD(E.StartDateTime, Interval Delta+0.5 Second))) as CalcEndTimeSecs, E.Length,max(F.FrameId) as Frames,E.MaxScore,E.Cause,E.Notes,E.Archived,E.MonitorId
// from Events as E
// inner join Monitors as M on (E.MonitorId = M.Id)
// inner join Frames F on F.EventId=E.Id
// where not isnull(E.Frames) and not isnull(StartTime) ";
// where not isnull(E.Frames) and not isnull(StartDateTime) ";
// Note that the delta value seems more accurate than the time stamp for some reason.
$framesSql = '
@ -219,14 +219,14 @@ $initialDisplayInterval = 1000;
if ( isset($_REQUEST['displayinterval']) )
$initialDisplayInterval = validHtmlStr($_REQUEST['displayinterval']);
#$eventsSql .= ' GROUP BY E.Id,E.Name,E.StartTime,E.Length,E.Frames,E.MaxScore,E.Cause,E.Notes,E.Archived,E.MonitorId';
#$eventsSql .= ' GROUP BY E.Id,E.Name,E.StartDateTime,E.Length,E.Frames,E.MaxScore,E.Cause,E.Notes,E.Archived,E.MonitorId';
$minTimeSecs = $maxTimeSecs = 0;
if ( isset($minTime) && isset($maxTime) ) {
$minTimeSecs = strtotime($minTime);
$maxTimeSecs = strtotime($maxTime);
$eventsSql .= " AND EndTime > '" . $minTime . "' AND StartTime < '" . $maxTime . "'";
$framesSql .= " AND EndTime > '" . $minTime . "' AND StartTime < '" . $maxTime . "'";
$eventsSql .= " AND EndDateTime > '" . $minTime . "' AND StartDateTime < '" . $maxTime . "'";
$framesSql .= " AND EndDateTime > '" . $minTime . "' AND StartDateTime < '" . $maxTime . "'";
$framesSql .= ") AND TimeStamp > '" . $minTime . "' AND TimeStamp < '" . $maxTime . "'";
} else {
$framesSql .= ')';

View File

@ -231,6 +231,7 @@ foreach ( array_map('basename', glob('skins/'.$skin.'/css/*', GLOB_ONLYDIR)) as
<td class="colUrl"><?php echo makeLink('#', validHtmlStr($Server->Url()), $canEdit, $svr_opt ) ?></td>
<td class="colPathToIndex"><?php echo makeLink('#', validHtmlStr($Server->PathToIndex()), $canEdit, $svr_opt ) ?></td>
<td class="colPathToZMS"><?php echo makeLink('#', validHtmlStr($Server->PathToZMS()), $canEdit, $svr_opt ) ?></td>
<td class="colPathToAPI"><?php echo makeLink('#', validHtmlStr($Server->PathToAPI()), $canEdit, $svr_opt ) ?></td>
<td class="colStatus <?php if ( $Server->Status() == 'NotRunning' ) { echo 'danger'; } ?>">
<?php echo makeLink('#', validHtmlStr($Server->Status()), $canEdit, $svr_opt) ?></td>
<td class="colMonitorCount"><?php echo makeLink('#', validHtmlStr($monitor_counts[$Server->Id()]), $canEdit, $svr_opt) ?></td>

View File

@ -65,8 +65,8 @@ $filterQuery = $filter['query'];
ZM\Debug($filterQuery);
$eventsSql = 'SELECT *,
UNIX_TIMESTAMP(E.StartTime) AS StartTimeSecs,
UNIX_TIMESTAMP(EndTime) AS EndTimeSecs
UNIX_TIMESTAMP(E.StartDateTime) AS StartTimeSecs,
UNIX_TIMESTAMP(EndDateTime) AS EndTimeSecs
FROM Events AS E
WHERE 1 > 0
';
@ -77,7 +77,7 @@ if ( count($selected_monitor_ids) ) {
$eventsSql .= ' AND MonitorId IN ('.implode(',', $selected_monitor_ids).')';
}
if ( isset($minTime) && isset($maxTime) ) {
$eventsSql .= " AND EndTime > '" . $minTime . "' AND StartTime < '" . $maxTime . "'";
$eventsSql .= " AND EndDateTime > '" . $minTime . "' AND StartDateTime < '" . $maxTime . "'";
}
$eventsSql .= ' ORDER BY Id ASC';
@ -211,8 +211,8 @@ for ( $monitor_i = 0; $monitor_i < count($displayMonitors); $monitor_i += 1 ) {
</div></td>
<td class="colServer"><?php echo validHtmlStr($Monitor->Server()->Name())?></td>
<td class="colEvents"><a href="?view=<?php echo ZM_WEB_EVENTS_VIEW ?>&amp;page=1<?php echo $monitor_filter['query'] ?>"><?php echo isset($EventsByMonitor[$Monitor->Id()])?count($EventsByMonitor[$Monitor->Id()]['Events']):0 ?></a></td>
<td class="colFirstEvent"><?php echo $FirstEvent ? $FirstEvent->link_to($FirstEvent->Id().' at '.$FirstEvent->StartTime()) : 'none'?></td>
<td class="colLastEvent"><?php echo $LastEvent ? $LastEvent->link_to($LastEvent->Id().' at '.$LastEvent->StartTime()) : 'none'?></td>
<td class="colFirstEvent"><?php echo $FirstEvent ? $FirstEvent->link_to($FirstEvent->Id().' at '.$FirstEvent->StartDateTime()) : 'none'?></td>
<td class="colLastEvent"><?php echo $LastEvent ? $LastEvent->link_to($LastEvent->Id().' at '.$LastEvent->StartDateTime()) : 'none'?></td>
<td class="colMinGap"><?php echo $MinGap ?></td>
<td class="colMaxGap"><?php echo $MaxGap ?></td>
<td class="colFileMissing<?php echo count($FileMissing) ? ' errorText' : ''?>">

View File

@ -128,9 +128,9 @@ $chart = array(
$monitors = array();
# The as E, and joining with Monitors is required for the filterSQL filters.
$rangeSql = 'SELECT min(E.StartTime) AS MinTime, max(E.EndTime) AS MaxTime FROM Events AS E INNER JOIN Monitors AS M ON (E.MonitorId = M.Id) WHERE NOT isnull(E.StartTime) AND NOT isnull(E.EndTime)';
$eventsSql = 'SELECT E.* FROM Events AS E INNER JOIN Monitors AS M ON (E.MonitorId = M.Id) WHERE NOT isnull(StartTime)';
$eventIdsSql = 'SELECT E.Id FROM Events AS E INNER JOIN Monitors AS M ON (E.MonitorId = M.Id) WHERE NOT isnull(StartTime)';
$rangeSql = 'SELECT min(E.StartDateTime) AS MinTime, max(E.EndDateTime) AS MaxTime FROM Events AS E INNER JOIN Monitors AS M ON (E.MonitorId = M.Id) WHERE NOT isnull(E.StartDateTime) AND NOT isnull(E.EndDateTime)';
$eventsSql = 'SELECT E.* FROM Events AS E INNER JOIN Monitors AS M ON (E.MonitorId = M.Id) WHERE NOT isnull(StartDateTime)';
$eventIdsSql = 'SELECT E.Id FROM Events AS E INNER JOIN Monitors AS M ON (E.MonitorId = M.Id) WHERE NOT isnull(StartDateTime)';
$eventsValues = array();
if ( !empty($user['MonitorIds']) ) {
@ -277,8 +277,8 @@ $midTimeT = $minTimeT + $halfRange;
$midTime = strftime(STRF_FMT_DATETIME_DB, $midTimeT);
if ( isset($minTime) && isset($maxTime) ) {
$eventsSql .= " AND EndTime >= '$minTime' AND StartTime <= '$maxTime'";
$eventIdsSql .= " AND EndTime >= '$minTime' AND StartTime <= '$maxTime'";
$eventsSql .= " AND EndDateTime >= '$minTime' AND StartDateTime <= '$maxTime'";
$eventIdsSql .= " AND EndDateTime >= '$minTime' AND StartDateTime <= '$maxTime'";
}
if ( 0 ) {
@ -332,13 +332,13 @@ while( $event = $events_result->fetch(PDO::FETCH_ASSOC) ) {
$currEventSlots = &$monEventSlots[$event['MonitorId']];
$currFrameSlots = &$monFrameSlots[$event['MonitorId']];
$startTimeT = strtotime($event['StartTime']);
$startTimeT = strtotime($event['StartDateTime']);
$startIndex = $rawStartIndex = (int)(($startTimeT - $chart['data']['x']['lo']) / $chart['data']['x']['density']);
if ( $startIndex < 0 )
$startIndex = 0;
if ( isset($event['EndTime']) )
$endTimeT = strtotime($event['EndTime']);
if ( isset($event['EndDateTime']) )
$endTimeT = strtotime($event['EndDateTime']);
else
$endTimeT = time();
$endIndex = $rawEndIndex = (int)(($endTimeT - $chart['data']['x']['lo']) / $chart['data']['x']['density']);