package OSSEC::MySQL; # ABSTRACT: Module for getting information from the OSSEC Mysql Database use strict; use warnings; use Moose; use OSSEC::Log; use DBI; use DBD::mysql; use DateTime; =head1 DESCRIPTION This Module/Class is part of the OSSEC distribution. It simplifies querying and working with OSSEC and its MySQL database output. At the moment you are able to search for an alert given by its id. Update the signature table within the database, which is not done by the current(3.5.0) version of OSSEC. =cut =attr server database server to conect to B localhost Type: String =cut has 'server' => (is => 'rw', isa => 'Str' , default => "localhost" ); =attr dbuser database user to use to connect to server B ossec Type: String =cut has 'dbuser' => (is => 'rw', isa => 'Str', default => "ossec"); =attr dbpass database password to use to connect to server Type: String =cut has 'dbpass' => (is => 'rw', isa => 'Str'); =attr database database to use to connect to server B ossec Type: String =cut has 'database' => (is => 'rw', isa => 'Str', default => "ossec"); =attr dbh database handle, valid after calling connect =cut has 'dbh' => (is => 'rw'); =method connect connect to the database server with the provided information =cut sub connect { my $self = shift; die("no server given") unless $self->server(); die("no user given") unless $self->dbuser(); die("no password given") unless $self->dbpass(); die("no database given") unless $self->database(); my $dsn = "DBI:mysql:database=" . $self->database() . ";host=" . $self->server() . ";port=3306"; $self->dbh(DBI->connect($dsn, $self->dbuser(), $self->dbpass),{'RaiseError' => 1}); } =method deleteAllRules deletes all rules from the signature table of ossec =cut sub deleteAllRules { my $self = shift; $self->dbh()->do("delete from signature"); } =method addRule add a rule to the signature table of ossec =over =item B=I =item B=I =item B=I =back =cut sub addRule { my $self = shift; my $ruleid = shift; my $level = shift; my $desc = shift; my $sth = $self->dbh()->prepare("insert into signature(rule_id,level,description) values(?,?,?)"); $sth->execute($ruleid, $level, $desc); $sth->finish; } =method deleteAllAgents deletes all agents from the agent table of ossec =cut sub deleteAllAgents { my $self = shift; $self->dbh()->do("delete from agent"); } =method addAgent add an agent to the agent table of ossec =over =item B=I =item B=I =item B=I =item B=I =item B=I =item B=I =back =cut sub addAgent { my $self = shift; my $server_id = shift; my $last_contact= shift; my $ip_address = shift; my $version = shift; my $name = shift; my $information = shift; my $sth = $self->dbh()->prepare("insert into agent(server_id, last_contact, ip_address, version, name, information) values(?,?,?,?,?,?)"); $sth->execute($server_id, $last_contact, $ip_address, $version, $name, $information); $sth->finish; } =method searchAlert search for a given alertid and return the full alert =over =item B=I =back =cut sub searchAlert { my $self = shift; my $alertid = shift; my $sth = $self->dbh()->prepare("select signature.rule_id as rule_id, signature.level as level, signature.description as description, location.name as location, timestamp, src_ip, dst_ip, src_port, dst_port, user, full_log from alert left join signature on alert.rule_id = signature.rule_id left join location on alert.location_id = location.id where alertid=?"); $sth->execute($alertid); if ($sth->rows != 1) { $sth->finish; } die("no alert found") unless $sth->rows > 0; die("too many alerts found") unless $sth->rows == 1; my $row = $sth->fetchrow_hashref; $sth->finish; my $dt = DateTime->from_epoch( epoch => $row->{timestamp} ); $row->{timestamp_string} = $dt->ymd() . " " . $dt->hms(); if ($row->{location}=~/^\((\S+)\)/) { $row->{agent}=$1; } else { $row->{agent}="server"; } return $row; } 1;