ILIAS  release_5-2 Revision v5.2.25-18-g3f80b828510
class.ilDBGenerator.php
Go to the documentation of this file.
1<?php
2
3/* Copyright (c) 1998-2009 ILIAS open source, Extended GPL, see docs/LICENSE */
4
13class ilDBGenerator {
14
18 protected $target_encoding = 'UTF-8';
22 protected $whitelist = array();
26 protected $blacklist = array();
30 protected $tables = array();
34 protected $filter = array();
35
36
40 public function __construct() {
41 global $ilDB;
42
43 $this->manager = $ilDB->loadModule(ilDBConstants::MODULE_MANAGER);
44 $this->reverse = $ilDB->loadModule(ilDBConstants::MODULE_REVERSE);
45 $this->il_db = $ilDB;
46 include_once("./Services/Database/classes/class.ilDBAnalyzer.php");
47 $this->analyzer = new ilDBAnalyzer();
48
49 $this->allowed_attributes = $ilDB->getAllowedAttributes();
50 }
51
56 public static function lookupAbstractedTables() {
57 global $ilDB;
58
59 $query = "SELECT DISTINCT(table_name) FROM abstraction_progress ";
60 $res = $ilDB->query($query);
61 $names = array();
62 while ($row = $res->fetchRow(ilDBConstants::FETCHMODE_OBJECT)) {
63 $names[] = $row->table_name;
64 }
65
66 // tables that have been already created in an abstracted
67 // way or tables that have been renamed after being abstracted
68 // (see db_update script)
69 $abs_tables = array_merge($names, array(
70 'acc_access_key',
71 'acc_user_access_key',
72 'ldap_rg_mapping',
73 'page_anchor',
74 'qpl_question_orderinghorizontal',
75 'qpl_question_fileupload',
76 'chat_smilies',
77 'style_color',
78 'style_template_class',
79 'style_template',
80 'page_style_usage',
81 'style_setting',
82 'page_editor_settings',
83 'mep_data',
84 'license_data',
85 'loginname_history',
86 'mep_item',
87 'qpl_a_cloze',
88 'qpl_a_imagemap',
89 'qpl_a_matching',
90 'qpl_num_range',
91 'qpl_qst_cloze',
92 'qpl_qst_essay',
93 'qpl_qst_fileupload',
94 'qpl_qst_flash',
95 'qpl_qst_horder',
96 'qpl_qst_imagemap',
97 'qpl_qst_javaapplet',
98 'qpl_qst_matching',
99 'qpl_qst_mc',
100 'qpl_qst_numeric',
101 'qpl_qst_ordering',
102 'qpl_qst_sc',
103 'qpl_qst_textsubset',
104 'qpl_qst_type',
105 'qpl_sol_sug',
106 'udf_text',
107 'udf_clob',
108 'xmlnestedsettmp',
109 'cache_text',
110 'cache_clob',
111 'qpl_a_errortext',
112 'qpl_qst_errortext',
113 'tst_rnd_cpy',
114 'tst_rnd_qpl_title',
115 'qpl_a_mdef',
116 ));
117
118 return $abs_tables;
119 }
120
121
142 public function setTargetEncoding($a_encoding) {
143 $this->target_encoding = $a_encoding;
144 }
145
146
152 public function getTargetEncoding() {
153 return $this->target_encoding;
154 }
155
156
163 public function setBlackList($a_blacklist) {
164 $this->blacklist = $a_blacklist;
165 }
166
167
173 public function getBlackList() {
174 return $this->blacklist;
175 }
176
177
185 public function setWhiteList($a_whitelist) {
186 $this->whitelist = $a_whitelist;
187 }
188
189
195 public function getWhiteList() {
196 return $this->whitelist;
197 }
198
199
204 public function setFilter($a_filter, $a_value) {
205 $this->filter[$a_filter] = $a_value;
206 }
207
208
212 public function getTables() {
213 $r = $this->manager->listTables();
214 $this->tables = $r;
215
216 return $this->tables;
217 }
218
219
223 public function checkProcessing($a_table) {
224 // check black list
225 if (in_array($a_table, $this->blacklist)) {
226 return false;
227 }
228
229 // check white list
230 if (count($this->whitelist) > 0 && !in_array($a_table, $this->whitelist)) {
231 return false;
232 }
233
234 return true;
235 }
236
237
238 protected function openFile($a_path) {
239 if (1) {
240 $file = fopen($a_path, "w");
241 $start .= "\t" . 'global $ilDB;' . "\n\n";
242 fwrite($file, $start);
243
244 return $file;
245 }
246
247 $file = fopen($a_path, "w");
248 $start = '<?php' . "\n" . 'function setupILIASDatabase()' . "\n{\n";
249 $start .= "\t" . 'global $ilDB;' . "\n\n";
250 fwrite($file, $start);
251
252 return $file;
253 }
254
255
256 protected function closeFile($fp) {
257 if (1) {
258 #fwrite ($fp, $end);
259 fclose($fp);
260
261 return;
262 }
263
264 $end = "\n}\n?>\n";
265 fwrite($fp, $end);
266 fclose($fp);
267 }
268
269
275 public function buildDBGenerationScript($a_filename = "") {
276 if (@is_dir($a_filename)) {
277 $isDirectory = true;
278 $path = $a_filename;
279 } else {
280 $isDirectory = false;
281 $path = '';
282 }
283
284 $file = "";
285 if ($a_filename != "" and !$isDirectory) {
286 $file = fopen($a_filename, "w");
287
288 $start = '<?php' . "\n" . 'function setupILIASDatabase()' . "\n{\n";
289 $start .= "\t" . 'global $ilDB;' . "\n\n";
290 fwrite($file, $start);
291 } elseif ($isDirectory) {
292 ;
293 } else {
294 echo "<pre>";
295 }
296
297 $this->getTables();
298
299 foreach ($this->tables as $table) {
300 if ($this->checkProcessing($table)) {
301 if ($a_filename != "") {
302 flush();
303 }
304
305 if ($isDirectory) {
306 $file = $this->openFile($path . '/' . $table);
307 }
308
309 // create table statement
310 $this->buildCreateTableStatement($table, $file);
311
312 // primary key
313 $this->buildAddPrimaryKeyStatement($table, $file);
314
315 // indices
316 $this->buildAddIndexStatements($table, $file);
317
318 // constraints (currently unique keys)
319 $this->buildAddUniqueConstraintStatements($table, $file);
320
321 // auto increment sequence
322 $this->buildCreateSequenceStatement($table, $file);
323
324 if (in_array($table, array('usr_session_stats', 'usr_session_raw', 'il_plugin'))) {
325 continue;
326 }
327
328 // inserts
329 if ($isDirectory) {
330 $this->buildInsertStatement($table, $path);
331 #$this->buildInsertStatementsXML($table,$path);
332 } else {
333 $this->buildInsertStatements($table, $file);
334 }
335
336 if ($isDirectory) {
337 $this->closeFile($file);
338 }
339 } else {
340 if ($a_filename != "") {
341 echo "<br><b>missing: " . $table . "</b>";
342 flush();
343 }
344 }
345 }
346
347 // sequence(s) without table (of same name)
348 $this->buildSingularSequenceStatement($file);
349
350 if ($a_filename == "") {
351 echo "</pre>";
352 } elseif (!$isDirectory) {
353 $end = "\n}\n?>\n";
354 $ok = fwrite($file, $end);
355 var_dump($ok);
356 fclose($file);
357 }
358 }
359
360
367 public function buildCreateTableStatement($a_table, $a_file = "") {
368 $fields = $this->analyzer->getFieldInformation($a_table, true);
369 $this->fields = $fields;
370 $create_st = "\n\n//\n// " . $a_table . "\n//\n";
371 $create_st .= '$fields = array (' . "\n";
372 $f_sep = "";
373 foreach ($fields as $f => $def) {
374
375 $create_st .= "\t" . $f_sep . '"' . $f . '" => array (' . "\n";
376 $f_sep = ",";
377 $a_sep = "";
378 foreach ($def as $k => $v) {
379 if ($k != "nativetype" && $k != "alt_types" && $k != "autoincrement" && !is_null($v)) {
380 switch ($k) {
381 case "notnull":
382 case "unsigned":
383 case "fixed":
384 $v = $v ? "true" : "false";
385 break;
386
387 case "default":
388 case "type":
389 $v = '"' . $v . '"';
390 break;
391
392 default:
393 break;
394 }
395 $create_st .= "\t\t" . $a_sep . '"' . $k . '" => ' . $v . "\n";
396 $a_sep = ",";
397 }
398 }
399 $create_st .= "\t" . ')' . "\n";
400 }
401 $create_st .= ');' . "\n";
402 $create_st .= '$ilDB->createTable("' . $a_table . '", $fields);' . "\n";
403
404 if ($a_file == "") {
405 echo $create_st;
406 } else {
407 fwrite($a_file, $create_st);
408 }
409 }
410
411
418 public function buildAddPrimaryKeyStatement($a_table, $a_file = "") {
419 $pk = $this->analyzer->getPrimaryKeyInformation($a_table);
420
421 if (is_array($pk["fields"]) && count($pk["fields"]) > 0) {
422 $pk_st = "\n" . '$pk_fields = array(';
423 $sep = "";
424 foreach ($pk["fields"] as $f => $pos) {
425 $pk_st .= $sep . '"' . $f . '"';
426 $sep = ",";
427 }
428 $pk_st .= ");\n";
429 $pk_st .= '$ilDB->addPrimaryKey("' . $a_table . '", $pk_fields);' . "\n";
430
431 if ($a_file == "") {
432 echo $pk_st;
433 } else {
434 fwrite($a_file, $pk_st);
435 }
436 }
437 }
438
439
446 public function buildAddIndexStatements($a_table, $a_file = "") {
447 $ind = $this->analyzer->getIndicesInformation($a_table, true);
448
449 if (is_array($ind)) {
450 foreach ($ind as $i) {
451 if ($i["fulltext"]) {
452 $ft = ", true";
453 } else {
454 $ft = ", false";
455 }
456 $in_st = "\n" . '$in_fields = array(';
457 $sep = "";
458 foreach ($i["fields"] as $f => $pos) {
459 $in_st .= $sep . '"' . $f . '"';
460 $sep = ",";
461 }
462 $in_st .= ");\n";
463 $in_st .= '$ilDB->addIndex("' . $a_table . '", $in_fields, "' . $i["name"] . '"' . $ft . ');' . "\n";
464
465 if ($a_file == "") {
466 echo $in_st;
467 } else {
468 fwrite($a_file, $in_st);
469 }
470 }
471 }
472 }
473
474
481 public function buildAddUniqueConstraintStatements($a_table, $a_file = "") {
482 $con = $this->analyzer->getConstraintsInformation($a_table, true);
483
484 if (is_array($con)) {
485 foreach ($con as $i) {
486 $in_st = "\n" . '$in_fields = array(';
487 $sep = "";
488 foreach ($i["fields"] as $f => $pos) {
489 $in_st .= $sep . '"' . $f . '"';
490 $sep = ",";
491 }
492 $in_st .= ");\n";
493 $in_st .= '$ilDB->addUniqueConstraint("' . $a_table . '", $in_fields, "' . $i["name"] . '");' . "\n";
494
495 if ($a_file == "") {
496 echo $in_st;
497 } else {
498 fwrite($a_file, $in_st);
499 }
500 }
501 }
502 }
503
504
511 public function buildCreateSequenceStatement($a_table, $a_file = "") {
512 $seq = $this->analyzer->hasSequence($a_table);
513 if ($seq !== false) {
514 $seq_st = "\n" . '$ilDB->createSequence("' . $a_table . '", ' . (int)$seq . ');' . "\n";
515
516 if ($a_file == "") {
517 echo $seq_st;
518 } else {
519 fwrite($a_file, $seq_st);
520 }
521 }
522 }
523
524
530 public function buildSingularSequenceStatement($a_file = "") {
531 $r = $this->manager->listSequences();
532
533 foreach ($r as $seq) {
534 if (!in_array($seq, $this->tables)) {
535 // 12570
536 if ($seq == "sahs_sc13_seq") {
537 continue;
538 }
539
540 $create_st = "\n" . '$ilDB->createSequence("' . $seq . '");' . "\n";
541
542 if ($a_file == "") {
543 echo $create_st;
544 } else {
545 fwrite($a_file, $create_st);
546 }
547 }
548 }
549
550 }
551
552
560 public function buildInsertStatement($a_table, $a_basedir) {
561 global $ilLog;
562
563 $ilLog->write('Starting export of:' . $a_table);
564
565 $set = $this->il_db->query("SELECT * FROM " . $this->il_db->quoteIdentifier($a_table));
566 $row = 0;
567
568 umask(0000);
569 mkdir($a_basedir . '/' . $a_table . '_inserts', fileperms($a_basedir));
570
571 $filenum = 1;
572 while ($rec = $this->il_db->fetchAssoc($set)) {
573 $values = array();
574 foreach ($rec as $f => $v) {
575 if ($this->fields[$f]['type'] == 'text' and $this->fields[$f]['length'] >= 1000) {
576 $v = $this->shortenText($a_table, $f, $v, $this->fields[$f]['length']);
577 }
578
579 $values[$f] = array(
580 $this->fields[$f]['type'],
581 $v,
582 );
583 }
584
585 $rows[$a_table][$row ++] = $values;
586
587 if ($row >= 1000) {
588 $ilLog->write('Writing insert statements after 1000 lines...');
589 $fp = fopen($a_basedir . '/' . $a_table . '_inserts/' . $filenum ++ . '.data', 'w');
590 fwrite($fp, serialize((array)$rows));
591 fclose($fp);
592
593 $row = 0;
594 unset($rows);
595 }
596 }
597 if ($rows) {
598 $fp = fopen($a_basedir . '/' . $a_table . '_inserts/' . $filenum ++ . '.data', 'w');
599 fwrite($fp, serialize((array)$rows) . "\n");
600 fclose($fp);
601 }
602
603 $ilLog->write('Finished export of: ' . $a_table);
604 if (function_exists('memory_get_usage')) {
605 $ilLog->write('Memory usage: ' . memory_get_usage(true));
606 }
607
608 return true;
609 }
610
611
618 public function buildInsertStatementsXML($a_table, $a_basedir) {
619 global $ilLog;
620
621 include_once './Services/Xml/classes/class.ilXmlWriter.php';
622 $w = new ilXmlWriter();
623 $w->xmlStartTag('Table', array( 'name' => $a_table ));
624
625 $set = $this->il_db->query("SELECT * FROM " . $this->il_db->quoteIdentifier($a_table));
626 $ins_st = "";
627 $first = true;
628 while ($rec = $this->il_db->fetchAssoc($set)) {
629 #$ilLog->write('Num: '.$num++);
630 $w->xmlStartTag('Row');
631
632 $fields = array();
633 $types = array();
634 $values = array();
635 foreach ($rec as $f => $v) {
636 if ($this->fields[$f]['type'] == 'text' and $this->fields[$f]['length'] >= 1000) {
637 $v = $this->shortenText($a_table, $f, $v, $this->fields[$f]['length']);
638 }
639
640 $w->xmlElement('Value', array(
641 'name' => $f,
642 'type' => $this->fields[$f]['type'],
643 ), $v);
644 }
645
646 $w->xmlEndTag('Row');
647 }
648 $w->xmlEndTag('Table');
649
650 $w->xmlDumpFile($a_basedir . '/' . $a_table . '.xml', false);
651 }
652
653
660 public function buildInsertStatements($a_table, $a_file = "") {
661 if ($a_table == "lng_data") {
662 return;
663 }
664
665 $set = $this->il_db->query("SELECT * FROM " . $this->il_db->quoteIdentifier($a_table));
666 $ins_st = "";
667 $first = true;
668 while ($rec = $this->il_db->fetchAssoc($set)) {
669 $fields = array();
670 $types = array();
671 $values = array();
672 $i_str = array();
673 foreach ($rec as $f => $v) {
674 $fields[] = $f;
675 $types[] = '"' . $this->fields[$f]["type"] . '"';
676 $v = str_replace('\\', '\\\\', $v);
677 $values[] = "'" . str_replace("'", "\'", $v) . "'";
678 $i_str[] = "'" . $f . "' => array('" . $this->fields[$f]["type"] . "', '" . str_replace("'", "\'", $v) . "')";
679 }
680 $fields_str = "(" . implode($fields, ",") . ")";
681 $types_str = "array(" . implode($types, ",") . ")";
682 $values_str = "array(" . implode($values, ",") . ")";
683 $ins_st = "\n" . '$ilDB->insert("' . $a_table . '", array(' . "\n";
684 $ins_st .= implode($i_str, ", ") . "));\n";
685 //$ins_st.= "\t".$fields_str."\n";
686 //$ins_st.= "\t".'VALUES '."(%s".str_repeat(",%s", count($fields) - 1).')"'.",\n";
687 //$ins_st.= "\t".$types_str.','.$values_str.');'."\n";
688
689 if ($a_file == "") {
690 echo $ins_st;
691 } else {
692 fwrite($a_file, $ins_st);
693 }
694 $ins_st = "";
695 }
696 }
697
698
704 public function getHTMLOverview($a_filename = "") {
705 $tpl = new ilTemplate("tpl.db_overview.html", true, true, "Services/Database");
706
707 $this->getTables();
708 $cnt = 1;
709 foreach ($this->tables as $table) {
710 if ($this->checkProcessing($table)) {
711 // create table statement
712 if ($this->addTableToOverview($table, $tpl, $cnt)) {
713 $cnt ++;
714 }
715 }
716 }
717
718 $tpl->setVariable("TXT_TITLE", "ILIAS Abstract DB Tables (" . ILIAS_VERSION . ")");
719
720 if ($a_filename == "") {
721 echo $tpl->get();
722 }
723 }
724
725
729 public function addTableToOverview($a_table, $a_tpl, $a_cnt) {
730 $fields = $this->analyzer->getFieldInformation($a_table);
731 $indices = $this->analyzer->getIndicesInformation($a_table);
732 $constraints = $this->analyzer->getConstraintsInformation($a_table);
733 $pk = $this->analyzer->getPrimaryKeyInformation($a_table);
734 $auto = $this->analyzer->getAutoIncrementField($a_table);
735 $has_sequence = $this->analyzer->hasSequence($a_table);
736
737 // table filter
738 if (isset($this->filter["has_sequence"])) {
739 if ((!$has_sequence && $auto == "" && $this->filter["has_sequence"])
740 || (($has_sequence || $auto != "") && !$this->filter["has_sequence"])
741 ) {
742 return false;
743 }
744 }
745
746 // indices
747 $indices_output = false;
748 if (is_array($indices) && count($indices) > 0 && !$this->filter["skip_indices"]) {
749 foreach ($indices as $index => $def) {
750 $f2 = array();
751 foreach ($def["fields"] as $f => $pos) {
752 $f2[] = $f;
753 }
754 $a_tpl->setCurrentBlock("index");
755 $a_tpl->setVariable("VAL_INDEX", $def["name"]);
756 $a_tpl->setVariable("VAL_FIELDS", implode($f2, ", "));
757 $a_tpl->parseCurrentBlock();
758 $indices_output = true;
759 }
760 $a_tpl->setCurrentBlock("index_table");
761 $a_tpl->parseCurrentBlock();
762 }
763
764 // constraints
765 $constraints_output = false;
766 if (is_array($constraints) && count($constraints) > 0 && !$this->filter["skip_constraints"]) {
767 foreach ($constraints as $index => $def) {
768 $f2 = array();
769 foreach ($def["fields"] as $f => $pos) {
770 $f2[] = $f;
771 }
772 $a_tpl->setCurrentBlock("constraint");
773 $a_tpl->setVariable("VAL_CONSTRAINT", $def["name"]);
774 $a_tpl->setVariable("VAL_CTYPE", $def["type"]);
775 $a_tpl->setVariable("VAL_CFIELDS", implode($f2, ", "));
776 $a_tpl->parseCurrentBlock();
777 $constraints_output = true;
778 }
779 $a_tpl->setCurrentBlock("constraint_table");
780 $a_tpl->parseCurrentBlock();
781 }
782
783 // fields
784 $fields_output = false;
785 foreach ($fields as $field => $def) {
786 // field filter
787 if (isset($this->filter["alt_types"])) {
788 if (($def["alt_types"] == "" && $this->filter["alt_types"])
789 || ($def["alt_types"] != "" && !$this->filter["alt_types"])
790 ) {
791 continue;
792 }
793 }
794 if (isset($this->filter["type"])) {
795 if ($def["type"] != $this->filter["type"]) {
796 continue;
797 }
798 }
799 if (isset($this->filter["nativetype"])) {
800 if ($def["nativetype"] != $this->filter["nativetype"]) {
801 continue;
802 }
803 }
804 if (isset($this->filter["unsigned"])) {
805 if ($def["unsigned"] != $this->filter["unsigned"]) {
806 continue;
807 }
808 }
809
810 $a_tpl->setCurrentBlock("field");
811 if (empty($pk["fields"][$field])) {
812 $a_tpl->setVariable("VAL_FIELD", strtolower($field));
813 } else {
814 $a_tpl->setVariable("VAL_FIELD", "<u>" . strtolower($field) . "</u>");
815 }
816 $a_tpl->setVariable("VAL_TYPE", $def["type"]);
817 $a_tpl->setVariable("VAL_LENGTH", (!is_null($def["length"])) ? $def["length"] : "&nbsp;");
818
819 if (strtolower($def["default"]) == "current_timestamp") {
820 //$def["default"] = "0000-00-00 00:00:00";
821 unset($def["default"]);
822 }
823
824 $a_tpl->setVariable("VAL_DEFAULT", (!is_null($def["default"])) ? $def["default"] : "&nbsp;");
825 $a_tpl->setVariable("VAL_NOT_NULL", (!is_null($def["notnull"])) ? (($def["notnull"]) ? "true" : "false") : "&nbsp;");
826 $a_tpl->setVariable("VAL_FIXED", (!is_null($def["fixed"])) ? (($def["fixed"]) ? "true" : "false") : "&nbsp;");
827 $a_tpl->setVariable("VAL_UNSIGNED", (!is_null($def["unsigned"])) ? (($def["unsigned"]) ? "true" : "false") : "&nbsp;");
828 $a_tpl->setVariable("VAL_ALTERNATIVE_TYPES", ($def["alt_types"] != "") ? $def["alt_types"] : "&nbsp;");
829 $a_tpl->setVariable("VAL_NATIVETYPE", ($def["nativetype"] != "") ? $def["nativetype"] : "&nbsp;");
830 $a_tpl->parseCurrentBlock();
831 $fields_output = true;
832 }
833
834 if ($fields_output) {
835 $a_tpl->setCurrentBlock("field_table");
836 $a_tpl->parseCurrentBlock();
837 }
838
839 // table information
840 if ($indices_output || $fields_output || $constraints_output) {
841 $a_tpl->setCurrentBlock("table");
842 $a_tpl->setVariable("TXT_TABLE_NAME", strtolower($a_table));
843 if ($has_sequence || $auto != "") {
844 $a_tpl->setVariable("TXT_SEQUENCE", "Has Sequence");
845 } else {
846 $a_tpl->setVariable("TXT_SEQUENCE", "No Sequence");
847 }
848 $a_tpl->setVariable("VAL_CNT", (int)$a_cnt);
849 $a_tpl->parseCurrentBlock();
850
851 return true;
852 }
853
854 return false;
855 }
856
857
867 protected function shortenText($table, $field, $a_value, $a_size) {
868 global $ilLog;
869
870 if ($this->getTargetEncoding() == 'UTF-8') {
871 return $a_value;
872 }
873 // Convert to target encoding
874 $shortened = mb_convert_encoding($a_value, $this->getTargetEncoding(), 'UTF-8');
875 // Shorten
876 include_once './Services/Utilities/classes/class.ilStr.php';
877 $shortened = ilStr::shortenText($shortened, 0, $a_size, $this->getTargetEncoding());
878 // Convert back to UTF-8
879 $shortened = mb_convert_encoding($shortened, 'UTF-8', $this->getTargetEncoding());
880
881 if (strlen($a_value) != strlen($shortened)) {
882 $ilLog->write('Table : ' . $table);
883 $ilLog->write('Field : ' . $field);
884 $ilLog->write('Type : ' . $this->fields[$field]['type']);
885 $ilLog->write('Length : ' . $this->fields[$field]['length']);
886 $ilLog->write('Before : ' . $a_value);
887 $ilLog->write('Shortened : ' . $shortened);
888 $ilLog->write('Strlen Before: ' . strlen($a_value));
889 $ilLog->write('Strlen After : ' . strlen($shortened));
890 }
891
892 return $shortened;
893 }
894}
895
896?>
memory_get_usage(true)/1024/1024)
global $tpl
Definition: ilias.php:8
$path
Definition: aliased.php:25
An exception for terminatinating execution or to throw for unit testing.
This class gives all kind of DB information using the MDB2 manager and reverse module.
static shortenText($a_string, $a_start_pos, $a_num_bytes, $a_encoding='UTF-8')
Shorten text to the given number of bytes.
special template class to simplify handling of ITX/PEAR
XML writer class.
$w
$r
Definition: example_031.php:79
const ILIAS_VERSION
if(!file_exists("$old.txt")) if( $old===$new) if(file_exists("$new.txt")) $file
global $ilDB
$errors fields
Definition: imgupload.php:52