facter: replay "Added new facter module and associated manifest file"
authorDaniel Kasen <djtecha@gmail.com>
Thu, 20 Dec 2012 18:44:05 +0000 (10:44 -0800)
committerDenis Ovsienko <infrastation@yandex.ru>
Fri, 19 Apr 2013 16:27:22 +0000 (20:27 +0400)
facter/facter.php
facter/manifest [new file with mode: 0644]

index 4dc2d6f5aff15bb1a850340c4b2c3370b7ca1d57..c49707a00dcd3c917bd0b28e7aef53a401377c36 100644 (file)
@@ -1,17 +1,18 @@
 <?php
 /*
- * Facter (Puppet) plugin for racktables 0.19.1 (and probably newer)
+ * Facter (Puppet) plugin for racktables 0.20.1 (and probably newer)
 *
 * This file is both a web GUI and REST webservice for auto create and update machines based on facter (puppet) files.
 *
-* REST examples:
-* curl -k -F myfile=@facter.txt -u username:password https://facter/racktables/process.php?page=depot&tab=facter&op=Update
-* curl -F myfile=@facter.txt -u username:password http://facter/racktables/process.php?page=depot&tab=facter&op=Update
+* REST example:
+* curl -F "userfile=@/root/facter.txt" -u username:password "http://racktables/index.php?module=redirect&page=depot&tab=facter&op=Update"
 *
 * Usage instructions:
-*  * Just symlink it to your inc folder
-*  * add it to the local.php file inn your inc folder: echo "<?php include_once 'facter.php'; ?>" >> inc/local.php
-*  * If you want you can add the CPU attribute and it will show you your cpu's aswell
+*  Add to plugins folder along with manifest file
+*  To get VMs to auto add you have to create a facter function to return a list like:
+*  export FACTER_VMs=$(virsh list | awk '$3 == "running" {printf $2","}' | sed -e 's/,$//');
+*  Whatever you use for VMs it should return a list like: vms => vm1,vm2
+*  
 *
 * Author: Torstein Hansen <huleboer@users.sourceforge.net>, sponsored by eniro.no
 *
 * - modified .yaml parsing to match to 'facter -py' format
 * - modified interface-type detection to use virtual port on VMs
 * - modified OS detection to match more better default sets (Testcase: CentOS).
+* 
+* 2012-12-13 modified by Daniel Kasen <djtech@gmail.com>
+* - added generic looping to easially add fields
+* - Corrected issues with VM's breaking script
+* - reverted .yaml parsing due to strings in facter not parsing right for mem. options
+* - added error checking to ignore unusable lines in manifest file
+* - fixed ip additions for 20.1
+* - added VM auto adding to Parent
 *
 */
 
@@ -31,7 +40,6 @@ $tab['depot']['facter'] = 'Facter';
 $tabhandler['depot']['facter'] = 'ViewHTML';
 $ophandler['depot']['facter']['Update'] = 'Update';
 
-
 // The ophandler to insert objects (if any)
 function Update()
 {
@@ -41,7 +49,7 @@ function Update()
        // add file contents to facter array
        foreach ($lines as $line_num => $line)
        {
-               $tmpfacter=explode(":",$line,2);
+               $tmpfacter=explode("=>",$line,2);
                $facter[trim($tmpfacter[0])]=str_replace('"', '',trim($tmpfacter[1]));
        }
 
@@ -66,7 +74,6 @@ function Update()
        if($resultarray) {
                $id=$resultarray[0]['id'];
        }
-
        // If it's a new machine
        if (! isset($id))
        {
@@ -97,7 +104,8 @@ function Update()
                        }
                }
                // Add the new machine
-               $newmachine=commitAddObject($facter['fqdn'],$facter['fqdn'],$virtual,$value = "");
+               $newmachine=commitAddObject($facter['fqdn'],"",$virtual,$value = "");
+               $type_id = getObjectTypeID($newmachine);
        }
        // If it's an existing machine
        else
@@ -105,19 +113,16 @@ function Update()
                // Just set some fields I use later down for updating
                $newmachine=$id;
                $machineupdate=1;
+               $type_id = getObjectTypeID($newmachine);
        }
 
 
-
-       // Add lot's of attributes to the machine. Next version use an array (from config file) and do a loop for most of these fields.....
-
        // 2011-08-31 <neil.scholten@gamigo.com>
        // * Update (unique) name of object.
        if (
                array_key_exists('serialnumber', $facter) &&
                strlen($facter['serialnumber']) > 0 &&
                $facter['serialnumber'] != 'Not Specified' ) {
-               
                unset($result);
                $query                          = "select * from RackObject where asset_no = \"$facter[serialnumber]\" LIMIT 1";
                $result                         = usePreparedSelectBlade ($query);
@@ -130,107 +135,138 @@ function Update()
                }
        }
 
-       // Find FQDN id
-       $query = "select id from Attribute where name='FQDN' LIMIT 1";
-       unset($result);
-       $result = usePreparedSelectBlade ($query);
-       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
-       if($resultarray) {
-               $id=$resultarray[0]['id'];
-               // Update FQDN
-               commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $facter['fqdn']);
-       }
-
-
        // Find HW type id
        // 2011-08-31 <neil.scholten@gamigo.com>
        // * adjust format to match default Dictionary Sets
-       $iHWTemp                                = preg_match('([a-zA-Z]{1,})', $facter['manufacturer'], $matches);
-       $sManufacturer  = $matches[0];
-       $sHW                                            = preg_replace('(\ )', '\1%GPASS%', $facter['productname']);
-       $sHWType                                = $sManufacturer.' '.$sHW;
-       $query                                  = "select id from Attribute where name='HW type' LIMIT 1";
-       unset($result);
-       $result = usePreparedSelectBlade ($query);
-       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
-       if($resultarray) {
-               $id=$resultarray[0]['id'];
-               // Update HW type
-               $hw_dict_key = getdict($sHWType, $chapter=11 );
-               commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $hw_dict_key);
+       if ($facter['is_virtual']=="false")
+       {       
+               $iHWTemp                                = preg_match('([a-zA-Z]{1,})', $facter['manufacturer'], $matches);
+               $sManufacturer  = $matches[0];
+               $sHW                                            = preg_replace('(\ )', '\1%GPASS%', $facter['productname']);
+               $sHWType                                = $sManufacturer.' '.$sHW;
+               $query                                  = "select id from Attribute where name='HW type' LIMIT 1";
+               unset($result);
+               $result = usePreparedSelectBlade ($query);
+               $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+               if($resultarray) {
+                       $id=$resultarray[0]['id'];
+                       // Update HW type
+                       $hw_dict_key = getdict($sHWType, $chapter=11 );
+                       commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $hw_dict_key);
+               }
+               //Also Check if HYPERVISOR
+               if (isset($facter['is_hypervisor']))
+               {
+                       $query = "select id from Attribute where name REGEXP '^ *Hypervisor Type$' LIMIT 1";
+                       unset($result);
+                       $result = usePreparedSelectBlade ($query);
+                       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+                       if($resultarray) {
+                       $id=$resultarray[0]['id'];
+                                       // Update Hypervisor type 
+                                       $hypervisor_type = $facter['is_hypervisor'];
+                       $hypervisor_type_dict_key = getdict($hw=$hypervisor_type, $chapter=10005);
+                       commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $hypervisor_type_dict_key);
+                       }
+                       //Set Value to Yes
+                       $query = "select id from Attribute where name REGEXP '^ *Hypervisor' LIMIT 1";
+                       unset($result);
+               $result = usePreparedSelectBlade ($query);
+               $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+               if($resultarray) {
+                               $id=$resultarray[0]['id'];
+                               // Update Hypervisor type 
+                               $hypervisor = "Yes";
+                               $hypervisor_dict_key = getdict($hypervisor, $chapter=29);
+                       commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $hypervisor_dict_key);
+                       }
+            //Find Running VMs
+            $vms = explode(',',$facter['vms']);
+            $vm_count = count($vms);
+            for ($i = 0; $i < $vm_count; $i++) {
+                               //addToParent
+                               addVmToParent ($vms[$i], $newmachine);
+                       }        
+               } else {
+                       $query = "select id from Attribute where name REGEXP '^ *Hypervisor' LIMIT 1";
+                       unset($result);
+                        $result = usePreparedSelectBlade ($query);
+                        $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+                        if($resultarray) {
+                                $id=$resultarray[0]['id'];
+                                // Update Hypervisor type
+                                $hypervisor = "No";
+                                $hypervisor_dict_key = getdict($hypervisor, $chapter=29);
+                                commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = "");
+                       }
+               }
        }
-
-
+       
        // Find SW type id (OS)
-       $query = "select id from Attribute where name='SW type' LIMIT 1";
+       $query = "select id from Attribute where name REGEXP '^ *SW type$' LIMIT 1";
        unset($result);
        $result = usePreparedSelectBlade ($query);
        $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
        if($resultarray) {
                $id=$resultarray[0]['id'];
                // Update SW type (OS)
-               $osrelease = $facter['lsbdistid'] . '%GSKIP%' . $facter['lsbdistid'] . ' V' . $facter['lsbmajdistrelease'];
+               $osrelease = $facter['operatingsystem'] . '%GSKIP%' . $facter['operatingsystem'] . ' V' . $facter['operatingsystemrelease'];
                $os_dict_key = getdict($hw=$osrelease, $chapter=13);
                commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $os_dict_key);
        }
 
-
-       // Find OEM S/N 1
-       $query = "select id from Attribute where name='OEM S/N 1' LIMIT 1";
-       unset($result);
-       $result = usePreparedSelectBlade ($query);
-       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
-       if($resultarray) {
-               $id=$resultarray[0]['id'];
-               // Update serial number
-               commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $facter['serialnumber']);
-       }
-
-
-       // Find Architecture id
-       $query = "select id from Attribute where name='Architecture' LIMIT 1";
-       unset($result);
-       $result = usePreparedSelectBlade ($query);
-       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
-       if($resultarray) {
-               $id=$resultarray[0]['id'];
-               // Update Architecture id
-               commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $facter['architecture']);
-       }
-
-
-
-       // Find Memory id
-       $query = "select id from Attribute where name='DRAM, GIB' LIMIT 1";
-       unset($result);
-       $result = usePreparedSelectBlade ($query);
-       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
-       if($resultarray) {
-               $id=$resultarray[0]['id'];
-               // Update Memory id
-               commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $facter['memorysize']);
-       }
-
-
-       // Find CPU id (custom field you'll need to add yourself)
-       $cpu = $facter['processorcount'] . " x " . $facter['processor0'];
-       $query = "select id from Attribute where name='CPU' LIMIT 1";
-       unset($result);
-       $result = usePreparedSelectBlade ($query);
-       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
-       if($resultarray) {
-               $id=$resultarray[0]['id'];
-               // Update CPU id
-               $cpu = $facter['processorcount'] . " x " . $facter['processor0'];
-               commitUpdateAttrValue ($object_id = $newmachine, $id, $value = $cpu);
+       //Generic to read in from file  
+       $manifest_file = fopen("manifest", "r") or die("Could not open manifest, make sure it is in the websrv root and called manifest \n");
+       while ( ! feof ($manifest_file)) {
+               $tmp_line = fgets($manifest_file);
+               if (!empty($tmp_line) && !preg_match("/\/\//",$tmp_line)) {
+                       @list($Fact, $Attr, $Chapter) = array_map('trim', (explode(',', $tmp_line, 3)));
+                       //check for multi-facter names
+                       if(strstr($Fact, '.')) {
+                               @list($Fact1, $Fact2) = array_map('trim', (explode('.', $Fact)));
+                               $value = $facter[$Fact1] .' '. $facter[$Fact2];
+                               if(!isset($facter[$Fact1]) || !isset($facter[$Fact2])) {
+                                       echo "WARNING: $Fact1 or $Fact2 does not exist in Facter for this object \n";
+                                       continue;
+                               }
+                       } else {
+                               if(!isset($facter[$Fact])) {
+                                       echo "WARNING: $Fact does not exist in Facter for this object \n";
+                                       continue;
+                               } else {
+                                       $value = $facter[$Fact];
+                               }
+                       }
+                       $query = "select id from Attribute where name REGEXP '^ *$Attr' LIMIT 1";
+                       unset($result);
+                       $result = usePreparedSelectBlade ($query);
+                       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+                       $id=$resultarray[0]['id'];
+                       if (!valid($type_id, $id)) {
+                               echo "WARNING: Not a valid Mapping for $Fact to $Attr for objectType $type_id \n";
+                       }
+                       else if($resultarray) {
+                               if(!empty($Chapter)) {
+                                       $name = $value;
+                                       $name_dict_key = getdict($hw=$name, $chapter=$Chapter);
+                                       commitUpdateAttrValue ($object_id = $newmachine, $attr_id = $id, $value = $name_dict_key);
+                               } else if (preg_match("/[0-9]{1,2}\/[0-9]{1,2}\/[0-9]{4}/",$value) || preg_match("/[0-9]{1,2}\-[0-9]{1,2}\-[0-9]{4}/",$value) || preg_match("/[0-9]{4}\-[0-9]{1,2}\-[0-9]{1,2}/",$value))  {
+                                       //handle dates
+                                       commitUpdateAttrValue ($newmachine, $id, strtotime($value) );
+                               } else {
+                                       commitUpdateAttrValue ($newmachine, $id, $value );
+                               }       
+                       }
+               }
        }
+       fclose($manifest_file);
 
        // Add network interfaces
 
        // Create an array with interfaces
        $nics = explode(',',$facter['interfaces']);
 
-       // Go thew all interfaces and add IP and MAC
+       // Go through all interfaces and add IP and MAC
        $count = count($nics);
        for ($i = 0; $i < $count; $i++) {
                // Remove newline from the field
@@ -241,7 +277,7 @@ function Update()
                // 2011-08-31 <neil.scholten@gamigo.com>
                // * Only Document real interfaces, dont do bridges, bonds, vlan-interfaces
                //   when they have no IP defined.
-               if ( preg_match('(_|^(br|bond|lo|sit|vnet|virbr))',$nics[$i]) != 0 && !isset($facter['ipaddress_' . $nics[$i]]) ) {
+               if ( preg_match('(_|^(bond|lo|sit|vnet|virbr|veth|peth))',$nics[$i]) != 0 ) {
                        // do nothing
                } else {
                        // Get IP
@@ -256,12 +292,12 @@ function Update()
                        if ($facter['is_virtual']=="false")
                        {
                                // Find 1000Base-T id
-                               $query = "select dict_key from Dictionary where dict_value='1000Base-T' LIMIT 1";
+                               $query = "select dict_key from Dictionary where dict_value REGEXP '^ *1000Base-T$' LIMIT 1";
                        }
                        else
                        {
                                // Find virtual port id
-                               $query = "select dict_key from Dictionary where dict_value='virtual port' LIMIT 1";
+                               $query = "select dict_key from Dictionary where dict_value REGEXP '^ *virtual port$' LIMIT 1";
                        }
                        unset($result);
                        $result = usePreparedSelectBlade ($query);
@@ -296,7 +332,6 @@ function Update()
                                unset($id);
                                $portcheck=$resultarray;
                        }
-       
                        // Add/update port
                        // 2011-08-31 <neil.scholten@gamigo.com>
                        // * Don't touch already existing complex ports
@@ -311,32 +346,32 @@ function Update()
                        } else {
                                //We've got a complex port, don't touch it, it raises an error with 'Database error: foreign key violation'
                        }
-       
-                       // Add/update ip
+
+                       // Add/update ip #Disabled for 20.1
                        if (count($ipcheck) == 1 ) {
                                if( $ip ) {
-                                       updateAddress($ip , $newmachine, $nics[$i],'regular');
+                                       updateAddress(ip_parse($ip) , $newmachine, $nics[$i],'regular');
                                }
                        }
                        else
                        {
                                if( $ip ) {
-                                       bindIpToObject($ip , $newmachine, $nics[$i],'regular');
+                                       bindIpToObject(ip_parse($ip), $newmachine, $nics[$i],'regular');
                                }
                        }
-       
                        unset($portcheck);
                        unset($ipcheck);
                        unset($ip);
                        unset($mac);
                }
        }
-       return buildWideRedirectURL ();
+       return buildRedirectURL ();
 }
 
 // Display the import page.
 function ViewHTML()
 {
+
        startPortlet();
 
        echo "<table with=90% align=center border=0 cellpadding=5 cellspacing=0 align=center class=cooltable><tr valign=top>";
@@ -385,4 +420,50 @@ function getdict ($hw,$chapter) {
                echo $e->getMessage();
        }
 }
+
+//new check to make sure the obkject type allows the string
+function valid ($type_id, $id) {
+       //Check to see if this combination exists in the AttributeMap
+       $valid = "SELECT * from AttributeMap WHERE objtype_id = '$type_id' AND attr_id = '$id' LIMIT 1";
+       unset($result);
+       $result = usePreparedSelectBlade ($valid);
+       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+       $exists = $resultarray[0]['objtype_id'];
+       if (!empty($exists))
+               return 1;
+       else
+               return 0;
+}
+
+function getObjectTypeID ($newmachine) {
+       $objtype = "SELECT objtype_id from RackObject WHERE id = $newmachine LIMIT 1";
+       unset($result);
+       $result = usePreparedSelectBlade ($objtype);
+       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+       return $resultarray[0]['objtype_id'];
+}
+
+//Find Parent of VM Object
+function addVmToParent ($vms, $newmachine) {
+       $search_for_child = "select id from RackObject WHERE name REGEXP '^ *$vms\\\.'";
+       unset($result);
+       $result = usePreparedSelectBlade ($search_for_child);
+       $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+       $child = $resultarray[0]['id'];
+       if (!empty($child)){
+               //make sure the association doesn't exist already or deal with it
+               $current_container = "SELECT parent_entity_id from EntityLink WHERE child_entity_id = $child";
+               unset($result);
+               $result = usePreparedSelectBlade ($current_container);
+               $resultarray = $result->fetchAll (PDO::FETCH_ASSOC);
+               $current_parent = $resultarray[0]['parent_entity_id'];
+               if ( ($current_parent != $newmachine ) && !empty($current_parent)){
+                       commitUpdateEntityLink('object',$current_parent,'object',$child,'object',$newmachine,'object',$child);
+               } else if (empty($current_parent)) {
+                       commitLinkEntities('object', $newmachine,'object',$child);
+               }
+       } else {
+               echo "WARNING: The $vms VM does not exist for this Parent \n";
+       }
+}
 ?>
diff --git a/facter/manifest b/facter/manifest
new file mode 100644 (file)
index 0000000..bc0c762
--- /dev/null
@@ -0,0 +1,10 @@
+//This is where you set what options you want auto populated
+// The facterkeyword must exist in facter
+// and the AttributeWord/Chapter must be created in the racktables attributes
+// and assigned to the object type
+//Declare these values like so:
+//facterkeyword AttributeWord ChapterNumber
+//to find facterkeyword use "facter"
+//ex1: memorysize,Memory
+//ex2: puppetversion,Puppet,10000
+