Code

Updated Copy & Paste
[gosa.git] / include / class_CopyPasteHandler.inc
1 <?php
3 define("LDAP_DUMP_PATH","/tmp/gosa");
5 class CopyPasteHandler {
7   var $config;
8   var $current;
10   /* This array contains all dns of the currently copyied objects */
11   var $queue       = array(); 
13   /* Attributes that should be overwritten */
14   var $setvar_array= array();
16   /* The dn of the last edited object */
17   var $lastdn      = "";
20   /* Create CP handler  */
21   function CopyPasteHandler($config)
22   {
23     $this->config = $config;    
24     $this->current= NULL;
25     $this->queue  = array();
26     $this->setvar_array = array();
27   }
30   /* Entry entry to Copy & Paste queue.
31    * A Queue entry is represented as follows.
32    *  array['file_name']  - Position on hdd 
33    *  array['method']     - copy/cut
34    *  array['dn']         - the dn of the object added to the queue 
35    *  array['tab_class']  - Tab object that should be used to initialize the new object
36    *  array['tab_object'] - Tab object name used to initialize correct object Type like USERTABS
37    */
38   function add_to_queue($dn,$action,$tab_class,$tab_object)
39   {
40     if(!class_exists($tab_class)){
41       trigger_error(sprintf("Specified class object '%s' does not exists.",$tab_class));
42       return(FALSE);
43     }
45     if(!isset($this->config->data['TABS'][$tab_object])){
46       trigger_error(sprintf("Specified tab object '%s' does not exists.",$tab_object));
47       return(FALSE);
48     }
50     if(!in_array($action,array("cut","copy"))){
51       trigger_error(sprintf("Specified action '%s' does not exists for copy & paste.",$action));
52       return(FALSE);
53     } 
55     if($file_name = $this->save_dn_attributes_to_hdd($dn)){
56       $tmp = array();
57       $tmp['file_name'] = $file_name;
58       $tmp['method']    = $action;  
59       $tmp['dn']        = $dn;
60       $tmp['tab_class'] = $tab_class;
61       $tmp['tab_object']= $tab_object;
62       $this->queue[]    = $tmp; 
63     }
64   }
67   /* This removes all objects from queue.
68    * Remove hdd dumps of current entries too.
69    * Remove entries older than 24 hours.
70    */
71   function cleanup_queue()
72   {
73     $this->current = FALSE;
74     $this->setvar_array = array();
76     /* Remove all entries from queue */  
77     foreach($this->queue as $key => $entry){
78       @rmdir($entry['file_name']);  
79       unset($this->queue[$key]);
80     }
82     /* Remove entries from hdd that are older than24 hours */
83     $fp = opendir(LDAP_DUMP_PATH);
84     while($file = readdir($fp)){
85       if(is_file(LDAP_DUMP_PATH."/".$file) && !preg_match("/^\./",$file)){
86         $file_time = fileatime(LDAP_DUMP_PATH."/".$file);
87         if($file_time < (time() - (24* 60 *60))){
88           @unlink(LDAP_DUMP_PATH."/".$file);
89         }
90       }
91     }
92   }
95   /* To increase performance we save the ldap dump on hdd 
96    * This function automatically creates the dumps and returns 
97    *  the name of the dumpfile we created 
98    */
99   function save_dn_attributes_to_hdd($dn)
100   {
101     $filename = "Should not be returned";
102     $ldap = $this->config->get_ldap_link();
103     $ldap->cd($this->config->current['BASE']);
104     $res  = $ldap->cat($dn);
106     /* Check if given dn is valid and ldap search was succesfull */ 
107     if(!$res){
108       print_red(sprintf(_("Specified object '%s' is not a valid ldap object, please check copy & paste  methods.")));
109       new log("copy","all/all",$dn,array(),"Could not create dump of ldap object, given object is not present in the ldap database.");
110       return(FALSE);
111     }
113     /* Create data to save given ldap dump on the hdd */
114     $filename = "gosa_copy-paste_dump_".preg_replace("/[^0-9]/","",microtime());
115     $path     = LDAP_DUMP_PATH;
117     /* Create patch if it doesn't exists */
118     if(!is_dir($path)){
119       @mkdir($path);
120     }    
122     /* check if we are able to create a new file the given directory */
123     if(!is_writeable($path)){
124       print_red(sprintf(_("We are not allowed to save ldap dump to '%s', please check permissions."),$path));
125       new log("copy","all/all",$dn,array(), 
126           sprintf("We are not allowed to save ldap dump to '%s', please check permissions.",$path));
127       return(FALSE);
128     }  
130     /* Create file handle */
131     $fp = @fopen($path."/".$filename,"w+");
132     if(!$fp){
133       print_red(sprintf(_("We are not allowed to save ldap dump to '%s/%s', please check permissions."),$path,$filename));
134       new log("copy","all/all",$dn,array(), 
135           sprintf("We are not allowed to save ldap dump to '%s/%s', please check permissions.",$path,$filename));
136       return(FALSE);
137     }    
139     $data = serialize($ldap->fetch());
140     fwrite($fp,$data,strlen($data));
141     fclose($fp);
143     /* Only the webserver should be able to read those files */
144     @chmod($path."/".$filename,0600); 
145     return($path."/".$filename);
146   }
149   /* Check if there are still entries the object queue */
150   function entries_queued()
151   {
152     return( count($this->queue) >=1 || $this->current != FALSE);
153   }
156   /* Paste one entry from queue */
157   function load_entry_from_queue()
158   {
160     /* Save posted variables, handle dialog posts like 'cancel' */
161     $this->save_object();
163     /* If there is currently no object pasted 
164      *  create new object and prepare object to be pasted
165      */
166     if(!$this->current && $this->entries_queued()){
167       $key    = key($this->queue);
168       $entry  = $this->queue[$key];
169       $tab_c = $entry['tab_class'];
170       $tab_o = $entry['tab_object'];
172       if($entry['method'] == "copy"){
173         $entry['object']      = new $tab_c($this->config,$this->config->data['TABS'][$tab_o],"new");
174       }else{
175         $entry['object']      = new $tab_c($this->config,$this->config->data['TABS'][$tab_o],$entry['dn']);
176       }
178       $entry['source_data'] = $this->load_attributes_from_hdd($entry['file_name']);
180       if($entry['method'] == "copy"){
182         /* Prepare each plugin of this tab object to be posted */
183         foreach($entry['object']->by_object as $name => $obj){
185           /* Prepare every single class, to be copied  */
186           $entry['object']->by_object[$name]->PrepareForCopyPaste($entry['source_data']);
188           /* handle some special vars */
189           foreach(array("is_account") as $attr){
190             if(isset($entry['source_data'][$attr])){
191               $entry['object']->by_object[$name]->$attr = $entry['source_data'][$attr];
192             }
193           }
194         }
195       }
197       /* Assign created object as current */
198       $this->current = $entry;
199       unset($this->queue[$key]);
200     }
201   }
204   /* Load dumped ldap entry specified by $filename and 
205    *  return data an unserailized data array
206    */
207   function load_attributes_from_hdd($filename)
208   {
209     $fp = @fopen($filename,"r");
210     if(is_file($filename) && is_readable($filename) && $fp){
211       $data = "";
212       while($str = fgets($fp,512)){
213         $data .= $str;
214       }
215       return(unserialize($data));
216     }else{
217       print_red(sprintf(_("Could not load dumped file '%s', from hard disk drive."),$filename));
218       new log("copy","all/all",$dn,array(), 
219           sprintf(sprintf("Could not load dumped file '%s', from hard disk drive.",$filename)));
220       return(FALSE);
221     }
222   }
225   /* Displays a dialog which allows the user to fix all dependencies of this object.
226      Create unique names, ids, or what ever */
227   function execute()
228   {
229     $type = $this->current['method'];
230     if($type == "cut"){
231       if(isset($_POST['PerformCopyPaste'])){
232         while($this->entries_queued()){
233           $this->load_entry_from_queue();      
234           $this->_update_vars();
236           $msgs = $this->check();
237           if(count ($msgs) ){
238             foreach( $msgs as $msg){
239               print_red($msg);
240             }
241           }else{
243             /* Load next queue entry */
244             $this->lastdn = $this->current['object']->dn;
245             $this->current['object']->save();
246           }
248           $this->current =FALSE;
249         }
250       }
251       if($this->current){
253         $dns = $this->current['dn']."\n";
254         foreach($this->queue as $entry){
255           $dns .= $entry['dn']."\n";
256         }
258         $smarty = get_smarty();
259         $smarty->assign("type","cut");
260         $smarty->assign("Complete",false);
261         $smarty->assign("AttributesToFix","&nbsp;");
262         $smarty->assign("SubDialog",$this->current['object']->SubDialog);
263         $smarty->assign("objectDN"     ,$dns);
264         $smarty->assign("message", sprintf(_("You are going to paste the cutted entry '%s'."), "<pre>".$dns."</pre>"));
265         return($smarty->fetch(get_template_path("copyPasteDialog.tpl",FALSE)));
266       }
267     }
268     if($type == "copy"){
269       if(isset($_POST['PerformCopyPaste'])){
270         $this->_update_vars();
271         $msgs = $this->check();
272         if(count ($msgs) ){
273           foreach( $msgs as $msg){
274             print_red($msg);
275           }
276         }else{
277           $this->current['object']->save();
278           $this->lastdn = $this->current['object']->dn;
279           $this->current =FALSE;
281           /* Load next queue entry */
282           $this->load_entry_from_queue();
283         }
284       }
285       if($this->current){
286         $smarty = get_smarty();
287         $smarty->assign("type","copy");
288         $smarty->assign("Complete",false);
289         $smarty->assign("AttributesToFix",$this->generateAttributesToFix());
290         $smarty->assign("SubDialog",$this->current['object']->SubDialog);
291         $smarty->assign("objectDN"     ,$this->current['source_data']['dn']);
292         $smarty->assign("message", sprintf(_("You are going to paste the copied entry '%s'."), $this->current['source_data']['dn']));
293         return($smarty->fetch(get_template_path("copyPasteDialog.tpl",FALSE)));
294       }
295     }
296   }
299   /* Return the dn of the last edited entry */
300   function last_entry()
301   {
302     return($this->lastdn);
303   }
306   /* Save new values posted by copy & paste dialog */
307   function save_object()
308   {
309     if(isset($_POST['abort_current_cut-copy_operation'])){
310       $this->current = FALSE;
311     }
313     if(isset($_POST['abort_all_cut-copy_operations'])){
314       $this->cleanup_queue();
315       $this->current = FALSE;
316     }
318     /* Assign posted var to all tabs
319      */
320     if($this->current){
321       $this->current['object']->saveCopyDialog();
322     }
323   }
326   /* Create dialog which asks unique attributes/values ... 
327    *  call tabs -> getCopyDialog() 
328    *    which calls tab -> getCopyDialog()  */
329   function generateAttributesToFix()
330   {
331     if($this->current){
332       return($this->current['object']->getCopyDialog());  
333     }
334   }
337   /* Set a single attribute to specified value
338    *  example :   ("base", $newBase );    */
339   function SetVar($name,$value)
340   {
341     $this->setvar_array[$name]=$value; 
342   }
345   /* Update current object attributes, collected via SetVar */
346   function _update_vars()
347   {
348     if($this->current){
350       /* Update all attributes specified with SetVar */
351       foreach($this->setvar_array as $name => $value){
352         if(isset($this->current['object']->$name)){
353           $this->current['object']->$name = $value;
354         }
355       }
357       /* Walk through tabs */
358       foreach($this->current['object']->by_object as $key => $obj){
360         /* Update all attributes specified with SetVar */
361         foreach($this->setvar_array as $name => $value){
362           if(isset($this->current['object']->by_object[$key]->$name)){
363             $this->current['object']->by_object[$key]->$name = $value;
364           }
365         }
366       }
367     }
368   }
371   /* Returns errors from including tabs. */
372   function check()
373   {
374     $ret = array();
375     foreach($this->current['object']->by_object as $obj){
376       if($obj->is_account){
377         $ret = array_merge($ret , $obj->check());
378       }
379     }
380     return($ret);
381   }
384   /* returns the paste icon for headpages */ 
385   function generatePasteIcon()
386   {
387     $Copy_Paste= "&nbsp;<img class='center' src='images/list_seperator.png' align='middle' alt='' height='16' width='1'>&nbsp;";
388     if($this->entries_queued()){
389       $img= "images/copypaste.png";
390       $Copy_Paste.= "<input type='image' name='editPaste' class='center'
391         src='".$img."' alt='"._("Paste")."'>&nbsp;";
392     }else{
393       $Copy_Paste.= "<img class='center' src='images/cant_editpaste.png' alt=\""._("Can't paste")."\">&nbsp;";
394     }
395     return ($Copy_Paste);
396   }
398 // vim:tabstop=2:expandtab:shiftwidth=2:filetype=php:syntax:ruler:
399 ?>