44 $lng = $DIC->language();
46 $pathinfo = pathinfo($a_file);
47 $file = $pathinfo[
"basename"];
50 if ($pathinfo[
"extension"] ??
'' ===
'') {
57 self::moveUploadedFile($a_file, $file, $a_directory .
"/" . $file);
58 self::unzip($a_directory .
"/" . $file);
59 unlink($a_directory .
"/" . $file);
67 if (empty($filearray)) {
69 $lng->txt(
"archive_broken"),
75 foreach ($filearray[
"file"] as
$key => $value) {
77 if (substr($value, 0, 1) ==
"." || stristr(
78 $filearray[
"path"][
$key],
81 unlink($filearray[
"path"][$key] . $value);
82 unset($filearray[
"path"][$key]);
83 unset($filearray[
"file"][$key]);
90 unlink($filearray[
'path'][$key]);
92 $lng->txt(
"file_is_infected") .
"<br />" . $vir[1],
95 } elseif ($vir[1] !=
"") {
106 foreach (array_count_values($filearray[
"file"]) as
$key => $value) {
112 if (strlen($doublettes) > 0) {
114 $lng->txt(
"exc_upload_error") .
"<br />" .
$lng->txt(
115 "zip_structure_error" 121 $mac_dir = $a_directory .
"/__MACOSX";
122 if (file_exists($mac_dir)) {
123 self::delDir($mac_dir);
141 $lng = $DIC->language();
143 $dirlist = opendir($dir);
144 while (
false !== ($file = readdir($dirlist))) {
145 if (!is_file($dir .
"/" . $file) && !is_dir($dir .
"/" . $file)) {
147 $lng->txt(
"filenames_not_supported"),
152 if ($file !=
'.' && $file !=
'..') {
153 $newpath = $dir .
'/' . $file;
154 $level = explode(
'/', $newpath);
155 if (is_dir($newpath)) {
158 $arr[
"path"][] = $dir .
"/";
159 $arr[
"file"][] = end($level);
181 [\x09\x0A\x0D\x20-\x7E] # ASCII 182 | [\xC2-\xDF][\x80-\xBF] # non-overlong 2-byte 183 | \xE0[\xA0-\xBF][\x80-\xBF] # excluding overlongs 184 | [\xE1-\xEC\xEE\xEF][\x80-\xBF]{2} # straight 3-byte 185 | \xED[\x80-\x9F][\x80-\xBF] # excluding surrogates 186 | \xF0[\x90-\xBF][\x80-\xBF]{2} # planes 1-3 187 | [\xF1-\xF3][\x80-\xBF]{3} # planes 4-15 188 | \xF4[\x80-\x8F][\x80-\xBF]{2} # plane 16 201 $DIC->fileServiceSettings()
204 return $sanitizer->
sanitize($a_filename);
210 public static function rename(
string $a_source,
string $a_target): bool
212 $pi = pathinfo($a_target);
215 $DIC->fileServiceSettings()
218 if (!$sanitizer->isClean($a_target)) {
222 return rename($a_source, $a_target);
245 bool $preserveTimeAttributes =
false 247 $sourceFS = LegacyPathHelper::deriveFilesystemFrom($a_sdir);
248 $targetFS = LegacyPathHelper::deriveFilesystemFrom($a_tdir);
250 $sourceDir = LegacyPathHelper::createRelativePath($a_sdir);
251 $targetDir = LegacyPathHelper::createRelativePath($a_tdir);
254 if (!$sourceFS->hasDir($sourceDir)) {
258 $sourceList = $sourceFS->listContents($sourceDir,
true);
260 foreach ($sourceList as $item) {
261 if ($item->isDir()) {
265 $itemPath = $targetDir .
'/' . substr(
269 $stream = $sourceFS->readStream($item->getPath());
270 $targetFS->writeStream($itemPath, $stream);
301 $a_dir = dirname($a_dir);
303 while ($last_dirname != $a_dir) {
304 array_unshift($dirs, $a_dir);
305 $last_dirname = $a_dir;
306 $a_dir = dirname($a_dir);
310 $reverse_paths = array_reverse($dirs,
true);
312 foreach ($reverse_paths as
$key => $value) {
313 if ($found_index == -1) {
314 if (is_dir($value)) {
320 $old_mask = umask(0000);
321 foreach ($dirs as $dirindex => $dir) {
323 if ($dirindex >= $found_index) {
324 if (!file_exists($dir)) {
325 if (strcmp(substr($dir, strlen($dir) - 1, 1),
"/") == 0) {
328 $dir = substr($dir, 0, strlen($dir) - 1);
331 error_log(
"Can't make directory: $dir");
334 } elseif (!is_dir($dir)) {
335 error_log(
"$dir is not a directory");
339 $umask = fileperms($dir);
374 if (!is_dir($directory)) {
376 $size = @filesize($directory);
377 return ($size ===
false) ? -1 : $size;
379 if ($DIR = opendir($directory)) {
380 while (($dirfile = readdir($DIR)) !==
false) {
382 $directory . DIRECTORY_SEPARATOR . $dirfile
383 ) || $dirfile ==
'.' || $dirfile ==
'..') {
386 if (is_file($directory . DIRECTORY_SEPARATOR . $dirfile)) {
388 $directory . DIRECTORY_SEPARATOR . $dirfile
390 } elseif (is_dir($directory . DIRECTORY_SEPARATOR . $dirfile)) {
392 $directory . DIRECTORY_SEPARATOR . $dirfile
424 public static function makeDir(
string $a_dir): bool
426 $a_dir = trim($a_dir);
429 if (substr($a_dir, -1) ==
"/") {
430 $a_dir = substr($a_dir, 0, -1);
434 if (!(
$path = substr(
437 strrpos($a_dir,
"/") - strlen($a_dir)
443 if (is_dir($a_dir)) {
446 $old_mask = umask(0000);
447 $result = @mkdir($a_dir, fileperms(
$path));
470 case strpos($a_target, ILIAS_ABSOLUTE_PATH .
'/Customizing') === 0:
475 "Can not move files to \"$a_target\" because path can not be mapped to web, storage or customizing location." 479 $absTargetDir = dirname($a_target);
480 $targetDir = LegacyPathHelper::createRelativePath($absTargetDir);
482 return [$targetFilesystem, $targetDir];
508 bool $a_raise_errors =
true,
509 string $a_mode =
"move_uploaded" 512 $main_tpl = $DIC->ui()->mainTemplate();
513 $target_filename = basename($a_target);
518 [$target_filesystem, $target_dir] = self::sanitateTargetPath($a_target);
520 $upload = $DIC->upload();
523 if (!$upload->hasBeenProcessed()) {
528 if (!$upload->hasUploads()) {
530 $DIC->language()->txt(
"upload_error_file_not_found")
533 $upload_result = $upload->getResults()[$a_file] ?? null;
535 if (!$upload_result->isOK()) {
536 throw new ilException($upload_result->getStatus()->getMessage());
542 if (!$a_raise_errors) {
543 $main_tpl->setOnScreenMessage(
'failure', $e->getMessage(),
true);
551 $upload->moveOneFileTo(
568 public static function zip(
571 bool $compress_content =
false 575 if ($compress_content) {
577 $pathinfo = pathinfo($a_dir);
578 chdir($pathinfo[
"dirname"]);
581 $pathinfo = pathinfo($a_file);
582 $dir = $pathinfo[
"dirname"];
583 $file = $pathinfo[
"basename"];
585 if (!$compress_content) {
596 if (is_array($a_dir)) {
598 foreach ($a_dir as $dir) {
599 $name = basename($dir);
603 $name = basename($a_dir);
604 if (trim(
$name) !=
"*") {
632 public static function delDir(
string $a_dir,
bool $a_clean_only =
false): void
634 if (!is_dir($a_dir) || is_int(strpos($a_dir,
".."))) {
638 $current_dir = opendir($a_dir);
647 while ($entryname = readdir($current_dir)) {
648 $files[] = $entryname;
651 foreach ($files as $file) {
654 ) and ($file !=
"." and $file !=
"..")) {
656 } elseif ($file !=
"." and $file !=
"..") {
657 unlink($a_dir .
"/" . $file);
661 closedir($current_dir);
662 if (!$a_clean_only) {
669 $file_peaces = explode(
'.', $a_initial_filename);
671 $file_extension = array_pop($file_peaces);
673 if (SUFFIX_REPL_ADDITIONAL) {
674 $string_extensions = SUFFIX_REPL_DEFAULT .
"," . SUFFIX_REPL_ADDITIONAL;
676 $string_extensions = SUFFIX_REPL_DEFAULT;
679 $sufixes = explode(
",", $string_extensions);
681 if (in_array($file_extension, $sufixes)) {
682 $file_extension =
"sec";
685 $file_peaces[] = $file_extension;
688 foreach ($file_peaces as $piece) {
689 $safe_filename .=
"$piece";
690 if ($piece != end($file_peaces)) {
691 $safe_filename .=
".";
695 return $safe_filename;
716 ?
string $a_sub_dir =
"" 718 $current_dir = opendir($a_dir . $a_sub_dir);
723 while ($entry = readdir($current_dir)) {
724 if (is_dir($a_dir .
"/" . $entry)) {
725 $dirs[$entry] = [
"type" =>
"dir",
727 "subdir" => $a_sub_dir
729 if ($a_rec && $entry !=
"." && $entry !=
"..") {
733 $a_sub_dir .
"/" . $entry
735 $subitems = array_merge($subitems, $si);
738 if ($entry !=
"." && $entry !=
"..") {
739 $size = filesize($a_dir . $a_sub_dir .
"/" . $entry);
740 $files[$entry] = [
"type" =>
"file",
743 "subdir" => $a_sub_dir
751 return array_merge($dirs, $files, $subitems);
771 if ($mode ===
"filesystem") {
774 if (defined(
"ILIAS_MODULE")) {
802 $size =
new DataSize(self::getUploadSizeLimitBytes(), DataSize::MB);
803 $max_filesize = $size->__toString();
804 $lng = $DIC->language();
806 return $lng->txt(
"file_notice") .
" $max_filesize.";
816 return $policy->
ascii($a_filename);
826 public static function ilTempnam(?
string $a_temp_path = null): string
828 if ($a_temp_path === null) {
831 $temp_path = $a_temp_path;
834 if (!is_dir($temp_path)) {
837 $temp_name = $temp_path .
"/" . uniqid(
"tmp");
843 string $path_to_zip_file,
844 bool $overwrite_existing =
false,
845 bool $unpack_flat =
false 850 $DIC->fileServiceSettings()
853 $log = $DIC->logger()->root();
855 if (!is_file($path_to_zip_file)) {
860 $temporary_unzip_directory = self::ilTempnam();
861 self::makeDir($temporary_unzip_directory);
862 copy($path_to_zip_file, $temporary_unzip_directory . DIRECTORY_SEPARATOR . basename($path_to_zip_file));
863 $original_path_to_zip_file = $path_to_zip_file;
864 $path_to_zip_file = $temporary_unzip_directory . DIRECTORY_SEPARATOR . basename($path_to_zip_file);
865 $original_zip_path_info = pathinfo($original_path_to_zip_file);
866 $unzippable_zip_path_info = pathinfo($path_to_zip_file);
868 $unzippable_zip_directory = $unzippable_zip_path_info[
"dirname"];
869 $unzippable_zip_filename = $unzippable_zip_path_info[
"basename"];
872 $current_directory = getcwd();
873 chdir($unzippable_zip_directory);
874 $unzip_command = PATH_TO_UNZIP;
877 if (!$overwrite_existing) {
884 chdir($current_directory);
888 $dir_realpath = realpath($unzippable_zip_directory);
890 if (is_link(
$name)) {
891 $target = readlink(
$name);
892 if (substr($target, 0, strlen($dir_realpath)) != $dir_realpath) {
894 $log->info(
"Removed symlink " .
$name);
905 self::renameExecutables($unzippable_zip_directory);
910 $target_dir_name = $original_zip_path_info[
"dirname"];
911 $target_dir_name = realpath($target_dir_name);
915 self::recursive_dirscan($temporary_unzip_directory, $file_array);
916 if (is_array($file_array[
"file"])) {
917 foreach ($file_array[
"file"] as $k =>
$f) {
919 substr(
$f, 0, 1) !==
"." 920 &&
$f !== basename($original_path_to_zip_file)
923 $file_array[
"path"][$k] .
$f,
924 $target_dir_name . DIRECTORY_SEPARATOR . $f
930 $target_directory = $target_dir_name;
932 $temporary_unzip_directory,
937 self::delDir($temporary_unzip_directory);
945 $def_arr = explode(
",", SUFFIX_REPL_DEFAULT);
946 foreach ($def_arr as $def) {
947 self::rRenameSuffix($a_dir, trim($def),
"sec");
950 $def_arr = explode(
",", SUFFIX_REPL_ADDITIONAL);
951 foreach ($def_arr as $def) {
952 self::rRenameSuffix($a_dir, trim($def),
"sec");
962 public static function rRenameSuffix(
string $a_dir,
string $a_old_suffix,
string $a_new_suffix): bool
966 || strpos($a_dir,
"..") !==
false 967 || trim($a_old_suffix) ===
"") {
972 if (!@is_dir($a_dir)) {
977 $dir = opendir($a_dir);
978 if ($dir ===
false) {
986 while ($file = readdir($dir)) {
992 if (in_array($file, $prohibited)) {
993 unlink($a_dir .
"/" . $file);
998 if (@is_dir($a_dir .
"/" . $file)) {
999 self::rRenameSuffix($a_dir .
"/" . $file, $a_old_suffix, $a_new_suffix);
1003 if (@is_file($a_dir .
"/" . $file)) {
1005 if (strrpos($file,
'.') == (strlen($file) - 1)) {
1007 rename($a_dir .
'/' . $file, substr($a_dir .
'/' . $file, 0, -1));
1010 unlink($a_dir .
'/' . $file);
1014 $file = substr($file, 0, -1);
1017 $path_info = pathinfo($a_dir .
"/" . $file);
1019 if (strtolower($path_info[
"extension"] ??
'') === strtolower($a_old_suffix)) {
1020 $pos = strrpos($a_dir .
"/" . $file,
".");
1021 $new_name = substr($a_dir .
"/" . $file, 0, $pos) .
"." . $a_new_suffix;
1023 if (file_exists($new_name)) {
1024 if (is_dir($new_name)) {
1025 self::delDir($new_name);
1030 rename($a_dir .
"/" . $file, $new_name);
1040 $path = preg_replace(
"/[\/\\\]+$/",
"", $path);
1041 return (
string)
$path;
1049 $convertPhpIniSizeValueToBytes =
function ($phpIniSizeValue) {
1050 if (is_numeric($phpIniSizeValue)) {
1051 return $phpIniSizeValue;
1054 $suffix = substr($phpIniSizeValue, -1);
1055 $value = substr($phpIniSizeValue, 0, -1);
1057 switch (strtoupper($suffix)) {
1079 $uploadSizeLimitBytes = min(
1080 $convertPhpIniSizeValueToBytes(ini_get(
'post_max_size')),
1081 $convertPhpIniSizeValueToBytes(ini_get(
'upload_max_filesize'))
1084 return $uploadSizeLimitBytes;
static getWebspaceDir(string $mode="filesystem")
get webspace directory
Class ilFileServicesPolicy.
const STORAGE
The filesystem outside of the ilias web root.
static utf8_encode(string $string)
utf8-encodes string if it is not a valid utf8-string.
Class ChatMainBarProvider .
static stripSlashes(string $a_str, bool $a_strip_html=true, string $a_allow="")
static processZipFile(string $a_directory, string $a_file, bool $structure)
static virusHandling(string $a_file, string $a_orig_name='', bool $a_clean=true)
This class provides the data size with additional information to remove the work to calculate the siz...
static rCopy(string $a_sdir, string $a_tdir, bool $preserveTimeAttributes=false)
Copies content of a directory $a_sdir recursively to a directory $a_tdir.
static getValidFilename(string $a_filename)
static rRenameSuffix(string $a_dir, string $a_old_suffix, string $a_new_suffix)
Renames all files with certain suffix and gives them a new suffix.
static escapeShellArg(string $a_arg)
static makeDirParents(string $a_dir)
Create a new directory and all parent directories.
static getUploadSizeLimitBytes()
static removeTrailingPathSeparators(string $path)
static unzip(string $path_to_zip_file, bool $overwrite_existing=false, bool $unpack_flat=false)
static getSafeFilename(string $a_initial_filename)
static getASCIIFilename(string $a_filename)
static renameExecutables(string $a_dir)
static recursive_dirscan(string $dir, array &$arr)
Recursively scans a given directory and writes path and filename into referenced array.
static dirsize(string $directory)
get size of a directory or a file.
static delDir(string $a_dir, bool $a_clean_only=false)
removes a dir and all its content (subdirs and files) recursively
static createDirectory(string $a_dir, int $a_mod=0755)
create directory
const CUSTOMIZING
The filesystem within the web root where all the skins and plugins are saved.
static getDir(string $a_dir, bool $a_rec=false, ?string $a_sub_dir="")
get directory
static moveUploadedFile(string $a_file, string $a_name, string $a_target, bool $a_raise_errors=true, string $a_mode="move_uploaded")
move uploaded file
static getDataDir()
get data directory (outside webspace)
static sanitateTargetPath(string $a_target)
static execQuoted(string $cmd, ?string $args=null)
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
static _sanitizeFilemame(string $a_filename)
Class ilFileServicesFilenameSanitizer.
static int $INFECTED_FILE
static ilTempnam(?string $a_temp_path=null)
Returns a unique and non existing Path for e temporary file or directory.
sanitize(string $filename)
static zip(string $a_dir, string $a_file, bool $compress_content=false)
zips given directory/file into given zip.file
const TEMPORARY
The ILIAS temporary directory.
static rename(string $a_source, string $a_target)
static int $DOUBLETTES_FOUND
Class FlySystemFileAccessTest disabled disabled disabled.
const WEB
The filesystem within the ilias web root.
static makeDir(string $a_dir)
creates a new directory and inherits all filesystem permissions of the parent directory You may pass ...