Started integrating external systems

This commit is contained in:
2026-07-23 14:48:30 +02:00
parent 8e218fd4ba
commit 4abb94b88c
21 changed files with 485 additions and 33 deletions
+1 -1
View File
@@ -2,7 +2,7 @@
/*****************************************************************************
IP Reg, a PHP/MySQL IPAM tool
Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)
Copyright (C) 2011-2023 Thomas Hooge
Copyright (C) 2011-2026 Thomas Hooge
SPDX-License-Identifier: GPL-3.0-or-later
*****************************************************************************/
+27 -5
View File
@@ -141,6 +141,7 @@ $sth = $dbh->prepare($sql);
$sth->execute($p);
$smarty->assign("assets", $sth->fetchAll());
$smarty->assign("extlink", extlink_enabled());
$smarty->display("asset.tpl");
elseif ($action == ACT_ADD):
@@ -192,24 +193,45 @@ $smarty->assign("nodes", $sth->fetchAll(PDO::FETCH_ASSOC));
// external systems
// extlink_id
// asset_id
// Type: enum('cdb','zabbix','topdesk', osticket
// Type: enum('cdb','zabbix','topdesk', osticket, loginventory
// ID: extlink_refid int
// extlink_uid string
// $smarty->assign('zabbix', print_r($config_ext['zabbix']['host'],true));
if ($config_ext['zabbix']['enabled']) {
$smarty->assign("zabbix", true);
$sql = "SELECT extlink_refid FROM extlink WHERE extlink_type='zabbix' AND asset_id=?";
$sth = $dbh->prepare($sql);
$sth->execute([$id]);
$refid = $sth->fetchColumn();
// TODO fetch ext data here
//$zbx = new PDO('mysql:host='.$config_ext['zabbix']['host'].';dbname='.$config_ext['zabbix']['db'].';', $config_ext['zabbix']['user'], $config_ext['zabbix']['pass']);
//$zbx->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
//$zbx->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
$zbxconn = false;
try {
$zbx = new PDO('mysql:host='.$config_ext['zabbix']['host'].';dbname='.$config_ext['zabbix']['db'].';', $config_ext['zabbix']['user'], $config_ext['zabbix']['pass']);
$zbx->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$zbx->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
$zbxconn = true;
} catch (Exception $e) {
$refid = "not_connected:" . $e->getMessage();
}
if ($zbxconn) {
$sql = "SELECT host FROM hosts WHERE hostid=?";
$sth = $zbx->prepare($sql);
$sth->execute([$refid]);
$zbx_hostname = $sth->fetchColumn();
if ($zbx_hostname === false) {
$zbx_hostname = 'not found';
}
$smarty->assign('zbx_hostname', $zbx_hostname);
$zbx = NULL; // close
}
$smarty->assign('refid', $refid);
}
$smarty->assign("extlink", extlink_enabled());
$smarty->display("assetview.tpl");
elseif ($action == ACT_EDIT):
+3 -1
View File
@@ -2,7 +2,7 @@
/*****************************************************************************
IP Reg, a PHP/MySQL IPAM tool
Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)
Copyright (C) 2011-2023 Thomas Hooge
Copyright (C) 2011-2026 Thomas Hooge
SPDX-License-Identifier: GPL-3.0-or-later
*****************************************************************************/
@@ -27,6 +27,7 @@ $config_lang_default = 'en';
// auth
$config_auth_ldap = false;
$config_ldap_host = array('localhost', 'otherhost.example.com');
$config_ldap_scheme = 'ldap://'
$config_ldap_port = 389;
$config_ldap_v3 = true;
$config_ldap_base_dn = 'ou=organizationalunit,dc=example,dc=com';
@@ -40,6 +41,7 @@ $config_ldap_bind_pass = 'secret';
$config_ext[] = [
'zabbix' => ['enabled' => false,
'host' => 'localhost',
'port' => 3306,
'db' => 'zabbix',
'user' => 'ipreg',
'pass' => 'topsecret']
+133
View File
@@ -0,0 +1,133 @@
<?php
/*****************************************************************************
IP Reg, a PHP/MySQL IPAM tool
Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)
Copyright (C) 2011-2023 Thomas Hooge
SPDX-License-Identifier: GPL-3.0-or-later
*****************************************************************************/
include("includes.php");
// ========== ACTIONS START ===================================================
switch ($submit = form_get_action()) {
case NULL: break;
case 'edit': $action = ACT_EDIT; break;
case 'pfsense':
if ($_FILES['xmlfile']['size'] == 0) {
$action = ACT_DEFAULT;
break;
}
$action = ACT_EDIT;
break;
case 'exec-pfsense':
$g_message->Add(print_r($_SESSION['pfimport'], true));
unset($_SESSION['pfimport']);
$action = ACT_DEFAULT;
break;
default:
$g_error->Add(submit_error($submit));
$valid = FALSE;
}
// ========== ACTIONS END =====================================================
$smarty->assign("scripts", 'checkbox.js');
include("header.php");
if ($action == ACT_DEFAULT):
// ========== VARIANT: default behavior =======================================
$smarty->display("import.tpl");
elseif ($action == ACT_EDIT):
// ========== VARIANT: edit display options ===================================
$smarty->assign("xmlfile",$_FILES['xmlfile']['name']);
$smarty->assign("xmlfiletype", $_FILES['xmlfile']['type']);
$smarty->assign("xmltmp", $_FILES['xmlfile']['tmp_name']);
$uploadfile = '/var/www/html/ipreg/import/'. basename($_FILES['xmlfile']['tmp_name']);
if (! move_uploaded_file($_FILES['xmlfile']['tmp_name'], $uploadfile)) {
$smarty->display("import.tpl");
$smarty->display('footer.tpl');
exit;
}
$xml = simplexml_load_file($uploadfile);
$conf_alias = $xml->xpath('/pfsense/aliases/alias');
$alias = array();
foreach ($conf_alias as $a) {
if ($a->type == 'host') {
$host = explode(' ', $a->address);
if (count($host) == 1) {
$alias[(string) $a->name] = $host[0];
}
}
}
$wanip = (string) $xml->xpath('/pfsense/interfaces/wan/ipaddr')[0];
$nat = $xml->xpath('/pfsense/nat/rule');
$res = array();
$ruleid = 0;
// for database checks
$sql = "SELECT COUNT(*)
FROM nat
JOIN node AS n1 ON nat.nat_ext=n1.node_id
JOIN node AS n2 ON nat.nat_int=n2.node_id
WHERE n1.node_ip=? AND n2.node_ip=?";
$sth = $dbh->prepare($sql);
foreach ($nat as $n) {
if (! $n->destination->address) {
if ($n->destination->network == 'wanip') {
$nat_ext = ip2long($wanip);
} else {
$nat_ext = ip2long((string) $n->destination->network);
}
} else {
$nat_ext = ip2long((string) $n->destination->address);
};
$nat_ext_port = (int) $n->destination->port;
$tgt = (string) $n->target;
if (array_key_exists($tgt, $alias)) {
$tgt = $alias[$tgt];
}
$nat_int = ip2long($tgt);
$nat_int_port = (int) $n->{'local-port'};
$description = (string) $n->descr;
// check if data already exists
$sth->execute([long2ip($nat_ext), long2ip($nat_int)]);
$dupe = $sth->fetchColumn() == 0;
$ruleid += 1;
$res[] = ['id' => $ruleid,
'ext' => $nat_ext,
'ext_port' => $nat_ext_port,
'int' => $nat_int,
'int_port' => $nat_int_port,
'description' => $description,
'dupe' => $dupe];
}
// store importdata for next selection step
$_SESSION['pfimport'] = $res;
$smarty->assign("natlist", $res);
$smarty->display("importpfsense.tpl");
else:
// ========== ERROR UNKNOWN VARIANT ===========================================
echo "<p>Unknown function call: Please report to system development!</p>\n";
endif; // $action == ...
// ========== END OF VARIANTS =================================================
$smarty->display('footer.tpl');
+1 -2
View File
@@ -23,13 +23,12 @@ if (empty($_SESSION['suser_id'])) {
// required config vars, may be overwritten later
$config_auth_ldap = false;
$config_ext = array();
// connect to database
$dbh = new PDO("mysql:host=$config_mysql_host;dbname=$config_mysql_dbname;charset=utf8", $config_mysql_username, $config_mysql_password);
$dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$dbh->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
include("lib.php");
include('lib.php');
// $language = lang_getfrombrowser($config_lang, $config_lang_default);
+2 -1
View File
@@ -54,10 +54,11 @@ CREATE TABLE cablevlan (
-- WIP
-- Reference to external systems
-- class 1=asset; per ext type different class-ids possible
-- TODO unique: asset_id, extlink_type, extlink_class
CREATE TABLE extlink (
extlink_id int(10) NOT NULL AUTO_INCREMENT,
asset_id int(10) NOT NULL,
extlink_type enum('cdb','zabbix', 'topdesk') NOT NULL DEFAULT 'cdb',
extlink_type enum('cdb','zabbix', 'topdesk', 'logi') NOT NULL DEFAULT 'cdb',
extlink_class tinyint(4) NOT NULL DEFAULT 1,
extlink_refid int(10) DEFAULT NULL,
extlink_uid varchar(65) DEFAULT NULL,
+2
View File
@@ -243,6 +243,8 @@ $lang = array(
'lang_about_license_ext' => 'Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)<br>Copyright (C) 2011-2023 Thomas Hooge<p>This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.<p>This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.<p> You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.',
'lang_about_changelog' => 'Changelog (major changes only)',
'lang_about_changelog_v10' => 'v0.10 (jul 2026)',
'lang_about_changelog_v10_ext' => '- Switched to Smarty v4<br>- LDAP configuration for PHP v8',
'lang_about_changelog_v09' => 'v0.9 (mar 2023)',
'lang_about_changelog_v09_ext' => '- Changed database interface to PDO / prepared statements<br>- LDAP authentication<br>- User rights<br>- Improved internal menu system',
'lang_about_changelog_v08' => 'v0.8 (feb 2023)',
+2
View File
@@ -243,6 +243,8 @@ $lang = array(
'lang_about_license_ext' => 'Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)<br>Copyright (C) 2011-2023 Thomas Hooge<p>This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.<p>This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.<p> You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.',
'lang_about_changelog' => 'Changelog (major changes only)',
'lang_about_changelog_v10' => 'v0.10 (jul 2026)',
'lang_about_changelog_v10_ext' => '- Switched to Smarty v4<br>- LDAP configuration for PHP v8',
'lang_about_changelog_v09' => 'v0.9 (mar 2023)',
'lang_about_changelog_v09_ext' => '- Changed database interface to PDO / prepared statements<br>- LDAP authentication<br>- User rights<br>- Improved internal menu system',
'lang_about_changelog_v08' => 'v0.8 (feb 2023)',
+25 -9
View File
@@ -2,7 +2,7 @@
/*****************************************************************************
IP Reg, a PHP/MySQL IPAM tool
Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)
Copyright (C) 2011-2023 Thomas Hooge
Copyright (C) 2011-2026 Thomas Hooge
SPDX-License-Identifier: GPL-3.0-or-later
*****************************************************************************/
@@ -30,14 +30,14 @@ define ('ACT_PASSWORD', 14);
// ========== GLOBAL PAGE START CODE ==========================================
// global version string
$config_version = 'v0.9.1';
$config_version = 'v0.10';
// available languages
$config_lang = array('de', 'en');
include("lib/functions.php");
require_once('smarty3/Smarty.class.php');
require_once('smarty4/Smarty.class.php');
$smarty = new Smarty();
$smarty->template_dir = 'tpl';
$smarty->compile_dir = 'tpl_c';
@@ -205,7 +205,7 @@ function submit_error($action) {
return sprintf('The action "%s" is unknown. It is probably a program error.<br> Please inform your administrator of the exact circumstances of how this situation came about.', strtoupper($action));
}
// ========== DATABASE FUCTIONS ===============================================
// ========== DATABASE FUNCTIONS ==============================================
function db_load_enum($table, $column) {
// returns array of enum-values as defined in database
@@ -305,7 +305,13 @@ function db_get_options_zone($default = NULL) {
return $options;
}
// ========== MISC FUCTIONS ===================================================
// ========== MISC FUNCTIONS ==================================================
function header_location($location) {
// redirect page
header('location:' . $location);
exit;
}
function strip_mac($mac, $caps=true) {
// strip mac address to 12 char string
@@ -347,8 +353,18 @@ function write_mac($mac, $user_mac='xx:xx:xx:xx:xx:xx') {
return $user_mac;
}
function header_location($location) {
// redirect page
header('location:' . $location);
exit;
function extlink_enabled() {
// check if any link to external system is enabled
global $config_ext;
foreach ($config_ext as $xcfg) {
if (!array_key_exists('enabled', $xcfg)) {
// invalid configuration
// TODO Throw warning!
continue;
}
if ($xcfg['enabled']) {
return true;
}
}
return false;
}
+6
View File
@@ -0,0 +1,6 @@
function toggle(source) {
checkboxes = document.getElementsByName('rule');
for(var i=0, n=checkboxes.length; i<n; i++) {
checkboxes[i].checked = source.checked;
}
}
+6
View File
@@ -0,0 +1,6 @@
<?php
// Computerdatenbank interface
// $config_ext['computerdb']
class Cdb {
}
+6
View File
@@ -0,0 +1,6 @@
<?php
// Loginventory interface
// $config_ext['loginventory']
class Loginventory {
}
+38
View File
@@ -0,0 +1,38 @@
<?php
// Topdesk interface
// $config_ext['topdesk']
class Topdesk {
}
/*
Topdesk-Infos / Interessante Tabellen
object
type
asset_typ_id
asset_summary
asset_status
ref_name
asset_type
unid 16 Byte GUID
name
am_entity
object.asset_id = am_entity.unid
am_field
id
displayname
properties (JSON)
am_value
entityid
fieldname
textvalue
numvalue
valuetype
am_relation
sourceId
targetId
*/
+36
View File
@@ -0,0 +1,36 @@
<?php
// Zabbix interface
// $config_ext['zabbix']
class Zabbix {
}
// $smarty->assign('zabbix', print_r($config_ext['zabbix']['host'],true));
if ($config_ext['zabbix']['enabled']) {
$smarty->assign("zabbix", true);
$sql = "SELECT extlink_refid FROM extlink WHERE extlink_type='zabbix' AND asset_id=?";
$sth = $dbh->prepare($sql);
$sth->execute([$id]);
$refid = $sth->fetchColumn();
// TODO fetch ext data here
$zbxconn = false;
try {
$zbx = new PDO('mysql:host='.$config_ext['zabbix']['host'].';dbname='.$config_ext['zabbix']['db'].';', $config_ext['zabbix']['user'], $config_ext['zabbix']['pass']);
$zbx->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$zbx->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
$zbxconn = true;
} catch (Exception $e) {
$refid = "not_connected:" . $e->getMessage();
}
if ($zbxconn) {
$sql = "SELECT host FROM hosts WHERE hostid=?";
$sth = $zbx->prepare($sql);
$sth->execute([$refid]);
$zbx_hostname = $sth->fetchColumn();
$smarty->assign('zbx_hostname', $zbx_hostname);
$zbx = NULL; // close
}
}
+59
View File
@@ -0,0 +1,59 @@
<?php
// External data source
class ExtSys {
public $name;
protected $conn;
function __construct($xtype, $dbconfig) {
if (! $config['enabled']) {
throw new Exception('Not allowed to create connection to ' . $xtype);
}
switch ($config['xtype']) {
'cdb':
$this->name = 'Computerdatenbank';
cdb_init($dbconfig);
break;
'logi':
$this->name = 'Loginventory';
logi_init($dbconfig);
break;
'topdesk':
$this->name = 'Topdesk';
tdesk_init($dbconfig);
break;
'zabbix':
$this->name = 'Zabbix';
zbx_init($dbconfig);
break;
default:
throw new Exception('Invalid xtype');
}
}
private function mariadb_connect() {
return false;
}
private function mssql_connect() {
return false;
}
private function cdb_init() {
mariadb_connect();
}
private function logi_init() {
mssql_connect();
}
private function tdesk_init() {
mssql_connect();
}
private function zbx_init() {
mariadb_connect();
}
}
+1 -8
View File
@@ -2,7 +2,7 @@
/*****************************************************************************
IP Reg, a PHP/MySQL IPAM tool
Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)
Copyright (C) 2011-2023 Thomas Hooge
Copyright (C) 2011-2026 Thomas Hooge
SPDX-License-Identifier: GPL-3.0-or-later
*****************************************************************************/
@@ -11,14 +11,8 @@ SPDX-License-Identifier: GPL-3.0-or-later
function sanitize($input) {
global $dblink;
// trim whitespaces
$input = @trim($input);
// magic quotes enabled?
if(get_magic_quotes_gpc()) {
// strip slashes
$input = stripslashes($input);
}
// convert to utf-8
iconv("UTF-8", "UTF-8", $input);
@@ -26,7 +20,6 @@ function sanitize($input) {
// convert special chars
$input = htmlentities($input, ENT_QUOTES, 'UTF-8');
// and return
return $input;
}
+4 -3
View File
@@ -2,7 +2,7 @@
/*****************************************************************************
IP Reg, a PHP/MySQL IPAM tool
Copyright (C) 2007-2009 Wietse Warendorff (up to v0.5)
Copyright (C) 2011-2023 Thomas Hooge
Copyright (C) 2011-2026 Thomas Hooge
SPDX-License-Identifier: GPL-3.0-or-later
*****************************************************************************/
@@ -25,11 +25,11 @@ $dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$dbh->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
include("lib.php"); // for smarty e.g.
// ========== LOGIN FUNCTIONS =================================================
function check_ldap_bind($user_name, $user_pass) {
global $config_ldap_host;
global $config_ldap_scheme;
global $config_ldap_port;
global $config_ldap_base_dn;
global $config_ldap_bind_dn;
@@ -37,7 +37,8 @@ function check_ldap_bind($user_name, $user_pass) {
global $config_ldap_login_attr;
$ldap_conn = NULL;
foreach ($config_ldap_host as $server) {
if ($ldap_conn = ldap_connect($server, $config_ldap_port)) {
$ldap_uri = $config_ldap_scheme . $server . ':' . $config_ldap_port;
if ($ldap_conn = ldap_connect($ldap_uri)) {
if ($res = ldap_bind($ldap_conn, $config_ldap_bind_dn, $config_ldap_bind_pass)) {
ldap_set_option($ldap_conn, LDAP_OPT_REFERRALS, 0);
ldap_set_option($ldap_conn, LDAP_OPT_PROTOCOL_VERSION, 3);
+9 -1
View File
@@ -20,7 +20,7 @@
{$lang_about_projectpage}
</td>
<td class="value">
<a href="https://git.piratenpartei-sh.de/thooge/ipreg">https://git.piratenpartei-sh.de/thooge/ipreg</a>
<a href="https://git.hoogi.de/thooge/ipreg">https://git.hoogi.de/thooge/ipreg</a>
</td>
</tr>
<tr>
@@ -83,6 +83,14 @@
&nbsp;
</td>
</tr>
<tr>
<td class="label">
{$lang_about_changelog_v10}
</td>
<td class="value">
{$lang_about_changelog_v10_ext}
</td>
</tr>
<tr>
<td class="label">
{$lang_about_changelog_v09}
+32
View File
@@ -119,3 +119,35 @@
</td>
</tr>
</table>
{if $extlink}
<table class="info">
<tr>
<td class="header">
External Links
</td>
</tr>
<tr>
<td>In development</td>
</tr>
</table>
{/if}
{if $refid}
<table class="info">
<tr>
<td class="header">
Externe Daten
</td>
<td class="header_right">
&nbsp;
</td>
</tr>
<tr>
<td class="label">Zabbix</td>
<td class="value">HostID = {$refid}, {$zbx_hostname}
</td>
</tr>
</table>
{/if}
+35
View File
@@ -0,0 +1,35 @@
<table class="title">
<tr>
<td class="header">
<img class="icon" src="images/settings.png" alt="" />
Import
</td>
<td align="right">
&nbsp;
</td>
</tr>
</table>
<table class="info">
<tr>
<td class="header">
IP Reg import module
</td>
</tr>
</table>
<table class="info">
<tr>
<td class="label">
Import pfsense NAT settings
</td>
<td>
<form enctype="multipart/form-data" action="import.php" method="post">
<input type="hidden" name="MAX_FILE_SIZE" value="1000000" />
pfSense Konfigurationsdatei: <input name="xmlfile" type="file" />
<input type="submit" name="submit[pfsense]" value="Upload" />
</form>
</td>
</tr>
</table>
+55
View File
@@ -0,0 +1,55 @@
<table class="title">
<tr>
<td class="header">
<img class="icon" src="images/settings.png" alt="" />
Import
</td>
<td align="right">
&nbsp;
</td>
</tr>
</table>
<table class="info">
<tr>
<td class="header">
IP Reg import module
</td>
</tr>
</table>
<form method="post" action="import.php">
<table class="info">
<tr>
<td class="label">
Configuration file
</td>
<td>
{$xmlfile} of type {$xmlfiletype} ({$xmltmp})
</td>
</tr>
<tr>
<td class="label">
Data
</td>
<td><table>
<tr>
<th><input type="checkbox" onclick="toggle(this)"></th>
<th>From</th><th>To</th><th>Description</th>
</tr>
{foreach item=nat from=$natlist}
<tr>
<td><input type="checkbox" name="rule" value="{$nat.id}"></td>
<td>{$nat.ext|long2ip}:{$nat.ext_port}</td>
<td>{$nat.int|long2ip}:{$nat.int_port}</td>
<td>{$nat.description}</td>
<td>{$nat.dupe}</td>
</tr>
{/foreach}
</table>
<input type="submit" name="submit[exec-pfsense]" value="Import">
</td>
</tr>
</table>
</form>