Fixed minor bug #0000728 in t3lib_modsettings::init()
[Packages/TYPO3.CMS.git] / t3lib / class.t3lib_modsettings.php
1 <?php
2 /***************************************************************
3 * Copyright notice
4 *
5 * (c) 1999-2004 Kasper Skaarhoj (kasperYYYY@typo3.com)
6 * All rights reserved
7 *
8 * This script is part of the TYPO3 project. The TYPO3 project is
9 * free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or
12 * (at your option) any later version.
13 *
14 * The GNU General Public License can be found at
15 * http://www.gnu.org/copyleft/gpl.html.
16 * A copy is found in the textfile GPL.txt and important notices to the license
17 * from the author is found in LICENSE.txt distributed with these scripts.
18 *
19 *
20 * This script is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
24 *
25 * This copyright notice MUST APPEAR in all copies of the script!
26 ***************************************************************/
27 /**
28 * Manage storing and restoring of $GLOBALS['SOBE']->MOD_SETTINGS settings.
29 * Provides a presets box for BE modules.
30 *
31 * inspired by t3lib_fullsearch
32 *
33 * $Id$
34 *
35 * @author René Fritz <r.fritz@colorcube.de>
36 */
37 /**
38 * [CLASS/FUNCTION INDEX of SCRIPT]
39 *
40 *
41 *
42 * 125: class t3lib_modSettings
43 *
44 * SECTION: Init / setup
45 * 181: function init($prefix='', $storeList='')
46 * 197: function setSessionType($type='ses')
47 *
48 * SECTION: Store list - which values should be stored
49 * 218: function setStoreList($storeList)
50 * 231: function addToStoreList($storeList)
51 * 245: function addToStoreListFromPrefix($prefix='')
52 *
53 * SECTION: Process storage array
54 * 279: function initStorage()
55 * 294: function cleanupStorageArray($storedSettings)
56 * 316: function compileEntry($data)
57 * 343: function getStoredData($storeIndex, $writeArray=array())
58 * 360: function processStoreControl($mconfName='')
59 * 442: function writeStoredSetting($writeArray=array(), $mconfName='')
60 *
61 * SECTION: GUI
62 * 474: function getStoreControl($showElements='load,remove,save', $useOwnForm=TRUE)
63 *
64 * SECTION: Misc
65 * 576: function processEntry($storageArr)
66 *
67 * TOTAL FUNCTIONS: 13
68 * (This index is automatically created/updated by the extension "extdeveval")
69 *
70 */
71
72
73
74
75 /**
76 * usage inside of scbase class
77 *
78 * ....
79 *
80 * $this->MOD_MENU = array(
81 * 'function' => array(
82 * 'xxx ...
83 * ),
84 * 'tx_dam_select_storedSettings' => '',
85 *
86 * ....
87 *
88 * function main() {
89 * // reStore settings
90 * $store = t3lib_div::makeInstance('t3lib_modSettings');
91 * $store->init('tx_dam_select');
92 * $store->setStoreList('tx_dam_select');
93 * $store->processStoreControl();
94 *
95 * // show control panel
96 * $this->content.= $this->doc->section('Settings',$store->getStoreControl(),0,1);
97 *
98 *
99 *
100 * Format of saved settings
101 *
102 * $SOBE->MOD_SETTINGS[$this->prefix.'_storedSettings'] = serialize(
103 * array (
104 * 'any id' => array (
105 * 'title' => 'title for saved settings',
106 * 'desc' => 'descritpion text, not mandatory',
107 * 'data' => array(), // data from MOD_SETTINGS
108 * 'user' => NULL, // can be used for extra data used by the application to identify this entry
109 * 'tstamp' => 12345, // time()
110 * ),
111 * 'another id' => ...
112 *
113 * ) );
114 *
115 */
116
117 /**
118 * Manage storing and restoring of $GLOBALS['SOBE']->MOD_SETTINGS settings.
119 * Provides a presets box for BE modules.
120 *
121 * @author René Fritz <r.fritz@colorcube.de>
122 * @package TYPO3
123 * @subpackage t3lib
124 */
125 class t3lib_modSettings {
126
127 /**
128 * If type is set 'ses' then the module data will be stored into the session and will be lost with logout.
129 * Type 'perm' will store the data permanently.
130 */
131 var $type = 'perm';
132
133 /**
134 * prefix of MOD_SETTING array keys that should be stored
135 */
136 var $prefix = '';
137
138 /**
139 * Names of keys of the MOD_SETTING array which should be stored
140 */
141 var $storeList = array();
142
143 /**
144 * The stored settings array
145 */
146 var $storedSettings = array();
147
148 /**
149 * Message from the last storage command
150 */
151 var $msg = '';
152
153
154 /**
155 * Name of the form. Needed for JS
156 */
157 var $formName = 'storeControl';
158
159
160
161 var $writeDevLog = 0; // write messages into the devlog?
162
163
164
165
166 /********************************
167 *
168 * Init / setup
169 *
170 ********************************/
171
172
173
174 /**
175 * Initializes the object
176 *
177 * @param string Prefix of MOD_SETTING array keys that should be stored
178 * @param array additional names of keys of the MOD_SETTING array which should be stored (array or comma list)
179 * @return void
180 */
181 function init($prefix='', $storeList='') {
182 $this->prefix = $prefix;
183 $this->setStoreList($storeList);
184 $this->type = 'perm';
185
186 // enable dev logging if set
187 if ($GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['t3lib/class.t3lib_modSettings.php']['writeDevLog']) $this->writeDevLog = TRUE;
188 if (TYPO3_DLOG) $this->writeDevLog = TRUE;
189 }
190
191 /**
192 * Set session type to 'ses' which will store the settings data not permanently.
193 *
194 * @param string Default is 'ses'
195 * @return void
196 */
197 function setSessionType($type='ses') {
198 $this->type = $type;
199 }
200
201
202
203
204 /********************************
205 *
206 * Store list - which values should be stored
207 *
208 ********************************/
209
210
211
212 /**
213 * Set MOD_SETTINGS keys which should be stored
214 *
215 * @param mixed array or string (,) - set additional names of keys of the MOD_SETTING array which should be stored
216 * @return void
217 */
218 function setStoreList($storeList) {
219 $this->storeList = is_array($storeList) ? $storeList : t3lib_div::trimExplode(',',$storeList,1);
220
221 if ($this->writeDevLog) t3lib_div::devLog('Store list:'.implode(',',$this->storeList), 't3lib_modSettings', 0);
222 }
223
224
225 /**
226 * Add MOD_SETTINGS keys to the current list
227 *
228 * @param mixed array or string (,) - add names of keys of the MOD_SETTING array which should be stored
229 * @return void
230 */
231 function addToStoreList($storeList) {
232 $storeList = is_array($storeList) ? $storeList : t3lib_div::trimExplode(',',$storeList,1);
233 $this->storeList = array_merge($this->storeList, $storeList);
234
235 if ($this->writeDevLog) t3lib_div::devLog('Store list:'.implode(',',$this->storeList), 't3lib_modSettings', 0);
236 }
237
238
239 /**
240 * Add names of keys of the MOD_SETTING array by a prefix
241 *
242 * @param string prefix of MOD_SETTING array keys that should be stored
243 * @return void
244 */
245 function addToStoreListFromPrefix($prefix='') {
246 global $SOBE;
247
248 $prefix = $prefix ? $prefix : $this->prefix;
249
250 reset($SOBE->MOD_SETTINGS);
251 while(list($key)=each($SOBE->MOD_SETTINGS)) {
252 if (ereg('^'.$prefix,$key)) {
253 $this->storeList[$key]=$key;
254 }
255 }
256
257 unset($this->storeList[$this->prefix.'_storedSettings']);
258
259 if ($this->writeDevLog) t3lib_div::devLog('Store list:'.implode(',',$this->storeList), 't3lib_modSettings', 0);
260 }
261
262
263
264
265
266 /********************************
267 *
268 * Process storage array
269 *
270 ********************************/
271
272
273
274 /**
275 * Get the stored settings from MOD_SETTINGS and set them in $this->storedSettings
276 *
277 * @return void
278 */
279 function initStorage() {
280 global $SOBE;
281
282 $storedSettings = unserialize($SOBE->MOD_SETTINGS[$this->prefix.'_storedSettings']);
283 $this->storedSettings = $this->cleanupStorageArray($storedSettings);
284 }
285
286
287
288 /**
289 * Remove corrupted data entries from the stored settings array
290 *
291 * @param array $storedSettings
292 * @return array $storedSettings
293 */
294 function cleanupStorageArray($storedSettings) {
295
296 $storedSettings = is_array($storedSettings) ? $storedSettings : array();
297
298 // clean up the array
299 foreach($storedSettings as $id => $sdArr) {
300 if (!is_array($sdArr)) unset($storedSettings[$id]);
301 if (!is_array($sdArr['data'])) unset($storedSettings[$id]);
302 if (!trim($sdArr['title'])) $storedSettings[$id]['title'] = '[no title]';
303 }
304
305 return $storedSettings;
306 }
307
308
309 /**
310 * Creates an entry for the stored settings array
311 * Collects data from MOD_SETTINGS selected by the storeList
312 *
313 * @param array Should work with data from _GP('storeControl'). This is ['title']: Title for the entry. ['desc']: A description text. Currently not used by this class
314 * @return array $storageArr: entry for the stored settings array
315 */
316 function compileEntry($data) {
317 global $SOBE;
318
319 $storageData = array();
320 foreach($this->storeList as $MS_key) {
321 $storageData[$MS_key] = $SOBE->MOD_SETTINGS[$MS_key];
322 }
323 $storageArr = array (
324 'title' => $data['title'],
325 'desc' => (string)$data['desc'],
326 'data' => $storageData,
327 'user' => NULL,
328 'tstamp' => time(),
329 );
330 $storageArr = $this->processEntry($storageArr);
331
332 return $storageArr;
333 }
334
335
336 /**
337 * Copies the stored data from entry $index to $writeArray which can be used to set MOD_SETTINGS
338 *
339 * @param mixed The entry key
340 * @param array Preset data array. Will be overwritten by copied values.
341 * @return array Data array
342 */
343 function getStoredData($storeIndex, $writeArray=array()) {
344 if ($this->storedSettings[$storeIndex]) {
345 foreach($this->storeList as $k) {
346 $writeArray[$k] = $this->storedSettings[$storeIndex]['data'][$k];
347 }
348 }
349 return $writeArray;
350 }
351
352
353
354 /**
355 * Processing of the storage command LOAD, SAVE, REMOVE
356 *
357 * @param string Name of the module to store the settings for. Default: $GLOBALS['SOBE']->MCONF['name'] (current module)
358 * @return string Storage message. Also set in $this->msg
359 */
360 function processStoreControl($mconfName='') {
361
362 $this->initStorage();
363
364 #debug($this->storedSettings, '$this->storedSettings', __LINE__, __FILE__);
365
366 $storeControl = t3lib_div::_GP('storeControl');
367 $storeIndex = $storeControl['STORE'];
368
369 if ($this->writeDevLog) t3lib_div::devLog('Store command: '.t3lib_div::arrayToLogString($storeControl), 't3lib_modSettings', 0);
370
371 $msg = '';
372 $saveSettings = FALSE;
373 $writeArray = array();
374
375 if (is_array($storeControl)) {
376
377 //
378 // processing LOAD
379 //
380
381 if ($storeControl['LOAD'] AND $storeIndex) {
382 $writeArray = $this->getStoredData($storeIndex, $writeArray);
383 $saveSettings = TRUE;
384 $msg = "'".$this->storedSettings[$storeIndex]['title']."' preset loaded!";
385
386 //
387 // processing SAVE
388 //
389
390 } elseif ($storeControl['SAVE']) {
391 if (trim($storeControl['title'])) {
392
393 // get the data to store
394 $newEntry = $this->compileEntry($storeControl);
395
396 // create an index for the storage array
397 if (!$storeIndex) {
398 $storeIndex = t3lib_div::shortMD5($newEntry['title']);
399 }
400
401 // add data to the storage array
402 $this->storedSettings[$storeIndex] = $newEntry;
403
404 $saveSettings = TRUE;
405 $msg = "'".$newEntry['title']."' preset saved!";
406
407 } else {
408 $msg = 'Please enter a name for the preset!';
409 }
410
411 //
412 // processing REMOVE
413 //
414
415 } elseif ($storeControl['REMOVE'] AND $storeIndex) {
416 // Removing entry
417 $msg = "'".$this->storedSettings[$storeIndex]['title']."' preset entry removed!";
418 unset($this->storedSettings[$storeIndex]);
419
420 $saveSettings = TRUE;
421 }
422
423
424 $this->msg = $msg;
425
426 if ($saveSettings) {
427 $this->writeStoredSetting($writeArray, $mconfName);
428 }
429
430 }
431 return $this->msg;
432 }
433
434
435 /**
436 * Write the current storage array and update MOD_SETTINGS
437 *
438 * @param array Array of settings which should be overwrite current MOD_SETTINGS
439 * @param string Name of the module to store the settings for. Default: $GLOBALS['SOBE']->MCONF['name'] (current module)
440 * @return void
441 */
442 function writeStoredSetting($writeArray=array(), $mconfName='') {
443 global $SOBE;
444
445 // for debugging: just removes all module data from user settings
446 # $GLOBALS['BE_USER']->pushModuleData($SOBE->MCONF['name'],array());
447
448 unset($this->storedSettings[0]); // making sure, index 0 is not set!
449 $this->storedSettings = $this->cleanupStorageArray($this->storedSettings);
450 $writeArray[$this->prefix.'_storedSettings'] = serialize($this->storedSettings);
451
452 $SOBE->MOD_SETTINGS = t3lib_BEfunc::getModuleData($SOBE->MOD_MENU, $writeArray, ($mconfName?$mconfName:$SOBE->MCONF['name']), $this->type);
453
454 if ($this->writeDevLog) t3lib_div::devLog('Settings stored:'.$this->msg, 't3lib_modSettings', 0);
455 }
456
457
458
459 /********************************
460 *
461 * GUI
462 *
463 ********************************/
464
465
466
467 /**
468 * Returns the storage control box
469 *
470 * @param string List of elemetns which should be shown: load,remove,save
471 * @param boolean If set the box is wrapped with own form tag
472 * @return string HTML code
473 */
474 function getStoreControl($showElements='load,remove,save', $useOwnForm=TRUE) {
475 global $TYPO3_CONF_VARS;
476
477 $showElements = t3lib_div::trimExplode(',', $showElements, 1);
478
479 $this->initStorage();
480
481 // Preset selector
482 $opt=array();
483 $opt[] = '<option value="0"> </option>';
484 foreach($this->storedSettings as $id => $v) {
485 $opt[] = '<option value="'.$id.'">'.htmlspecialchars($v['title']).'</option>';
486 }
487 $storedEntries = count($opt)>1;
488
489
490
491 $codeTD = array();
492
493
494 // LOAD, REMOVE, but also show selector so you can overwrite an entry with SAVE
495 if($storedEntries AND (count($showElements))) {
496
497 // selector box
498 $onChange = 'document.forms[\''.$this->formName.'\'][\'storeControl[title]\'].value= this.options[this.selectedIndex].value!=0 ? this.options[this.selectedIndex].text : \'\';';
499 $code = '
500 <select name="storeControl[STORE]" onChange="'.htmlspecialchars($onChange).'">
501 '.implode('
502 ', $opt).'
503 </select>';
504
505 // load button
506 if(in_array('load', $showElements)) {
507 $code.= '
508 <input type="submit" name="storeControl[LOAD]" value="Load" /> ';
509 }
510
511 // remove button
512 if(in_array('remove', $showElements)) {
513 $code.= '
514 <input type="submit" name="storeControl[REMOVE]" value="Remove" /> ';
515 }
516 $codeTD[] = '<td width="1%">Preset:</td>';
517 $codeTD[] = '<td nowrap="nowrap">'.$code.'&nbsp;&nbsp;</td>';
518 }
519
520
521 // SAVE
522 if(in_array('save', $showElements)) {
523 $onClick = (!$storedEntries) ? '' : 'if (document.forms[\''.$this->formName.'\'][\'storeControl[STORE]\'].options[document.forms[\''.$this->formName.'\'][\'storeControl[STORE]\'].selectedIndex].value<0) return confirm(\'Are you sure you want to overwrite the existing entry?\');';
524 $code = '<input name="storeControl[title]" value="" type="text" max="80" width="25"> ';
525 $code.= '<input type="submit" name="storeControl[SAVE]" value="Save" onClick="'.htmlspecialchars($onClick).'" />';
526 $codeTD[] = '<td nowrap="nowrap">'.$code.'</td>';
527 }
528
529
530 $codeTD = implode ('
531 ', $codeTD);
532
533 if (trim($code)) {
534 $code = '
535 <!--
536 Store control
537 -->
538 <table border="0" cellpadding="3" cellspacing="0" width="100%">
539 <tr class="bgColor4">
540 '.$codeTD.'
541 </tr>
542 </table>
543 ';
544 }
545
546 if ($this->msg) {
547 $code.= '
548 <div><strong>'.htmlspecialchars($this->msg).'</strong></div>';
549 }
550 #TODO need to add parameters
551 if ($useOwnForm AND trim($code)) {
552 $code = '
553 <form action="'.t3lib_div::getIndpEnv('SCRIPT_NAME').'" method="POST" name="'.$this->formName.'" enctype="'.$TYPO3_CONF_VARS['SYS']['form_enctype'].'">'.$code.'</form>';
554 }
555
556 return $code;
557 }
558
559
560
561
562 /********************************
563 *
564 * Misc
565 *
566 ********************************/
567
568
569 /**
570 * Processing entry for the stored settings array
571 * Can be overwritten by extended class
572 *
573 * @param array $storageData: entry for the stored settings array
574 * @return array $storageData: entry for the stored settings array
575 */
576 function processEntry($storageArr) {
577 return $storageArr;
578 }
579 }
580
581 if (defined('TYPO3_MODE') && $TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['t3lib/class.t3lib_modSettings.php']) {
582 include_once($TYPO3_CONF_VARS[TYPO3_MODE]['XCLASS']['t3lib/class.t3lib_modSettings.php']);
583 }
584 ?>