Merge branch '2.4' into sslclientsync

pull/1486/head
iglocska 2016-08-18 09:58:52 +02:00
commit 444171bd2d
104 changed files with 2762 additions and 1831 deletions

View File

@ -1,7 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<?eclipse-pydev version="1.0"?>
<pydev_project>
<pydev_property name="org.python.pydev.PYTHON_PROJECT_INTERPRETER">Default</pydev_property>
<pydev_property name="org.python.pydev.PYTHON_PROJECT_VERSION">python 2.7</pydev_property>
</pydev_project>

View File

@ -36,7 +36,6 @@ pear install Crypt_GPG # we need version >1.3.0
mkdir /var/www/MISP
cd /var/www/MISP
git clone https://github.com/MISP/MISP.git /var/www/MISP
git clone https://github.com/MISP/MISP.git /var/www/MISP
git checkout tags/$(git describe --tags `git rev-list --tags --max-count=1`)
# if the last shortcut doesn't work, specify the latest version manually
# example: git checkout tags/v2.4.XY

View File

@ -61,7 +61,8 @@ CREATE TABLE IF NOT EXISTS `cake_sessions` (
`id` varchar(255) COLLATE utf8_bin NOT NULL DEFAULT '',
`data` text COLLATE utf8_bin NOT NULL,
`expires` int(11) NOT NULL,
PRIMARY KEY (`id`)
PRIMARY KEY (`id`),
INDEX `expires` (`expires`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- --------------------------------------------------------
@ -850,26 +851,26 @@ INSERT INTO `feeds` (`id`, `provider`, `name`, `url`, `distribution`, `default`,
-- 7. Read Only - read
--
INSERT INTO `roles` (`id` ,`name` ,`created` ,`modified` ,`perm_add` ,`perm_modify` ,`perm_modify_org` ,`perm_publish` ,`perm_sync` ,`perm_admin` ,`perm_audit` ,`perm_full` ,`perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES (1, 'admin', NOW() , NOW() , 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
INSERT INTO `roles` (`id` ,`name` ,`created` ,`modified` ,`perm_add` ,`perm_modify` ,`perm_modify_org` ,`perm_publish` ,`perm_sync` ,`perm_admin` ,`perm_audit` ,`perm_full` ,`perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES ('2', 'Org Admin', NOW() , NOW() , 1, 1, 1 , 1, 1, 1, 1, 0 , 1, 0, 1, 0, 1, 1, 1, 1);
INSERT INTO `roles` (`id` ,`name` ,`created` ,`modified` ,`perm_add` ,`perm_modify` ,`perm_modify_org` ,`perm_publish` ,`perm_sync` ,`perm_admin` ,`perm_audit` ,`perm_full` ,`perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES ('3', 'User', NOW() , NOW() , 1, 1, 1 , 0 , 0 , 0 , 0 , 0 , 0, 0, 0, 0, 0, 0, 0, 0);
INSERT INTO `roles` (`id` ,`name` ,`created` ,`modified` ,`perm_add` ,`perm_modify` ,`perm_modify_org` ,`perm_publish` ,`perm_sync` ,`perm_admin` ,`perm_audit` ,`perm_full` ,`perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES ('4', 'Publisher', NOW() , NOW() , 1, 1, 1 , 1 , 0 , 0 , 0 , 0 , 0, 0, 0, 0, 0, 0, 0, 1);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES (1, 'admin', NOW(), NOW(), 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES ('5', 'Sync user', NOW(), NOW(), 1, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1);
VALUES (2, 'Org Admin', NOW(), NOW(), 1, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES ('6', 'Automation user', NOW(), NOW(), 1, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1);
VALUES (3, 'User', NOW(), NOW(), 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES ('7', 'Read Only', NOW(), NOW(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
VALUES (4, 'Publisher', NOW(), NOW(), 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES (5, 'Sync user', NOW(), NOW(), 1, 1, 1, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES (6, 'Automation user', NOW(), NOW(), 1, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1);
INSERT INTO `roles` (`id`, `name`, `created`, `modified`, `perm_add`, `perm_modify`, `perm_modify_org`, `perm_publish`, `perm_sync`, `perm_admin`, `perm_audit`, `perm_full`, `perm_auth`, `perm_regexp_access`, `perm_tagger`, `perm_site_admin`, `perm_template`, `perm_sharing_group`, `perm_tag_editor`, `perm_delegate`)
VALUES (7, 'Read Only', NOW(), NOW(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
-- --------------------------------------------------------
@ -879,10 +880,10 @@ VALUES ('7', 'Read Only', NOW(), NOW(), 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
INSERT INTO `threat_levels` (`id`, `name`, `description`, `form_description`)
VALUES
(1,'High','*high* means sophisticated APT malware or 0-day attack','Sophisticated APT malware or 0-day attack'),
(2,'Medium','*medium* means APT malware','APT malware'),
(3,'Low','*low* means mass-malware','Mass-malware'),
(4,'Undefined','*undefined* no risk','No risk');
(1, 'High', '*high* means sophisticated APT malware or 0-day attack', 'Sophisticated APT malware or 0-day attack'),
(2, 'Medium', '*medium* means APT malware', 'APT malware'),
(3, 'Low', '*low* means mass-malware', 'Mass-malware'),
(4, 'Undefined', '*undefined* no risk', 'No risk');
-- --------------------------------------------------------

View File

@ -1,52 +0,0 @@
dir=`dirname $0`
FILE_PATH=`cd $dir;pwd`
cd ..
MISP_PATH=`pwd`
clear
printf '=========================================================\n'
printf '| |\n'
printf '| \e[34mM\e[39malware \e[34mI\e[39mnformation \e[34mS\e[39mharing \e[34mP\e[39mlatform |\n'
printf '| |\n'
printf '| 2.2 Installation |\n'
printf '| |\n'
printf '=========================================================\n\n'
YUM_CMD=$(which yum)
APT_GET_CMD=$(which apt-get)
BREW_CMD=$(which brew)
if [[ ! -z $APT_GET_CMD ]]
then
printf '\n\nInstalling Redis using apt-get'
apt-get install vim zip php-pear git redis-server
elif [[ ! -z $YUM_CMD ]]
then
printf '\n\nNo redis package with yum, please download and install Redis manually.'
yum install vim zip php-pear git
elif [[ ! -z $OTHER_CMD ]]
then
printf '\n\nInstalling Redis using brew'
brew install vim zip php-pear git redis-server
else
echo "Error, you need either apt-get, yum or brew to install zip, php-pear, git, redis using this script. Please install them manually.";
fi
pear install Crypt_GPG
pear install Net_GeoIP
git config core.filemode false
cd "$MISP_PATH"
git submodule init
git submodule update
cd "$MISP_PATH/app"
curl -s https://getcomposer.org/installer | php
php composer.phar require --no-update kamisama/cake-resque:4.1.0
php composer.phar config vendor-dir Vendor
php composer.phar install
cd "$MISP_PATH"
chown -R www-data:www-data "$MISP_PATH"
chmod -R 750 "$MISP_PATH"
chmod -R g+ws "$MISP_PATH/app/tmp"
chmod -R g+ws "$MISP_PATH/app/files"
cp -fa "$FILE_PATH/setup/config.php" "$MISP_PATH/app/Plugin/CakeResque/Config/config.php"
printf '\n\n=========================================================\n'
printf '| \e[34mI\e[39mnstallation \e[34mC\e[39momplete |\n'
printf '=========================================================\n\n'

View File

@ -1,68 +0,0 @@
dir=`dirname $0`
FILE_PATH=`cd $dir;pwd`
cd ..
MISP_PATH=`pwd`
printf '========================================================\n'
printf '| |\n'
printf '| \e[34mM\e[39malware \e[34mI\e[39mnformation \e[34mS\e[39mharing \e[34mP\e[39mlatform |\n'
printf '| |\n'
printf '| 2.1 => 2.2 upgrade |\n'
printf '| |\n'
printf '========================================================\n\n'
read -p 'Do you wish to upgrade your database now? [y/n] ' -n 1 -r
if [[ $REPLY =~ ^[Yy]$ ]]
then
printf '\n\nIn order to upgrade your MISP database to version 2.2, enter your database credentials.'
printf '\nUsername: '
read name
printf '\nPassword: '
read password
printf '\nDatabase: '
read database
cd "$FILE_PATH"
mysql -u $name -p$password $database < upgrade_2.2.sql
printf '\n\n'
else
printf '\n\nDatabase not updated. You will have to update it manually by executing\n\nmysql -u [username] -p[password] [database name] < upgrade_2.2.sql from the MISP/INSTALL directory\n\n'
fi
cd "$MISP_PATH"
git submodule init
git submodule update
YUM_CMD=$(which yum)
APT_GET_CMD=$(which apt-get)
BREW_CMD=$(which brew)
if [[ ! -z $APT_GET_CMD ]]
then
printf '\n\nInstalling Redis using apt-get'
apt-get install redis-server
elif [[ ! -z $YUM_CMD ]]
then
printf '\n\nNo Redis package available with yum, please install it manually.'
yum install redis
elif [[ ! -z $OTHER_CMD ]]
then
printf '\n\nInstalling Redis using brew'
brew install redis-server
else
echo "Error, you need either apt-get, yum or brew to install Redis using this script. Please install it manually.";
fi
cd "$MISP_PATH/app"
curl -s https://getcomposer.org/installer | php
php composer.phar require --no-update kamisama/cake-resque:4.1.0
php composer.phar config vendor-dir Vendor
php composer.phar install
cd "$MISP_PATH"
chown -R www-data:www-data "$MISP_PATH"
chmod -R 750 "$MISP_PATH"
chmod -R g+ws "$MISP_PATH/app/tmp"
chmod -R g+ws "$MISP_PATH/app/files"
rm app/tmp/cache/*/*
cp -fa "$FILE_PATH/setup/config.php" "$MISP_PATH/app/Plugin/CakeResque/Config/config.php"
printf '\n\n=========================================================\n'
printf '| \e[34mI\e[39mnstallation \e[34mC\e[39momplete |\n'
printf '=========================================================\n\n'

View File

@ -1,32 +0,0 @@
Upgrade procedure from v2.1 to v2.2
- git pull the latest version of MISP from https://github.com/MISP/MISP.git
- execute UPGRADE.SH in the MISP/INSTALL folder (this also includes the installation of Redis for CakeResque)
- cd /var/www/MISP/INSTALL
- ./UPGRADE.SH
- Replace your current bootstrap.php file found in /MISP/app/Config/ with bootstrap.default.php and change set your instance up to your liking
- Log in with the site admin credentials and execute the following commands by changing the url
(where <MISP> is the address of your instance):
- https://<MISP>/events/generateThreatLevelFromRisk
================================================================================================================================================
Enabling background jobs via CakeResque
(assuming /var/www/MISP as your installation directory)
- Enable CakeResque in MISP
- vim /var/www/MISP/app/Config/bootstrap.php
- set Configure::write('MISP.background_jobs', false); to Configure::write('MISP.background_jobs', true);
- uncomment CakePlugin::load('CakeResque', array('bootstrap' => true));
- in Core.php (if you have just recently updated MISP, just add this line at the end of the file): require_once dirname(__DIR__) . '/Vendor/autoload.php';
- start the background workers
- cd /var/www/MISP/app/Console/worker/
- ./start.sh
Make sure you configure your OS to start this script as boot time !
================================================================================================================================================

View File

@ -1,175 +0,0 @@
-- Copyright (c) 2009 www.cryer.co.uk
-- Script is free to use provided this copyright header is included.
drop procedure if exists AddColumnUnlessExists;
delimiter '//'
create procedure AddColumnUnlessExists(
IN dbName tinytext,
IN tableName tinytext,
IN fieldName tinytext,
IN fieldDef text)
begin
IF NOT EXISTS (
SELECT * FROM information_schema.COLUMNS
WHERE column_name=fieldName
and table_name=tableName
and table_schema=dbName
)
THEN
set @ddl=CONCAT('ALTER TABLE ',dbName,'.',tableName,
' ADD COLUMN ',fieldName,' ',fieldDef);
prepare stmt from @ddl;
execute stmt;
END IF;
end;
//
delimiter ';'
call AddColumnUnlessExists(Database(), 'roles', 'perm_site_admin', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'roles', 'perm_regexp_access', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'roles', 'perm_tagger', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
CREATE TABLE IF NOT EXISTS `threads` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`date_created` datetime NOT NULL,
`date_modified` datetime NOT NULL,
`distribution` tinyint(4) NOT NULL,
`user_id` int(11) NOT NULL,
`post_count` int(11) NOT NULL,
`event_id` int(11) NOT NULL,
`title` varchar(255) CHARACTER SET utf8 COLLATE utf8_unicode_ci NOT NULL,
`org` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `posts` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`date_created` datetime NOT NULL,
`date_modified` datetime NOT NULL,
`user_id` int(11) NOT NULL,
`contents` text CHARACTER SET utf8 COLLATE utf8_unicode_ci NOT NULL,
`post_id` int(11) NOT NULL DEFAULT '0',
`thread_id` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `event_tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`event_id` int(11) NOT NULL,
`tag_id` int(11) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`colour` varchar(7) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `threat_levels` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(50) NOT NULL,
`description` varchar(255) DEFAULT NULL,
`form_description` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `tasks` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`type` varchar(100) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`timer` int(11) NOT NULL,
`scheduled_time` varchar(8) NOT NULL DEFAULT '6:00',
`job_id` int(11) NOT NULL,
`description` varchar(255) NOT NULL,
`next_execution_time` int(11) NOT NULL,
`message` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `jobs` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`worker` varchar(32) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`job_type` varchar(32) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`job_input` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`status` tinyint(4) NOT NULL DEFAULT '0',
`retries` int(11) NOT NULL DEFAULT '0',
`message` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`progress` int(11) NOT NULL DEFAULT '0',
`org` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`process_id` varchar(32) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
call AddColumnUnlessExists(Database(), 'attributes', 'comment', 'TEXT CHARACTER SET utf8 COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'events', 'threat_level_id', 'int(11) NOT NULL');
call AddColumnUnlessExists(Database(), 'events', 'publish_timestamp', 'int(11) NOT NULL');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'event_org', 'VARCHAR( 255 ) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'comment', 'TEXT CHARACTER SET utf8 COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'event_uuid', 'varchar(40) COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'servers', 'self_signed', ' tinyint(1) NOT NULL');
call AddColumnUnlessExists(Database(), 'servers', 'cert_file', 'varchar(255) COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'regexp', 'type', 'COLLATE utf8_bin NOT NULL DEFAULT "ALL"');
drop procedure AddColumnUnlessExists;
UPDATE `regexp` SET `type` = 'ALL';
UPDATE `roles` SET `perm_site_admin` = 1 WHERE `id` = 1;
UPDATE `roles` SET `perm_tagger` = 1 WHERE `id` = 1;
UPDATE `roles` SET `perm_regexp_access` = 1 WHERE `id` = 1;
INSERT IGNORE INTO `threat_levels` (`id`, `name`, `description`, `form_description`)
VALUES
(1,'High','*high* means sophisticated APT malware or 0-day attack','Sophisticated APT malware or 0-day attack'),
(2,'Medium','*medium* means APT malware','APT malware'),
(3,'Low','*low* means mass-malware','Mass-malware'),
(4,'Undefined','*undefined* no risk','No risk');
INSERT IGNORE INTO `tasks` (`id`, `type`, `timer`, `scheduled_time`, `job_id`, `description`, `next_execution_time`, `message`) VALUES
(1, 'cache_exports', 0, '12:00', 0, 'Generates export caches for every export type and for every organisation. This process is heavy, schedule so it might be a good idea to schedule this outside of working hours and before your daily automatic imports on connected services are scheduled.', 1391601600, 'Not scheduled yet.'),
(2, 'pull_all', 0, '12:00', 0, 'Initiates a full pull for all eligible instances.', 1391601600, 'Not scheduled yet.'),
(3, 'push_all', 0, '12:00', 0, 'Initiates a full push for all eligible instances.', 1391601600, 'Not scheduled yet.');
CREATE TABLE IF NOT EXISTS `templates` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`description` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`org` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`share` tinyint(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `template_elements` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_id` int(11) NOT NULL,
`position` int(11) NOT NULL,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`description` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`to_ids` tinyint(1) NOT NULL DEFAULT '1',
`category` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`mandatory` tinyint(1) NOT NULL,
`batch` tinyint(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `template_tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_id` int(11) NOT NULL,
`tag_id` int(11) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
CREATE TABLE IF NOT EXISTS `template_element_types` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_element_id` int(11) NOT NULL,
`type` varchar(100) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;

View File

@ -1,83 +0,0 @@
# 1. Upgrade procedure from v2.2 to v2.3
# - git pull the latest version of MISP from https://github.com/MISP/MISP.git
# delete everything from MISP's cache directory to get rid of the cached models
find /var/www/MISP/app/tmp/cache/ -type f -not -name 'empty' -delete
# clear the old submodule cached entry for CakeResque
cd /var/www/MISP
git rm --cached app/Plugin/CakeResque/
# Check if the permissions are set correctly using the following commands as root:
chown -R www-data:www-data /var/www/MISP
chmod -R 750 /var/www/MISP
chmod -R g+ws /var/www/MISP/app/tmp
chmod -R g+ws /var/www/MISP/app/files
chmod -R g+ws /var/www/MISP/app/files/scripts/tmp
# 2. Get the new dependencies introduced in version 2.3
# install Mitre's STIX and its dependencies by running the following commands:
apt-get install python-dev python-pip libxml2-dev libxslt-dev zlib1g-dev
cd /var/www/MISP/app/files/scripts
git clone https://github.com/CybOXProject/python-cybox.git
git clone https://github.com/STIXProject/python-stix.git
cd /var/www/MISP/app/files/scripts/python-cybox
git checkout v2.1.0.10
python setup.py install
cd /var/www/MISP/app/files/scripts/python-stix
git checkout v1.1.1.4
python setup.py install
# install / update CakeResque (using the background workers is optional buy highly recommended)
cd /var/www/MISP/app
curl -s https://getcomposer.org/installer | php
php composer.phar require kamisama/cake-resque:4.1.2
php composer.phar config vendor-dir Vendor
php composer.phar install
# To use the scheduler worker for scheduled tasks, do the following:
cp -fa /var/www/MISP/INSTALL/setup/config.php /var/www/MISP/app/Plugin/CakeResque/Config/config.php
# 3. Update the database and settings to be compatible with MISP 2.3
# Update the database of MISP by running the following command
mysql -u <database login> -p<database password> <misp table name> < /var/www/MISP/INSTALL/upgrade_2.3.sql
# MISP has moved to a new configuration system. It might be a good idea to note down the old settings before removing them.
# Wherever applicable, you can remove .b from the default configuration file's name to get the non-background worker enabled version, however this is not recommended
mv /var/www/MISP/app/Config/bootstrap.b.default.php /var/www/MISP/app/Config/bootstrap.php
mv /var/www/MISP/app/Config/core.b.default.php /var/www/MISP/app/Config/core.php
mv /var/www/MISP/app/Config/config.default.php /var/www/MISP/app/Config/config.php
# Enable the background workers by uncommenting CakePlugin::loadall(array('CakeResque' => array('bootstrap' => true))); in /var/www/MISP/app/Config/bootstrap.php
# Make sure that the files in config are owned by the apache user
chown -R www-data:www-data /var/www/MISP/app/Config/*
# Log into MISP using your site admin credentials
# navigate to Administration -> Server settings
# Make sure that all of settings related tabs are filled out correctly.
# The tool will tell you about any potential issues and remedies, just follow the instructions
# Once done, have a look at the diagnostics
# If any of the directories that MISP uses to store files is not writeable to the apache user, change the permissions
# you can do this by running the following commands:
chmod -R 750 /var/www/MISP/<directory path with an indicated issue>
chown -R www-data:www-data /var/www/MISP/<directory path with an indicated issue>
# Make sure that the STIX libraries and GnuPG work as intended, if not, refer to INSTALL.txt's paragraphs dealing with these two items
# If you still have the background workers started from before the upgrade, the interface will not allow you to restart the workers
# This is because according to the install script in the previous version the background workers were advised to be started after boot in rc.local using the root user
# If this is the case for you, make sure that you stop the workers using the command line with the following command:
/var/www/MISP/app/Console/cake CakeResque.CakeResque stop --all
# Amend your rc.local using the following command to always start the background workers using the apache user (substitute www-data with your apache user)
su www-data -c 'bash /var/www/MISP/app/Console/worker/start.sh'
# Start the background workers using the application by navigating to the workers tab in the server settings and clicking on the "Restart all workers" button.

View File

@ -1,244 +0,0 @@
-- Copyright (c) 2009 www.cryer.co.uk
-- Script is free to use provided this copyright header is included.
drop procedure if exists AddColumnUnlessExists;
delimiter '//'
create procedure AddColumnUnlessExists(
IN dbName tinytext,
IN tableName tinytext,
IN fieldName tinytext,
IN fieldDef text)
begin
IF NOT EXISTS (
SELECT * FROM information_schema.COLUMNS
WHERE column_name=fieldName
and table_name=tableName
and table_schema=dbName
)
THEN
set @ddl=CONCAT('ALTER TABLE ',dbName,'.',tableName,
' ADD COLUMN ',fieldName,' ',fieldDef);
prepare stmt from @ddl;
execute stmt;
END IF;
end;
//
delimiter ';'
call AddColumnUnlessExists(Database(), 'roles', 'perm_template', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'deleted', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'timestamp', 'INT( 11 ) NOT NULL DEFAULT 0');
-- --------------------------------------------------------
--
-- Table structure for table `templates`
--
CREATE TABLE IF NOT EXISTS `templates` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`description` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`org` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`share` tinyint(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
--
-- Table structure for table `template_elements`
--
CREATE TABLE IF NOT EXISTS `template_elements` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_id` int(11) NOT NULL,
`position` int(11) NOT NULL,
`element_definition` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
--
-- Table structure for table `template_element_attributes`
--
CREATE TABLE IF NOT EXISTS `template_element_attributes` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_element_id` int(11) NOT NULL,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`description` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`to_ids` tinyint(1) NOT NULL DEFAULT '1',
`category` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`complex` tinyint(1) NOT NULL,
`type` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`mandatory` tinyint(1) NOT NULL,
`batch` tinyint(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
--
-- Table structure for table `template_element_files`
--
CREATE TABLE IF NOT EXISTS `template_element_files` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_element_id` int(11) NOT NULL,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`description` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`category` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`malware` tinyint(1) NOT NULL,
`mandatory` tinyint(1) NOT NULL,
`batch` tinyint(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
--
-- Table structure for table `template_element_texts`
--
CREATE TABLE IF NOT EXISTS `template_element_texts` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
`template_element_id` int(11) NOT NULL,
`text` text CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
--
-- Table structure for table `template_tags`
--
CREATE TABLE IF NOT EXISTS `template_tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`template_id` int(11) NOT NULL,
`tag_id` int(11) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
--
-- Change in the servers table and the logs table, addressing
-- hotfixes 2.3.57 and 2.3.78
--
ALTER TABLE `servers` MODIFY COLUMN `organization` varchar(255) NOT NULL;
ALTER TABLE `logs` MODIFY COLUMN `title` text, MODIFY COLUMN `change` text;
-- --------------------------------------------------------
--
-- Default templates
--
INSERT INTO `templates` (`id`, `name`, `description`, `org`, `share`) VALUES
(1, 'Phishing E-mail', 'Create a MISP event about a Phishing E-mail.', 'MISP', 1),
(2, 'Phishing E-mail with malicious attachment', 'A MISP event based on Spear-phishing containing a malicious attachment. This event can include anything from the description of the e-mail itself, the malicious attachment and its description as well as the results of the analysis done on the malicious f', 'MISP', 1),
(3, 'Malware Report', 'This is a template for a generic malware report. ', 'MISP', 1),
(4, 'Indicator List', 'A simple template for indicator lists.', 'MISP', 1);
INSERT INTO `template_elements` (`id`, `template_id`, `position`, `element_definition`) VALUES
(1, 1, 2, 'attribute'),
(2, 1, 3, 'attribute'),
(3, 1, 1, 'text'),
(4, 1, 4, 'attribute'),
(5, 1, 5, 'text'),
(6, 1, 6, 'attribute'),
(7, 1, 7, 'attribute'),
(8, 1, 8, 'attribute'),
(11, 2, 1, 'text'),
(12, 2, 2, 'attribute'),
(13, 2, 3, 'text'),
(14, 2, 4, 'file'),
(15, 2, 5, 'attribute'),
(16, 2, 10, 'text'),
(17, 2, 6, 'attribute'),
(18, 2, 7, 'attribute'),
(19, 2, 8, 'attribute'),
(20, 2, 9, 'attribute'),
(21, 2, 11, 'file'),
(22, 2, 12, 'attribute'),
(23, 2, 13, 'attribute'),
(24, 2, 14, 'attribute'),
(25, 2, 15, 'attribute'),
(26, 2, 16, 'attribute'),
(27, 2, 17, 'attribute'),
(28, 2, 18, 'attribute'),
(29, 3, 1, 'text'),
(30, 3, 2, 'file'),
(31, 3, 4, 'text'),
(32, 3, 9, 'text'),
(33, 3, 11, 'text'),
(34, 3, 10, 'attribute'),
(35, 3, 12, 'attribute'),
(36, 3, 3, 'attribute'),
(37, 3, 5, 'attribute'),
(38, 3, 6, 'attribute'),
(39, 3, 7, 'attribute'),
(40, 3, 8, 'file'),
(41, 3, 13, 'text'),
(42, 3, 14, 'attribute'),
(43, 3, 15, 'attribute'),
(44, 3, 16, 'attribute'),
(45, 4, 1, 'text'),
(46, 4, 2, 'attribute'),
(47, 4, 3, 'attribute');
INSERT INTO `template_element_attributes` (`id`, `template_element_id`, `name`, `description`, `to_ids`, `category`, `complex`, `type`, `mandatory`, `batch`) VALUES
(1, 1, 'From address', 'The source address from which the e-mail was sent.', 1, 'Payload delivery', 0, 'email-src', 1, 1),
(2, 2, 'Malicious url', 'The malicious url in the e-mail body.', 1, 'Payload delivery', 0, 'url', 1, 1),
(3, 4, 'E-mail subject', 'The subject line of the e-mail.', 0, 'Payload delivery', 0, 'email-subject', 1, 0),
(4, 6, 'Spoofed source address', 'If an e-mail address was spoofed, specify which.', 1, 'Payload delivery', 0, 'email-src', 0, 0),
(5, 7, 'Source IP', 'The source IP from which the e-mail was sent', 1, 'Payload delivery', 0, 'ip-src', 0, 1),
(6, 8, 'X-mailer header', 'It could be useful to capture which application and which version thereof was used to send the message, as described by the X-mailer header.', 1, 'Payload delivery', 0, 'text', 0, 1),
(7, 12, 'From address', 'The source address from which the e-mail was sent', 1, 'Payload delivery', 0, 'email-src', 1, 1),
(8, 15, 'Spoofed From Address', 'The spoofed source address from which the e-mail appears to be sent.', 1, 'Payload delivery', 0, 'email-src', 0, 1),
(9, 17, 'E-mail Source IP', 'The IP address from which the e-mail was sent.', 1, 'Payload delivery', 0, 'ip-src', 0, 1),
(10, 18, 'X-mailer header', 'It could be useful to capture which application and which version thereof was used to send the message, as described by the X-mailer header.', 1, 'Payload delivery', 0, 'text', 0, 0),
(11, 19, 'Malicious URL in the e-mail', 'If there was a malicious URL (or several), please specify it here', 1, 'Payload delivery', 0, 'ip-dst', 0, 1),
(12, 20, 'Exploited vulnerablity', 'The vulnerabilities exploited during the payload delivery.', 0, 'Payload delivery', 0, 'vulnerability', 0, 1),
(13, 22, 'C2 information', 'Command and Control information detected during the analysis.', 1, 'Network activity', 1, 'CnC', 0, 1),
(14, 23, 'Artifacts dropped (File)', 'Any information about the files dropped during the analysis', 1, 'Artifacts dropped', 1, 'File', 0, 1),
(15, 24, 'Artifacts dropped (Registry key)', 'Any registry keys touched during the analysis', 1, 'Artifacts dropped', 0, 'regkey', 0, 1),
(16, 25, 'Artifacts dropped (Registry key + value)', 'Any registry keys created or altered together with the value.', 1, 'Artifacts dropped', 0, 'regkey|value', 0, 1),
(17, 26, 'Persistance mechanism (filename)', 'Filenames (or filenames with filepaths) used as a persistence mechanism', 1, 'Persistence mechanism', 0, 'regkey|value', 0, 1),
(18, 27, 'Persistence mechanism (Registry key)', 'Any registry keys touched as part of the persistence mechanism during the analysis ', 1, 'Persistence mechanism', 0, 'regkey', 0, 1),
(19, 28, 'Persistence mechanism (Registry key + value)', 'Any registry keys created or modified together with their values used by the persistence mechanism', 1, 'Persistence mechanism', 0, 'regkey|value', 0, 1),
(20, 34, 'C2 Information', 'You can drop any urls, domains, hostnames or IP addresses that were detected as the Command and Control during the analysis here. ', 1, 'Network activity', 1, 'CnC', 0, 1),
(21, 35, 'Other Network Activity', 'Drop any applicable information about other network activity here. The attributes created here will NOT be marked for IDS exports.', 0, 'Network activity', 1, 'CnC', 0, 1),
(22, 36, 'Vulnerability', 'The vulnerability or vulnerabilities that the sample exploits', 0, 'Payload delivery', 0, 'vulnerability', 0, 1),
(23, 37, 'Artifacts Dropped (File)', 'Insert any data you have on dropped files here.', 1, 'Artifacts dropped', 1, 'File', 0, 1),
(24, 38, 'Artifacts dropped (Registry key)', 'Any registry keys touched during the analysis', 1, 'Artifacts dropped', 0, 'regkey', 0, 1),
(25, 39, 'Artifacts dropped (Registry key + value)', 'Any registry keys created or altered together with the value.', 1, 'Artifacts dropped', 0, 'regkey|value', 0, 1),
(26, 42, 'Persistence mechanism (filename)', 'Insert any filenames used by the persistence mechanism.', 1, 'Persistence mechanism', 0, 'filename', 0, 1),
(27, 43, 'Persistence Mechanism (Registry key)', 'Paste any registry keys that were created or modified as part of the persistence mechanism', 1, 'Persistence mechanism', 0, 'regkey', 0, 1),
(28, 44, 'Persistence Mechanism (Registry key and value)', 'Paste any registry keys together with the values contained within created or modified by the persistence mechanism', 1, 'Persistence mechanism', 0, 'regkey|value', 0, 1),
(29, 46, 'Network Indicators', 'Paste any combination of IP addresses, hostnames, domains or URL', 1, 'Network activity', 1, 'CnC', 0, 1),
(30, 47, 'File Indicators', 'Paste any file hashes that you have (MD5, SHA1, SHA256) or filenames below. You can also add filename and hash pairs by using the following syntax for each applicable column: filename|hash ', 1, 'Payload installation', 1, 'File', 0, 1);
INSERT INTO `template_element_files` (`id`, `template_element_id`, `name`, `description`, `category`, `malware`, `mandatory`, `batch`) VALUES
(1, 14, 'Malicious Attachment', 'The file (or files) that was (were) attached to the e-mail itself.', 'Payload delivery', 1, 0, 1),
(2, 21, 'Payload installation', 'Payload installation detected during the analysis', 'Payload installation', 1, 0, 1),
(3, 30, 'Malware sample', 'The sample that the report is based on', 'Payload delivery', 1, 0, 0),
(4, 40, 'Artifacts dropped (Sample)', 'Upload any files that were dropped during the analysis.', 'Artifacts dropped', 1, 0, 1);
INSERT INTO `template_element_texts` (`id`, `name`, `template_element_id`, `text`) VALUES
(1, 'Required fields', 3, 'The fields below are mandatory.'),
(2, 'Optional information', 5, 'All of the fields below are optional, please fill out anything that''s applicable.'),
(4, 'Required Fields', 11, 'The following fields are mandatory'),
(5, 'Optional information about the payload delivery', 13, 'All of the fields below are optional, please fill out anything that''s applicable. This section describes the payload delivery, including the e-mail itself, the attached file, the vulnerability it is exploiting and any malicious urls in the e-mail.'),
(6, 'Optional information obtained from analysing the malicious file', 16, 'Information about the analysis of the malware (if applicable). This can include C2 information, artifacts dropped during the analysis, persistance mechanism, etc.'),
(7, 'Malware Sample', 29, 'If you can, please upload the sample that the report revolves around.'),
(8, 'Dropped Artifacts', 31, 'Describe any dropped artifacts that you have encountered during your analysis'),
(9, 'C2 Information', 32, 'The following field deals with Command and Control information obtained during the analysis. All fields are optional.'),
(10, 'Other Network Activity', 33, 'If any other Network activity (such as an internet connection test) was detected during the analysis, please specify it using the following fields'),
(11, 'Persistence mechanism', 41, 'The following fields allow you to describe the persistence mechanism used by the malware'),
(12, 'Indicators', 45, 'Just paste your list of indicators based on type into the appropriate field. All of the fields are optional, so inputting a list of IP addresses into the Network indicator field for example is sufficient to complete this template.');

View File

@ -1,177 +0,0 @@
-- Copyright (c) 2009 www.cryer.co.uk
-- Script is free to use provided this copyright header is included.
drop procedure if exists AddColumnUnlessExists;
delimiter '//'
create procedure AddColumnUnlessExists(
IN dbName tinytext,
IN tableName tinytext,
IN fieldName tinytext,
IN fieldDef text)
begin
IF NOT EXISTS (
SELECT * FROM information_schema.COLUMNS
WHERE column_name=fieldName
and table_name=tableName
and table_schema=dbName
)
THEN
set @ddl=CONCAT('ALTER TABLE ',dbName,'.',tableName,
' ADD COLUMN ',fieldName,' ',fieldDef);
prepare stmt from @ddl;
execute stmt;
END IF;
end;
//
delimiter ';'
call AddColumnUnlessExists(Database(), 'attributes', 'sharing_group_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'attributes', 'deleted', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'events', 'sharing_group_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'events', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'events', 'orgc_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'jobs', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'jobs', 'date_created', 'datetime NOT NULL');
call AddColumnUnlessExists(Database(), 'jobs', 'date_modified', 'datetime NOT NULL');
call AddColumnUnlessExists(Database(), 'roles', 'perm_sharing_group', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'servers', 'pull_rules', 'TEXT( 11 ) COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'servers', 'push_rules', 'TEXT( 11 ) COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'servers', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'servers', 'remote_org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'servers', 'name', 'varchar(255) COLLATE utf8_bin NOT NULL');
call AddColumnUnlessExists(Database(), 'servers', 'client_cert_file', 'varchar(255) COLLATE utf8_bin DEFAULT NULL');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'event_org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'shadow_attributes', 'proposal_to_delete', 'BOOLEAN NOT NULL');
call AddColumnUnlessExists(Database(), 'tags', 'exportable', 'TINYINT( 1 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'threads', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'threads', 'sharing_group_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'users', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'users', 'server_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'users', 'disabled', 'BOOLEAN NOT NULL');
call AddColumnUnlessExists(Database(), 'users', 'expiration', 'datetime DEFAULT NULL');
call AddColumnUnlessExists(Database(), 'correlations', 'org_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'correlations', 'distribution', 'tinyint( 4 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'correlations', 'a_distribution', 'tinyint( 4 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'correlations', 'sharing_group_id', 'INT( 11 ) NOT NULL DEFAULT 0');
call AddColumnUnlessExists(Database(), 'correlations', 'a_sharing_group_id', 'INT( 11 ) NOT NULL DEFAULT 0');
CREATE TABLE IF NOT EXISTS `organisations` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) COLLATE utf8_bin NOT NULL,
`date_created` datetime NOT NULL,
`date_modified` datetime NOT NULL,
`description` text CHARACTER SET utf8 COLLATE utf8_unicode_ci,
`type` varchar(255) CHARACTER SET utf8 COLLATE utf8_unicode_ci,
`nationality` varchar(255) CHARACTER SET utf8 COLLATE utf8_unicode_ci,
`sector` varchar(255) CHARACTER SET utf8 COLLATE utf8_unicode_ci,
`created_by` int(11) NOT NULL,
`uuid` varchar(40) COLLATE utf8_bin NOT NULL,
`contacts` text CHARACTER SET utf8 COLLATE utf8_unicode_ci,
`local` tinyint(1) NOT NULL DEFAULT '0',
`landingpage` text CHARACTER SET utf8 COLLATE utf8_unicode_ci,
PRIMARY KEY (`id`),
KEY `uuid` (`uuid`),
INDEX `name` (`name`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
CREATE TABLE IF NOT EXISTS `sharing_group_servers` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`sharing_group_id` int(11) NOT NULL,
`server_id` int(11) NOT NULL,
`all_orgs` tinyint(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
CREATE TABLE IF NOT EXISTS `sharing_group_orgs` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`sharing_group_id` int(11) NOT NULL,
`org_id` int(11) NOT NULL,
`extend` tinyint(1) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
CREATE TABLE IF NOT EXISTS `sharing_groups` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(255) CHARACTER SET utf8 COLLATE utf8_unicode_ci NOT NULL,
`releasability` text CHARACTER SET utf8 COLLATE utf8_unicode_ci NOT NULL,
`description` text CHARACTER SET utf8 COLLATE utf8_unicode_ci NOT NULL,
`uuid` varchar(40) COLLATE utf8_bin NOT NULL,
`organisation_uuid` varchar(40) COLLATE utf8_bin NOT NULL,
`org_id` int(11) NOT NULL,
`active` tinyint(1) NOT NULL,
`created` datetime NOT NULL,
`modified` datetime NOT NULL,
`local` tinyint(1) NOT NULL,
`sync_user_id` INT( 11 ) NOT NULL DEFAULT 0,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- --------------------------------------------------------
CREATE TABLE IF NOT EXISTS `taxonomies` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`namespace` varchar(255) COLLATE utf8_bin NOT NULL,
`description` text COLLATE utf8_bin NOT NULL,
`version` int(11) NOT NULL,
`enabled` tinyint(1) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin ;
-- --------------------------------------------------------
CREATE TABLE IF NOT EXISTS `taxonomy_entries` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`taxonomy_predicate_id` int(11) NOT NULL,
`value` text COLLATE utf8_bin NOT NULL,
`expanded` text COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`),
KEY `taxonomy_predicate_id` (`taxonomy_predicate_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- --------------------------------------------------------
CREATE TABLE IF NOT EXISTS `taxonomy_predicates` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`taxonomy_id` int(11) NOT NULL,
`value` text COLLATE utf8_bin NOT NULL,
`expanded` text COLLATE utf8_bin NOT NULL,
PRIMARY KEY (`id`),
KEY `taxonomy_id` (`taxonomy_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-- --------------------------------------------------------
CREATE TABLE IF NOT EXISTS `favourite_tags` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`tag_id` int(11) NOT NULL,
`user_id` int(11) NOT NULL,
PRIMARY KEY (`id`),
INDEX `user_id` (`user_id`),
INDEX `tag_id` (`tag_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
-- --------------------------------------------------------
CREATE TABLE IF NOT EXISTS `news` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`message` text COLLATE utf8_bin NOT NULL,
`title` text COLLATE utf8_bin NOT NULL,
`user_id` int(11) NOT NULL,
`date_created` int(11) unsigned NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
ALTER TABLE `users` CHANGE `newsread` `newsread` int(11) unsigned;
ALTER TABLE `organisations` CHANGE `uuid` `uuid` varchar(40) COLLATE utf8_bin DEFAULT NULL;

3
INSTALL/ansible/.gitignore vendored Normal file
View File

@ -0,0 +1,3 @@
tmp
.DS_Store
*.retry

48
INSTALL/ansible/README.md Normal file
View File

@ -0,0 +1,48 @@
MISP - Ansible installation script
----------------------------------------
- V0.1
* Nginx support only
* Backup script provided
Instructions
----------------------------------------
- From the ansible repository, run the following command:
```bash
ansible-playbook -i <host>, misp.yml -K -u <user>
```
- Update the self-signed certificate in /etc/nginx/ssl
- Create and export your GPG key:
```bash
sudo -u www-data gpg --homedir /opt/misp-server/misp/.gnupg --gen-key
sudo -u www-data gpg --homedir /opt/misp-server/misp/.gnupg --export --armor YOUR-EMAIL > /opt/misp-server/misp/app/webroot/gpg.asc
```
- Login with:
* user: admin@admin.test
* password: admin
and update the admin password
- Configure MISP in administration panel, server settings
Notes
----------------------------------------
- the user must have admin rights
- a self-signed certificate is generated to allow you to test the installation
- installation directory is: /opt/misp-server/misp
- backup directory is: /opt/misp-server/backup
Backup script
----------------------------------------
If enabled, a backup script create each day a new archive with a MySQL misp database dump and misp files to allow easy restore.
- these archives are created in: /opt/misp-server/backup
- a script to easy restore MISP from an archive is provided in the same directory
- to use the restore script, login as misp user and run the following command:
```bash
./misp_restore <archive_timestamp>.tar.gz
```

View File

@ -0,0 +1,3 @@
[ssh_connection]
ssh_args = -F ssh.cfg
pipelining = True

30
INSTALL/ansible/misp.yml Normal file
View File

@ -0,0 +1,30 @@
---
- hosts: all
become: true
roles:
- { role: mysql}
- { role: misp}
- { role: nginx}
vars_prompt:
- name: "proxy_host"
prompt: "Enter the proxy host (e.g. myproxy.be)"
private: no
- name: "proxy_port"
prompt: "Enter the proxy port (e.g. 3128)"
private: no
- name: "servername"
prompt: "Enter the servername address to use for the webserver (e.g. misp.com)"
private: no
- name: "mysql_root_old_pass"
prompt: "MySQL root password (current or default/empty)"
private: yes
- name: "mysql_root_new_pass"
prompt: "MySQL root password (new/current)"
private: yes
- name: mysql_misp_password
prompt: "Enter the mysql misp user password"
private: yes
- name: enable_auto_backup
prompt: "Do you want to enable automatic backup everyday ? (y/n)"
private: no

View File

@ -0,0 +1,2 @@
---
# default lower priority variables for this role

View File

@ -0,0 +1,2 @@
---
# Handlers file

View File

@ -0,0 +1,2 @@
---
# Role dependancies

View File

@ -0,0 +1,364 @@
---
# Install basic packages
- name: Create misp user
user:
name: misp
state: present
- name: Create Ansible directory
file:
path: "/home/misp/ansible"
owner: misp
group: misp
mode: 0775
state: directory
- name: Install all needed packages
apt:
pkg: "{{ item }}"
state: latest
update_cache: yes
with_items:
- gcc
- zip
- php-pear
- git
- redis-server
- make
- python-dev
- python-pip
- libxml2-dev
- libxslt1-dev
- zlib1g-dev
- php5-dev
- curl
- gnupg-agent
- php5-mysql
- php5-redis
######### MISP users and groups #########
- name: Add MISP group
group:
name: "{{ item }}"
state: present
system: yes
with_items:
- "misp-server"
- name: Add misp in misp-server
user:
name: misp
append: yes
groups: misp-server
state: present
- name: Add www-data in misp-server
user:
name: www-data
append: yes
groups: misp-server
######### MISP directories #########
- name: Create MISP server directory
file:
path: "{{ item }}"
owner: misp
group: misp-server
mode: 02775
state: directory
with_items:
- "/opt/misp-server"
- "/opt/misp-server/misp"
- "/opt/misp-server/tmp"
- "/opt/misp-server/backup"
######### PEAR: CRYPTPGP #########
- name: Configure PEAR proxy
shell: "{{ item }}"
args:
creates: /home/misp/ansible/ansible_shell_pear_configure_proxy.log
with_items:
- "pear config-set http_proxy http://{{proxy_host}}:{{proxy_port}} > /home/misp/ansible/ansible_shell_pear_configure_proxy.log"
- name: Configure PEAR tmp
shell: "{{ item }}"
args:
creates: /home/misp/ansible/ansible_shell_pear_configure_tmp.log
with_items:
- pear config-set temp_dir /opt/misp-server/tmp/ > /home/misp/ansible/ansible_shell_pear_configure_tmp.log
- name: Install CryptGPG
pear:
name: Crypt_GPG
state: present
######### MISP REPOSITORY #########
- name: Clone MISP repository
become: true
become_user: misp
git:
repo: "https://github.com/MISP/MISP.git"
dest: "/opt/misp-server/misp"
recursive: yes
force: no
update: no
version: v2.4.49
accept_hostkey: yes
- name: Configure Git
git_config:
name: core.filemode
scope: global
value: false
- name: Create scripts directories
file:
path: "{{ item }}"
owner: misp
group: misp-server
mode: 02775
state: directory
with_items:
- "/opt/misp-server/misp/app/files/scripts/python-cybox"
- "/opt/misp-server/misp/app/files/scripts/python-stix"
- name: Clone MISP depedencies | Python-Cybox
become: true
become_user: misp
git:
repo: "https://github.com/CybOXProject/python-cybox.git"
dest: "/opt/misp-server/misp/app/files/scripts/python-cybox"
force: no
update: no
version: v2.1.0.12
accept_hostkey: yes
- name: Clone MISP depedencies | Python-Stix
become: true
become_user: misp
git:
repo: "https://github.com/STIXProject/python-stix.git"
dest: "/opt/misp-server/misp/app/files/scripts/python-stix"
force: no
update: no
version: v1.1.1.4
accept_hostkey: yes
- name: Install MISP depedencies | Python-Cybox
become: true
shell: "{{ item }}"
args:
chdir: /opt/misp-server/misp/app/files/scripts/python-cybox
creates: /home/misp/ansible/ansible_shell_pythoncybox_setup.log
with_items:
- python setup.py install > /home/misp/ansible/ansible_shell_pythoncybox_setup.log
- name: Install MISP depedencies | Python-Stix
become: true
shell: "{{ item }}"
args:
chdir: /opt/misp-server/misp/app/files/scripts/python-stix
creates: /home/misp/ansible/ansible_shell_pythonstix_setup.log
with_items:
- python setup.py install > /home/misp/ansible/ansible_shell_pythonstix_setup.log
######### CAKE PHP #########
- name: Curl PHP installer
shell: "{{ item }}"
args:
chdir: /opt/misp-server/misp/app/
creates: /home/misp/ansible/ansible_shell_curl_php.log
with_items:
- curl -s https://getcomposer.org/installer | php > /home/misp/ansible/ansible_shell_curl_php.log
- name: Install COMPOSER in /bin
copy:
remote_src: True
src: /opt/misp-server/misp/app/composer.phar
dest: /usr/local/bin/composer
owner: root
group: root
mode: 0755
- name: Cake-resque installation
composer:
command: "require"
arguments: "kamisama/cake-resque:4.1.2"
working_dir: "/opt/misp-server/misp/app"
register: cakeresque_install
- name: Vendor configure
composer:
command: "config"
arguments: "vendor-dir Vendor"
working_dir: "/opt/misp-server/misp/app"
when: cakeresque_install.changed
- name: PHP composer install
composer:
command: "install"
arguments: ""
working_dir: "/opt/misp-server/misp/app"
- name: Copy CakeResque config file
copy:
remote_src: True
src: /opt/misp-server/misp/INSTALL/setup/config.php
dest: /opt/misp-server/misp/app/Plugin/CakeResque/Config/config.php
force: yes
owner: misp
group: misp-server
mode: 0774
######### MISP CONFIGURATION #########
- name: Copy MISP configuration files
template:
src: "misp/config/{{item}}"
dest: "/opt/misp-server/misp/app/Config/{{item}}"
force: yes
owner: misp
group: misp-server
mode: 0774
with_items:
- bootstrap.php
- config.php
- core.php
- database.php
######### GNUPG #########
- name: Create the directory for GNUPG
file:
path: "/opt/misp-server/misp/.gnupg"
owner: misp
group: misp-server
mode: 0770
state: directory
######### MISP WORKERS #########
- name: Check MISP worker launcher permissions
file:
path: /opt/misp-server/misp/app/Console/worker/start.sh
owner: misp
group: misp-server
mode: 0764
- name: Check MISP worker autolaunch at boot
lineinfile:
state: present
dest: /etc/rc.local
insertbefore: "exit 0"
line: "sudo -u www-data bash /opt/misp-server/misp/app/Console/worker/start.sh"
######### ADD-ON #########
- name: Install ZeroMQ
pip:
name: pyzmq
state: latest
- name: Install Python client for Redis
pip:
name: redis
state: latest
######### MYSQL CONFIGURATION #########
- name: MySQL | Create MISP database
become: true
mysql_db:
login_user: root
login_password: "{{ mysql_root_new_pass }}"
name: misp
state: present
register: mysql_init
- name: MySQL | Create MISP user
become: true
mysql_user:
login_user: root
login_password: "{{ mysql_root_new_pass }}"
name: misp
password: "{{mysql_misp_password}}"
priv: "misp.*:ALL,GRANT"
state: present
register: mysql_init
- name: MySQL | Create password file
template:
src: "mysql/{{item}}"
dest: "/home/misp/{{item}}"
force: no
owner: misp
group: misp
mode: 0600
with_items:
- .my.cnf
- name: MySQL | Create password file for root
template:
src: "mysql/{{item}}"
dest: "/root/{{item}}"
force: no
owner: root
group: root
mode: 0600
with_items:
- .my.cnf
- name: MySQL | Initialize MISP database
shell: "{{ item }}"
with_items:
- mysql -D misp < /opt/misp-server/misp/INSTALL/MYSQL.sql
when: mysql_init.changed
######### PERMISSIONS #########
- name: Fix all files permissions
file:
path: /opt/misp-server/misp
recurse: yes
state: directory
mode: "g=u"
############################################
##### BACKUP ####
############################################
- name: Copy backup script
become: true
template:
src: misp/{{item}}
dest: /bin/{{item}}
mode: 0755
with_items:
- misp_backup
when: enable_auto_backup == 'y'
- name: Copy restore script
template:
src: misp/{{item}}
dest: /opt/misp-server/backup/{{item}}
mode: 0755
owner: misp
group: misp
with_items:
- misp_backup
when: enable_auto_backup == 'y'
- name: Create backup cronjob
become: true
become_user: misp
cron:
name: "misp backup cronjob"
minute: "0"
hour: "4"
job: "sh /bin/misp_backup"
when: enable_auto_backup == 'y'

View File

@ -0,0 +1,164 @@
<?php
/**
* This file is loaded automatically by the app/webroot/index.php file after core.php
*
* This file should load/create any application wide configuration settings, such as
* Caching, Logging, loading additional configuration files.
*
* You should also use this file to include any files that provide global functions/constants
* that your application uses.
*/
/**
* Cache Engine Configuration
* Default settings provided below
*
* File storage engine.
*
* Cache::config('default', array(
* 'engine' => 'File', //[required]
* 'duration'=> 3600, //[optional]
* 'probability'=> 100, //[optional]
* 'path' => CACHE, //[optional] use system tmp directory - remember to use absolute path
* 'prefix' => 'cake_', //[optional] prefix every cache file with this string
* 'lock' => false, //[optional] use file locking
* 'serialize' => true, // [optional]
* 'mask' => 0666, // [optional] permission mask to use when creating cache files
* ));
*
* APC (http://pecl.php.net/package/APC)
*
* Cache::config('default', array(
* 'engine' => 'Apc', //[required]
* 'duration'=> 3600, //[optional]
* 'probability'=> 100, //[optional]
* 'prefix' => Inflector::slug(APP_DIR) . '_', //[optional] prefix every cache file with this string
* ));
*
* Xcache (http://xcache.lighttpd.net/)
*
* Cache::config('default', array(
* 'engine' => 'Xcache', //[required]
* 'duration'=> 3600, //[optional]
* 'probability'=> 100, //[optional]
* 'prefix' => Inflector::slug(APP_DIR) . '_', //[optional] prefix every cache file with this string
* 'user' => 'user', //user from xcache.admin.user settings
* 'password' => 'password', //plaintext password (xcache.admin.pass)
* ));
*
* Memcache (http://memcached.org/)
*
* Cache::config('default', array(
* 'engine' => 'Memcache', //[required]
* 'duration'=> 3600, //[optional]
* 'probability'=> 100, //[optional]
* 'prefix' => Inflector::slug(APP_DIR) . '_', //[optional] prefix every cache file with this string
* 'servers' => array(
* '127.0.0.1:11211' // localhost, default port 11211
* ), //[optional]
* 'persistent' => true, // [optional] set this to false for non-persistent connections
* 'compress' => false, // [optional] compress data in Memcache (slower, but uses less memory)
* ));
*
* Wincache (http://php.net/wincache)
*
* Cache::config('default', array(
* 'engine' => 'Wincache', //[required]
* 'duration'=> 3600, //[optional]
* 'probability'=> 100, //[optional]
* 'prefix' => Inflector::slug(APP_DIR) . '_', //[optional] prefix every cache file with this string
* ));
*
* Redis (http://http://redis.io/)
*
* Cache::config('default', array(
* 'engine' => 'Redis', //[required]
* 'duration'=> 3600, //[optional]
* 'probability'=> 100, //[optional]
* 'prefix' => Inflector::slug(APP_DIR) . '_', //[optional] prefix every cache file with this string
* 'server' => '127.0.0.1' // localhost
* 'port' => 6379 // default port 6379
* 'timeout' => 0 // timeout in seconds, 0 = unlimited
* 'persistent' => true, // [optional] set this to false for non-persistent connections
* ));
*/
Cache::config('default', array('engine' => 'File'));
Configure::load('config');
if (!Configure::read('MISP.baseurl')) {
if (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off' || $_SERVER['SERVER_PORT'] == 443) {
if ($_SERVER['SERVER_PORT'] == 443) {
Configure::write('MISP.baseurl', sprintf('https://%s', $_SERVER['SERVER_ADDR']));
} else {
Configure::write('MISP.baseurl', sprintf('https://%s:%d', $_SERVER['SERVER_ADDR'], $_SERVER['SERVER_PORT']));
}
} else {
if ($_SERVER['SERVER_PORT'] == 80) {
Configure::write('MISP.baseurl', sprintf('http://%s', $_SERVER['SERVER_ADDR']));
} else {
Configure::write('MISP.baseurl', sprintf('http://%s:%d', $_SERVER['SERVER_ADDR'], $_SERVER['SERVER_PORT']));
}
}
}
/**
* Plugins need to be loaded manually, you can either load them one by one or all of them in a single call
* Uncomment one of the lines below, as you need. make sure you read the documentation on CakePlugin to use more
* advanced ways of loading plugins
*
* CakePlugin::loadAll(); // Loads all plugins at once
* CakePlugin::load('DebugKit'); //Loads a single plugin named DebugKit
*
*/
CakePlugin::load('SysLog');
CakePlugin::load('Assets'); // having Logable
CakePlugin::load('SysLogLogable');
CakePlugin::load('UrlCache');
/**
* Uncomment the following line to enable client SSL certificate authentication.
* It's also necessary to configure the plugin for more information, please read app/Plugin/CertAuth/reame.md
*/
// CakePlugin::load('CertAuth');
/**
* You can attach event listeners to the request lifecyle as Dispatcher Filter . By Default CakePHP bundles two filters:
*
* - AssetDispatcher filter will serve your asset files (css, images, js, etc) from your themes and plugins
* - CacheDispatcher filter will read the Cache.check configure variable and try to serve cached content generated from controllers
*
* Feel free to remove or add filters as you see fit for your application. A few examples:
*
* Configure::write('Dispatcher.filters', array(
* 'MyCacheFilter', // will use MyCacheFilter class from the Routing/Filter package in your app.
* 'MyPlugin.MyFilter', // will use MyFilter class from the Routing/Filter package in MyPlugin plugin.
* array('callable' => $aFunction, 'on' => 'before', 'priority' => 9), // A valid PHP callback type to be called on beforeDispatch
* array('callable' => $anotherMethod, 'on' => 'after'), // A valid PHP callback type to be called on afterDispatch
*
* ));
*/
Configure::write('Dispatcher.filters', array(
'AssetDispatcher',
'CacheDispatcher'
));
/**
* Configures default file logging options
*/
App::uses('CakeLog', 'Log');
CakeLog::config('debug', array(
'engine' => 'FileLog',
'types' => array('notice', 'info', 'debug'),
'file' => 'debug',
));
CakeLog::config('error', array(
'engine' => 'FileLog',
'types' => array('warning', 'error', 'critical', 'alert', 'emergency'),
'file' => 'error',
));
// comment the following out if you do not with to use the background processing (not recommended)
CakePlugin::loadAll(array(
'CakeResque' => array('bootstrap' => true)
));

View File

@ -0,0 +1,83 @@
<?php
$config = array (
'debug' => 0,
'Security' =>
array (
'level' => 'medium',
'salt' => 'juFghZsg7128Eeyo<Qu2eeNfterd-dd+',
'cipherSeed' => '',
//'auth'=>array('CertAuth.Certificate'), // additional authentication methods
),
'MISP' =>
array (
'baseurl' => 'https://{{servername}}',
'footermidleft' => '',
'footermidright' => '',
'org' => '',
'showorg' => true,
'background_jobs' => true,
'cached_attachments' => true,
'email' => '',
'contact' => '',
'cveurl' => 'http://cve.circl.lu/cve/',
'disablerestalert' => false,
'default_event_distribution' => '1',
'default_attribute_distribution' => 'event',
'tagging' => true,
'full_tags_on_event_index' => true,
'footer_logo' => '',
'take_ownership_xml_import' => false,
'unpublishedprivate' => false,
'disable_emailing' => false,
),
'GnuPG' =>
array (
'onlyencrypted' => false,
'email' => '',
'homedir' => '/opt/misp-server/misp/.gnupg',
'password' => '',
'bodyonlyencrypted' => false,
),
'Proxy' =>
array (
'host' => '{{proxy_host}}',
'port' => '{{proxy_port}}',
'method' => '',
'user' => '',
'password' => '',
),
'SecureAuth' =>
array (
'amount' => 5,
'expire' => 300,
),
// Uncomment the following to enable client SSL certificate authentication
/*
'CertAuth' =>
array(
'ca' => array( 'FIRST.Org' ), // allowed CAs
'caId' => 'O', // which attribute will be used to verify the CA
'userModel' => 'User', // name of the User class to check if user exists
'userModelKey' => 'nids_sid', // User field that will be used for querying
'map' => array( // maps client certificate attributes to User properties
'O' => 'org',
'emailAddress'=>'email',
),
'syncUser' => true, // should the User be synchronized with an external REST API
'userDefaults'=> array( // default user attributes, only used when creating new users
'role_id' => 4,
),
'restApi' => array( // API parameters
'url' => 'https://example.com/data/users', // URL to query
'headers' => array(), // additional headers, used for authentication
'param' => array( 'email' => 'email'), // query parameters to add to the URL, mapped to USer properties
'map' => array( // maps REST result to the User properties
'uid' => 'nids_sid',
'team' => 'org',
'email' => 'email',
'pgp_public'=> 'gpgkey',
),
),
),
*/
);

View File

@ -0,0 +1,286 @@
<?php
/**
* This is core configuration file.
*
* Use it to configure core behavior of Cake.
*
* PHP 5
*
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
* Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
*
* Licensed under The MIT License
* Redistributions of files must retain the above copyright notice.
*
* @copyright Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
* @link http://cakephp.org CakePHP(tm) Project
* @package app.Config
* @since CakePHP(tm) v 0.2.9
* @license MIT License (http://www.opensource.org/licenses/mit-license.php)
*/
/**
* CakePHP Debug Level:
*
* Production Mode:
* 0: No error messages, errors, or warnings shown. Flash messages redirect.
*
* Development Mode:
* 1: Errors and warnings shown, model caches refreshed, flash messages halted.
* 2: As in 1, but also with full debug messages and SQL output.
*
* In production mode, flash messages redirect after a time interval.
* In development mode, you need to click the flash message to continue.
*/
Configure::write('debug', 0); // 0 = for production, 2 = full debug mode
/**
* Configure the Error handler used to handle errors for your application. By default
* ErrorHandler::handleError() is used. It will display errors using Debugger, when debug > 0
* and log errors with CakeLog when debug = 0.
*
* Options:
*
* - `handler` - callback - The callback to handle errors. You can set this to any callable type,
* including anonymous functions.
* - `level` - int - The level of errors you are interested in capturing.
* - `trace` - boolean - Include stack traces for errors in log files.
*
* @see ErrorHandler for more information on error handling and configuration.
*/
Configure::write('Error', array(
'handler' => 'ErrorHandler::handleError',
'level' => E_ALL & ~E_DEPRECATED,
'trace' => true
));
/**
* Configure the Exception handler used for uncaught exceptions. By default,
* ErrorHandler::handleException() is used. It will display a HTML page for the exception, and
* while debug > 0, framework errors like Missing Controller will be displayed. When debug = 0,
* framework errors will be coerced into generic HTTP errors.
*
* Options:
*
* - `handler` - callback - The callback to handle exceptions. You can set this to any callback type,
* including anonymous functions.
* - `renderer` - string - The class responsible for rendering uncaught exceptions. If you choose a custom class you
* should place the file for that class in app/Lib/Error. This class needs to implement a render method.
* - `log` - boolean - Should Exceptions be logged?
*
* @see ErrorHandler for more information on exception handling and configuration.
*/
Configure::write('Exception', array(
'handler' => 'ErrorHandler::handleException',
'renderer' => 'ExceptionRenderer',
'log' => true,
'skipLog' => array(
'NotFoundException',
)
));
/**
* Application wide charset encoding
*/
Configure::write('App.encoding', 'UTF-8');
/**
* To configure CakePHP *not* to use mod_rewrite and to
* use CakePHP pretty URLs, remove these .htaccess
* files:
*
* /.htaccess
* /app/.htaccess
* /app/webroot/.htaccess
*
* And uncomment the App.baseUrl below:
*/
//Configure::write('App.baseUrl', env('SCRIPT_NAME'));
/**
* Uncomment the define below to use CakePHP prefix routes.
*
* The value of the define determines the names of the routes
* and their associated controller actions:
*
* Set to an array of prefixes you want to use in your application. Use for
* admin or other prefixed routes.
*
* Routing.prefixes = array('admin', 'manager');
*
* Enables:
* `admin_index()` and `/admin/controller/index`
* `manager_index()` and `/manager/controller/index`
*
*/
Configure::write('Routing.prefixes', array('admin'));
/**
* Turn off all caching application-wide.
*
*/
Configure::write('Cache.disable', false);
/**
* Enable cache checking.
*
* If set to true, for view caching you must still use the controller
* public $cacheAction inside your controllers to define caching settings.
* You can either set it controller-wide by setting public $cacheAction = true,
* or in each action using $this->cacheAction = true.
*
*/
//Configure::write('Cache.check', true);
/**
* Defines the default error type when using the log() function. Used for
* differentiating error logging and debugging. Currently PHP supports LOG_DEBUG.
*/
define('LOG_ERROR', LOG_ERR);
/**
* Session configuration.
*
* Contains an array of settings to use for session configuration. The defaults key is
* used to define a default preset to use for sessions, any settings declared here will override
* the settings of the default config.
*
* ## Options
*
* - `Session.cookie` - The name of the cookie to use. Defaults to 'CAKEPHP'
* - `Session.timeout` - The number of minutes you want sessions to live for. This timeout is handled by CakePHP
* - `Session.cookieTimeout` - The number of minutes you want session cookies to live for.
* - `Session.checkAgent` - Do you want the user agent to be checked when starting sessions? You might want to set the
* value to false, when dealing with older versions of IE, Chrome Frame or certain web-browsing devices and AJAX
* - `Session.defaults` - The default configuration set to use as a basis for your session.
* There are four builtins: php, cake, cache, database.
* - `Session.handler` - Can be used to enable a custom session handler. Expects an array of of callables,
* that can be used with `session_save_handler`. Using this option will automatically add `session.save_handler`
* to the ini array.
* - `Session.autoRegenerate` - Enabling this setting, turns on automatic renewal of sessions, and
* sessionids that change frequently. See CakeSession::$requestCountdown.
* - `Session.ini` - An associative array of additional ini values to set.
*
* The built in defaults are:
*
* - 'php' - Uses settings defined in your php.ini.
* - 'cake' - Saves session files in CakePHP's /tmp directory.
* - 'database' - Uses CakePHP's database sessions.
* - 'cache' - Use the Cache class to save sessions.
*
* To define a custom session handler, save it at /app/Model/Datasource/Session/<name>.php.
* Make sure the class implements `CakeSessionHandlerInterface` and set Session.handler to <name>
*
* To use database sessions, run the app/Config/Schema/sessions.php schema using
* the cake shell command: cake schema create Sessions
*
*/
Configure::write('Session', array(
'timeout' => 60, // Session timeout, default is 1 hour
'defaults' => 'database'
));
/**
* The level of CakePHP security.
*/
Configure::write('Security.level', 'medium');
/**
* A random string used in security hashing methods.
*/
Configure::write('Security.salt', 'Rooraenietu8Eeyo<Qu2eeNfterd-dd+');
/**
* A random numeric string (digits only) used to encrypt/decrypt strings.
*/
Configure::write('Security.cipherSeed', '395786739573056621429506834955');
/**
* Apply timestamps with the last modified time to static assets (js, css, images).
* Will append a querystring parameter containing the time the file was modified. This is
* useful for invalidating browser caches.
*
* Set to `true` to apply timestamps when debug > 0. Set to 'force' to always enable
* timestamping regardless of debug value.
*/
//Configure::write('Asset.timestamp', true);
/**
* Compress CSS output by removing comments, whitespace, repeating tags, etc.
* This requires a/var/cache directory to be writable by the web server for caching.
* and /vendors/csspp/csspp.php
*
* To use, prefix the CSS link URL with '/ccss/' instead of '/css/' or use HtmlHelper::css().
*/
//Configure::write('Asset.filter.css', 'css.php');
/**
* Plug in your own custom JavaScript compressor by dropping a script in your webroot to handle the
* output, and setting the config below to the name of the script.
*
* To use, prefix your JavaScript link URLs with '/cjs/' instead of '/js/' or use JavaScriptHelper::link().
*/
//Configure::write('Asset.filter.js', 'custom_javascript_output_filter.php');
/**
* The classname and database used in CakePHP's
* access control lists.
*/
Configure::write('Acl.classname', 'DbAcl');
Configure::write('Acl.database', 'default');
/**
* Uncomment this line and correct your server timezone to fix
* any date & time related errors.
*/
//date_default_timezone_set('UTC');
/**
* Pick the caching engine to use. If APC is enabled use it.
* If running via cli - apc is disabled by default. ensure it's available and enabled in this case
*
* Note: 'default' and other application caches should be configured in app/Config/bootstrap.php.
* Please check the comments in boostrap.php for more info on the cache engines available
* and their setttings.
*/
$engine = 'File';
if (extension_loaded('apc') && function_exists('apc_dec') && (php_sapi_name() !== 'cli' || ini_get('apc.enable_cli'))) {
$engine = 'Apc';
}
// In development mode, caches should expire quickly.
$duration = '+999 days';
if (Configure::read('debug') >= 1) {
$duration = '+10 seconds';
}
// Prefix each application on the same server with a different string, to avoid Memcache and APC conflicts.
$prefix = 'myapp_';
/**
* Configure the cache used for general framework caching. Path information,
* object listings, and translation cache files are stored with this configuration.
*/
Cache::config('_cake_core_', array(
'engine' => $engine,
'prefix' => $prefix . 'cake_core_',
'path' => CACHE . 'persistent' . DS,
'serialize' => ($engine === 'File'),
'duration' => $duration
));
/**
* Configure the cache for model and datasource caches. This cache configuration
* is used to store schema descriptions, and table listings in connections.
*/
Cache::config('_cake_model_', array(
'engine' => $engine,
'prefix' => $prefix . 'cake_model_',
'path' => CACHE . 'models' . DS,
'serialize' => ($engine === 'File'),
'duration' => $duration
));
//Comment the following out if you do not with to use the background workers (not recommended)
require_once dirname(__DIR__) . '/Vendor/autoload.php';

View File

@ -0,0 +1,73 @@
<?php
/**
* This is core configuration file.
*
* Use it to configure core behaviour of Cake.
*
* PHP 5
*
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
* Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
*
* Licensed under The MIT License
* Redistributions of files must retain the above copyright notice.
*
* @copyright Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
* @link http://cakephp.org CakePHP(tm) Project
* @package app.Config
* @since CakePHP(tm) v 0.2.9
* @license MIT License (http://www.opensource.org/licenses/mit-license.php)
*/
/**
* In this file you set up your database connection details.
*
* @package cake.config
*/
/**
* Database configuration class.
* You can specify multiple configurations for production, development and testing.
*
* datasource => The name of a supported datasource; valid options are as follows:
* Database/Mysql - MySQL 4 & 5,
* Database/Sqlite - SQLite (PHP5 only),
* Database/Postgres - PostgreSQL 7 and higher,
* Database/Sqlserver - Microsoft SQL Server 2005 and higher
*
* You can add custom database datasources (or override existing datasources) by adding the
* appropriate file to app/Model/Datasource/Database. Datasources should be named 'MyDatasource.php',
*
*
* persistent => true / false
* Determines whether or not the database should use a persistent connection
*
* host =>
* the host you connect to the database. To add a socket or port number, use 'port' => #
*
* prefix =>
* Uses the given prefix for all the tables in this database. This setting can be overridden
* on a per-table basis with the Model::$tablePrefix property.
*
* schema =>
* For Postgres specifies which schema you would like to use the tables in. Postgres defaults to 'public'.
*
* encoding =>
* For MySQL, Postgres specifies the character encoding to use when connecting to the
* database. Uses database default not specified.
*
* unix_socket =>
* For MySQL to connect via socket specify the `unix_socket` parameter instead of `host` and `port`
*/
class DATABASE_CONFIG {
public $default = array(
'datasource' => 'Database/Mysql',
'persistent' => false,
'host' => 'localhost',
'login' => 'misp',
'port' => 3306,
'password' => '{{mysql_misp_password}}',
'database' => 'misp',
'prefix' => '',
//'encoding' => 'utf8',
);
}

View File

@ -0,0 +1,35 @@
#!/bin/bash
###########################################
####### MISP BACKUP SCRIPT #######
###########################################
TIMESTAMP=`date +%m%d%Y%H%M`
BACKUP_PATH='/opt/misp-server/backup'
BACKUP_DIR="$BACKUP_PATH/$TIMESTAMP"
BACKUP_MYSQL_DIR="$BACKUP_DIR/mysql"
BACKUP_FILES_DIR="$BACKUP_DIR/misp"
MISP_FILES="/opt/misp-server/misp/app/files"
MISP_CONF="/opt/misp-server/misp/app/Config"
mkdir "$BACKUP_DIR"
mkdir "$BACKUP_MYSQL_DIR"
mkdir "$BACKUP_FILES_DIR"
#### 1 | MYSQL ####
mysqldump -u misp --opt --single-transaction misp > "$BACKUP_MYSQL_DIR/mysql_dump.sql"
#### 2 | CONFIGURATION FILES ####
cp -R $MISP_CONF $BACKUP_FILES_DIR
#### 3 | FILES ####
cp -R $MISP_FILES $BACKUP_FILES_DIR
cd $BACKUP_PATH
tar -cpzf ${TIMESTAMP}.tar.gz ./${TIMESTAMP}
rm -rf $BACKUP_DIR
#### Remove old backups ####
find . -mtime +30 -exec rm {} \;

View File

@ -0,0 +1,45 @@
#!/bin/bash
###########################################
####### MISP RESTORE SCRIPT #######
###########################################
ARCHIVE=$1
EXTRACTION=${ARCHIVE::-7}
BACKUP_MYSQL_DUMP_FILE="./$EXTRACTION/mysql/mysql_dump.sql"
BACKUP_CONFIG_DIR="./$EXTRACTION/misp/Config/"
BACKUP_FILES_DIR="./$EXTRACTION/misp/files/"
MISP_INSTALL_DIR="/opt/misp-server/misp/"
MISP_INSTALL_APP_DIR="$MISP_INSTALL_DIR/app/"
MYSQL_USER="misp"
MYSQL_DATABASE="misp"
echo "------ MISP RESTORE SCRIPT ------"
#### 0 | OPEN BACKUP ARCHIVE ####
echo "*** Unpacking $1 ***"
tar -xf $ARCHIVE
echo "Done."
#### 1 | RESTORE MYSQL ####
echo "*** Restoring MySQL misp database ***"
echo "Connecting to MySQL database:"
echo "database:$MYSQL_DATABASE"
echo "user:$MYSQL_USER"
mysql -u $MYSQL_USER -p $MYSQL_DATABASE < $BACKUP_MYSQL_DUMP_FILE
echo "Done."
#### 2 | RESTORE CONFIGURATION FILES ####
echo "*** Restoring MISP configuration files ***"
cp -R $BACKUP_CONFIG_DIR $MISP_INSTALL_APP_DIR
echo "Done."
#### 3 | RESTORE MISP FILES ####
echo "*** Restoring MISP files ***"
cp -R $BACKUP_FILES_DIR $MISP_INSTALL_APP_DIR
echo "Done."
echo "------ COMPLETE ------"

View File

@ -0,0 +1,7 @@
[client]
user=misp
password="{{mysql_misp_password}}"
[mysqldump]
user=misp
password="{{mysql_misp_password}}"

View File

@ -0,0 +1,2 @@
---

View File

@ -0,0 +1,2 @@
---
# default lower priority variables for this role

View File

View File

@ -0,0 +1,3 @@
---
# Handlers file

View File

@ -0,0 +1,2 @@
---
# Role dependancies

View File

@ -0,0 +1,45 @@
---
- name: mysql-server - installation
apt:
pkg: mysql-server-5.6
state: present
- name: python-mysqldb - installation
apt:
pkg: python-mysqldb
state: present
- name: MySQL - Update mysql root passwd
mysql_user:
name: root
host: "{{item}}"
password: "{{mysql_root_new_pass}}"
login_user: root
login_password: "{{mysql_root_old_pass}}"
with_items:
- "{{ansible_hostname}}"
- 127.0.0.1
- ::1
- localhost
when: mysql_root_new_pass != mysql_root_old_pass and
mysql_root_new_pass != ""
- name: MySQL - Delete anonymous mysql user
mysql_user:
name: ""
state: absent
login_user: root
login_password: "{{mysql_root_new_pass}}"
- name: MySQL - Remove mysql test database
mysql_db:
name: test
state: absent
login_user: root
login_password: "{{mysql_root_new_pass}}"
- name: Restart MySQL
service:
name: mysql
state: restarted

View File

@ -0,0 +1,2 @@
---
# Variables associated with this role

View File

@ -0,0 +1,2 @@
---
# default lower priority variables for this role

View File

View File

@ -0,0 +1,3 @@
---
# Handlers file

View File

@ -0,0 +1,2 @@
---
# Role dependancies

View File

@ -0,0 +1,59 @@
---
- name: Install all needed packages
apt:
pkg: "{{ item }}"
state: latest
update_cache: yes
with_items:
- nginx
- php5-fpm
######### WEB-SERVER CONFIGURATION #########
- name: Make NGINX SSL directory
file:
path: /etc/nginx/ssl
state: directory
owner: root
group: root
mode: 0644
register: nginx_init
- name: Remove default NGINX configuration
file:
path: /etc/nginx/{{item}}
state: absent
with_items:
- sites-enabled/default
- sites-available/default
register: nginx_init
- name: Copy Nginx site configurations
template:
src: nginx/{{item}}
dest: /etc/nginx/sites-available/{{item}}
force: no
mode: 0644
with_items:
- misp
register: nginx_init
- name: Create NGINX configuration symlinks
file:
src: /etc/nginx/sites-available/{{item}}
dest: /etc/nginx/sites-enabled/{{item}}
state: link
with_items:
- misp
register: nginx_init
- name: Create self-signed SSL certificate for Nginx
command: openssl req -new -nodes -x509 -subj "/C=XX/ST=AAAAAAA/L=BBBBBB/O=Organization/CN={{servername}}" -days 3650 -newkey rsa:4096 -keyout /etc/nginx/ssl/misp.key -out /etc/nginx/ssl/misp.crt
when: nginx_init.changed
- name: Restart Nginx
service:
name: mysql
state: restarted
when: nginx_init.changed

View File

@ -0,0 +1,27 @@
# MISP WEB SERVER CONFIGURATION
server {
server_name {{servername}};
listen 443 ssl spdy;
root /opt/misp-server/misp/app/webroot;
index index.php;
# Configure Crypto Keys/Certificates/DH
ssl_certificate /etc/nginx/ssl/misp.crt;
ssl_certificate_key /etc/nginx/ssl/misp.key;
# enable HSTS
add_header Strict-Transport-Security "max-age=15768000; includeSubdomains";
add_header X-Frame-Options SAMEORIGIN;
location / {
try_files $uri $uri/ /index.php;
}
location ~ \.php$ {
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass unix:/var/run/php5-fpm.sock;
fastcgi_index index.php;
include fastcgi_params;
}
}

View File

@ -0,0 +1,2 @@
---
# Variables associated with this role

2
INSTALL/ansible/ssh.cfg Normal file
View File

@ -0,0 +1,2 @@

2
PyMISP

@ -1 +1 @@
Subproject commit fd5c22d8d9c5ba922c268d210f1d987dea284146
Subproject commit 709770e36711f0668d3b4104bf236dbb25359bd6

View File

@ -1 +1 @@
{"major":2, "minor":4, "hotfix":49}
{"major":2, "minor":4, "hotfix":50}

View File

@ -1,72 +0,0 @@
<?php
/**
* This is Acl Schema file
*
* Use it to configure database for ACL
*
* PHP 5
*
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
* Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
*
* Licensed under The MIT License
* Redistributions of files must retain the above copyright notice.
*
* @copyright Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
* @link http://cakephp.org CakePHP(tm) Project
* @package app.Config.Schema
* @since CakePHP(tm) v 0.2.9
* @license MIT License (http://www.opensource.org/licenses/mit-license.php)
*/
/*
*
* Using the Schema command line utility
* cake schema run create DbAcl
*
*/
class DbAclSchema extends CakeSchema {
public $name = 'DbAcl';
public function before($event = array()) {
return true;
}
public function after($event = array()) {
}
public $acos = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 10, 'key' => 'primary'),
'parent_id' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'model' => array('type' => 'string', 'null' => true),
'foreign_key' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'alias' => array('type' => 'string', 'null' => true),
'lft' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'rght' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'indexes' => array('PRIMARY' => array('column' => 'id', 'unique' => 1))
);
public $aros = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 10, 'key' => 'primary'),
'parent_id' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'model' => array('type' => 'string', 'null' => true),
'foreign_key' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'alias' => array('type' => 'string', 'null' => true),
'lft' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'rght' => array('type' => 'integer', 'null' => true, 'default' => null, 'length' => 10),
'indexes' => array('PRIMARY' => array('column' => 'id', 'unique' => 1))
);
public $aros_acos = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 10, 'key' => 'primary'),
'aro_id' => array('type' => 'integer', 'null' => false, 'length' => 10, 'key' => 'index'),
'aco_id' => array('type' => 'integer', 'null' => false, 'length' => 10),
'_create' => array('type' => 'string', 'null' => false, 'default' => '0', 'length' => 2),
'_read' => array('type' => 'string', 'null' => false, 'default' => '0', 'length' => 2),
'_update' => array('type' => 'string', 'null' => false, 'default' => '0', 'length' => 2),
'_delete' => array('type' => 'string', 'null' => false, 'default' => '0', 'length' => 2),
'indexes' => array('PRIMARY' => array('column' => 'id', 'unique' => 1), 'ARO_ACO_KEY' => array('column' => array('aro_id', 'aco_id'), 'unique' => 1))
);
}

View File

@ -1,40 +0,0 @@
# $Id$
#
# Copyright 2005-2012, Cake Software Foundation, Inc.
#
# Licensed under The MIT License
# Redistributions of files must retain the above copyright notice.
# MIT License (http://www.opensource.org/licenses/mit-license.php)
CREATE TABLE acos (
id INTEGER(10) UNSIGNED NOT NULL AUTO_INCREMENT,
parent_id INTEGER(10) DEFAULT NULL,
model VARCHAR(255) DEFAULT '',
foreign_key INTEGER(10) UNSIGNED DEFAULT NULL,
alias VARCHAR(255) DEFAULT '',
lft INTEGER(10) DEFAULT NULL,
rght INTEGER(10) DEFAULT NULL,
PRIMARY KEY (id)
);
CREATE TABLE aros_acos (
id INTEGER(10) UNSIGNED NOT NULL AUTO_INCREMENT,
aro_id INTEGER(10) UNSIGNED NOT NULL,
aco_id INTEGER(10) UNSIGNED NOT NULL,
_create CHAR(2) NOT NULL DEFAULT 0,
_read CHAR(2) NOT NULL DEFAULT 0,
_update CHAR(2) NOT NULL DEFAULT 0,
_delete CHAR(2) NOT NULL DEFAULT 0,
PRIMARY KEY(id)
);
CREATE TABLE aros (
id INTEGER(10) UNSIGNED NOT NULL AUTO_INCREMENT,
parent_id INTEGER(10) DEFAULT NULL,
model VARCHAR(255) DEFAULT '',
foreign_key INTEGER(10) UNSIGNED DEFAULT NULL,
alias VARCHAR(255) DEFAULT '',
lft INTEGER(10) DEFAULT NULL,
rght INTEGER(10) DEFAULT NULL,
PRIMARY KEY (id)
);

View File

@ -1,52 +0,0 @@
<?php
/**
* This is i18n Schema file
*
* Use it to configure database for i18n
*
* PHP 5
*
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
* Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
*
* Licensed under The MIT License
* Redistributions of files must retain the above copyright notice.
*
* @copyright Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
* @link http://cakephp.org CakePHP(tm) Project
* @package app.Config.Schema
* @since CakePHP(tm) v 0.2.9
* @license MIT License (http://www.opensource.org/licenses/mit-license.php)
*/
// @codingStandardsIgnoreStart
/*
*
* Using the Schema command line utility
* cake schema run create i18n
*/
class i18nSchema extends CakeSchema {
// @codingStandardsIgnoreEnd
public $name = 'i18n';
public function before($event = array()) {
return true;
}
public function after($event = array()) {
}
public $i18n = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 10, 'key' => 'primary'),
'locale' => array('type' => 'string', 'null' => false, 'length' => 6, 'key' => 'index'),
'model' => array('type' => 'string', 'null' => false, 'key' => 'index'),
'foreign_key' => array('type' => 'integer', 'null' => false, 'length' => 10, 'key' => 'index'),
'field' => array('type' => 'string', 'null' => false, 'key' => 'index'),
'content' => array('type' => 'text', 'null' => true, 'default' => null),
'indexes' => array('PRIMARY' => array('column' => 'id', 'unique' => 1), 'locale' => array('column' => 'locale', 'unique' => 0), 'model' => array('column' => 'model', 'unique' => 0), 'row_id' => array('column' => 'foreign_key', 'unique' => 0), 'field' => array('column' => 'field', 'unique' => 0))
);
}

View File

@ -1,26 +0,0 @@
# $Id$
#
# Copyright 2005-2012, Cake Software Foundation, Inc.
#
# Licensed under The MIT License
# Redistributions of files must retain the above copyright notice.
# MIT License (http://www.opensource.org/licenses/mit-license.php)
CREATE TABLE i18n (
id int(10) NOT NULL auto_increment,
locale varchar(6) NOT NULL,
model varchar(255) NOT NULL,
foreign_key int(10) NOT NULL,
field varchar(255) NOT NULL,
content mediumtext,
PRIMARY KEY (id),
# UNIQUE INDEX I18N_LOCALE_FIELD(locale, model, foreign_key, field),
# INDEX I18N_LOCALE_ROW(locale, model, foreign_key),
# INDEX I18N_LOCALE_MODEL(locale, model),
# INDEX I18N_FIELD(model, foreign_key, field),
# INDEX I18N_ROW(model, foreign_key),
INDEX locale (locale),
INDEX model (model),
INDEX row_id (foreign_key),
INDEX field (field)
);

View File

@ -1,16 +0,0 @@
0.1.0
+Events.uuid
+Attributes.uuid
0.2.0
Attributes.value -> Attributes.value1
0.2.0.1
+Attributes.value2
0.2.1
Servers.lastfetchedid -> Servers.lastpulledid
0.2.1.1
+Servers.lastpushedid
0.2.2
+Users.role_id
+Roles
+Logs
0.2.3

View File

@ -1,287 +0,0 @@
<?php
class AppSchema extends CakeSchema {
public function before($event = array()) {
return true;
}
public function after($event = array()) {
}
public $attributes = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'event_id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'index'),
'category' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'type' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 100, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'value1' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'value2' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'to_ids' => array('type' => 'boolean', 'null' => false, 'default' => '1'),
'uuid' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'key' => 'index', 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'timestamp' => array('type' => 'integer', 'null' => false, 'default' => '0'),
'distribution' => array('type' => 'integer', 'null' => false, 'default' => '0', 'length' => 4),
'comment' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1),
'event_id' => array('column' => 'event_id', 'unique' => 0),
'uuid' => array('column' => 'uuid', 'unique' => 0)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $bruteforces = array(
'ip' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'username' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'expire' => array('type' => 'datetime', 'null' => false, 'default' => null),
'indexes' => array(
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $event_tags = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'event_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'tag_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $events = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'org' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'date' => array('type' => 'date', 'null' => false, 'default' => null),
'info' => array('type' => 'text', 'null' => false, 'default' => null, 'key' => 'index', 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'user_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'published' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'uuid' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'key' => 'index', 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'attribute_count' => array('type' => 'integer', 'null' => false, 'default' => null),
'analysis' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 4),
'orgc' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'timestamp' => array('type' => 'integer', 'null' => false, 'default' => '0'),
'distribution' => array('type' => 'integer', 'null' => false, 'default' => '0', 'length' => 4),
'proposal_email_lock' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'locked' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'threat_level_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'publish_timestamp' => array('type' => 'integer', 'null' => false, 'default' => null),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1),
'uuid' => array('column' => 'uuid', 'unique' => 0),
'info' => array('column' => 'info', 'type' => 'fulltext')
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $jobs = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'worker' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 32, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'job_type' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 32, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'job_input' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'status' => array('type' => 'integer', 'null' => false, 'default' => '0', 'length' => 4),
'retries' => array('type' => 'integer', 'null' => false, 'default' => '0'),
'message' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'progress' => array('type' => 'integer', 'null' => false, 'default' => '0'),
'org' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'process_id' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 32, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $logs = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'title' => array('type' => 'string', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'created' => array('type' => 'datetime', 'null' => true, 'default' => null),
'model' => array('type' => 'string', 'null' => true, 'default' => null, 'length' => 20, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'model_id' => array('type' => 'integer', 'null' => true, 'default' => null),
'action' => array('type' => 'string', 'null' => true, 'default' => null, 'length' => 20, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'user_id' => array('type' => 'integer', 'null' => true, 'default' => null),
'change' => array('type' => 'string', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'email' => array('type' => 'string', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'org' => array('type' => 'string', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'description' => array('type' => 'string', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $posts = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'date_created' => array('type' => 'datetime', 'null' => false, 'default' => null),
'date_modified' => array('type' => 'datetime', 'null' => false, 'default' => null),
'user_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'contents' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'post_id' => array('type' => 'integer', 'null' => false, 'default' => '0'),
'thread_id' => array('type' => 'integer', 'null' => false, 'default' => '0'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $regexp = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'regexp' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'replacement' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'type' => array('type' => 'string', 'null' => false, 'default' => 'ALL', 'length' => 100, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $roles = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'name' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 100, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'created' => array('type' => 'datetime', 'null' => true, 'default' => null),
'modified' => array('type' => 'datetime', 'null' => true, 'default' => null),
'perm_add' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_modify' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_modify_org' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_publish' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_sync' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_admin' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_audit' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_full' => array('type' => 'boolean', 'null' => true, 'default' => null),
'perm_auth' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'perm_site_admin' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'perm_regexp_access' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'perm_tagger' => array('type' => 'boolean', 'null' => false, 'default' => '0'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $servers = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'url' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'authkey' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'org' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'organization' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 10, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'push' => array('type' => 'boolean', 'null' => false, 'default' => null),
'pull' => array('type' => 'boolean', 'null' => false, 'default' => null),
'lastpulledid' => array('type' => 'integer', 'null' => false, 'default' => null),
'lastpushedid' => array('type' => 'integer', 'null' => false, 'default' => null),
'self_signed' => array('type' => 'boolean', 'null' => false, 'default' => null),
'cert_file' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'client_cert_file' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $shadow_attributes = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'old_id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'index'),
'event_id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'index'),
'type' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 100, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'category' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'value1' => array('type' => 'text', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'to_ids' => array('type' => 'boolean', 'null' => false, 'default' => '1'),
'uuid' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'key' => 'index', 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'value2' => array('type' => 'text', 'null' => true, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'org' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'email' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'event_org' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'comment' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'event_uuid' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1),
'event_id' => array('column' => 'event_id', 'unique' => 0),
'uuid' => array('column' => 'uuid', 'unique' => 0),
'old_id' => array('column' => 'old_id', 'unique' => 0)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $tags = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'name' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'colour' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 7, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $tasks = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'type' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 100, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'timer' => array('type' => 'integer', 'null' => false, 'default' => null),
'scheduled_time' => array('type' => 'string', 'null' => false, 'default' => '6:00', 'length' => 8, 'collate' => 'latin1_swedish_ci', 'charset' => 'latin1'),
'job_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'description' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'latin1_swedish_ci', 'charset' => 'latin1'),
'next_execution_time' => array('type' => 'integer', 'null' => false, 'default' => null),
'message' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $threads = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'date_created' => array('type' => 'datetime', 'null' => false, 'default' => null),
'date_modified' => array('type' => 'datetime', 'null' => false, 'default' => null),
'distribution' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 4),
'user_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'post_count' => array('type' => 'integer', 'null' => false, 'default' => null),
'event_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'title' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'org' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $threat_levels = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'name' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 50, 'collate' => 'latin1_swedish_ci', 'charset' => 'latin1'),
'description' => array('type' => 'string', 'null' => true, 'default' => null, 'collate' => 'latin1_swedish_ci', 'charset' => 'latin1'),
'form_description' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'latin1_swedish_ci', 'charset' => 'latin1'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'latin1', 'collate' => 'latin1_swedish_ci', 'engine' => 'InnoDB')
);
public $users = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'password' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'key' => 'index', 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'org' => array('type' => 'string', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'email' => array('type' => 'string', 'null' => false, 'default' => null, 'key' => 'index', 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'autoalert' => array('type' => 'boolean', 'null' => false, 'default' => null),
'authkey' => array('type' => 'string', 'null' => false, 'default' => null, 'length' => 40, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'invited_by' => array('type' => 'integer', 'null' => false, 'default' => null),
'gpgkey' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'certif_public' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_bin', 'charset' => 'utf8'),
'nids_sid' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 15),
'termsaccepted' => array('type' => 'boolean', 'null' => false, 'default' => null),
'newsread' => array('type' => 'date', 'null' => false, 'default' => null),
'role_id' => array('type' => 'integer', 'null' => false, 'default' => null),
'change_pw' => array('type' => 'integer', 'null' => false, 'default' => null, 'length' => 4),
'contactalert' => array('type' => 'boolean', 'null' => false, 'default' => null),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1),
'email' => array('column' => 'email', 'unique' => 0),
'password' => array('column' => 'password', 'unique' => 0)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
public $whitelist = array(
'id' => array('type' => 'integer', 'null' => false, 'default' => null, 'key' => 'primary'),
'name' => array('type' => 'text', 'null' => false, 'default' => null, 'collate' => 'utf8_unicode_ci', 'charset' => 'utf8'),
'indexes' => array(
'PRIMARY' => array('column' => 'id', 'unique' => 1)
),
'tableParameters' => array('charset' => 'utf8', 'collate' => 'utf8_bin', 'engine' => 'MyISAM')
);
}

View File

@ -1,46 +0,0 @@
<?php
/**
* This is Sessions Schema file
*
* Use it to configure database for Sessions
*
* PHP 5
*
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
* Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
*
* Licensed under The MIT License
* Redistributions of files must retain the above copyright notice.
*
* @copyright Copyright 2005-2012, Cake Software Foundation, Inc. (http://cakefoundation.org)
* @link http://cakephp.org CakePHP(tm) Project
* @package app.Config.Schema
* @since CakePHP(tm) v 0.2.9
* @license MIT License (http://www.opensource.org/licenses/mit-license.php)
*/
/*
*
* Using the Schema command line utility
* cake schema run create Sessions
*
*/
class SessionsSchema extends CakeSchema {
public $name = 'Sessions';
public function before($event = array()) {
return true;
}
public function after($event = array()) {
}
public $cake_sessions = array(
'id' => array('type' => 'string', 'null' => false, 'key' => 'primary'),
'data' => array('type' => 'text', 'null' => true, 'default' => null),
'expires' => array('type' => 'integer', 'null' => true, 'default' => null),
'indexes' => array('PRIMARY' => array('column' => 'id', 'unique' => 1))
);
}

View File

@ -1,16 +0,0 @@
# $Id$
#
# Copyright 2005-2012, Cake Software Foundation, Inc.
# 1785 E. Sahara Avenue, Suite 490-204
# Las Vegas, Nevada 89104
#
# Licensed under The MIT License
# Redistributions of files must retain the above copyright notice.
# MIT License (http://www.opensource.org/licenses/mit-license.php)
CREATE TABLE cake_sessions (
id varchar(255) NOT NULL default '',
data text,
expires int(11) default NULL,
PRIMARY KEY (id)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;

View File

@ -127,7 +127,7 @@ CakePlugin::load('UrlCache');
* It's also necessary to configure the plugin for more information, please read app/Plugin/CertAuth/reame.md
*/
// CakePlugin::load('CertAuth');
// CakePlugin::load('ShibbAuth');
/**
* You can attach event listeners to the request lifecyle as Dispatcher Filter . By Default CakePHP bundles two filters:
*

View File

@ -7,6 +7,7 @@ $config = array (
'salt' => '',
'cipherSeed' => '',
//'auth'=>array('CertAuth.Certificate'), // additional authentication methods
//'auth'=>array('ShibbAuth.ApacheShibb'),
),
'MISP' =>
array (
@ -89,6 +90,24 @@ $config = array (
'userDefaults' => array ( 'role_id' => 3 ), // default attributes for new users
),
*/
/*
'ApacheShibbAuth' => // Configuration for shibboleth authentication
array(
'apacheEnv' => 'REMOTE_USER', // If proxy variable = HTTP_REMOTE_USER
'ssoAuth' => 'AUTH_TYPE',
'MailTag' => 'EMAIL_TAG',
'OrgTag' => 'FEDERATION_TAG',
'GroupTag' => 'GROUP_TAG',
'GroupSeparator' => ';',
'GroupRoleMatching' => array( // 3:User, 1:admin. May be good to set "1" for the first user
'group_three' => 3,
'group_two' => 2,
'group_one' => 1,
),
'DefaultRoleId' => 3,
'DefaultOrg' => 'DEFAULT_ORG',
),
*/
// Warning: The following is a 3rd party contribution and still untested (including security) by the MISP-project team.
// Feel free to enable it and report back to us if you run into any issues.
//

View File

@ -67,7 +67,7 @@ class EventShell extends AppShell
$this->Job->saveField('message', 'Job done. (in '.$timeDelta.'s)');
$this->Job->saveField('date_modified', date("y-m-d H:i:s"));
}
public function cachejson() {
$timeStart = time();
$userId = $this->args[0];
@ -85,7 +85,7 @@ class EventShell extends AppShell
}
App::uses('JSONConverterTool', 'Tools');
$converter = new JSONConverterTool();
$file->append('{"response":[');
$file->write('{"response":[');
foreach ($eventIds as $k => $eventId) {
$result = $this->Event->fetchEvent($user, array('eventid' => $eventId['Event']['id'], 'includeAttachments' => Configure::read('MISP.cached_attachments')));
$file->append($converter->event2JSON($result[0]));
@ -384,7 +384,7 @@ class EventShell extends AppShell
$i = 0;
foreach ($users as $user) {
foreach ($this->Event->export_types as $k => $type) {
$this->Job->cache($k, $user['User'], 'Events visible to: ' . ($user['Role']['perm_site_admin'] ? 'ADMIN' : $user['Organisation']['name']));
$this->Job->cache($k, $user['User']);
$i++;
}
}

View File

@ -45,8 +45,8 @@ class AppController extends Controller {
public $helpers = array('Utility');
private $__jsVersion = '2.4.49';
public $phpmin = '5.5.9';
private $__jsVersion = '2.4.50';
public $phpmin = '5.5.9';
public $phprec = '5.6.0';
// Used for _isAutomation(), a check that returns true if the controller & action combo matches an action that is a non-xml and non-json automation method
@ -322,9 +322,20 @@ class AppController extends Controller {
} else {
$this->set('me', false);
}
if (Configure::read('site_admin_debug') && $this->_isSiteAdmin() && (Configure::read('debug') < 2)) {
if ($this->_isSiteAdmin()) {
if (Configure::read('Session.defaults') !== 'database') {
$db = ConnectionManager::getDataSource('default');
$sqlResult = $db->query('SELECT COUNT(id) AS session_count FROM cake_sessions WHERE expires < ' . time() . ';');
if (isset($sqlResult[0][0]['session_count']) && $sqlResult[0][0]['session_count'] > 1000) {
$this->loadModel('Server');
$this->Server->updateDatabase('cleanSessionTable');
}
}
if (Configure::read('site_admin_debug') && (Configure::read('debug') < 2)) {
Configure::write('debug', 1);
}
}
$this->debugMode = 'debugOff';
if (Configure::read('debug') > 1) $this->debugMode = 'debugOn';
$this->set('loggedInUserName', $this->__convertEmailToName($this->Auth->user('email')));
@ -439,6 +450,7 @@ class AppController extends Controller {
$this->loadModel('User');
$user = $this->User->getAuthUserByUuid($authkey);
if (empty($user)) return false;
if (!$user['Role']['perm_auth']) return false;
if ($user['Role']['perm_site_admin']) $user['siteadmin'] = true;
return $user;
}
@ -566,7 +578,8 @@ class AppController extends Controller {
$process_id = CakeResque::enqueue(
'default',
'AdminShell',
array('jobUpgrade24', $jobId, $this->Auth->user('id'))
array('jobUpgrade24', $jobId, $this->Auth->user('id')),
true
);
$job->saveField('process_id', $process_id);
$this->Session->setFlash(__('Job queued. You can view the progress if you navigate to the active jobs view (administration -> jobs).'));

View File

@ -881,11 +881,22 @@ class AttributesController extends AppController {
throw new MethodNotAllowedException();
}
if ($this->__delete($id, $hard)) {
$this->Session->setFlash(__('Attribute deleted'));
if ($this->_isRest() || $this->response->type() === 'application/json') {
$this->set('message', 'Attribute deleted.');
$this->set('_serialize', array('message'));
} else {
$this->Session->setFlash(__('Attribute deleted'));
$this->redirect($this->referer());
}
} else {
$this->Session->setFlash(__('Attribute was not deleted'));
if ($this->_isRest() || $this->response->type() === 'application/json') {
throw new Exception('Attribute was not deleted');
} else {
$this->Session->setFlash(__('Attribute was not deleted'));
$this->redirect(array('action' => 'index'));
}
$this->Session->setFlash(__('Attribute deleted'));
}
$this->redirect(array('controller' => 'events', 'action' => 'view', $attribute['Attribute']['event_id'])); // TODO check
}
}
@ -1928,7 +1939,8 @@ class AttributesController extends AppController {
$process_id = CakeResque::enqueue(
'default',
'AdminShell',
array('jobGenerateCorrelation', $jobId)
array('jobGenerateCorrelation', $jobId),
true
);
$job->saveField('process_id', $process_id);
$this->Session->setFlash(__('Job queued. You can view the progress if you navigate to the active jobs view (administration -> jobs).'));

View File

@ -326,7 +326,7 @@ class ACLComponent extends Component {
'initiatePasswordReset' => array('perm_admin'),
'login' => array('*'),
'logout' => array('*'),
'memberslist' => array('*'),
'attributehistogram' => array('*'),
'resetauthkey' => array('*'),
'routeafterlogin' => array('*'),
'statistics' => array('*'),

View File

@ -194,7 +194,7 @@ class EventsController extends AppController {
);
$attributeHits = $this->Event->Attribute->fetchAttributes($this->Auth->user(), array(
'conditions' => $conditions,
'fields' => array('event_id', 'comment', 'distribution', 'value1', 'value2')
'fields' => array('event_id', 'comment', 'distribution', 'value1', 'value2')
));
// rearrange the data into an array where the keys are the event IDs
$eventsWithAttributeHits = array();
@ -1156,13 +1156,14 @@ class EventsController extends AppController {
if (!empty($this->data)) {
$ext = '';
if (isset($this->data['Event']['submittedfile'])) {
App::uses('File', 'Utility');
$file = new File($this->data['Event']['submittedfile']['name']);
$ext = $file->ext();
$ext = pathinfo($this->data['Event']['submittedfile']['name'], PATHINFO_EXTENSION);
}
if (isset($this->data['Event']['submittedfile']) && ($ext != 'xml' && $ext != 'json') && $this->data['Event']['submittedfile']['size'] > 0 &&
is_uploaded_file($this->data['Event']['submittedxml']['tmp_name'])) {
if (isset($this->data['Event']['submittedfile']) && (strtolower($ext) != 'xml' && strtolower($ext) != 'json') && $this->data['Event']['submittedfile']['size'] > 0 &&
is_uploaded_file($this->data['Event']['submittedfile']['tmp_name'])) {
$log = ClassRegistry::init('Log');
$log->createLogEntry($this->Auth->user(), 'file_upload', 'Event', 0, 'MISP export file upload failed', 'File details: ' . json_encode($this->data['Event']['submittedfile']));
$this->Session->setFlash(__('You may only upload MISP XML or MISP JSON files.'));
throw new MethodNotAllowedException('File upload failed or file does not have the expected extension (.xml / .json).');
}
if (isset($this->data['Event']['submittedfile'])) {
if (Configure::read('MISP.take_ownership_xml_import')
@ -2722,6 +2723,11 @@ class EventsController extends AppController {
if (!$this->Event->EventTag->Tag->exists()) {
return new CakeResponse(array('body'=> json_encode(array('saved' => false, 'errors' => 'Invalid Tag.')), 'status'=>200));
}
$tag = $this->Event->EventTag->Tag->find('first', array(
'conditions' => array('Tag.id' => $tag_id),
'recursive' => -1,
'fields' => array('Tag.name')
));
$found = $this->Event->EventTag->find('first', array(
'conditions' => array(
'event_id' => $id,
@ -2734,7 +2740,7 @@ class EventsController extends AppController {
$this->Event->EventTag->create();
if ($this->Event->EventTag->save(array('event_id' => $id, 'tag_id' => $tag_id))) {
$log = ClassRegistry::init('Log');
$log->createLogEntry($this->Auth->user(), 'tag', 'Event', $id, 'Attached tag (' . $tag_id . ') to event (' . $id . ')', 'Event (' . $id . ') tagged as Tag (' . $tag_id . ')');
$log->createLogEntry($this->Auth->user(), 'tag', 'Event', $id, 'Attached tag (' . $tag_id . ') "' . $tag['Tag']['name'] . '" to event (' . $id . ')', 'Event (' . $id . ') tagged as Tag (' . $tag_id . ')');
return new CakeResponse(array('body'=> json_encode(array('saved' => true, 'success' => 'Tag added.')), 'status'=>200));
} else {
return new CakeResponse(array('body'=> json_encode(array('saved' => false, 'errors' => 'Tag could not be added.')),'status'=>200));
@ -2778,7 +2784,14 @@ class EventsController extends AppController {
));
$this->autoRender = false;
if (empty($eventTag)) return new CakeResponse(array('body'=> json_encode(array('saved' => false, 'errors' => 'Invalid event - tag combination.')),'status'=>200));
$tag = $this->Event->EventTag->Tag->find('first', array(
'conditions' => array('Tag.id' => $tag_id),
'recursive' => -1,
'fields' => array('Tag.name')
));
if ($this->Event->EventTag->delete($eventTag['EventTag']['id'])) {
$log = ClassRegistry::init('Log');
$log->createLogEntry($this->Auth->user(), 'tag', 'Event', $id, 'Removed tag (' . $tag_id . ') "' . $tag['Tag']['name'] . '" from event (' . $id . ')', 'Event (' . $id . ') untagged of Tag (' . $tag_id . ')');
return new CakeResponse(array('body'=> json_encode(array('saved' => true, 'success' => 'Tag removed.')), 'status'=>200));
} else {
return new CakeResponse(array('body'=> json_encode(array('saved' => false, 'errors' => 'Tag could not be removed.')),'status'=>200));
@ -2867,10 +2880,22 @@ class EventsController extends AppController {
if ($attribute['type'] == 'ip-src/ip-dst') {
$types = array('ip-src', 'ip-dst');
} else if ($attribute['type'] == 'malware-sample') {
App::uses('FileAccess', 'Tools');
$tmpdir = Configure::read('MISP.tmpdir') ? Configure::read('MISP.tmpdir') : '/tmp';
$tempFile = explode('|', $attribute['data']);
if (!preg_match('/^[a-z0-9]*$/i', $tempFile[0])) {
throw new MethodNotAllowedException('Invalid filename, stop tampering with it.');
}
$attribute['data'] = FileAccess::readFromFile($tmpdir . '/' . $tempFile[0], $tempFile[1]);
unlink($tmpdir . '/' . $tempFile[0]);
$result = $this->Event->Attribute->handleMaliciousBase64($id, $attribute['value'], $attribute['data'], array('md5', 'sha1', 'sha256'), $objectType == 'ShadowAttribute' ? true : false);
if (!$result['success']) {
$failed++;
continue;
}
$attribute['data'] = $result['data'];
$shortValue = $attribute['value'];
$attribute['value'] = $shortValue . '|' . $result['md5'];
$attribute['data'] = $result['data'];
$additionalHashes = array('sha1', 'sha256');
foreach ($additionalHashes as $hash) {
$temp = $attribute;
@ -3181,11 +3206,68 @@ class EventsController extends AppController {
'checkbox' => false
);
}
$this->loadModel('Module');
$modules = $this->Module->getEnabledModules(false, 'Export');
if (is_array($modules) && !empty($modules)) {
foreach ($modules['modules'] as $module) {
$exports[$module['name']] = array(
'url' => '/events/exportModule/' . $module['name'] . '/' . $id,
'text' => Inflector::humanize($module['name']),
'requiresPublished' => true,
'checkbox' => false,
);
}
}
$this->set('exports', $exports);
$this->set('id', $id);
$this->render('ajax/exportChoice');
}
public function importChoice($id) {
if (!is_numeric($id)) throw new MethodNotAllowedException('Invalid ID');
$event = $this->Event->fetchEvent($this->Auth->user(), array('eventid' => $id));
if (empty($event)) throw new NotFoundException('Event not found or you are not authorised to view it.');
$event = $event[0];
$imports = array(
'freetext' => array(
'url' => '/events/freeTextImport/' . $id,
'text' => 'Freetext Import',
'ajax' => true,
'target' => 'popover_form'
),
'template' => array(
'url' => '/templates/templateChoices/' . $id,
'text' => 'Populate using a Template',
'ajax' => true,
'target' => 'popover_form'
),
'OpenIOC' => array(
'url' => '/events/addIOC/' . $id,
'text' => 'OpenIOC Import',
'ajax' => false,
),
'ThreatConnect' => array(
'url' => '/attributes/add_threatconnect/' . $id,
'text' => 'ThreatConnect Import',
'ajax' => false
)
);
$this->loadModel('Module');
$modules = $this->Module->getEnabledModules(false, 'Import');
if (is_array($modules) && !empty($modules)) {
foreach ($modules['modules'] as $k => $module) {
$imports[$module['name']] = array(
'url' => '/events/importModule/' . $module['name'] . '/' . $id,
'text' => Inflector::humanize($module['name']),
'ajax' => false
);
}
}
$this->set('imports', $imports);
$this->set('id', $id);
$this->render('ajax/importChoice');
}
// API for pushing samples to MISP
// Either send it to an existing event, or let MISP create a new one automatically
public function upload_sample($event_id = null) {
@ -3627,69 +3709,11 @@ class EventsController extends AppController {
if (!empty($options)) $data['config'] = $options;
$data = json_encode($data);
$result = $this->Module->queryModuleServer('/query', $data);
if (!$result) return 'Enrichment service not reachable.';
if (!$result) throw new MethodNotAllowedException('Enrichment service not reachable.');
if (isset($result['error'])) $this->Session->setFlash($result['error']);
if (!is_array($result)) throw new Exception($result);
$resultArray = array();
$freetextResults = array();
App::uses('ComplexTypeTool', 'Tools');
$complexTypeTool = new ComplexTypeTool();
if (isset($result['results']) && !empty($result['results'])) {
foreach ($result['results'] as $k => &$r) {
if (!is_array($r['values'])) {
$r['values'] = array($r['values']);
}
if (!is_array($r['types'])) {
$r['types'] = array($r['types']);
}
if (isset($r['categories']) && !is_array($r['categories'])) {
$r['categories'] = array($r['categories']);
}
foreach ($r['values'] as &$value) {
if (!is_array($r['values']) || !isset($r['values'][0])) {
$r['values'] = array($r['values']);
}
}
foreach ($r['values'] as &$value) {
if (in_array('freetext', $r['types'])) {
if (is_array($value)) $value = json_encode($value);
$freetextResults = array_merge($freetextResults, $complexTypeTool->checkComplexRouter($value, 'FreeText'));
if (!empty($freetextResults)) {
foreach ($freetextResults as &$ft) {
$temp = array();
foreach ($ft['types'] as $type) {
$temp[$type] = $type;
}
$ft['types'] = $temp;
}
}
$r['types'] = array_diff($r['types'], array('freetext'));
// if we just removed the only type in the result then more on to the next result
if (empty($r['types'])) continue 2;
$r['types'] = array_values($r['types']);
}
}
foreach ($r['values'] as &$value) {
$temp = array(
'event_id' => $attribute[0]['Attribute']['event_id'],
'types' => $r['types'],
'default_type' => $r['types'][0],
'comment' => isset($r['comment']) ? $r['comment'] : false,
'to_ids' => isset($r['to_ids']) ? $r['to_ids'] : false,
'value' => $value
);
if (isset($r['categories'])) {
$temp['categories'] = $r['categories'];
$temp['default_category'] = $r['categories'][0];
}
if (isset($r['data'])) $temp['data'] = $r['data'];
$resultArray[] = $temp;
}
}
$resultArray = array_merge($resultArray, $freetextResults);
}
if(isset($result['comment']) && $result['comment'] != "") {
$resultArray = $this->Event->handleModuleResult($result, $attribute[0]['Attribute']['event_id']);
if (isset($result['comment']) && $result['comment'] != "") {
$importComment = $result['comment'];
}
else {
@ -3708,6 +3732,13 @@ class EventsController extends AppController {
'order' => false
);
$result['related'] = $this->Event->Attribute->fetchAttributes($this->Auth->user(), $options);
if (isset($result['data'])) {
App::uses('FileAccess', 'Tools');
$tmpdir = Configure::read('MISP.tmpdir') ? Configure::read('MISP.tmpdir') : '/tmp';
$tempFile = FileAccess::createTempFile($tmpdir, $prefix = 'MISP');
FileAccess::writeToFile($tempFile, $result['data']);
$result['data'] = basename($tempFile) . '|' . filesize($tempFile);
}
}
$this->set('event', array('Event' => $attribute[0]['Event']));
@ -3720,4 +3751,106 @@ class EventsController extends AppController {
$this->render('resolved_attributes');
}
}
public function importModule($module, $eventId) {
$this->loadModel('Module');
$module = $this->Module->getEnabledModule($module, 'Import');
if (!is_array($module)) throw new MethodNotAllowedException($module);
if (!isset($module['mispattributes']['inputSource'])) $module['mispattributes']['inputSource'] = array('paste');
if ($this->request->is('post')) {
$fail = false;
$modulePayload = array(
'module' => $module['name']
);
foreach ($module['mispattributes']['userConfig'] as $configName => $config) {
if (!$fail) {
$validation = call_user_func_array(array($this->Module, $this->Module->configTypes[$config['type']]['validation']), array($this->request->data['Event']['config'][$configName]));
if ($validation !== true) {
$fail = ucfirst($configName) . ': ' . $validation;
} else {
if (isset($config['regex']) && !empty($config['regex'])) {
$fail = preg_match($config['regex'], $this->request->data['Event']['config'][$configName]) ? false : ucfirst($configName) . ': ' . 'Invalid setting' . ($config['errorMessage'] ? ' - ' . $config['errorMessage'] : '');
if (!empty($fail)) {
$modulePayload['config'][$configName] = $this->request->data['Event']['config'][$configName];
}
} else {
$modulePayload['config'][$configName] = $this->request->data['Event']['config'][$configName];
}
}
}
}
if (!$fail) {
if (!isset($this->request->data['Event']['source'])) {
if (in_array('paste', $module['mispattributes']['inputSource'])) $this->request->data['Event']['source'] = '0';
else $this->request->data['Event']['source'] = '1';
}
if ($this->request->data['Event']['source'] == '1') {
if (!isset($this->request->data['Event']['fileupload']) || empty($this->request->data['Event']['fileupload'])) {
$fail = 'Invalid file upload.';
} else {
$fileupload = $this->request->data['Event']['fileupload'];
$tmpfile = new File($fileupload['tmp_name']);
if ((isset($fileupload['error']) && $fileupload['error'] == 0) || (!empty($fileupload['tmp_name']) && $fileupload['tmp_name'] != 'none') && is_uploaded_file($tmpfile->path)) {
$filename = basename($fileupload['name']);
App::uses('FileAccess', 'Tools');
$modulePayload['data'] = FileAccess::readFromFile($fileupload['tmp_name'], $fileupload['size']);
} else {
$fail = 'Invalid file upload.';
}
}
} else {
$modulePayload['data'] = $this->request->data['Event']['paste'];
}
if (!$fail) {
$modulePayload['data'] = base64_encode($modulePayload['data']);
$result = $this->Module->queryModuleServer('/query', json_encode($modulePayload, true), false, $moduleFamily = 'Import');
if (!$result) throw new Exception('Import service not reachable.');
if (isset($result['error'])) $this->Session->setFlash($result['error']);
if (!is_array($result)) throw new Exception($result);
$resultArray = $this->Event->handleModuleResult($result, $eventId);
if (isset($result['comment']) && $result['comment'] != "") {
$importComment = $result['comment'];
}
else {
$importComment = 'Enriched via the ' . $module['name'] . ' module';
}
$typeCategoryMapping = array();
foreach ($this->Event->Attribute->categoryDefinitions as $k => $cat) {
foreach ($cat['types'] as $type) {
$typeCategoryMapping[$type][$k] = $k;
}
}
foreach ($resultArray as &$result) {
$options = array(
'conditions' => array('OR' => array('Attribute.value1' => $result['value'], 'Attribute.value2' => $result['value'])),
'fields' => array('Attribute.type', 'Attribute.category', 'Attribute.value', 'Attribute.comment'),
'order' => false
);
$result['related'] = $this->Event->Attribute->fetchAttributes($this->Auth->user(), $options);
}
$this->set('event', array('Event' => array('id' => $eventId)));
$this->set('resultArray', $resultArray);
$this->set('typeList', array_keys($this->Event->Attribute->typeDefinitions));
$this->set('defaultCategories', $this->Event->Attribute->defaultCategories);
$this->set('typeCategoryMapping', $typeCategoryMapping);
$this->set('title', 'Enrichment Results');
$this->set('importComment', $importComment);
$this->render('resolved_attributes');
}
}
$this->Session->setFlash($fail);
} else {
}
$this->set('configTypes', $this->Module->configTypes);
$this->set('module', $module);
$this->set('eventId', $eventId);
}
public function exportModule($module, $id) {
$result = $this->Event->export($this->Auth->user(), $module, array('eventid' => $id));
$this->response->body(base64_decode($result['data']));
$this->response->type($result['response']);
$this->response->download('misp.event.' . $id . '.' . $module . '.export.' . $result['extension']);
return $this->response;
}
}

View File

@ -132,7 +132,8 @@ class FeedsController extends AppController {
$process_id = CakeResque::enqueue(
'default',
'ServerShell',
array('fetchFeed', $this->Auth->user('id'), $feedId, $jobId)
array('fetchFeed', $this->Auth->user('id'), $feedId, $jobId),
true
);
$this->Job->saveField('process_id', $process_id);
$message = 'Pull queued for background execution.';

View File

@ -24,35 +24,57 @@ class JobsController extends AppController {
public function index($queue = false) {
if (!$this->_isSiteAdmin()) throw new MethodNotAllowedException();
if (!Configure::read('MISP.background_jobs')) throw new NotFoundException('Background jobs are not enabled on this instance.');
$this->loadModel('Server');
$issueCount = 0;
$workers = $this->Server->workerDiagnostics($issueCount);
$this->recursive = 0;
$queues = array('email', 'default', 'cache', 'prio');
if ($queue && in_array($queue, $queues)) $this->paginate['conditions'] = array('Job.worker' => $queue);
$jobs = $this->paginate();
foreach ($jobs as &$job) {
if ($job['Job']['process_id']) {
if ($job['Job']['process_id'] !== false) {
$job['Job']['status'] = $this->__jobStatusConverter(CakeResque::getJobStatus($job['Job']['process_id']));
$job['Job']['failed'] = false;
if ($job['Job']['status'] === 'Failed') {
$job['Job']['failed'] = true;
}
} else {
$job['Job']['status'] = '???';
$job['Job']['status'] = 'Unknown';
}
$job['Job']['worker_status'] = isset($workers[$job['Job']['worker']]) && $workers[$job['Job']['worker']]['ok'] ? true : false;
}
$this->set('list', $jobs);
$this->set('queue', $queue);
}
public function getError($id) {
$fields = array(
'Failed at' => 'failed_at',
'Exception' => 'exception',
'Error' => 'error'
);
$this->set('fields', $fields);
$this->set('response', CakeResque::getFailedJobLog($id));
$this->render('/Jobs/ajax/error');
}
private function __jobStatusConverter($status) {
switch ($status) {
case 1:
return 'In progress...';
return 'Waiting';
break;
case 2:
return 'Unknown';
return 'Running';
break;
case 3:
return 'Unknown';
return 'Failed';
break;
case 4:
return 'Completed';
break;
default:
return 'Unknown';
break;
}
}
@ -68,12 +90,13 @@ class JobsController extends AppController {
}
public function getProgress($type) {
$org = $this->Auth->user('Organisation')['name'];
if ($this->_isSiteAdmin()) $org = 'ADMIN';
$org_id = $this->Auth->user('org_id');
if ($this->_isSiteAdmin()) $org_id = 0;
$progress = $this->Job->find('first', array(
'conditions' => array(
'job_type' => $type,
'org_id' => $org
'org_id' => $org_id
),
'fields' => array('id', 'progress'),
'order' => array('Job.id' => 'desc'),
@ -92,7 +115,7 @@ class JobsController extends AppController {
} else {
$target = 'Events visible to: '.$this->Auth->user('Organisation')['name'];
}
$id = $this->Job->cache($type, $this->Auth->user(), $target);
$id = $this->Job->cache($type, $this->Auth->user());
return new CakeResponse(array('body' => json_encode($id)));
}
}

View File

@ -42,6 +42,7 @@ class OrganisationsController extends AppController {
'conditions' => $conditions,
'recursive' => -1,
);
$usersPerOrg = $this->User->getMembersCount();
$orgs = $this->paginate();
if ($this->_isSiteAdmin()) {
$this->loadModel('User');
@ -60,6 +61,7 @@ class OrganisationsController extends AppController {
}
$this->set('scope', $scope);
$this->set('orgs', $orgs);
$this->set('members', $usersPerOrg);
}
public function admin_add() {

View File

@ -597,7 +597,9 @@ class ServersController extends AppController {
public function serverSettingsReloadSetting($setting, $id) {
if (!$this->_isSiteAdmin()) throw new MethodNotAllowedException();
$pathToSetting = explode('.', $setting);
if (strpos($setting, 'Plugin.Enrichment') !== false) $settingObject = $this->Server->getCurrentServerSettings();
if (strpos($setting, 'Plugin.Enrichment') !== false || strpos($setting, 'Plugin.Import') !== false || strpos($setting, 'Plugin.Export') !== false) {
$settingObject = $this->Server->getCurrentServerSettings();
}
else $settingObject = $this->Server->serverSettings;
foreach ($pathToSetting as $key) {
if (!isset($settingObject[$key])) throw new MethodNotAllowedException();
@ -820,7 +822,9 @@ class ServersController extends AppController {
if (!$this->_isSiteAdmin()) throw new MethodNotAllowedException();
if (!isset($setting) || !isset($id)) throw new MethodNotAllowedException();
$this->set('id', $id);
if (strpos($setting, 'Plugin.Enrichment') !== false) $serverSettings = $this->Server->getCurrentServerSettings();
if (strpos($setting, 'Plugin.Enrichment') !== false || strpos($setting, 'Plugin.Import') !== false || strpos($setting, 'Plugin.Export') !== false) {
$serverSettings = $this->Server->getCurrentServerSettings();
}
else $serverSettings = $this->Server->serverSettings;
$relevantSettings = (array_intersect_key(Configure::read(), $serverSettings));
$found = null;
@ -1109,6 +1113,16 @@ class ServersController extends AppController {
}
$this->redirect('/servers/serverSettings/diagnostics');
}
public function clearWorkerQueue($worker) {
if (!$this->_isSiteAdmin() || !$this->request->is('Post') || $this->request->is('ajax')) throw new MethodNotAllowedException();
$worker_array = array('cache', 'default', 'email', 'prio');
if (!in_array($worker, $worker_array)) throw new MethodNotAllowedException('Invalid worker');
$redis = Resque::redis();
$redis->del('queue:' . $worker);
$this->Session->setFlash('Queue cleared.');
$this->redirect($this->referer());
}
public function getVersion() {
if (!$this->userRole['perm_auth']) throw new MethodNotAllowedException('This action requires API access.');

View File

@ -726,18 +726,8 @@ class UsersController extends AppController {
$this->redirect($this->referer());
}
public function memberslist() {
// Orglist
$fields = array('Organisation.name', 'count(User.id) as `num_members`');
$params = array(
'fields' => $fields,
'recursive' => -1,
'contain' => array('Organisation'),
'group' => array('Organisation.name', 'Organisation.id'),
'order' => array('UPPER(Organisation.name)'),
);
$orgs = $this->User->find('all', $params);
$this->set('orgs', $orgs);
public function attributehistogram() {
//all code is called via JS
}
public function histogram($selected = null) {
@ -758,7 +748,7 @@ class UsersController extends AppController {
$this->loadModel('Attribute');
$conditions = array();
if ($selected) $conditions[] = array('Attribute.type' => $selectedTypes, 'Attribute.deleted' => false);
$fields = array('Event.orgc_id', 'Attribute.type', 'count(Attribute.type) as `num_types`');
$fields = array('Event.orgc_id', 'Attribute.type', 'COUNT(Attribute.type) AS num_types');
$params = array('recursive' => 0,
'fields' => $fields,
'group' => array('Attribute.type', 'Event.orgc_id'),

View File

@ -76,12 +76,18 @@ class ComplexTypeTool {
public function checkFreeText($input) {
$iocArray = preg_split("/\r\n|\n|\r|\s|\s+|,|;/", $input);
$quotedText = explode('"', $input);
foreach ($quotedText as $k => &$temp) {
$temp = trim($temp);
if (empty($temp)) {
unset($quotedText[$k]);
}
}
$iocArray = array_merge($iocArray, $this->__returnOddElements($quotedText));
$resultArray = array();
if (!empty($iocArray)) {
foreach ($iocArray as $ioc) {
$ioc = trim($ioc);
$ioc = trim($ioc, '"');
$ioc = trim($ioc, ',');
$ioc = preg_replace('/\p{C}+/u', '', $ioc);
if (empty($ioc)) continue;
@ -170,8 +176,8 @@ class ComplexTypeTool {
if (strpos($input, '\\') !== false) {
$temp = explode('\\', $input);
if (strpos($temp[count($temp)-1], '.')) {
if ($this->__resolveFilename($temp[count($temp)-1])) return array('types' => array('filename'), 'categories' => array('Payload installation'), 'to_ids' => false, 'default_type' => 'filename');
if (strpos($temp[count($temp)-1], '.') || preg_match('/^.:/i', $temp[0])) {
if ($this->__resolveFilename($temp[count($temp)-1])) return array('types' => array('filename'), 'categories' => array('Payload installation'), 'to_ids' => true, 'default_type' => 'filename');
} else {
return array('types' => array('regkey'), 'to_ids' => false, 'default_type' => 'regkey');
}
@ -184,13 +190,7 @@ class ComplexTypeTool {
}
private function __resolveFilename($input) {
if (
strpos($input, '.') != 0 &&
strpos($input, '..') == 0 &&
strpos($input, '.') != (strlen($input)-1) &&
preg_match('/(.*)\.[^(\|\<\>\^\=\?\/\[\]\"\;\*)]*$/', $input) &&
!preg_match('/[?:<>|\\*:\/@]/', $input)
) return true;
return false;
if ((preg_match('/^.:/', $input) || strpos($input, '.') !=0)) return true;
return false;
}
}

View File

@ -35,7 +35,7 @@ class FileAccess {
private static function __checkForFalse($result, $errorMsgPart) {
if ($result === false) {
throw new Exception(self::$__fileErrorMsgPrefix . $errorMsgPart . '".');
throw new MethodNotAllowedException(self::$__fileErrorMsgPrefix . $errorMsgPart . '".');
}
}
}

@ -1 +1 @@
Subproject commit 64e7c8d9914c845efa8d1865fe0472fd6b6706b6
Subproject commit 0a22058e356b7346221f26d3be47a6c93e12c2f5

View File

@ -156,11 +156,11 @@ class AppModel extends Model {
$sql = 'ALTER TABLE `events` ADD UNIQUE (uuid);';
break;
case 'cleanSessionTable':
$sql = 'DELETE FROM `cake_sessions` WHERE `expires` < ' . time() . ';';
$sql = 'DELETE FROM cake_sessions WHERE expires < ' . time() . ';';
$clean = false;
break;
case 'destroyAllSessions':
$sql = 'DELETE FROM `cake_sessions`;';
$sql = 'DELETE FROM cake_sessions;';
$clean = false;
break;
case 'addIPLogging':
@ -425,17 +425,19 @@ class AppModel extends Model {
// DB changes to solve https://github.com/MISP/MISP/issues/1354
$sqlArray[] = "ALTER TABLE `taxonomy_entries` MODIFY `expanded` text COLLATE utf8_bin;";
$sqlArray[] = "ALTER TABLE `taxonomy_predicates` MODIFY `expanded` text COLLATE utf8_bin;";
// Sharing group propagate to instances freely setting
// Sharing group propagate to instances freely setting
$sqlArray[] = "ALTER TABLE `sharing_groups` ADD `roaming` tinyint(1) NOT NULL DEFAULT 0;";
// table: shadow_attributes
$sqlArray[] = "ALTER TABLE `shadow_attributes` MODIFY `email` varchar(255) CHARACTER SET utf8 COLLATE utf8_unicode_ci DEFAULT NULL;";
// table: tasks
$sqlArray[] = "ALTER TABLE `tasks` CHANGE `job_id` `process_id` varchar(32) DEFAULT NULL;";
// Adding tag org restrictions
// Adding tag org restrictions
$sqlArray[] = "ALTER TABLE `tags` ADD `org_id` int(11) NOT NULL DEFAULT 0;";
$sqlArray[] = 'ALTER TABLE `tags` ADD INDEX `org_id` (`org_id`);';
break;
case '2.4.50':
$sqlArray[] = 'ALTER TABLE `cake_sessions` ADD INDEX `expires` (`expires`);';
$sqlArray[] = "ALTER TABLE `users` ADD `certif_public` longtext COLLATE utf8_bin AFTER `gpgkey`;";
$sqlArray[] = "ALTER TABLE `servers` ADD `client_cert_file` varchar(255) COLLATE utf8_bin DEFAULT NULL;";
break;
case 'fixNonEmptySharingGroupID':
@ -546,7 +548,7 @@ class AppModel extends Model {
if (!empty($value[$field])) return true;
return ucfirst($field) . ' cannot be empty.';
}
public function valueIsID($value) {
$field = array_keys($value);
$field = $field[0];

View File

@ -9,11 +9,11 @@ App::uses('Sanitize', 'Utility');
class Bruteforce extends AppModel {
public function insert($ip, $username) {
$expire = Configure::read('SecureAuth.expire');
$expire = time() + Configure::read('SecureAuth.expire');
// sanitize fields
$ip = Sanitize::clean($ip);
$username = Sanitize::clean($username);
$this->query("INSERT INTO `bruteforces` (`ip` , `username` , `expire` ) VALUES ('$ip', '$username', TIMESTAMPADD(SECOND,$expire, NOW()));");
$this->query("INSERT INTO bruteforces (ip, username, `expire`) VALUES ('$ip', '$username', '$expire');");
if ($this->isBlacklisted($ip, $username)) {
$this->Log = ClassRegistry::init('Log');
$this->Log->create();
@ -29,7 +29,7 @@ class Bruteforce extends AppModel {
}
public function clean() {
$this->query("DELETE FROM `bruteforces` WHERE `expire`<=NOW();");
$this->query("DELETE FROM bruteforces WHERE `expire` <= NOW();");
}
public function isBlacklisted($ip,$username) {

View File

@ -76,14 +76,14 @@ class Event extends AppModel {
'type' => 'JSON',
'requiresPublished' => 0,
'canHaveAttachments' => true,
'description' => 'Click this to download all events and attributes that you have access to in MISP XML format.',
'description' => 'Click this to download all events and attributes that you have access to in MISP JSON format.',
),
'xml' => array(
'extension' => '.xml',
'type' => 'XML',
'requiresPublished' => 0,
'canHaveAttachments' => true,
'description' => 'Click this to download all events and attributes that you have access to in MISP JSON format.',
'description' => 'Click this to download all events and attributes that you have access to in MISP XML format.',
),
'csv_sig' => array(
'extension' => '.csv',
@ -1486,7 +1486,8 @@ class Event extends AppModel {
$process_id = CakeResque::enqueue(
'email',
'EventShell',
array('alertemail', $user['id'], $jobId, $id)
array('alertemail', $user['id'], $jobId, $id),
true
);
$job->saveField('process_id', $process_id);
return true;
@ -2224,7 +2225,8 @@ class Event extends AppModel {
$process_id = CakeResque::enqueue(
'prio',
'EventShell',
array('publish', $id, $passAlong, $jobId, $user['id'])
array('publish', $id, $passAlong, $jobId, $user['id']),
true
);
$job->saveField('process_id', $process_id);
return $process_id;
@ -2306,7 +2308,8 @@ class Event extends AppModel {
$process_id = CakeResque::enqueue(
'email',
'EventShell',
array('contactemail', $id, $message, $creator_only, $user['id'], $isSiteAdmin, $jobId)
array('contactemail', $id, $message, $creator_only, $user['id'], $isSiteAdmin, $jobId),
true
);
$job->saveField('process_id', $process_id);
return true;
@ -2629,7 +2632,7 @@ class Event extends AppModel {
$correlatedAttributes = isset($event['RelatedAttribute']) ? array_keys($event['RelatedAttribute']) : array();
$correlatedShadowAttributes = isset($event['RelatedShadowAttribute']) ? array_keys($event['RelatedShadowAttribute']) : array();
foreach ($event['Attribute'] as $attribute) {
if ($filterType && !in_array($filterType, array('proposal', 'correlation', 'warning'))) if (!in_array($attribute['type'], $this->Attribute->typeGroupings[$filterType])) continue;
if ($filterType && !in_array($filterType, array('proposal', 'correlation', 'warning'))) if (!in_array($attribute['type'], $this->Attribute->typeGroupings[$filterType])) continue;
if (isset($attribute['distribution']) && $attribute['distribution'] != 4) unset($attribute['SharingGroup']);
$attribute['objectType'] = 0;
if (!empty($attribute['ShadowAttribute'])) $attribute['hasChildren'] = 1;
@ -2715,4 +2718,84 @@ class Event extends AppModel {
}
return $conditions;
}
public function handleModuleResult($result, $event_id) {
$resultArray = array();
$freetextResults = array();
App::uses('ComplexTypeTool', 'Tools');
$complexTypeTool = new ComplexTypeTool();
if (isset($result['results']) && !empty($result['results'])) {
foreach ($result['results'] as $k => &$r) {
if (!is_array($r['values'])) {
$r['values'] = array($r['values']);
}
if (!is_array($r['types'])) {
$r['types'] = array($r['types']);
}
if (isset($r['categories']) && !is_array($r['categories'])) {
$r['categories'] = array($r['categories']);
}
foreach ($r['values'] as &$value) {
if (!is_array($r['values']) || !isset($r['values'][0])) {
$r['values'] = array($r['values']);
}
}
foreach ($r['values'] as &$value) {
if (in_array('freetext', $r['types'])) {
if (is_array($value)) $value = json_encode($value);
$freetextResults = array_merge($freetextResults, $complexTypeTool->checkComplexRouter($value, 'FreeText'));
if (!empty($freetextResults)) {
foreach ($freetextResults as &$ft) {
$temp = array();
foreach ($ft['types'] as $type) {
$temp[$type] = $type;
}
$ft['types'] = $temp;
}
}
$r['types'] = array_diff($r['types'], array('freetext'));
// if we just removed the only type in the result then more on to the next result
if (empty($r['types'])) continue 2;
$r['types'] = array_values($r['types']);
}
}
foreach ($r['values'] as &$value) {
$temp = array(
'event_id' => $event_id,
'types' => $r['types'],
'default_type' => $r['types'][0],
'comment' => isset($r['comment']) ? $r['comment'] : false,
'to_ids' => isset($r['to_ids']) ? $r['to_ids'] : false,
'value' => $value
);
if (isset($r['categories'])) {
$temp['categories'] = $r['categories'];
$temp['default_category'] = $r['categories'][0];
}
if (isset($r['data'])) $temp['data'] = $r['data'];
$resultArray[] = $temp;
}
}
$resultArray = array_merge($resultArray, $freetextResults);
}
return $resultArray;
}
public function export($user = false, $module = false, $options = array()) {
if (empty($user)) return 'Invalid user.';
if (empty($module)) return 'Invalid module.';
$this->Module = ClassRegistry::init('Module');
$module = $this->Module->getEnabledModule($module, 'Export');
$events = $this->fetchEvent($user, $options);
if (empty($events)) return 'Invalid event.';
$modulePayload = array('module' => $module['name']);
$modulePayload['data'] = $events;
$result = $this->Module->queryModuleServer('/query', json_encode($modulePayload, true), false, 'Export');
return array(
'data' => $result['data'],
'extension' => $module['mispattributes']['outputFileExtension'],
'response' => $module['mispattributes']['responseType']
);
}
}

View File

@ -27,7 +27,7 @@ class Job extends AppModel {
}
}
public function cache($type, $user, $target, $jobOrg = null) {
public function cache($type, $user) {
$extra = null;
$extra2 = null;
$shell = 'Event';
@ -35,13 +35,13 @@ class Job extends AppModel {
$data = array(
'worker' => 'cache',
'job_type' => 'cache_' . $type,
'job_input' => $target,
'job_input' => $user['Role']['perm_site_admin'] ? 'All events.' : 'Events visible to: ' . $user['Organisation']['name'],
'status' => 0,
'retries' => 0,
'org_id' => $user['Role']['perm_site_admin'] ? 0 : $user['org_id'],
'message' => 'Fetching events.',
);
if ($type === 'md5' || $type === 'sha1' || $type = 'sha256') {
if ($type === 'md5' || $type === 'sha1' || $type === 'sha256') {
$extra = $type;
$type = 'hids';
}

View File

@ -45,7 +45,8 @@ class Log extends AppModel {
'accept_delegation',
'request_delegation',
'merge',
'undelete'
'undelete',
'file_upload'
)),
'message' => 'Options : ...'
)
@ -95,7 +96,7 @@ class Log extends AppModel {
$validDates = $this->find('all', array(
'fields' => array('DISTINCT UNIX_TIMESTAMP(DATE(created)) AS Date', 'count(id) AS count'),
'conditions' => $conditions,
'group' => array('DATE(created)'),
'group' => array('Date'),
'order' => array('Date')
));
$data = array();

View File

@ -4,21 +4,85 @@ App::uses('AppModel', 'Model');
class Module extends AppModel {
public $useTable = false;
private $__validTypes = array(
'Enrichment' => array('hover', 'expansion'),
'Import' => array('import'),
'Export' => array('export')
);
public function getModules($type = false) {
$modules = $this->queryModuleServer('/modules');
private $__typeToFamily = array(
'Import' => 'Import',
'Export' => 'Export',
'hover' => 'Enrichment',
'expansion' => 'Enrichment'
);
public $configTypes = array(
'IP' => array(
'validation' => 'validateIPField',
'field' => 'text',
'class' => 'input-xxlarge'
),
'String' => array(
'validation' => 'validateStringField',
'field' => 'text',
'class' => 'input-xxlarge'
),
'Integer' => array(
'validation' => 'validateIntegerField',
'field' => 'number',
),
'Boolean' => array(
'validation' => 'validateBooleanField',
'field' => 'checkbox'
),
'Select' => array(
'validation' => 'validateSelectField',
'field' => 'select'
)
);
public function validateIPField($value) {
if (!filter_var($value, FILTER_VALIDATE_IP) === false) {
return 'Value is not a valid IP.';
}
return true;
}
public function validateStringField($value) {
if (!empty($value)) return true;
return 'Field cannot be empty.';
}
public function validateIntegerField($value) {
if (is_numeric($value) && is_int(intval($value))) {
return true;
}
return 'Value is not an integer.';
}
public function validateBooleanField($value) {
if ($value == true || $value == false) {
return true;
}
return 'Value has to be a boolean.';
}
public function getModules($type = false, $moduleFamily = 'Enrichment') {
$modules = $this->queryModuleServer('/modules', false, false, $moduleFamily);
if (!$modules) return 'Module service not reachable.';
if (!empty($modules)) {
$result = array('modules' => $modules);
return $result;
} else return 'The module service reports that it found no modules.';
}
public function getEnabledModules($type = false) {
$modules = $this->getModules($type);
public function getEnabledModules($type = false, $moduleFamily = 'Enrichment') {
$modules = $this->getModules($type, $moduleFamily);
if (is_array($modules)) {
foreach ($modules['modules'] as $k => &$module) {
if (!Configure::read('Plugin.Enrichment_' . $module['name'] . '_enabled') || ($type && in_array($type, $module['meta']['module-type']))) {
if (!Configure::read('Plugin.' . $moduleFamily . '_' . $module['name'] . '_enabled') || ($type && in_array(strtolower($type), $module['meta']['module-type']))) {
unset($modules['modules'][$k]);
}
}
@ -27,8 +91,8 @@ class Module extends AppModel {
if (isset($modules['modules']) && !empty($modules['modules'])) $modules['modules'] = array_values($modules['modules']);
if (!is_array($modules)) return array();
foreach ($modules['modules'] as $temp) {
if (isset($temp['meta']['module-type']) && in_array('import', $temp['meta']['module-type'])) $modules['import'] = $temp['name'];
else if (isset($temp['meta']['module-type']) && in_array('export', $temp['meta']['module-type'])) $modules['export'] = $temp['name'];
if (isset($temp['meta']['module-type']) && in_array('import', $temp['meta']['module-type'])) $modules['Import'] = $temp['name'];
else if (isset($temp['meta']['module-type']) && in_array('export', $temp['meta']['module-type'])) $modules['Export'] = $temp['name'];
else {
foreach ($temp['mispattributes']['input'] as $input) {
if (!isset($temp['meta']['module-type']) || in_array('expansion', $temp['meta']['module-type'])) $modules['types'][$input][] = $temp['name'];
@ -38,23 +102,43 @@ class Module extends AppModel {
}
return $modules;
}
private function __getModuleServer() {
public function getEnabledModule($name, $type) {
$moduleFamily = $this->__typeToFamily[$type];
$url = $this->__getModuleServer($moduleFamily);
$modules = $this->getModules($type, $moduleFamily);
$module = false;
if (!Configure::read('Plugin.' . $moduleFamily . '_' . $name . '_enabled')) return 'The requested module is not enabled.';
if (is_array($modules)) {
foreach ($modules['modules'] as $k => &$module) {
if ($module['name'] == $name) {
if ($type && in_array(strtolower($type), $module['meta']['module-type'])) {
return $module;
} else {
return 'The requested module is not available for the requested action.';
}
}
}
} else return $modules;
return 'The modules system reports that it found no suitable modules.';
}
private function __getModuleServer($moduleFamily = 'Enrichment') {
if (!Configure::read('Plugin.' . $moduleFamily . '_services_enable')) return false;
$this->Server = ClassRegistry::init('Server');
if (!Configure::read('Plugin.Enrichment_services_enable')) return false;
$url = Configure::read('Plugin.Enrichment_services_url') ? Configure::read('Plugin.Enrichment_services_url') : $this->Server->serverSettings['Plugin']['Enrichment_services_url']['value'];
$port = Configure::read('Plugin.Enrichment_services_port') ? Configure::read('Plugin.Enrichment_services_port') : $this->Server->serverSettings['Plugin']['Enrichment_services_port']['value'];
$url = Configure::read('Plugin.' . $moduleFamily . '_services_url') ? Configure::read('Plugin.' . $moduleFamily . '_services_url') : $this->Server->serverSettings['Plugin'][$moduleFamily . '_services_url']['value'];
$port = Configure::read('Plugin.' . $moduleFamily . '_services_port') ? Configure::read('Plugin.' . $moduleFamily . '_services_port') : $this->Server->serverSettings['Plugin'][$moduleFamily . '_services_port']['value'];
return $url . ':' . $port;
}
public function queryModuleServer($uri, $post = false, $hover = false) {
$url = $this->__getModuleServer();
public function queryModuleServer($uri, $post = false, $hover = false, $moduleFamily = 'Enrichment') {
$url = $this->__getModuleServer($moduleFamily);
if (!$url) return false;
App::uses('HttpSocket', 'Network/Http');
if ($hover) {
$httpSocket = new HttpSocket(array('timeout' => Configure::read('Plugin.Enrichment_hover_timeout') ? Configure::read('Plugin.Enrichment_hover_timeout') : 2));
$httpSocket = new HttpSocket(array('timeout' => Configure::read('Plugin.' . $moduleFamily . '_hover_timeout') ? Configure::read('Plugin.' . $moduleFamily . '_hover_timeout') : 2));
} else {
$httpSocket = new HttpSocket(array('timeout' => Configure::read('Plugin.Enrichment_timeout') ? Configure::read('Plugin.Enrichment_timeout') : 5));
$httpSocket = new HttpSocket(array('timeout' => Configure::read('Plugin.' . $moduleFamily . '_timeout') ? Configure::read('Plugin.' . $moduleFamily . '_timeout') : 5));
}
try {
if ($post) $response = $httpSocket->post($url . $uri, $post);
@ -65,13 +149,15 @@ class Module extends AppModel {
}
}
public function getModuleSettings() {
$modules = $this->getModules();
public function getModuleSettings($moduleFamily = 'Enrichment') {
$modules = $this->getModules(false, $moduleFamily);
$result = array();
if (!empty($modules['modules'])) {
foreach ($modules['modules'] as $module) {
$result[$module['name']][0] = array('name' => 'enabled', 'type' => 'boolean');
if (isset($module['meta']['config'])) foreach ($module['meta']['config'] as $conf) $result[$module['name']][] = array('name' => $conf, 'type' => 'string');
if (array_intersect($this->__validTypes[$moduleFamily], $module['meta']['module-type'])) {
$result[$module['name']][0] = array('name' => 'enabled', 'type' => 'boolean');
if (isset($module['meta']['config'])) foreach ($module['meta']['config'] as $conf) $result[$module['name']][] = array('name' => $conf, 'type' => 'string');
}
}
}
return $result;

View File

@ -204,7 +204,7 @@ class Organisation extends AppModel{
if (!$logFile->create()) throw new MethodNotAllowedException('Merge halted because the log file (default location: /var/www/MISP/app/tmp/logs/merges/[old_org_id]_[new_org_id]_timestamp.log) could not be created. This is most likely a permission issue, make sure that MISP can write to the logs directory and try again.');
$backupFile = new File($dirPath . DS . 'merge_' . $currentOrg['Organisation']['id'] . '_' . $targetOrg['Organisation']['id'] . '_' . time() . '.sql');
if (!$backupFile->create()) throw new MethodNotAllowedException('Merge halted because the backup script file (default location: /var/www/MISP/app/tmp/logs/merges/[old_org_id]_[new_org_id]_timestamp.sql) could not be created. This is most likely a permission issue, make sure that MISP can write to the logs directory and try again.');
$backupFile->append('INSERT INTO `organisations` (`' . implode('`, `', array_keys($currentOrg['Organisation'])) . '`) VALUES (\'' . implode('\', \'', array_values($currentOrg['Organisation'])) . '\');' . PHP_EOL);
$backupFile->append('INSERT INTO organisations (`' . implode('`, `', array_keys($currentOrg['Organisation'])) . '`) VALUES (\'' . implode('\', \'', array_values($currentOrg['Organisation'])) . '\');' . PHP_EOL);
$this->Log->create();
$this->Log->save(array(
'org' => $user['Organisation']['name'],

View File

@ -47,7 +47,8 @@ class Post extends AppModel {
$process_id = CakeResque::enqueue(
'email',
'EventShell',
array('postsemail', $user_id, $post_id, $event_id, $title, $message, $jobId)
array('postsemail', $user_id, $post_id, $event_id, $title, $message, $jobId),
true
);
$job->saveField('process_id', $process_id);
return true;

View File

@ -606,6 +606,15 @@ class Server extends AppModel {
'type' => 'string',
'null' => true,
),
'tmpdir' => array(
'level' => 1,
'description' => 'Please indicate the temp directory you wish to use for certain functionalities in MISP. By default this is set to /tmp and will be used among others to store certain temporary files extracted from imports during the import process.',
'value' => '/tmp',
'errorMessage' => '',
'test' => 'testForPath',
'type' => 'string',
'null' => true,
),
'custom_css' => array(
'level' => 2,
'description' => 'If you would like to customise the css, simply drop a css file in the /var/www/MISP/webroot/css directory and enter the name here.',
@ -1042,6 +1051,70 @@ class Server extends AppModel {
'test' => 'testForEmpty',
'type' => 'numeric'
),
'Import_services_enable' => array(
'level' => 0,
'description' => 'Enable/disable the import services',
'value' => false,
'errorMessage' => '',
'test' => 'testBool',
'type' => 'boolean'
),
'Import_timeout' => array(
'level' => 1,
'description' => 'Set a timeout for the import services',
'value' => 5,
'errorMessage' => '',
'test' => 'testForEmpty',
'type' => 'numeric'
),
'Import_services_url' => array(
'level' => 1,
'description' => 'The url used to access the import services. By default, it is accessible at http://127.0.0.1:6666',
'value' => 'http://127.0.0.1',
'errorMessage' => '',
'test' => 'testForEmpty',
'type' => 'string'
),
'Import_services_port' => array(
'level' => 1,
'description' => 'The port used to access the import services. By default, it is accessible at 127.0.0.1:6666',
'value' => '6666',
'errorMessage' => '',
'test' => 'testForPortNumber',
'type' => 'numeric'
),
'Export_services_url' => array(
'level' => 1,
'description' => 'The url used to access the export services. By default, it is accessible at http://127.0.0.1:6666',
'value' => 'http://127.0.0.1',
'errorMessage' => '',
'test' => 'testForEmpty',
'type' => 'string'
),
'Export_services_port' => array(
'level' => 1,
'description' => 'The port used to access the export services. By default, it is accessible at 127.0.0.1:6666',
'value' => '6666',
'errorMessage' => '',
'test' => 'testForPortNumber',
'type' => 'numeric'
),
'Export_services_enable' => array(
'level' => 0,
'description' => 'Enable/disable the import services',
'value' => false,
'errorMessage' => '',
'test' => 'testBool',
'type' => 'boolean'
),
'Export_timeout' => array(
'level' => 1,
'description' => 'Set a timeout for the import services',
'value' => 5,
'errorMessage' => '',
'test' => 'testForEmpty',
'type' => 'numeric'
),
'Enrichment_hover_enable' => array(
'level' => 0,
'description' => 'Enable/disable the hover over information retrieved from the enrichment modules',
@ -1058,6 +1131,22 @@ class Server extends AppModel {
'test' => 'testForEmpty',
'type' => 'numeric'
),
'Enrichment_services_url' => array(
'level' => 1,
'description' => 'The url used to access the enrichment services. By default, it is accessible at http://127.0.0.1:6666',
'value' => 'http://127.0.0.1',
'errorMessage' => '',
'test' => 'testForEmpty',
'type' => 'string'
),
'Enrichment_services_port' => array(
'level' => 1,
'description' => 'The port used to access the enrichment services. By default, it is accessible at 127.0.0.1:6666',
'value' => '6666',
'errorMessage' => '',
'test' => 'testForPortNumber',
'type' => 'numeric'
),
'CustomAuth_custom_password_reset' => array(
'level' => 2,
'description' => 'Provide your custom authentication users with an external URL to the authentication system to reset their passwords.',
@ -1075,22 +1164,6 @@ class Server extends AppModel {
'test' => 'testForEmpty',
'type' => 'string',
'null' => true
),
'Enrichment_services_url' => array(
'level' => 1,
'description' => 'The url used to access the enrichment services. By default, it is accessible at http://127.0.0.1:6666',
'value' => 'http://127.0.0.1',
'errorMessage' => '',
'test' => 'testForEmpty',
'type' => 'string'
),
'Enrichment_services_port' => array(
'level' => 1,
'description' => 'The port used to access the enrichment services. By default, it is accessible at 127.0.0.1:6666',
'value' => '6666',
'errorMessage' => '',
'test' => 'testForPortNumber',
'type' => 'numeric'
)
),
'debug' => array(
@ -1757,23 +1830,26 @@ class Server extends AppModel {
public function getCurrentServerSettings() {
$this->Module = ClassRegistry::init('Module');
$serverSettings = $this->serverSettings;
if (Configure::read('Plugin.Enrichment_services_enable')) {
$results = $this->Module->getModuleSettings();
foreach ($results as $module => $data) {
foreach ($data as $result) {
$setting = array('level' => 1, 'errorMessage' => '');
if ($result['type'] == 'boolean') {
$setting['test'] = 'testBool';
$setting['type'] = 'boolean';
$setting['description'] = 'Enable or disable the ' . $module . ' module.';
$setting['value'] = false;
} else {
$setting['test'] = 'testForEmpty';
$setting['type'] = 'string';
$setting['description'] = 'Set this required module specific setting.';
$setting['value'] = '';
$moduleTypes = array('Enrichment', 'Import', 'Export');
foreach ($moduleTypes as $moduleType) {
if (Configure::read('Plugin.' . $moduleType . '_services_enable')) {
$results = $this->Module->getModuleSettings($moduleType);
foreach ($results as $module => $data) {
foreach ($data as $result) {
$setting = array('level' => 1, 'errorMessage' => '');
if ($result['type'] == 'boolean') {
$setting['test'] = 'testBool';
$setting['type'] = 'boolean';
$setting['description'] = 'Enable or disable the ' . $module . ' module.';
$setting['value'] = false;
} else {
$setting['test'] = 'testForEmpty';
$setting['type'] = 'string';
$setting['description'] = 'Set this required module specific setting.';
$setting['value'] = '';
}
$serverSettings['Plugin'][$moduleType . '_' . $module . '_' . $result['name']] = $setting;
}
$serverSettings['Plugin']['Enrichment_' . $module . '_' . $result['name']] = $setting;
}
}
}
@ -1944,7 +2020,7 @@ class Server extends AppModel {
public function testForTermsFile($value) {
return $this->__testForFile($value, APP . 'files' . DS . 'terms');
}
public function testForStyleFile($value) {
if (empty($value)) return true;
return $this->__testForFile($value, APP . 'webroot' . DS . 'css');
@ -2341,24 +2417,25 @@ class Server extends AppModel {
App::uses('Folder', 'Utility');
// check writeable directories
$writeableDirs = array(
'tmp' => 0,
'files' => 0,
'files' . DS . 'scripts' . DS . 'tmp' => 0,
'tmp' . DS . 'csv_all' => 0,
'tmp' . DS . 'csv_sig' => 0,
'tmp' . DS . 'md5' => 0,
'tmp' . DS . 'sha1' => 0,
'tmp' . DS . 'snort' => 0,
'tmp' . DS . 'suricata' => 0,
'tmp' . DS . 'text' => 0,
'tmp' . DS . 'xml' => 0,
'tmp' . DS . 'files' => 0,
'tmp' . DS . 'logs' => 0,
'/tmp' => 0,
APP . 'tmp' => 0,
APP . 'files' => 0,
APP . 'files' . DS . 'scripts' . DS . 'tmp' => 0,
APP . 'tmp' . DS . 'csv_all' => 0,
APP . 'tmp' . DS . 'csv_sig' => 0,
APP . 'tmp' . DS . 'md5' => 0,
APP . 'tmp' . DS . 'sha1' => 0,
APP . 'tmp' . DS . 'snort' => 0,
APP . 'tmp' . DS . 'suricata' => 0,
APP . 'tmp' . DS . 'text' => 0,
APP . 'tmp' . DS . 'xml' => 0,
APP . 'tmp' . DS . 'files' => 0,
APP . 'tmp' . DS . 'logs' => 0,
);
foreach ($writeableDirs as $path => &$error) {
$dir = new Folder(APP . $path);
$dir = new Folder($path);
if (is_null($dir->path)) $error = 1;
$file = new File(APP . $path . DS . 'test.txt', true);
$file = new File($path . DS . 'test.txt', true);
if ($error == 0 && !$file->write('test')) $error = 2;
if ($error != 0) $diagnostic_errors++;
$file->delete();
@ -2480,24 +2557,23 @@ class Server extends AppModel {
return $proxyStatus;
}
public function sessionDiagnostics(&$diagnostic_errors, &$sessionCount) {
public function sessionDiagnostics(&$diagnostic_errors = 0, &$sessionCount = '') {
if (Configure::read('Session.defaults') !== 'database') {
$sessionCount = 'N/A';
return 2;
}
$sql = 'SELECT COUNT(id) FROM `cake_sessions` WHERE `expires` < ' . time() . ';';
$sql = 'SELECT COUNT(id) AS session_count FROM cake_sessions WHERE expires < ' . time() . ';';
$sqlResult = $this->query($sql);
if (isset($sqlResult[0][0])) $sessionCount = $sqlResult[0][0]['COUNT(id)'];
if (isset($sqlResult[0][0])) $sessionCount = $sqlResult[0][0]['session_count'];
else {
$sessionCount = 'Error';
return 3;
}
$sessionStatus = 0;
if ($sessionCount > 100) {
$sessionStatus = 1;
if ($sessionCount > 1000) {
$diagnostic_errors++;
return 1;
}
return $sessionStatus;
return 0;
}
public function workerDiagnostics(&$workerIssueCount) {
@ -2588,7 +2664,7 @@ class Server extends AppModel {
'action' => 'remove_dead_workers',
'user_id' => $user['id'],
'title' => 'Removing a dead worker.',
'change' => 'Removind dead worker data. Worker was of type ' . $worker['queue'] . ' with pid ' . $pid
'change' => 'Removing dead worker data. Worker was of type ' . $worker['queue'] . ' with pid ' . $pid
));
}
$this->ResqueStatus->removeWorker($pid);
@ -2617,7 +2693,7 @@ class Server extends AppModel {
'action' => 'remove_dead_workers',
'user_id' => $user['id'],
'title' => 'Removing a dead worker.',
'change' => 'Removind dead worker data. Worker was of type ' . $worker['queue'] . ' with pid ' . $pid
'change' => 'Removing dead worker data. Worker was of type ' . $worker['queue'] . ' with pid ' . $pid
));
}
}
@ -2674,8 +2750,8 @@ class Server extends AppModel {
$this->Job->saveField('progress', 10);
$this->Job->saveField('message', 'Starting the migration of the database to 2.4');
}
$this->query('UPDATE `roles` SET `perm_template` = 1 WHERE `perm_site_admin` = 1 OR `perm_admin` = 1');
$this->query('UPDATE `roles` SET `perm_sharing_group` = 1 WHERE `perm_site_admin` = 1 OR `perm_sync` = 1');
$this->query('UPDATE roles SET perm_template = 1 WHERE perm_site_admin = 1 OR perm_admin = 1');
$this->query('UPDATE roles SET perm_sharing_group = 1 WHERE perm_site_admin = 1 OR perm_sync = 1');
$orgs = array('local' => array(), 'external' => array());
$captureRules = array(
'events_org' => array('table' => 'events', 'old' => 'org', 'new' => 'org_id'),
@ -2781,9 +2857,9 @@ class Server extends AppModel {
// will result in the same visibility, etc. Once events / attributes get put into a sharing group this will get recorrelated anyway
// Also by unsetting the org field after the move the changes we ensure that these correlations won't get hit again by the script if we rerun it
// and that we don't accidentally "upgrade" a 2.4 correlation
$this->query('UPDATE `correlations` SET `distribution` = 1, `a_distribution` = 1 WHERE `org` != "" AND `private` = 0');
$this->query('UPDATE correlations SET distribution = 1, a_distribution = 1 WHERE org != "" AND private = 0');
foreach ($orgMapping as $old => $new) {
$this->query('UPDATE `correlations` SET `org_id` = "' . $new . '", `org` = "" WHERE `org` = "' . $old . '";');
$this->query('UPDATE correlations SET org_id = "' . $new . '", org = "" WHERE org = "' . $old . '";');
}
if (Configure::read('MISP.background_jobs') && $jobId) {
$this->Job->saveField('progress', 60);

44
app/Model/ServerTag.php Normal file
View File

@ -0,0 +1,44 @@
<?php
App::uses('AppModel', 'Model');
class ServerTag extends AppModel {
public $actsAs = array('Containable');
public $validate = array(
'server_id' => array(
'valueNotEmpty' => array(
'rule' => array('valueNotEmpty'),
),
),
'tag_id' => array(
'valueNotEmpty' => array(
'rule' => array('valueNotEmpty'),
),
),
);
public $belongsTo = array(
'Server' => array(
'className' => 'Server',
),
'Tag' => array(
'className' => 'Tag',
),
);
public function attachTagToServer($server_id, $tag_id) {
$existingAssociation = $this->find('first', array(
'recursive' => -1,
'conditions' => array(
'tag_id' => $tag_id,
'server_id' => $server_id
)
));
if (empty($existingAssociation)) {
$this->create();
if (!$this->save(array('server_id' => $server_id, 'tag_id' => $tag_id))) return false;
}
return true;
}
}

View File

@ -571,7 +571,8 @@ class ShadowAttribute extends AppModel {
$process_id = CakeResque::enqueue(
'default',
'AdminShell',
array('jobGenerateShadowAttributeCorrelation', $jobId)
array('jobGenerateShadowAttributeCorrelation', $jobId),
true
);
$job->saveField('process_id', $process_id);
$this->Log->create();

View File

@ -915,4 +915,21 @@ class User extends AppModel {
}
return $fields;
}
public function getMembersCount() {
// for Organizations List
$fields = array('org_id', 'COUNT(User.id) AS num_members');
$params = array(
'fields' => $fields,
'recursive' => -1,
'group' => array('org_id'),
'order' => array('org_id'),
);
$orgs = $this->find('all', $params);
$usersPerOrg = [];
foreach ($orgs as $key => $value){
$usersPerOrg[$value['User']['org_id']] = $value[0]['num_members'];
}
return $usersPerOrg;
}
}

View File

@ -0,0 +1,222 @@
<?php
App::uses('BaseAuthenticate', 'Controller/Component/Auth');
session_start();
session_regenerate_id();
/*
* custom class for Apache-based authentication
*
* User for ApacheAuthenticate you can pass in settings to which fields, model and additional conditions
* are used. See FormAuthenticate::$settings for more information.
* TODO: clarification needed, text almost the same as in lib/Cake/Controller/Component/Auth/FormAuthenticate.php
*
* CakePHP version 2.8.5
*
* @package Controller.Component.Auth
* @since 2.0
* @see ApacheAuthComponent::$authenticate
*/
class ApacheShibbAuthenticate extends BaseAuthenticate {
/**
* Authentication class
*
* Configuration in app/Config/Config.php is:
*
* 'ApacheShibbAuth' => // Configuration for shibboleth authentication
* array(
* 'apacheEnv' => 'REMOTE_USER', // If proxy variable = HTTP_REMOTE_USER
* 'ssoAuth' => 'AUTH_TYPE', // NOT to modify
* 'MailTag' => 'EMAIL_TAG',
* 'OrgTag' => 'FEDERATION_TAG',
* 'GroupTag' => 'GROUP_TAG',
* 'GroupSeparator' => ';',
* 'GroupRoleMatching' => array( // 3:User, 1:admin. May be good to set "1" for the first user
* 'group_three' => '3',
* 'group_two' => 2,
* 'group_one' => 1,
* ),
* 'DefaultRoleId' => 3,
* 'DefaultOrg' => 'MY_ORG',
* ),
* @param CakeRequest $request The request that contains login information.
* @param CakeResponse $response Unused response object.
* @return mixed False on login failure. An array of User data on success.
*/
public function authenticate(CakeRequest $request, CakeResponse $response)
{
return self::getUser($request);
}
/**
* @return array|bool
*/
public function getUser(CakeRequest $request)
{
//If the url contains sso=disable we return false so the main misp authentication form is used to log in
if(array_key_exists('sso', $request->query) && $request->query['sso'] == 'disable' || $_SESSION["sso_disable"] === True){
$_SESSION["sso_disable"]=True;
return false;
}
// Get Default parameters
$roleId = Configure::read('ApacheShibbAuth.DefaultRoleId');
$org = Configure::read('ApacheShibbAuth.DefaultOrg');
// Get tags from SSO config
$mailTag = Configure::read('ApacheShibbAuth.MailTag');
$OrgTag = Configure::read('ApacheShibbAuth.OrgTag');
$groupTag = Configure::read('ApacheShibbAuth.GroupTag');
$groupRoleMatching = Configure::read('ApacheShibbAuth.GroupRoleMatching');
// Get user values
$mispUsername = $_SERVER[$mailTag];
//Change username column for email (username in shibboleth attributes corresponds to the email in MISPs DB)
$this->settings['fields'] = array('username' => 'email');
// Find user with real username (mail)
$user = $this->_findUser($mispUsername);
//Obtain default org. If not, org keeps the default value
if (isset($_SERVER[$OrgTag])) {
$org = $_SERVER[$OrgTag];
}
//Check if the organization exits and create it if not
$org = $this->checkOrganization($org, $user);
//Get user role from its list of groups
list($roleChanged, $roleId) = $this->getUserRoleFromGroup($groupTag, $groupRoleMatching, $roleId);
// Database model object
$userModel = ClassRegistry::init($this->settings['userModel']);
if ($user) { // User already exists
$user = $this->updateUserRole($roleChanged, $user, $roleId, $userModel);
$user = $this->updateUserOrg($org, $user, $userModel);
return $user;
}
//Insert user in database if not existent
//Generate random password
$password = $this->randPasswordGen(40);
// create user
$userData = array('User' => array(
'email' => $mispUsername,
'org_id' => $org,
'password' => $password, //Since it is done via shibboleth the password will be a random 40 character string
'confirm_password' => $password,
'authkey' => $userModel->generateAuthKey(),
'nids_sid' => 4000000,
'newsread' => date('Y-m-d'),
'role_id' => $roleId,
'change_pw' => 0
));
// save user
$userModel->save($userData, false);
return $this->_findUser(
$mispUsername
);
}
private function randPasswordGen($len){
$result = "";
$chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ\$_?!-0123456789";
$charArray = str_split($chars);
for($i = 0; $i < $len; $i++){
$randItem = array_rand($charArray);
$result .= "".$charArray[$randItem];
}
return $result;
}
/**
* @param $roleChanged
* @param $user
* @param $roleId
* @param $userModel
* @return mixed
*/
public function updateUserRole($roleChanged, $user, $roleId, $userModel)
{
if ($roleChanged && $user['role_id'] != $roleId) {
$user['role_id'] = $roleId; // Different role either increase or decrease permissions
$userUpdatedData = array('User' => $user);
$userModel->set(array(
'role_id' => $roleId,
'id' => $user['id'],
)); // Update the user
$userModel->save($userUpdatedData, false);
return $user;
}
return $user;
}
/**
* @param $groupTag
* @param $groupRoleMatching
* @param $roleId
* @return array
*/
public function getUserRoleFromGroup($groupTag, $groupRoleMatching, $roleId)
{
//Check the role mapping to get the user's role level and update it if needed
$roleChanged = false;
if (isset($_SERVER[$groupTag])) {
$groupSeparator = Configure::read('ApacheShibbAuth.GroupSeparator');
$groupList = explode($groupSeparator, $_SERVER[$groupTag]);
//Check user roles and egroup match and update if needed
foreach ($groupList as $group) {
//TODO: Can be optimized inverting the search group and using only array_key_exists
if (array_key_exists($group, $groupRoleMatching)) { //In case there is an group not defined in the config.php file
$roleVal = $groupRoleMatching[$group];
if ($roleVal <= $roleId) {
$roleId = $roleVal;
$roleChanged = true;
}
}
}
return array($roleChanged, $roleId);
}
return array($roleChanged, $roleId);
}
/**
* @param $org
* @param $user
* @return array|bool|int|mixed|string
*/
public function checkOrganization($org, $user)
{
$orgModel = ClassRegistry::init('Organisation');
$orgAux = $orgModel->find($org);
$orgId = $orgAux['id'];
if ($orgAux == null) {
$organisations = new Organisation();
$orgUserId = 1; //By default created by the admin
if ($user) $orgUserId = $user['id'];
$orgId = $organisations->createOrgFromName($org, $orgUserId, 0); //Created with local set to 0 by default
}
return $orgId;
}
private function updateUserOrg($org, $user, $userModel)
{
if ($user['org_id'] != $org) {
$user['org_id'] = $org; // Different role either increase or decrease permissions
$userUpdatedData = array('User' => $user);
$userModel->set(array(
'org_id' => $org,
'id' => $user['id'],
)); // Update the user
$userModel->save($userUpdatedData, false);
return $user;
}
return $user;
}
}

View File

@ -0,0 +1,50 @@
#Client SSO Authentication (Shibboleth based) for CakePHP
This plugin enables CakePHP applications to use Single Sing-On to authenticate its users. It gets the information given by Apache environment variables.
## Usage
Enable the plugin at bootstrap.php:
```php
CakePlugin::load('ShibbAuth');
```
And configure it at config.php:
Uncomment the following line to enable SSO authorization
```php
'auth'=>array('ShibbAuth.ApacheShibb'),
```
And configure it. apacheEnv ans ssoAuth are parametert that come by default which values should not be changed unless
it is explicitly needed. MailTag, OrgTag and GroupTag are the string that represent the key for the values needed by the plugin.
For example if you are using ADFS OrgTag will be ADFS_FEDERATION, GroupTag will be ADFS_GROUP, etc. meaning the key for the values needed.
DefaultRoleId and DefaultOrg are values that come by default just in case they are not defined or obtained from the environment variables.
The GroupRoleMatching is an array that allows the definition and correlation between groups and roles in MISP, being them updated
if the groups are updated (i.e. a user that was admin and their groups changed inside the organization will have his role changed in MISP
upon the next login being now user or org admin respectively). The GroupSeparator is the character used to separate the different groups
in the list given by apache.
```php
'ApacheShibbAuth' => // Configuration for shibboleth authentication
array(
'apacheEnv' => 'REMOTE_USER', // If proxy variable = HTTP_REMOTE_USER
'ssoAuth' => 'AUTH_TYPE',
'MailTag' => 'EMAIL_TAG',
'OrgTag' => 'FEDERATION_TAG',
'GroupTag' => 'GROUP_TAG',
'GroupSeparator' => ';',
'GroupRoleMatching' => array( // 3:User, 1:admin. May be good to set "1" for the first user
'group_three' => '3',
'group_two' => 2,
'group_one' => 1,
),
'DefaultRoleId' => 3,
'DefaultOrg' => 'DEFAULT_ORG',
),
```

View File

@ -145,7 +145,7 @@
<?php if ($mayModify && !empty($event['objects'])): ?>
<th><input class="select_all" type="checkbox" onClick="toggleAllAttributeCheckboxes();" /></th>
<?php endif;?>
<th><?php echo $this->Paginator->sort('date');?></th>
<th><?php echo $this->Paginator->sort('timestamp', 'Date');?></th>
<th><?php echo $this->Paginator->sort('Org.name', 'Org'); ?>
<th><?php echo $this->Paginator->sort('category');?></th>
<th><?php echo $this->Paginator->sort('type');?></th>

View File

@ -77,7 +77,6 @@
<li><a href="<?php echo $baseurl;?>/news">News</a></li>
<li><a href="<?php echo $baseurl;?>/users/view/me">My Profile</a></li>
<li><a href="<?php echo $baseurl;?>/users/dashboard">Dashboard</a></li>
<li><a href="<?php echo $baseurl;?>/users/memberslist">Members List</a></li>
<li><a href="<?php echo $baseurl;?>/organisations/index">Organisations</a></li>
<li><a href="<?php echo $baseurl;?>/roles/index">Role Permissions</a></li>
<li class="divider"></li>
@ -89,6 +88,7 @@
<li><a href="<?php echo $baseurl;?>/pages/display/doc/quickstart">User Guide</a></li>
<li><a href="<?php echo $baseurl;?>/users/terms">Terms &amp; Conditions</a></li>
<li><a href="<?php echo $baseurl;?>/users/statistics">Statistics</a></li>
<li><a href="<?php echo $baseurl;?>/users/attributehistogram">Attribute Histogram</a></li>
</ul>
</li>
@ -129,7 +129,6 @@
<?php endif; ?>
<?php if ($isSiteAdmin): ?>
<li class="divider"></li>
<li><a href="<?php echo $baseurl;?>/pages/display/administration">Administrative tools</a></li>
<li><a href="<?php echo $baseurl;?>/servers/serverSettings">Server settings</a></li>
<?php if (Configure::read('MISP.background_jobs')): ?>
<li class="divider"></li>

View File

@ -56,7 +56,7 @@
$message = 'Directory ' . $message;
$colour = 'red';
}
echo 'app/' . $dir . '.....<span style="color:' . $colour . ';">' . $message . '</span><br />';
echo $dir . '.....<span style="color:' . $colour . ';">' . $message . '</span><br />';
}
?>
</div>
@ -188,8 +188,13 @@
endif;
?>
<h3>
Clean model cache
Clean model cache
</h3>
<p>If you ever run into issues with missing database fields / tables, please run the following script to clean the model cache.</p>
<?php echo $this->Form->postLink('<span class="btn btn-inverse" style="padding-top:1px;padding-bottom:1px;">Clean cache</span>', $baseurl . '/events/cleanModelCaches', array('escape' => false));?>
<h3>
Legacy Administrative Tools
</h3>
<p>Click the following button to go to the legacy administrative tools page. There should in general be no need to do this unless you are upgrading a very old MISP instance (<2.4), all updates are done automatically with more current versions.</p>
<span class="btn btn-inverse" style="padding-top:1px;padding-bottom:1px;" onClick="location.href = '<?php echo $baseurl; ?>/pages/display/administration';">Legacy Administrative Tools</span>
</div>

View File

@ -29,7 +29,14 @@
?>
<h3><?php echo 'Worker type: ' . h($type);?></h3>
<?php if ($type !== 'scheduler'): ?>
<p><b>Jobs in the queue: </b><?php echo h($data['jobCount']);?></p>
<span><b>Jobs in the queue: </b>
<?php
echo h($data['jobCount']);
if ($data['jobCount'] > 0) {
echo $this->Form->postLink('<span class="icon-trash useCursorPointer"></span>', $baseurl . '/servers/clearWorkerQueue/' . h($type), array('escape' => false, 'inline' => true, 'style' => 'margin-left:2px;'));
}
?>
</span>
<p><b>Queue status: </b>
<?php
$color = "green";

View File

@ -1,7 +1,37 @@
<h2>Attribute Types Histogram</h2>
<table>
<tr>
<td class="membersList-histogram-left-table">
<td colspan="2"><h4 class="histogram-legendH4">Attributes</h4> (you can also choose specific histogram items by clicking on attributes below)</td>
</tr>
<tr>
<td class="attributehistogram-legend">
<div class="attributehistogram-legend-line col">
<?php
$cnt = 0;
foreach ($typeDb as $type => $colour):
?>
<div class="attributehistogram-legend-line">
<div class="attributehistogram-legend-box" style="display: block;float: left;margin: 4px 6px 0 0;background-color:<?php echo $colour; ?>">&nbsp;</div>
<div style="display: inline-block;cursor: pointer;<?php if (in_array($type, $selectedTypes)) echo 'font-weight:bold';?>" onClick='toggleHistogramType("<?php echo $type; ?>", [<?php foreach ($selectedTypes as $t) echo '"' . $t . '", ' ?>]);'><?php echo $type;?></div>
</div>
<?php
if ($cnt % 12 == 11):
?>
</div>
<div class="attributehistogram-legend-line col">
<?php
endif;
$cnt++;
endforeach;
?>
</div>
</td>
</tr>
<tr>
<td colspan="2"><h4 >Attributes per organization</h4></td>
</tr>
<tr>
<td class="attributehistogram-left-table">
<table style="border-spacing:0px !important;">
<?php
end($data);
@ -10,29 +40,23 @@
?>
<tr>
<td style="text-align:right"><?php echo h($k);?></td>
<td <?php echo ($k == $lastElement ? 'class="membersList-histogram-last"' : '');?> style="border-left:1px solid;padding-left:0px;width:500px;border-spacing:0px !important;">
<ul style="width:<?php echo 600 * $org['total'] / $max;?>px;" class="memberslistBar">
<td <?php echo ($k == $lastElement ? 'class="attributehistogram-last"' : '');?> style="border-left:1px solid;padding-left:0px;width:500px;border-spacing:0px !important;">
<ul style="width:<?php echo 600 * $org['total'] / $max;?>px;" class="attributehistogramBar">
<?php
foreach ($org['data'] as $orgType => $orgTypeCount):
?>
<li title="<?php echo h($orgType) . ' : ' . $orgTypeCount; ?>" class="type_<?php echo h($orgType); ?>" style="display:block;height:30px;float:left;width:<?php echo (100 * $orgTypeCount / $org['total']);?>%;background:<?php echo $typeDb[$orgType];?>">&nbsp;</li>
<?php endforeach;?>
<li title="<?php echo h($orgType) . ' : ' . $orgTypeCount; ?>" class="type_<?php echo h($orgType); ?>" style="display:block;height:30px;float:left;width:<?php echo (100 * $orgTypeCount / $org['total']);?>%;background:<?php echo $typeDb[$orgType];?>">&nbsp;</li>
<?php
endforeach;
?>
</ul>
</td>
</tr>
<?php endforeach; ?>
<?php
endforeach;
?>
</table>
</td>
<td class="membersList-histogram-legend">
<?php foreach ($typeDb as $type => $colour): ?>
<div class="membersList-histogram-legend-line">
<div class="membersList-histogram-legend-box" style="background-color:<?php echo $colour; ?>">&nbsp;</div>
<div style="display: inline-block;<?php if (in_array($type, $selectedTypes)) echo 'font-weight:bold';?>" onClick='toggleHistogramType("<?php echo $type; ?>", [<?php foreach ($selectedTypes as $t) echo '"' . $t . '", ' ?>]);'><?php echo $type;?></div>
</div>
<?php
endforeach;
?>
</td>
</tr>
</table>

View File

@ -32,9 +32,7 @@
<li><?php echo $this->Form->postLink('Delete Event', array('action' => 'delete', h($event['Event']['id'])), null, __('Are you sure you want to delete # %s?', h($event['Event']['id']))); ?></li>
<li id='liaddAttribute'><a href="<?php echo $baseurl;?>/attributes/add/<?php echo h($event['Event']['id']);?>">Add Attribute</a></li>
<li id='liaddAttachment'><a href="<?php echo $baseurl;?>/attributes/add_attachment/<?php echo h($event['Event']['id']);?>">Add Attachment</a></li>
<li id='liaddFreetext'><a href="#" onClick="getPopup(<?php echo $event['Event']['id']; ?>, 'events', 'freeTextImport');">Populate via Freetext Import</a></li>
<li id='liaddIOC'><a href="<?php echo $baseurl;?>/events/addIOC/<?php echo h($event['Event']['id']);?>">Populate from OpenIOC</a></li>
<li id='liaddThreatConnect'><a href="<?php echo $baseurl;?>/attributes/add_threatconnect/<?php echo h($event['Event']['id']); ?>">Populate from ThreatConnect</a></li>
<li id='import'><a onClick="getPopup('<?php echo h($event['Event']['id']); ?>', 'events', 'importChoice');" style="cursor:pointer;">Populate from...</a></li>
<?php if ($menuItem === 'populateFromtemplate'): ?>
<li class="active"><a href="<?php echo $baseurl;?>/templates/populateEventFromTemplate/<?php echo $template_id . '/' . h($event['Event']['id']); ?>">Populate From Template</a></li>
<?php endif; ?>
@ -140,7 +138,6 @@
<?php endif; ?>
<li id='liview'><a href="<?php echo $baseurl;?>/users/view/me">My Profile</a></li>
<li id='lidashboard'><a href="<?php echo $baseurl;?>/users/dashboard">Dashboard</a></li>
<li id='limembers'><a href="<?php echo $baseurl;?>/users/memberslist">Members List</a></li>
<li id='liindexOrg'><a href="<?php echo $baseurl;?>/organisations/index">List Organisations</a></li>
<?php if ($menuItem === 'viewOrg'): ?>
<li class="active"><a href="<?php echo $baseurl;?>/organisations/view/<?php echo h($id);?>">View Organisation</a></li>
@ -157,6 +154,7 @@
<li id='liuserGuide'><a href="<?php echo $baseurl;?>/pages/display/doc/general">User Guide</a></li>
<li id='literms'><a href="<?php echo $baseurl;?>/users/terms">Terms &amp; Conditions</a></li>
<li id='listatistics'><a href="<?php echo $baseurl;?>/users/statistics">Statistics</a></li>
<li id='limembers'><a href="<?php echo $baseurl;?>/users/attributehistogram">Attribute Histogram</a></li>
<?php
break;
@ -184,7 +182,7 @@
case 'admin':
if ($menuItem === 'editUser' || $menuItem === 'viewUser'): ?>
<li id='liviewUser'><?php echo $this->Html->link('View User', array('controller' => 'users', 'action' => 'view', 'admin' => true, h($id))); ?> </li>
<li><a href="#/" onClick="initiatePasswordReset('<?php echo h($id); ?>');">Send Credentials</a></li>
<li><a href="#/" onClick="initiatePasswordReset('<?php echo h($id); ?>');">Reset Password</a></li>
<li id='lieditUser'><?php echo $this->Html->link('Edit User', array('controller' => 'users', 'action' => 'edit', 'admin' => true, h($id))); ?> </li>
<li><?php echo $this->Form->postLink('Delete User', array('admin' => true, 'action' => 'delete', h($id)), null, __('Are you sure you want to delete # %s? It is highly recommended to never delete users but to disable them instead.', h($id)));?></li>
<li class="divider"></li>
@ -218,7 +216,6 @@
<li id='liindexRole'><?php echo $this->Html->link('List Roles', array('controller' => 'roles', 'action' => 'index', 'admin' => true)); ?> </li>
<?php if ($isSiteAdmin): ?>
<li class="divider"></li>
<li id='liadminTools'><a href="<?php echo $baseurl;?>/pages/display/administration">Administrative Tools</a></li>
<li id='liserverSettings'><a href="<?php echo $baseurl;?>/servers/serverSettings">Server Settings</a></li>
<li class="divider"></li>
<?php if (Configure::read('MISP.background_jobs')): ?>

View File

@ -1,30 +1,36 @@
<div class="confirmation">
<?php
echo $this->Form->create('Event', array('style' => 'margin:0px;', 'id' => 'PromptForm', 'url' => '/events/' . $type . '/' . $id));
$extraTitle = "";
if ($type == 'publish') $extraTitle = ' (no email)';
?>
<legend>Publish Event<?php echo $extraTitle; ?></legend>
<div style="padding-left:5px;padding-right:5px;padding-bottom:5px;">
<?php if ($type == 'alert'): ?>
<p>Are you sure this event is complete and everyone should be informed?</p>
<?php else: ?>
<p>Publish but do NOT send alert email? Only for minor changes!</p>
<?php endif; ?>
<table>
<tr>
<td style="vertical-align:top">
<span id="PromptYesButton" class="btn btn-primary" onClick="submitPublish()">Yes</span>
</td>
<td style="width:540px;">
</td>
<td style="vertical-align:top;">
<span class="btn btn-inverse" id="PromptNoButton" onClick="cancelPrompt();">No</span>
</td>
</tr>
</table>
</div>
<?php
echo $this->Form->end();
?>
<?php
echo $this->Form->create('Event', array('style' => 'margin:0px;', 'id' => 'PromptForm', 'url' => '/events/' . $type . '/' . $id));
$extraTitle = "";
if ($type == 'publish') $extraTitle = ' (no email)';
?>
<legend>Publish Event<?php echo $extraTitle; ?></legend>
<div style="padding-left:5px;padding-right:5px;padding-bottom:5px;">
<?php
if ($type == 'alert'):
?>
<p>Are you sure this event is complete and everyone should be informed?</p>
<?php
else:
?>
<p>Publish but do NOT send alert email? Only for minor changes!</p>
<?php
endif;
?>
<table>
<tr>
<td style="vertical-align:top">
<span id="PromptYesButton" class="btn btn-primary" onClick="submitPublish()">Yes</span>
</td>
<td style="width:540px;">
</td>
<td style="vertical-align:top;">
<span class="btn btn-inverse" id="PromptNoButton" onClick="cancelPrompt();">No</span>
</td>
</tr>
</table>
</div>
<?php
echo $this->Form->end();
?>
</div>

View File

@ -0,0 +1,22 @@
<div class="popover_choice">
<legend><?php echo __('Choose the format that you would like to use for the import'); ?></legend>
<div class="popover_choice_main" id ="popover_choice_main">
<table style="width:100%;">
<?php foreach ($imports as $k => $import): ?>
<tr style="border-bottom:1px solid black;" class="templateChoiceButton">
<td style="padding-left:10px; text-align:center;width:100%;" onClick="importChoiceSelect('<?php echo h($import['url']); ?>', '<?php echo h($k); ?>', '<?php echo $import['ajax'] ? h($import['target']) : "false"; ?>')"><?php echo h($import['text']); ?></td>
</tr>
<?php endforeach; ?>
</table>
</div>
<div class="templateChoiceButton templateChoiceButtonLast" onClick="cancelPopoverForm();">Cancel</div>
</div>
<script type="text/javascript">
$(document).ready(function() {
resizePopoverBody();
});
$(window).resize(function() {
resizePopoverBody();
});
</script>

View File

@ -0,0 +1,127 @@
<div class="events form">
<?php echo $this->Form->create('', array('type' => 'file'));?>
<fieldset>
<legend><?php echo h(Inflector::humanize($module['name']));?></legend>
<?php
if (isset($module['mispattributes']['userConfig']) && !empty($module['mispattributes']['userConfig'])) {
foreach ($module['mispattributes']['userConfig'] as $configName => $config) {
$settings = array(
'label' => false,
'div' => false
);
if (isset($configTypes[$config['type']]['class'])) {
$settings['class'] = $configTypes[$config['type']]['class'];
}
if (isset($configTypes[$config['type']]['field'])) {
$settings['type'] = $configTypes[$config['type']]['field'];
}
?>
<span class="bold">
<?php
echo ucfirst(h($configName));
?>
</span><br />
<?php
if ($settings['type'] == 'checkbox'):
echo $this->Form->input('Event.config.' . $configName, $settings);
if (isset($config['message']) && !empty($config['message'])):
echo h($config['message']);
?>
<br />
<?php
endif;
else:
if (isset($config['message']) && !empty($config['message'])):
?>
<p><?php echo h($config['message']); ?></p>
<?php
endif;
echo $this->Form->input('Event.config.' . $configName, $settings);
endif;
?>
<div class="input clear"></div><br />
<?php
}
}
$source = 'paste';
if (in_array('paste', $module['mispattributes']['inputSource']) && in_array('file', $module['mispattributes']['inputSource'])) {
$source = 'both';
} else if (in_array('file', $module['mispattributes']['inputSource'])) {
$source = 'file';
}
?>
<?php
echo $this->Form->input('Event.source', array(
'label' => false,
'checked' => $source == 'file' ? true : false,
'disabled' => $source == 'both' ? false : true,
'div' => false,
'style' => 'margin-bottom:5px;'
));
?>
<span class="bold">
File upload
</span>
<div class="input clear"></div>
<div id="pasteDiv">
<p class="bold">
Paste Input
</p>
<?php
if (in_array('paste', $module['mispattributes']['inputSource'])) {
echo $this->Form->input('Event.paste', array(
'label' => false,
'type' => 'textarea',
'class' => 'input-xxlarge',
'rows' => 12,
'div' => false
));
}
?>
</div>
<div class="input clear"></div>
<div id="fileDiv">
<p class="bold">
Input File
</p>
<?php
if (in_array('file', $module['mispattributes']['inputSource'])) {
echo $this->Form->input('Event.fileupload', array(
'label' => false,
'type' => 'file',
'div' => 'clear'
));
}
?>
</div>
<div class="input clear"></div>
</fieldset>
<?php
echo $this->Form->button('Import', array('class' => 'btn btn-primary'));
echo $this->Form->end();
?>
</div>
<?php
echo $this->element('side_menu', array('menuList' => 'event-collection', 'menuItem' => 'import'));
?>
<script type="text/javascript">
$(document).ready(function() {
changeImportSource();
$('#EventSource').change(function() {
changeImportSource();
});
});
function changeImportSource() {
if ($('#EventSource').is(':checked')) {
$('#fileDiv').show();
$('#pasteDiv').hide();
} else {
$('#fileDiv').hide();
$('#pasteDiv').show();
};
}
</script>

View File

@ -165,46 +165,46 @@
<?php endif;?>
</dl>
</div>
<?php if (!empty($event['RelatedEvent'])):?>
<div class="related span4">
<h3>Related Events</h3>
<ul class="inline">
<?php foreach ($event['RelatedEvent'] as $relatedEvent): ?>
<li>
<?php
$relatedData = array('Orgc' => $relatedEvent['Orgc']['name'], 'Date' => $relatedEvent['Event']['date'], 'Info' => $relatedEvent['Event']['info']);
$popover = '';
foreach ($relatedData as $k => $v) {
$popover .= '<span class=\'bold\'>' . h($k) . '</span>: <span class="blue">' . h($v) . '</span><br />';
}
?>
<div data-toggle="popover" data-content="<?php echo h($popover); ?>" data-trigger="hover">
<?php
$linkText = $relatedEvent['Event']['date'] . ' (' . $relatedEvent['Event']['id'] . ')';
if ($relatedEvent['Event']['org_id'] == $me['org_id']) {
echo $this->Html->link($linkText, array('controller' => 'events', 'action' => 'view', $relatedEvent['Event']['id'], true, $event['Event']['id']), array('style' => 'color:red;'));
} else {
echo $this->Html->link($linkText, array('controller' => 'events', 'action' => 'view', $relatedEvent['Event']['id'], true, $event['Event']['id']));
}
?>
</div></li>
<?php endforeach; ?>
</ul>
<?php if (!empty($event['Event']['warnings'])): ?>
<div class="warning_container" style="width:80%;">
<h4 class="red">Warning: Potential false positives</h4>
<?php
$total = count($event['Event']['warnings']);
$current = 1;
foreach ($event['Event']['warnings'] as $id => $name) {
echo '<a href="' . $baseurl . '/warninglists/view/' . $id . '">' . h($name) . '</a>' . ($current == $total ? '' : '<br />');
$current++;
<div class="related span4">
<?php if (!empty($event['RelatedEvent'])):?>
<h3>Related Events</h3>
<ul class="inline">
<?php foreach ($event['RelatedEvent'] as $relatedEvent): ?>
<li>
<?php
$relatedData = array('Orgc' => $relatedEvent['Orgc']['name'], 'Date' => $relatedEvent['Event']['date'], 'Info' => $relatedEvent['Event']['info']);
$popover = '';
foreach ($relatedData as $k => $v) {
$popover .= '<span class=\'bold\'>' . h($k) . '</span>: <span class="blue">' . h($v) . '</span><br />';
}
?>
</div>
<?php endif; ?>
</div>
<?php endif; ?>
?>
<div data-toggle="popover" data-content="<?php echo h($popover); ?>" data-trigger="hover">
<?php
$linkText = $relatedEvent['Event']['date'] . ' (' . $relatedEvent['Event']['id'] . ')';
if ($relatedEvent['Event']['org_id'] == $me['org_id']) {
echo $this->Html->link($linkText, array('controller' => 'events', 'action' => 'view', $relatedEvent['Event']['id'], true, $event['Event']['id']), array('style' => 'color:red;'));
} else {
echo $this->Html->link($linkText, array('controller' => 'events', 'action' => 'view', $relatedEvent['Event']['id'], true, $event['Event']['id']));
}
?>
</div></li>
<?php endforeach; ?>
</ul>
<?php endif; ?>
<?php if (!empty($event['Event']['warnings'])): ?>
<div class="warning_container" style="width:80%;">
<h4 class="red">Warning: Potential false positives</h4>
<?php
$total = count($event['Event']['warnings']);
$current = 1;
foreach ($event['Event']['warnings'] as $id => $name) {
echo '<a href="' . $baseurl . '/warninglists/view/' . $id . '">' . h($name) . '</a>' . ($current == $total ? '' : '<br />');
$current++;
}
?>
</div>
<?php endif; ?>
</div>
</div>
<br />
<div class="toggleButtons">

View File

@ -47,7 +47,7 @@
<?php endforeach; ?>
</td>
<td class="short" ondblclick="document.location.href ='<?php echo $eventViewURL . h($uuid);?>'">
<?php echo $event['date']; ?>&nbsp;
<?php echo h($event['date']); ?>&nbsp;
</td>
<td class="short" ondblclick="document.location.href ='<?php echo $eventViewURL . h($uuid);?>'">
<?php

View File

@ -58,8 +58,32 @@
<th><?php echo $this->Paginator->sort('status');?></th>
<th><?php echo $this->Paginator->sort('retries');?></th>
<th><?php echo $this->Paginator->sort('progress');?></th>
</tr><?php
foreach ($list as $k => $item): ?>
</tr>
<?php
foreach ($list as $k => $item):
$progress = '100';
$startRefreshing = false;
if ($item['Job']['failed']) {
$progress_message = 'Failed';
$progress_bar_type = 'progress progress-danger active';
} else if (!$item['Job']['worker_status'] && $item['Job']['progress'] != 100) {
$progress_message = 'No worker active';
$progress_bar_type = 'progress progress-striped progress-warning active';
} else if ($item['Job']['progress'] == 0) {
$progress_bar_type = 'progress progress-striped progress-queued active';
$progress_message = 'Queued';
} else {
$progress = h($item['Job']['progress']);
if ($item['Job']['progress'] == 100) {
$progress_bar_type = 'progress';
$progress_message = 'Completed';
} else {
$progress_bar_type = 'progress progress-striped';
$progress_message = $item['Job']['progress'] . '%';
$startRefreshing = true;
}
}
?>
<tr>
<td class="short"><?php echo h($item['Job']['id']); ?>&nbsp;</td>
<td class="short"><?php echo h($item['Job']['date_created']); ?>&nbsp;</td>
@ -70,22 +94,34 @@
<td class="short"><?php echo h($item['Job']['job_input']); ?>&nbsp;</td>
<td><?php echo h($item['Job']['message']); ?>&nbsp;</td>
<td class="short"><?php echo isset($item['Org']['name']) ? h($item['Org']['name']) : 'SYSTEM'; ?>&nbsp;</td>
<td class="short"><?php echo h($item['Job']['status']); ?>&nbsp;</td>
<td class="short">
<?php
echo h($item['Job']['status']);
if ($item['Job']['failed']):
?>
<div class="icon-search useCursorPointer queryPopover" data-url="/jobs/getError" data-id="<?php echo h($item['Job']['process_id']); ?>"></div>
<?php
endif;
?>
</td>
<td class="short"><?php echo h($item['Job']['retries']); ?>&nbsp;</td>
<td style="width:200px;">
<div class="progress progress-striped active" style="margin-bottom: 0px;">
<div id="bar<?php echo h($item['Job']['id']); ?>" class="bar" style="width: <?php echo h($item['Job']['progress']); ?>%;">
<div class="<?php echo $progress_bar_type; ?>" style="margin-bottom: 0px;">
<div id="bar<?php echo h($item['Job']['id']); ?>" class="bar" style="width: <?php echo $progress; ?>%;">
<?php
if ($item['Job']['progress'] > 0 && $item['Job']['progress'] < 100) echo h($item['Job']['progress']) . '%';
if ($item['Job']['progress'] == 100) echo 'Completed.';
echo h($progress_message);
?>
</div>
</div>
<?php if ($item['Job']['progress'] != 100): ?>
<script type="text/javascript">
queueInterval("<?php echo $k; ?>", "<?php echo h($item['Job']['id']); ?>");
</script>
<?php endif; ?>
<?php
if ($startRefreshing):
?>
<script type="text/javascript">
queueInterval("<?php echo $k; ?>", "<?php echo h($item['Job']['id']); ?>");
</script>
<?php
endif;
?>
</td>
</tr><?php
endforeach; ?>

View File

@ -7,6 +7,9 @@
<?php echo $title_for_layout, ' - MISP'; ?>
</title>
<?php
if (!isset($debugMode)) {
$debugMode == 'debugOff';
}
echo $this->Html->meta('icon');
echo $this->Html->css('roboto');
echo $this->Html->css('bootstrap');

View File

@ -1,6 +1,6 @@
<div class="events">
<?php echo $this->Form->create('Organisation', array(
'onsubmit' => 'return confirm("This will remove the selected organisation and hand over all objects belonging to it to the target organisation. This process is irreversible. Are you sure you");',
'onsubmit' => 'return confirm("This will remove the selected organisation and hand over all objects belonging to it to the target organisation. This process is irreversible. Are you sure you want to proceed?");',
));?>
<div class="legend">Merge Organisation</div>
<p class="red-background white">Warning: Merging an organisation into another will be transfer all users and data belonging to the organisation to another.</p>

View File

@ -61,6 +61,7 @@ echo $this->Paginator->next(__('next') . ' &raquo;', array('tag' => 'li', 'escap
<th>Added by</th>
<?php endif; ?>
<th><?php echo $this->Paginator->sort('local');?></th>
<th>Users</th>
<th class="actions">Actions</th>
</tr>
<?php
@ -88,6 +89,7 @@ foreach ($orgs as $org): ?>
<td class="short" ondblclick="document.location.href ='/organisations/view/<?php echo $org['Organisation']['id'];?>'"><?php echo h($org_creator_ids[$org['Organisation']['created_by']]); ?></td>
<?php endif; ?>
<td class="short <?php echo $org['Organisation']['local'] ? 'green' : 'red';?>" ondblclick="document.location.href ='/organisations/view/<?php echo $org['Organisation']['id'];?>'"><?php echo $org['Organisation']['local'] ? 'Yes' : 'No';?></td>
<td class="short"><?php echo isset($members[$org['Organisation']['id']]) ? $members[$org['Organisation']['id']] : '0';?></td>
<td class="short action-links">
<?php if ($isSiteAdmin): ?>
<a href='/admin/organisations/edit/<?php echo $org['Organisation']['id'];?>' class = "icon-edit" title = "Edit"></a>

View File

@ -55,7 +55,7 @@
<ul>
<li><b>News:</b> Read about the latest news regarding the MISP system</li>
<li><b>My Profile:</b> Manage your user account.</li>
<li><b>Members List:</b> View the number of users per organisation and get some statistics about the currently stored attributes.</li>
<li><b>Attribute Histogram:</b> View some statistics about the currently stored attributes.</li>
<li><b>Role Permissions:</b> You can view the role permissions here. </li>
<li><b>User Guide:</b> A link to this user guide.</li>
<li><b>Terms &amp; Conditions:</b> View the terms &amp; conditions again.</li>

View File

@ -49,7 +49,7 @@ To alter any details regarding your profile, use the "My Profile" menu button to
MISP also provides its users with some information about itself and its users through the links provided in the Global Actions menu.<br><br>
<ul>
<li><b>News:</b> To read about the news regarding the system itself, click on News on the left menu. This will bring up a list of news items concerning updates and changes to MISP itself.<br /><br /></li>
<li><b>Member statistics:</b> By using the Members List menu button on the left, you can get a quick overview over how many users each organisation has registered on your server, and a histogram, depicting the distribution of attribute types created by each organisation.<br /><br /></li>
<li><b>Member statistics:</b> By using the Attribute Histogram menu button on the left, you can see a quick histogram depicting the distribution of attribute types created by each organisation.<br /><br /></li>
<li><b>User Guide:</b> The user guide is also accessible via the Global Actions menu. You can find out more about how to use the system by reading this.<br /><br /></li>
<li><b>Terms &amp; Conditions:</b> It is possible to review the terms &amp; conditions that were shown during the first run of the system by clicking on the terms &amp; conditions link in the Global Actions menu.<br /><br /></li>
<li><b>Statistics:</b> View statistics about the users and the data contained within this instance.

View File

@ -52,6 +52,7 @@
<div class = "input clear"></div>
<?php
echo $this->Form->input('authkey', array(
'placeholder' => 'Leave empty to use current key'
));
?>
<div class = "input clear"></div>

View File

@ -28,8 +28,6 @@
<th><?php echo $this->Paginator->sort('client_cert_file');?></th>
<th><?php echo $this->Paginator->sort('self_signed');?></th>
<th><?php echo $this->Paginator->sort('org');?></th>
<th>Last Pulled ID</th>
<th>Last Pushed ID</th>
<th class="actions">Actions</th>
</tr>
<?php
@ -74,8 +72,6 @@ foreach ($servers as $server):
<td class="short"><?php echo h($server['Server']['client_cert_file']); ?>&nbsp;</td>
<td class="short"><span class="<?php echo ($server['Server']['self_signed'] ? 'icon-ok' : 'icon-remove'); ?>"></span></td>
<td class="short"><a href="/organisations/view/<?php echo h($server['Organisation']['id']); ?>"><?php echo h($server['Organisation']['name']); ?></a></td>
<td class="short"><?php echo $server['Server']['lastpulledid']; ?></td>
<td class="short"><?php echo $server['Server']['lastpushedid']; ?></td>
<td class="short action-links">
<?php
echo $this->Html->link('', array('action' => 'previewIndex', $server['Server']['id']), array('class' => 'icon-search', 'title' => 'Explore'));

View File

@ -0,0 +1,14 @@
<div class="users index">
<div id = "histogram"></div>
<?php //echo $this->element('histogram');?>
<br /><br />
</div>
<?php
echo $this->element('side_menu', array('menuList' => 'globalActions', 'menuItem' => 'members'));
?>
<script type="text/javascript">
// tooltips
$(document).ready(function () {
updateHistogram('');
});
</script>

View File

@ -1,35 +0,0 @@
<div class="users index">
<h2>Members</h2>
<table class="table table-striped table-condensed table-bordered" style="width:300px;">
<tr>
<th>Organisation</th>
<th># of members</th>
<th>Logo</th>
</tr>
<?php
foreach ($orgs as $org):?>
<tr>
<td><a href="<?php echo $baseurl; ?>/organisations/view/<?php echo h($org['Organisation']['id']);?>"><?php echo h($org['Organisation']['name']); ?></a>&nbsp;</td>
<td><?php echo h($org[0]['num_members']); ?>&nbsp;</td>
<?php
$imgRelativePath = 'orgs' . DS . h($org['Organisation']['name']) . '.png';
$imgAbsolutePath = APP . WEBROOT_DIR . DS . 'img' . DS . $imgRelativePath;
?>
<td><?php if (file_exists($imgAbsolutePath)) echo $this->Html->image('orgs/' . h($org['Organisation']['name']) . '.png', array('alt' => h($org['Organisation']['name']),'width' => '48','hight' => '48'));?>&nbsp;</td>
</tr>
<?php
endforeach; ?>
</table>
<div id = "histogram"></div>
<?php //echo $this->element('histogram');?>
<br /><br />
</div>
<?php
echo $this->element('side_menu', array('menuList' => 'globalActions', 'menuItem' => 'members'));
?>
<script type="text/javascript">
// tooltips
$(document).ready(function () {
updateHistogram('');
});
</script>

Some files were not shown because too many files have changed in this diff Show More