class IPF_Admin_FileBrowser_Controller extends IPF_Admin_Base_Controller
{
- static function cmp($a, $b)
- {
- if ($a['name'] == $b['name'])
- return 0;
- return ($a['name'] < $b['name']) ? -1 : 1;
- }
-
- /** @var string */
- protected $root;
-
- /** @var string */
- protected $dir;
-
- /** @var string */
- protected $relative;
-
- protected function setRoot()
- {
- $this->root = realpath(IPF::getUploadPath()) . DIRECTORY_SEPARATOR;
- }
-
- protected function validatePath($path)
- {
- $path = realpath($path) . DIRECTORY_SEPARATOR;
- if (!\PFF\Str::startsWith($path, $this->root))
- throw new IPF_Admin_AccessDenied;
- return $path;
- }
-
- protected function setCurrentDir()
- {
- $this->setRoot();
- $this->dir = $this->validatePath(IPF::getUploadPath() . DIRECTORY_SEPARATOR . \PFF\Arr::get($this->request->REQUEST, 'dir', ''));
- $this->relative = substr($this->dir, strlen($this->root));
- }
-
- protected function validateName($name)
- {
- $name = basename($name);
- if (!$name || $name === '.' || $name === '..')
- throw new IPF_Admin_AccessDenied;
-
- return $name;
- }
-
protected function before($action)
{
$this->ensureUserIsStaff();
- $this->setCurrentDir();
}
function index()
function listDirectory()
{
- list($dirs, $files) = self::listDir($this->dir);
+ $dir = $this->validateDirectory($this->request->GET['dir']);
+
+ list($dirs, $files) = self::listDir($dir);
return new IPF_HTTP_Response_Json([
'dirs' => $dirs,
'files' => $files,
function rename()
{
+ $dir = $this->validateDirectory($this->request->POST['dir']);
$old_name = $this->validateName($this->request->POST['old_name']);
$new_name = $this->validateName($this->request->POST['new_name']);
- rename($this->dir . $old_name, $this->dir . $new_name);
+ rename($dir . $old_name, $dir . $new_name);
return $this->noContent();
}
function move()
{
- $destination = $this->validatePath(IPF::getUploadPath() . DIRECTORY_SEPARATOR . \PFF\Arr::get($this->request->POST, 'destination', ''));
+ $dir = $this->validateDirectory($this->request->POST['dir']);
+ $destination = $this->validateDirectory($this->request->POST['destination']);
$name = $this->validateName($this->request->POST['name']);
- rename($this->dir . $name, $destination . $name);
+
+ rename($dir . $name, $destination . $name);
return $this->noContent();
}
function mkdir()
{
+ $dir = $this->validateDirectory($this->request->POST['dir']);
$name = $this->validateName($this->request->POST['name']);
- mkdir($this->dir . $name);
+ mkdir($dir . $name);
return $this->noContent();
}
function delete()
{
+ $dir = $this->validateDirectory($this->request->POST['dir']);
$name = $this->validateName($this->request->POST['name']);
- IPF_Utils::removeDirectories($this->dir . $name);
+ IPF_Utils::removeDirectories($dir . $name);
return $this->noContent();
}
function upload()
{
+ $dir = $this->validateDirectory($this->request->POST['dir']);
foreach ($this->request->FILES['files'] as $file) {
- $uploadfile = $this->dir . basename($file['name']);
+ $uploadfile = $dir . basename($file['name']);
move_uploaded_file($file['tmp_name'], $uploadfile);
}
return $this->noContent();
}
+ private function validateDirectory($path)
+ {
+ $settings = $this->container['settings'];
+ $uploadPath = $settings->get('document_root') . $settings->get('upload_url');
+ $root = realpath($uploadPath) . DIRECTORY_SEPARATOR;
+ $realpath = realpath($root . $path) . DIRECTORY_SEPARATOR;
+ if (!\PFF\Str::startsWith($realpath, $root))
+ throw new IPF_Admin_AccessDenied;
+ return $realpath;
+ }
+
+ private function validateName($name)
+ {
+ $name = basename($name);
+ if (!$name || $name === '.' || $name === '..')
+ throw new IPF_Admin_AccessDenied;
+
+ return $name;
+ }
+
private static function withErrors($callable)
{
set_error_handler(function ($errno, $errstr, $errfile, $errline) {
});
}
+ static function cmp($a, $b)
+ {
+ if ($a['name'] == $b['name'])
+ return 0;
+ return ($a['name'] < $b['name']) ? -1 : 1;
+ }
+
/**
* @return IPF_HTTP_Response
*/