Code

Replaced in_array calls for gosa-plugins
[gosa.git] / gosa-plugins / dns / admin / systems / services / dns / class_DNS.inc
index 20db6f1d8b3e947d6701eab6f7e1e7d0be1b0f98..61e492c9ab8f4377cba91b5aa7c1e5ed11a44810 100644 (file)
@@ -1,61 +1,56 @@
 <?php
 
-
-/* All available record types 
- */
-$RecordTypes['aRecord']       = "aRecord";           
-$RecordTypes['mDRecord']      = "mDRecord";         
-$RecordTypes['mXRecord']      = "mXRecord";         
-$RecordTypes['nSRecord']      = "nSRecord";          
-$RecordTypes['pTRRecord']     = "relativeDomainName";
-$RecordTypes['hInfoRecord']   = "hInfoRecord";      
-$RecordTypes['mInfoRecord']   = "mInfoRecord";       
-$RecordTypes['cNAMERecord']   = "relativeDomainName";
-$RecordTypes['tXTRecord']     = "tXTRecord";         
-$RecordTypes['aFSDBRecord']   = "aFSDBRecord";       
-$RecordTypes['SigRecord']     = "SigRecord";         
-$RecordTypes['KeyRecord']     = "KeyRecord";         
-$RecordTypes['aAAARecord']    = "aAAARecord";        
-$RecordTypes['LocRecord']     = "LocRecord";         
-$RecordTypes['nXTRecord']     = "nXTRecord";        
-$RecordTypes['sRVRecord']     = "sRVRecord";         
-$RecordTypes['nAPTRRecord']   = "nAPTRRecord";       
-$RecordTypes['kXRecord']      = "kXRecord";          
-$RecordTypes['certRecord']    = "certRecord";        
-$RecordTypes['a6Record']      = "a6Record";          
-$RecordTypes['dSRecord']      = "dSRecord";          
-$RecordTypes['sSHFPRecord']   = "sSHFPRecord";       
-$RecordTypes['rRSIGRecord']   = "rRSIGRecord";      
-$RecordTypes['nSECRecord']    = "nSECRecord";       
-
 class DNS
 {
-
+  static $RecordTypes= array('aRecord' => "aRecord",
+                    'mDRecord'      => "mDRecord",         
+                    'mXRecord'      => "mXRecord",         
+                    'nSRecord'      => "nSRecord",          
+                    'pTRRecord'     => "relativeDomainName",
+                    'hInfoRecord'   => "hInfoRecord",      
+                    'mInfoRecord'   => "mInfoRecord",       
+                    'cNAMERecord'   => "relativeDomainName",
+                    'tXTRecord'     => "tXTRecord",         
+                    'aFSDBRecord'   => "aFSDBRecord",       
+                    'SigRecord'     => "SigRecord",         
+                    'KeyRecord'     => "KeyRecord",         
+                    'aAAARecord'    => "aAAARecord",        
+                    'LocRecord'     => "LocRecord",         
+                    'nXTRecord'     => "nXTRecord",        
+                    'sRVRecord'     => "sRVRecord",         
+                    'nAPTRRecord'   => "nAPTRRecord",       
+                    'kXRecord'      => "kXRecord",          
+                    'certRecord'    => "certRecord",        
+                    'a6Record'      => "a6Record",          
+                    'dSRecord'      => "dSRecord",          
+                    'sSHFPRecord'   => "sSHFPRecord",       
+                    'rRSIGRecord'   => "rRSIGRecord",      
+                    'nSECRecord'    => "nSECRecord");
+  /* All available record types */
   /* Return all record types 
    */
   static function getDnsRecordTypes($ForZones = false)
   {
-    global $RecordTypes;
     if($ForZones){
-      $tmp = $RecordTypes;
+      $tmp = DNS::$RecordTypes;
       unset($tmp['cNAMERecord']);
       unset($tmp['pTRRecord']);
       unset($tmp['tXTRecord']);
       return($tmp);
     }else{
-      return($RecordTypes);
+      return(DNS::$RecordTypes);
     }
   }
 
 
   /* This fucntion is used to flip the ip address, for example
      12.3.45  ->  45.3.12
-     Because some entries (like zones) are store like that 45.3.12.in-addr.arpa
+     Because some entries (like zones) are store like that 45.3.12.in-addr.arpa.
      but we want to display 12.3.45.
    */
   static function FlipIp($ip)
   {
-    $tmp = array_reverse(split("\.",$ip));
+    $tmp = array_reverse(explode(".",$ip));
     $new = "";
     foreach($tmp as $section){
       $new .= $section.".";
@@ -68,8 +63,6 @@ class DNS
    */
   static function getDNSZoneEntries($config,$HostDn,$silent = false)
   {
-    global $RecordTypes;
-
     $ldap = $config->get_ldap_link();
     $ldap->cd($config->current['BASE']); 
 
@@ -126,7 +119,7 @@ class DNS
       /* Generate SOA entry
        */
       if(isset($attrs['sOARecord'][0])){
-        $tmp = split("\ ",$attrs['sOARecord'][0]) ;
+        $tmp = explode(" ",$attrs['sOARecord'][0]) ;
         $tmp2 = array();
 
         /* Assign soa vars */
@@ -141,11 +134,11 @@ class DNS
 
       /* Get record attributes 
        */
-      foreach($RecordTypes as $name => $value){
+      foreach(DNS::$RecordTypes as $name => $value){
 
         /* Skip some attributes 
          */
-        if(in_array($name,$SkipRecords)) continue;
+        if(in_array_strict($name,$SkipRecords)) continue;
 
         /* If there is a record attribute
          */
@@ -175,8 +168,8 @@ class DNS
         unset($Zones[$zoneName]);
       }else{
         $tmp = $ldap->fetch();
-        $Zones[$zoneName]['ReverseZone']        = DNS::FlipIp(str_replace(".in-addr.arpa","",$tmp['zoneName'][0]));
-        $Zones[$zoneName]['InitialReverseZone'] = DNS::FlipIp(str_replace(".in-addr.arpa","",$tmp['zoneName'][0]));
+        $Zones[$zoneName]['ReverseZone']        = DNS::FlipIp(str_replace(".in-addr.arpa.","",$tmp['zoneName'][0]));
+        $Zones[$zoneName]['InitialReverseZone'] = DNS::FlipIp(str_replace(".in-addr.arpa.","",$tmp['zoneName'][0]));
       }
     }
     return($Zones);
@@ -256,9 +249,9 @@ class DNS
       if(!empty($zone['InitialReverseZone'])){
         if($zone['InitialReverseZone'] != $zone['ReverseZone']){
           $base = "zoneName=".$zone['zoneName'].",".$HostDn;
-          $oldRDn = "zoneName=". DNS::FlipIp($zone['InitialReverseZone']).".in-addr.arpa,".$base; 
-          $newRDn = "zoneName=". DNS::FlipIp($zone['ReverseZone']).".in-addr.arpa,".$base;
-          $PrePareZoneEntries[DNS::FlipIp($zone['InitialReverseZone']).".in-addr.arpa"] = DNS::FlipIp($zone['ReverseZone']).".in-addr.arpa";
+          $oldRDn = "zoneName=". DNS::FlipIp($zone['InitialReverseZone']).".in-addr.arpa.,".$base; 
+          $newRDn = "zoneName=". DNS::FlipIp($zone['ReverseZone']).".in-addr.arpa.,".$base;
+          $PrePareZoneEntries[DNS::FlipIp($zone['InitialReverseZone']).".in-addr.arpa."] = DNS::FlipIp($zone['ReverseZone']).".in-addr.arpa.";
           $move [$oldRDn] = $newRDn;
         }
       }
@@ -289,7 +282,7 @@ class DNS
       /* Create Reverse Entry 
        * And append it to our add queue
        */
-      $zone['ReverseZone'] = DNS::FlipIp($zone['ReverseZone']).".in-addr.arpa";
+      $zone['ReverseZone'] = DNS::FlipIp($zone['ReverseZone']).".in-addr.arpa.";
       $base = "zoneName=".$zone['zoneName'].",".$HostDn;
       $newRDn = "zoneName=".$zone['ReverseZone'].",".$base;
       $rObj = $obj;
@@ -337,14 +330,12 @@ class DNS
    */
   static function getDNSHostEntries($config,$name,$silent = false)
   {
-    global $RecordTypes;
-
     $types = array();
     $ret = array();
     $ret['RECORDS']   = array();
     $ret['dNSClass']  = "IN";
     $ret['zoneName']  = "";
-    $ret['dNSTTL']    = "7440";
+    $ret['dNSTTL']    = "";
     $ret['exists']    = false;
 
     $ldap = $config->get_ldap_link();
@@ -355,10 +346,9 @@ class DNS
      */
     $foundIn = array();
     $zones = DNS::getAvailableZones($config);
-
     $zonesArr = array();
     foreach($zones as $zoneMix){
-      $zoneIndex = split("/",$zoneMix);
+      $zoneIndex = explode("/",$zoneMix);
       if(!array_key_exists($zoneIndex[0],$zonesArr)) {
         $zonesArr[$zoneIndex[0]] = array();
       }
@@ -368,9 +358,19 @@ class DNS
     foreach($zonesArr as $nameServer => $nameServerArr){
       $foundInTmp = array();
       foreach($nameServerArr as $zoneArr => $zone){
+
+        /* Strip eventually domain part from hostname 
+         */
+        $zN = trim($zone,".");
+        $nN = trim($name,".");  
+        if(preg_match("/".preg_quote($zN, '/')."$/",$nN)){
+          $nN = preg_replace("/[\.]*".preg_quote($zN, '/')."[\.]*$/","",$nN);
+        }else{
+          $nN = $name;
+        }
         $zoneMix = $nameServer."/".$zone;
         $zoneDn = DNS::getDNSZoneDN($config,$zoneMix);
-        $ldap->ls("(&(objectClass=dNSZone)(zoneName=*)(relativeDomainName=".$name.")(!(relativeDomainName=@)))", $zoneDn,$attrs = array("*"));
+        $ldap->ls("(&(objectClass=dNSZone)(zoneName=*)(relativeDomainName=".$nN.")(!(relativeDomainName=@)))", $zoneDn,$attrs = array("*"));
         while($attrs = $ldap->fetch()){
           $foundInTmp [$zoneMix] = $attrs['dn'];
           $foundIn [$zoneMix] = $attrs['dn'];
@@ -391,10 +391,15 @@ class DNS
     $ldap->search("(&(objectClass=dNSZone)(zoneName=*)(!(relativeDomainName=@)))",array("*"));
     while($attrs = $ldap->fetch()){
 
-      /* If relative domainname == cn
-       * Try to read dnsclass / TTl / zone
+      /* Strip eventually domain part from hostname 
        */
-      if($attrs['relativeDomainName'][0] == $name){
+      $zN = trim($attrs['zoneName'][0],".");
+      $nN = trim($name,"."); 
+      $testname = $attrs['relativeDomainName'][0].".".$zN;
+
+      /* Check given host name with zone settings 
+       */ 
+      if(preg_match("/".preg_quote($testname, '/')."[\.]*$/",$nN) || $attrs['relativeDomainName'][0] == $name){
         $ret['exists'] = true;
         $ret['zoneName'] = $id_tmp;
         foreach(array("dNSClass","dNSTTL") as $atr){
@@ -405,7 +410,7 @@ class DNS
       }
 
       /* Create list with all used records */
-      foreach($RecordTypes as $name => $value){
+      foreach(DNS::$RecordTypes as $name => $value){
 
         /* If there is a record attribute  */
         if(isset($attrs[$name])){
@@ -432,8 +437,6 @@ class DNS
    */
   static function getDNSHostEntriesDiff($config,$oldName,$newEntry,$newName)
   {
-    global $RecordTypes;
-
     $oldEntry = DNS::getDNSHostEntries($config,$oldName);
 
     $add    = array();
@@ -455,6 +458,14 @@ class DNS
     $tmp                = array_flip($zones);
     $zoneName                                  = DNS::getNameFromMix($zoneNameMix);
 
+    /* Strip domain part out of dns host entry 
+     */
+    $zN = trim($zoneName,".");
+    $nN = trim($newName,".");
+    $oN = trim($oldName,".");
+    $newName = preg_replace("/[\.]*".preg_quote($zN, '/')."$/i","",$nN);
+    $oldName = preg_replace("/[\.]*".preg_quote($zN, '/')."$/i","",$oN);
+
     /* If reverseZone can't be resolved ... this 
      *  can't be a valid entry, so remove this account
      */ 
@@ -526,7 +537,9 @@ class DNS
      */
     $baseObj =  array();
     $baseObj['objectClass']       = array("top","dNSZone");
-    $baseObj['dNSTTL']            = $newEntry['dNSTTL'];
+    if(!empty($newEntry['dNSTTL'])){
+      $baseObj['dNSTTL']            = $newEntry['dNSTTL'];
+    }
     $baseObj['dNSClass']          = $newEntry['dNSClass'];
     $baseObj['zoneName']          = $zoneName; 
     $baseObj['relativeDomainName']= $newName; 
@@ -547,7 +560,7 @@ class DNS
      *  Or overwritten and filled with new values.
      */
     foreach($newRecords as $name => $def){
-      if(!in_array($name,$specialAttributes)){
+      if(!in_array_strict($name,$specialAttributes)){
         $add[$stdDn][$name] = $def;
       }
     }
@@ -555,7 +568,7 @@ class DNS
     /* Delete all OLD special attributes.
      */
     foreach($oldEntry['RECORDS'] as $id => $rec){
-      if(in_array($rec['type'],$specialAttributes)){
+      if(in_array_strict($rec['type'],$specialAttributes)){
         $deldn= "relativeDomainName=".$rec['value'].",".$baseDn;
         $del[$deldn] = "";
       }
@@ -604,7 +617,7 @@ class DNS
   static function getNameFromMix($zoneMix){
     $ret = "";
     if(!strstr($zoneMix, '/')) return($ret);   
-    $zoneIndex                 = split("/",$zoneMix);
+    $zoneIndex                 = explode("/",$zoneMix);
     return($zoneIndex[1]);
   }
 
@@ -618,7 +631,7 @@ class DNS
       return($ret);
     }
 
-    $zoneNameIndex             = split("/",$zoneNameMix); 
+    $zoneNameIndex             = explode("/",$zoneNameMix); 
     $zoneName           = $zoneNameIndex[1];
     $nameServer                                = strtolower($zoneNameIndex[0]);
     $ldap               = $config->get_ldap_link();
@@ -648,38 +661,94 @@ class DNS
    */
   static function getAvailableZones($config)
   {
-    $ret = array();
-    $ldap = $config->get_ldap_link();
-    $ldap->cd ($config->current['BASE']);
+    $ReverseZones = $ForwardZones = $zones = array();
+    $runtime_cache = session::get("runtime_cache");
+    if(!isset($runtime_cache['DNS']['getAvailableZones'])){
+    
+      $ret = array();
+      $ldap = $config->get_ldap_link();
+      $tmp = get_sub_list("(&(objectClass=dNSZone)(sOARecord=*))","",get_ou("serverRDN"),
+          $config->current['BASE'],array("zoneName"),GL_NO_ACL_CHECK | GL_SUBSEARCH);
 
-    /* Search for zones ...
-     */
-    $ldap->search("(&(objectClass=dNSZone)(sOARecord=*))",array("zoneName"));
+      foreach($tmp as $at){
+        if(preg_match("/\.in\-addr\.arpa\./",$at['zoneName'][0])){
+          $ReverseZones[$at['dn']] = $at;
+        }else{
+          $ForwardZones[$at['dn']] = $at;
+        }
+      }
 
-    $ForwardZones = array();
-    $ReverseZones = array();
-    $zones = array();
+      foreach($ForwardZones as $dn => $obj){
 
-    while($at = $ldap->fetch()){
-      if(preg_match("/\.in\-addr\.arpa/",$at['zoneName'][0])){
-        $ReverseZones[$at['dn']] = $at;
-      }else{
-        $ForwardZones[$at['dn']] = $at;
+        /* try to find reverse
+         */  
+        foreach($ReverseZones as $Rdn => $Robj ){
+          if(preg_match("/".$dn."/",$Rdn)){
+            $zones[strtoupper($ldap->getCn($dn))."/".$Robj['zoneName'][0]] =  
+              strtoupper($ldap->getCn($dn))."/".$obj['zoneName'][0];
+          }
+        }   
       }
+      $runtime_cache['DNS']['getAvailableZones'] = $zones;
+      session::set("runtime_cache",$runtime_cache);
+    }
+    return($runtime_cache['DNS']['getAvailableZones']);
+  }
+
+
+  static function touchDNSZone($config,$zoneName)
+  {
+    if(empty($zoneName)){
+      return null;
     }
 
-    foreach($ForwardZones as $dn => $obj){
+    preg_match('@(?<server>[^/]*)/(?<name>.*)@',$zoneName,$matches);
+    $name = $matches['name'];
+    $server = strtolower($matches['server']);
 
-      /* try to find reverse
-       */  
-      foreach($ReverseZones as $Rdn => $Robj ){
-        if(preg_match("/".$dn."/",$Rdn)){
-          $zones[strtoupper($ldap->getCn($dn))."/".$Robj['zoneName'][0]] =  
-            strtoupper($ldap->getCn($dn))."/".$obj['zoneName'][0];
+    // Search for the zone entry and its reverse entry.
+    $ldap = $config->get_ldap_link();
+    $ldap-> cd($config->current['BASE']);
+    $ldap->search("(&(objectClass=dNSZone)(zoneName=$name)(sOARecord=*))",array("sOARecord"));
+    if($ldap->count() != 1){
+      trigger_error("Invalid Zone ".$zoneName);
+    }else{
+      $to_update= array();
+      $forward = $ldap->fetch();
+      $to_update[$forward['dn']] = $forward;
+      $ldap->cd($forward['dn']);
+      $ldap->search("(&(objectClass=dNSZone)(relativeDomainName=@)(sOARecord=*))",array("sOARecord"));
+  
+      // We may have multiple reverse zones later.
+      while($attrs = $ldap->fetch()){
+        $to_update[$attrs['dn']] = $attrs;
+      }
+
+      // Increase the sAONumber for each zone
+      foreach($to_update as $zone){
+        $tmp = explode(' ',$zone['sOARecord'][0]);
+        $sOA = $tmp[2];
+        $sOAdate = substr($sOA,0,8);
+        $sOAnumber = substr($sOA,-2);
+        $date = date('Ymd');
+        $number = '01';
+        if($sOAdate < $date){
+          $sOA = $date.$number;
+        } else {
+          $number = sprintf("%02d", $sOAnumber+1);
+          $sOA = $sOAdate.$number;
         }
-      }   
+        $tmp[2] = $sOA;
+        $zone['sOARecord'][0] = implode(' ', $tmp);
+        $attrs = array('sOARecord' => $zone['sOARecord'][0]);
+        $ldap = $config->get_ldap_link();
+        $ldap->cd($zone['dn']);
+        $ldap->modify($attrs);
+        if (!$ldap->success()){
+          msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $dn, LDAP_DEL, get_class()));
+        }
+      }
     }
-    return($zones);
   }
 }
 // vim:tabstop=2:expandtab:shiftwidth=2:filetype=php:syntax:ruler: