<?php
namespace Cms\FileBundle\Controller;
use Cms\ContainerBundle\Entity\Container;
use Cms\ContainerBundle\Entity\Containers\GenericContainer;
use Cms\ContainerBundle\Entity\Containers\IntranetContainer;
use Cms\ContainerBundle\Entity\Containers\PersonalContainer;
use Cms\ContainerBundle\Entity\Containers\StorageContainer;
use Cms\CoreBundle\Model\Scenes\DashboardScenes\AjaxScene;
use Cms\CoreBundle\Model\Url;
use Cms\CoreBundle\Service\Aws\S3Wrapper;
use Cms\CoreBundle\Util\ModalsController;
use Cms\DomainBundle\Entity\Domain;
use Cms\FileBundle\Doctrine\Nodes\FileRepository;
use Cms\FileBundle\Entity\Nodes\File;
use Cms\FileBundle\Entity\Nodes\Folder;
use Cms\FileBundle\Entity\Optimizations\ImageOptimization;
use Cms\FileBundle\Form\Type\FolderType;
use Cms\FileBundle\Service\FileManager;
use Doctrine\Common\Util\ClassUtils;
use Symfony\Component\Routing\Annotation\Route;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
use Laminas\Uri\Uri;
/**
* Class ModalController
* @package Cms\FileBundle\Controller
*/
final class ModalController extends ModalsController
{
const ROUTES__THUMB = 'campussuite.cms.file.modal.thumb';
const ROUTES__START = 'campussuite.cms.file.modal.start';
const ROUTES__CONTAINER = 'campussuite.cms.file.modal.container';
const ROUTES__CONTAINER_SORT = 'campussuite.cms.file.modal.container_sort';
const ROUTES__FOLDER = 'campussuite.cms.file.modal.folder';
const ROUTES__FOLDER_SORT = 'campussuite.cms.file.modal.folder_sort';
const ROUTES__FOLDER_ROOT_CREATE = 'campussuite.cms.file.modal.folder_root_create';
const ROUTES__FOLDER_CHILD_CREATE = 'campussuite.cms.file.modal.folder_child_create';
const ROUTES__UPLOAD = 'campussuite.cms.file.modal.upload';
const ROUTES__URL = 'campussuite.cms.file.modal.url';
const ROUTES__FOLDER_FILES = 'campussuite.cms.file.modal.folder_files';
const SESSION__LAST_LOCATION = 'campussuite.cms.file.modal.last_location';
const SESSION__LAST_LOCATION_TYPE = 'campussuite.cms.file.modal.last_location_type';
const SESSION__SORT = 'campussuite.cms.file.modal.sort';
const MODES = array(
self::MODES__ID,
self::MODES__URL,
self::MODES__MIXED,
self::MODES__FOLDER,
self::MODES__ABSOLUTE,
self::MODES__SMM,
self::MODES__ATTACHMENTS,
);
const MODES__ID = 'id';
const MODES__URL = 'url';
const MODES__MIXED = 'mixed';
const MODES__FOLDER = 'folder';
const MODES__ABSOLUTE = 'absolute';
const MODES__SMM = 'smm';
const MODES__ATTACHMENTS = 'attachments';
const PARAMS = array(
self::PARAMS__MODE,
self::PARAMS__TYPE,
self::PARAMS__CONTAINER,
self::PARAMS__VALUE,
self::PARAMS__SORT,
);
const PARAMS__MODE = 'mode';
const PARAMS__TYPE = 'type';
const PARAMS__CONTAINER = 'container';
const PARAMS__VALUE = 'value';
const PARAMS__SORT = 'sort';
const DEFAULTS__PARAMS = array(
self::PARAMS__MODE => null,
self::PARAMS__TYPE => null,
self::PARAMS__CONTAINER => null,
self::PARAMS__VALUE => null,
self::PARAMS__SORT => null,
);
/**
* @param string $folderId
* @return JsonResponse
* @throws \Exception
*
* @Route(
* "/folder-files/{folderId}",
* name = ModalController::ROUTES__FOLDER_FILES
* )
*/
public function folderFilesAction($folderId)
{
$folder = $this->getEntityManager()->getRepository(Folder::class)->findExact($folderId);
$files = $this->getEntityManager()->getRepository(File::class)->findBy(
array(
'parent' => $folder->getId(),
),
array(
'name' => 'ASC',
'extension' => 'ASC',
)
);
$result = [];
$path = '';
$fold = $folder;
do {
$path = '/' . $fold->getName() . $path;
$fold = $fold->getParent();
} while ( ! empty($fold));
foreach ($files as $file) {
$result[] = array(
'id' => $file->getId(),
'name' => $file->getName(),
'url' => (new Url(
null,
null,
null,
null,
null,
('/files' . $path . '/' . $file->getFilename()),
null,
null
))
->setCurrentContainer($folder->getContainer())
->compile(Url::FLAGS__FORCE_ROOT)
);
}
return new JsonResponse($result);
}
/**
* @param Request $request
* @return RedirectResponse
* @throws \Exception
*
* @Route(
* "/thumb",
* name = ModalController::ROUTES__THUMB
* )
*/
public function thumbAction(Request $request)
{
// get the query string pieces
$value = $request->query->get('value');
$host = $request->query->get('host');
$size = $request->query->get('size');
// value could be percent encoded, decode it
if (strpos($value, '%') !== false) {
$value = rawurldecode($value);
}
// handle cases when there is no host
if (empty($host)) {
$host = $this->getEntityManager()->getRepository(GenericContainer::class)->findBy(
array(
'parent' => null,
),
array(
'id' => 'ASC',
)
)[0];
$host = sprintf(
'%s.%s.campussuite.site',
$host->getSlug(),
$host->getTenant()->getSlug()
);
}
// assemble the url we will be redirecting to
$url = null;
switch (true) {
// id; find the file and use file url service to get it
case preg_match('/^([1-9]\\d*)$/', $value, $matches) === 1:
if (empty($size) || ! array_key_exists($size, ImageOptimization::$sizes)) {
$size = ImageOptimization::MASKS__SQUARE__MEDIUM;
}
$file = $this->getEntityManager()->getRepository(File::class)->findExact($value);
$url = $this->getS3Wrapper()->entityUrl(
S3Wrapper::BUCKETS__STORAGE,
$file,
'/optimizations/' . $size
);
break;
// absolute url
case preg_match('/^https?:\\/\\/([^\\/]+)/', $value, $matches) === 1:
// see if we host the domain
$domain = $this->getEntityManager()->getRepository(Domain::class)->findOneByHost($matches[1]);
if ( ! empty($domain)) {
// we do host, so we can assume that we can add a mask to the query string
$purl = new Uri($value);
$purl->setQuery(array_merge(
$purl->getQueryAsArray(),
array(
'size' => null,
'mask' => ImageOptimization::MASKS__SQUARE__MEDIUM,
'const' => null,
)
));
$url = $purl->toString();
} else {
$url = $value;
}
break;
// file url
case preg_match('/^(.*?)\\/files\\/(.+)/', $value, $matches) === 1:
$containers = array_values(array_filter(explode('/', $matches[1])));
// handle intranet requests
switch (true) {
case (count($containers) > 0 && strpos($containers[0], '~') === 0):
$site = $this->getEntityManager()->getRepository(IntranetContainer::class)->findOneBy(array(
'parent' => null,
'slug' => ltrim($containers[0], '~'),
));
$containers = array_slice($containers, 1);
break;
default:
$fixedhost = preg_replace('/^https?:\\/\\/([^\\/]+).*$/', '$1', $host);
if (preg_match('/^([-a-zA-Z0-9]+)\\.([-a-zA-Z0-9]+)\\.campussuite\\.site$/', $fixedhost, $hostmatches) === 1) {
$site = $this->getEntityManager()->getRepository(GenericContainer::class)->findOneBy(array(
'parent' => null,
'slug' => $hostmatches[1],
));
} else if (preg_match('/^[0-9]+$/', $fixedhost) === 1) {
$site = $this->getEntityManager()->getRepository(Container::class)->findExact($fixedhost);
$site = array_merge(
$this->getEntityManager()->getRepository(Container::class)->findAncestors($site),
array($site)
)[0];
} else {
$domain = $this->getEntityManager()->getRepository(Domain::class)->findOneByHost(
$fixedhost
);
$site = $this->getEntityManager()->getRepository(GenericContainer::class)->findOneByDomain(
$domain
);
}
}
$container = $site;
$slugs = [];
foreach ($containers as $slug) {
$slugs[] = urldecode($slug);
$container = $this->getEntityManager()->getRepository(Container::class)->findOneBy(array(
'parent' => $container,
'slug' => urldecode($slug),
));
if (empty($container)) {
throw new NotFoundHttpException(sprintf(
'Could not find container for path: /%s',
implode('/', $slugs)
));
}
}
$folders = array_values(array_filter(explode('/', $matches[2])));
$fileparts = [];
$possibleFile = array_pop($folders);
if (preg_match('/(.*)\\.([a-zA-Z0-9]+)([?].*)?$/', $possibleFile, $fileparts) !== 1) {
throw new NotFoundHttpException(sprintf(
'Possible file lookup does not match file regex: %s',
$possibleFile
));
}
$folder = null;
$names = [];
foreach ($folders as $name) {
$names[] = urldecode($name);
$folder = $this->getEntityManager()->getRepository(Folder::class)->findOneBy(array(
'container' => $container,
'parent' => $folder,
'name' => urldecode($name),
));
if (empty($folder)) {
throw new NotFoundHttpException(sprintf(
'Could not find folder for path: /%s',
implode('/', $names)
));
}
}
$file = $this->getEntityManager()->getRepository(File::class)->findOneBy(array(
'parent' => $folder,
'name' => urldecode($fileparts[1]),
'extension' => urldecode($fileparts[2]),
));
if (empty($file)) {
throw new NotFoundHttpException(sprintf(
'Could not find file: %s.%s',
urldecode($fileparts[1]),
urldecode($fileparts[2])
));
}
$qs = [];
if (isset($fileparts[3])) {
parse_str(ltrim($fileparts[3], '?'), $qs);
}
if ($size === '-1' && array_key_exists('mask', $qs)) {
$size = intval($qs['mask']);
} else if ($size === '-1') {
$size = ImageOptimization::MASKS__GENERIC__FULL;
}
if (empty($size) || ! array_key_exists($size, ImageOptimization::$sizes)) {
$size = ImageOptimization::MASKS__SQUARE__MEDIUM;
}
$url = $this->getS3Wrapper()->entityUrl(
S3Wrapper::BUCKETS__STORAGE,
$file,
'/optimizations/' . $size
);
break;
// ident
case preg_match('/^([1-9]\\d*):([^:]+):([1-9]\\d*):([^:]+)(?:[:](.+))?$/', $value, $matches) === 1:
if (empty($size) || ! array_key_exists($size, ImageOptimization::$sizes)) {
$size = ImageOptimization::MASKS__SQUARE__MEDIUM;
}
$url = $this->getFileManager()->identUrlOverride(
$value,
array(
'extra' => 'optimizations/' . $size,
)
);
break;
}
// check for result
if (empty($url)) {
throw new NotFoundHttpException();
}
// send back a redirect to the location of the preview
return new RedirectResponse($url, 302, array(
'Cache-Control' => 'public, max-age=3600',
));
}
/**
* @return AjaxScene|RedirectResponse
*
* @Route(
* "/",
* name = ModalController::ROUTES__START
* )
*/
public function startAction()
{
// get params
$last = null;
// attempt to get container
$container = null;
if ( ! empty($this->getModalParam(self::PARAMS__CONTAINER))) {
$container = $this->getEntityManager()->getRepository(Container::class)->find(
$this->getModalParam(self::PARAMS__CONTAINER)
);
}
// attempt to determine if there is a last location thing set
$lastId = $this->getSession()->get(self::SESSION__LAST_LOCATION);
if ( ! empty($lastId)) {
$last = $this->getEntityManager()
->getRepository($this->getSession()->get(self::SESSION__LAST_LOCATION_TYPE))
->findExact($lastId);
}
// if we are in id mode, the value might be an id we can latch onto for a file, and we can get a folder from it
if (
$this->getModalParam(self::PARAMS__MODE) === self::MODES__FOLDER
&&
preg_match('/^[1-9]\d*$/', $this->getModalParam(self::PARAMS__VALUE)) === 1
) {
$folder = $this->getEntityManager()->getRepository(Folder::class)->find(
$this->getModalParam(self::PARAMS__VALUE)
);
if ( ! empty($folder)) {
$last = $folder;
}
}
else if (
$this->getModalParam(self::PARAMS__MODE) !== self::MODES__URL
&&
preg_match('/^[1-9]\d*$/', $this->getModalParam(self::PARAMS__VALUE)) === 1
) {
$file = $this->getEntityManager()->getRepository(File::class)->find(
$this->getModalParam(self::PARAMS__VALUE)
);
if ( ! empty($file)) {
$last = $file->getParent();
}
}
// generate redirect based on information
if ($last instanceof Folder && ! empty($container) && $this->compareLastToCurrent($last->getContainer(), $container)) {
// redirect to that folder's view
return $this->redirectToRoute(
self::ROUTES__FOLDER,
array(
'containerId' => $last->getContainer()->getId(),
'folderId' => $last->getId(),
)
);
} else if ($last instanceof Container && ! empty($container) && $this->compareLastToCurrent($last, $container)) {
// redirect to last container's view
return $this->redirectToRoute(
self::ROUTES__CONTAINER,
array(
'containerId' => $last->getId(),
)
);
} else if ( ! empty($container)) {
// redirect to the root view of the container
return $this->redirectToRoute(
self::ROUTES__CONTAINER,
array(
'containerId' => $container->getId(),
)
);
}
return $this->viewAjax(
array(
'containers' => $this->getEntityManager()->getRepository(Container::class)->findAllHierarchy(),
)
);
}
private function compareLastToCurrent(Container $last, Container $current)
{
switch (true) {
// if both are generic, just allow
case $last instanceof GenericContainer && $current instanceof GenericContainer:
return true;
// if we are in an intranet for the first time, really don't want to jump to a public one
case $last instanceof GenericContainer && $current instanceof IntranetContainer:
return false;
// personal containers are not allowed to cross with anything
case $last instanceof GenericContainer && $current instanceof PersonalContainer:
return false;
// cannot pull intranet stuff from public
case $last instanceof IntranetContainer && $current instanceof GenericContainer:
return false;
// allow intranet of same type
case $last instanceof IntranetContainer && $current instanceof IntranetContainer:
return true;
// personal containers are not allowed to cross with anything
case $last instanceof IntranetContainer && $current instanceof PersonalContainer:
return false;
// personal containers are not allowed to cross with anything
case $last instanceof PersonalContainer && $current instanceof GenericContainer:
return false;
// personal containers are not allowed to cross with anything
case $last instanceof PersonalContainer && $current instanceof IntranetContainer:
return false;
// allow only if the containers are owned by the same person
case $last instanceof PersonalContainer && $current instanceof PersonalContainer:
return ($last->getAccount() === $current->getAccount());
// if both are storage, they must be of the same storage type
case $last instanceof StorageContainer && $current instanceof StorageContainer:
return ($last->getSlug() === $current->getSlug());
// TODO: finish all storage container checks
}
// this function should cover all cases, but if not, assume false
return false;
}
/**
* @param string|null $sort
* @param string|null $direction
* @return array
*/
protected function fixOrdering($sort = null, $direction = null)
{
// get the default params
$param = $this->getModalParam(self::PARAMS__SORT);
// get the session value
$session = $this->getSession()->get(self::SESSION__SORT);
// generate the given value
$given = $sort;
if ( ! empty($given)) {
$given .= '/' . (( ! empty($direction)) ? $direction : 'asc');
}
// decide based on lookup chain
$ordering = $given;
if (empty($ordering)) {
$ordering = $session;
}
if (empty($ordering)) {
$ordering = $param;
}
if (empty($ordering)) {
$ordering = 'name/asc';
}
// save most recent ordering in session
$this->getSession()->set(self::SESSION__SORT, $ordering);
return explode('/', $ordering);
}
/**
* @param string $sort
* @param string $direction
* @param bool $files
* @return array
*/
protected function generateOrdering($sort, $direction, $files = false)
{
// fix into orm ordering array
$direction = strtoupper($direction);
switch ($sort) {
case 'name':
$ordering = array(
'name' => $direction,
);
if ($files === true) {
$ordering['extension'] = $direction;
}
break;
case 'timestamp':
$ordering = array(
(($files === true) ? 'uploadedAt' : 'touchedAt') => $direction,
);
if ($files === true) {
$ordering['name'] = 'ASC';
$ordering['extension'] = 'ASC';
}
break;
default:
throw new \Exception();
}
return $ordering;
}
/**
* @param string $containerId
* @param string|null $sort
* @param string|null $direction
* @return AjaxScene
*
* @Route(
* "/{containerId}",
* name = ModalController::ROUTES__CONTAINER,
* requirements = {
* "containerId" = "[1-9]\d*"
* }
* )
*
* @Route(
* "/{containerId}/{sort}/{direction}",
* name = ModalController::ROUTES__CONTAINER_SORT,
* requirements = {
* "containerId" = "[1-9]\d*",
* "sort" = "name|timestamp",
* "direction" = "asc|desc"
* }
* )
*/
public function containerAction($containerId, $sort = null, $direction = null)
{
// get objects
$container = $this->getEntityManager()->getRepository(Container::class)->findExact($containerId);
$containers = $this->assembleDepartments(
( ! empty($this->getModalParam(self::PARAMS__CONTAINER)))
? $this->getEntityManager()->getRepository(Container::class)->findExact($this->getModalParam(self::PARAMS__CONTAINER))
: $container
);
// get root folders for this container
[$sort, $direction] = $this->fixOrdering($sort, $direction);
$folders = $this->getEntityManager()->getRepository(Folder::class)->findRoots(
$container,
$this->generateOrdering($sort, $direction)
);
// set the last location
$this->getSession()->set(self::SESSION__LAST_LOCATION, $container->getId());
$this->getSession()->set(self::SESSION__LAST_LOCATION_TYPE, ClassUtils::getClass($container));
// done
return $this->viewAjax(
array(
'containers' => $containers,
'container' => $container,
'folders' => $folders,
'sort' => $sort,
'direction' => $direction,
'ancestors' => [],
'folder' => null,
'parent' => null,
'files' => [],
)
);
}
/**
* @param Folder $folder
* @param array $ordering
* @return array|File[]
*/
private function queryFiles(Folder $folder, array $ordering = [])
{
// default if none given
if (empty($ordering)) {
$ordering = array(
'name' => 'ASC',
'extension' => 'ASC',
);
}
// see if we have a type set for our modal
if (empty($this->getModalParam(self::PARAMS__TYPE))) {
// we do not, use generic file repository
$repo = $this->getEntityManager()->getRepository(File::class);
} else {
// try and get the specific type
$class = sprintf(
'Cms\\FileBundle\\Entity\\Nodes\\Files\\%sFile',
$this->getModalParam(self::PARAMS__TYPE)
);
// see if our file type exists
if ( ! class_exists($class)) {
// use the base again
$repo = $this->getEntityManager()->getRepository(File::class);
} else {
// use it's repo
/** @var FileRepository $repo */
$repo = $this->getEntityManager()->getRepository($class);
}
}
// use the repo to query for files
return $repo->findBy(
array(
'parent' => $folder->getId(),
'container' => $folder->getContainer(),
),
$ordering
);
}
/**
* @param string $containerId
* @param string $folderId
* @param string|null $sort
* @param string|null $direction
* @return AjaxScene
* @throws \Exception
*
* @Route(
* "/{containerId}/{folderId}",
* name = ModalController::ROUTES__FOLDER,
* requirements = {
* "containerId" = "[1-9]\d*",
* "folderId" = "[1-9]\d*"
* }
* )
*
* @Route(
* "/{containerId}/{folderId}/sort/{sort}/{direction}",
* name = ModalController::ROUTES__FOLDER_SORT,
* requirements = {
* "containerId" = "[1-9]\d*",
* "folderId" = "[1-9]\d*",
* "sort" = "name|timestamp",
* "direction" = "asc|desc"
* }
* )
*/
public function folderAction($containerId, $folderId, $sort = null, $direction = null)
{
// get objects and validate associations
$container = $this->getEntityManager()->getRepository(Container::class)->findExact($containerId);
$containers = $this->assembleDepartments(
( ! empty($this->getModalParam(self::PARAMS__CONTAINER)))
? $this->getEntityManager()->getRepository(Container::class)->findExact($this->getModalParam(self::PARAMS__CONTAINER))
: $container
);
$folder = $this->getEntityManager()->getRepository(Folder::class)->findExact($folderId);
if ($folder->getContainer() !== $container) {
throw new \Exception();
}
// get the ancestor folders
$ancestors = $this->getEntityManager()->getRepository(Folder::class)->findAncestors($folder);
// fix sorting vars
[$sort, $direction] = $this->fixOrdering($sort, $direction);
// get subfolders
$folders = $this->getEntityManager()->getRepository(Folder::class)->findImmediateChildren(
$folder,
$this->generateOrdering($sort, $direction)
);
// get files, be sure to account for specific type if set in modal params
$files = $this->queryFiles(
$folder,
$this->generateOrdering($sort, $direction, true)
);
// set last location
$this->getSession()->set(self::SESSION__LAST_LOCATION, $folder->getId());
$this->getSession()->set(self::SESSION__LAST_LOCATION_TYPE, ClassUtils::getClass($folder));
// done
return $this->viewAjax(
array(
'containers' => $containers,
'container' => $container,
'folder' => $folder,
'ancestors' => $ancestors,
'folders' => $folders,
'files' => $files,
'routes' => array(
'crop' => DashboardController::ROUTES__CROP
),
'sort' => $sort,
'direction' => $direction,
)
);
}
/**
* @param Request $request
* @param string $containerId
* @param string $folderId
* @return AjaxScene|RedirectResponse
* @throws \Exception
*
* @Route(
* "/{containerId}/create-folder",
* name = ModalController::ROUTES__FOLDER_ROOT_CREATE,
* requirements = {
* "containerId" = "[1-9]\d*"
* }
* )
* @Route(
* "/{containerId}/{folderId}/create-folder",
* name = ModalController::ROUTES__FOLDER_CHILD_CREATE,
* requirements = {
* "containerId" = "[1-9]\d*",
* "folderId" = "[1-9]\d*"
* }
* )
*/
public function folderCreateAction(Request $request, $containerId, $folderId = null)
{
// get objects and validate associations
$container = $this->getEntityManager()->getRepository(Container::class)->findExact($containerId);
$containers = $this->assembleDepartments(
( ! empty($this->getModalParam(self::PARAMS__CONTAINER)))
? $this->getEntityManager()->getRepository(Container::class)->findExact($this->getModalParam(self::PARAMS__CONTAINER))
: $container
);
// AUDIT
$this->denyAccessUnlessGranted(
array_filter(array(
'campussuite.cms.file.manage',
($container instanceof StorageContainer && $container->getSlug() === 'smm')
? 'campussuite.smm.manage'
: null,
)),
array($container, $container)
);
$parent = null;
if ($folderId !== null) {
$parent = $this->getEntityManager()->getRepository(Folder::class)->findExact($folderId);
if ($parent->getContainer() !== $container) {
throw new \Exception();
}
}
// get the ancestor folders
$ancestors = [];
if ($parent !== null) {
$ancestors = $this->getEntityManager()->getRepository(Folder::class)->findAncestors($parent);
}
// generate object and form
$folder = new Folder();
$form = $this->createForm(FolderType::class, $folder, []);
$form->remove('description');
// handle submission
if ($this->handleForm($form, $request)) {
// enforce things
$folder
->setContainer($container)
->setParent($parent);
// save and log
$this->getEntityManager()->save($folder);
// record log
$this->getActivityLogger()->createLog($folder);
// redirect to new folders view
return $this->redirectToRoute(
self::ROUTES__FOLDER,
array(
'containerId' => $container->getId(),
'folderId' => $folder->getId(),
)
);
}
// done
return $this->viewAjax(
array(
'containers' => $containers,
'container' => $container,
'folder' => $parent,
'ancestors' => $ancestors,
'form' => $form->createView(),
)
);
}
/**
* @param string $containerId
* @param string $folderId
* @return AjaxScene
* @throws \Exception
*
* @Route(
* "/{containerId}/{folderId}/upload",
* name = ModalController::ROUTES__UPLOAD,
* requirements = {
* "containerId" = "[1-9]\d*",
* "folderId" = "[1-9]\d*"
* }
* )
*/
public function uploadAction($containerId, $folderId)
{
// get and validate objects
$container = $this->getEntityManager()->getRepository(Container::class)->findExact($containerId);
$containers = $this->assembleDepartments(
( ! empty($this->getModalParam(self::PARAMS__CONTAINER)))
? $this->getEntityManager()->getRepository(Container::class)->findExact($this->getModalParam(self::PARAMS__CONTAINER))
: $container
);
// AUDIT
$this->denyAccessUnlessGranted(
array_filter(array(
'campussuite.cms.file.manage',
($container instanceof StorageContainer && $container->getSlug() === 'smm')
? 'campussuite.smm.manage'
: null,
)),
array($container, $container)
);
$folder = $this->getEntityManager()->getRepository(Folder::class)->findExact($folderId);
if ($folder->getContainer() !== $container) {
throw new \Exception();
}
// get the ancestor folders
$ancestors = $this->getEntityManager()->getRepository(Folder::class)->findAncestors($folder);
// just show view
return $this->viewAjax(
array(
'containers' => $containers,
'container' => $container,
'folder' => $folder,
'ancestors' => $ancestors,
)
);
}
/**
* @param string $containerId
* @return AjaxScene
* @throws \Exception
*
* @Route(
* "/url/{containerId}",
* name = ModalController::ROUTES__URL,
* requirements = {
* "containerId" = "[1-9]\d*"
* },
* defaults = {
* "containerId" = null
* }
* )
*/
public function urlAction($containerId = null)
{
// make sure we support this
if ($this->getModalParam(self::PARAMS__MODE) === self::MODES__ID) {
throw new \Exception();
}
// get and validate objects
$container = null;
if ( ! empty($containerId)) {
$container = $this->getEntityManager()->getRepository(Container::class)->findExact($containerId);
} else if ( ! empty($this->getSession()->get(self::SESSION__LAST_LOCATION))) {
$last = $this->getEntityManager()
->getRepository($this->getSession()->get(self::SESSION__LAST_LOCATION_TYPE))
->findExact($this->getSession()->get(self::SESSION__LAST_LOCATION));
switch (true) {
case $last instanceof Folder:
$container = $last->getContainer();
break;
case $last instanceof Container:
$container = $last;
break;
}
} else if ( ! empty($this->getModalParam(self::PARAMS__CONTAINER))) {
$container = $this->getEntityManager()->getRepository(Container::class)->findExact($this->getModalParam(self::PARAMS__CONTAINER));
}
$containers = $this->assembleDepartments(
( ! empty($this->getModalParam(self::PARAMS__CONTAINER)))
? $this->getEntityManager()->getRepository(Container::class)->findExact($this->getModalParam(self::PARAMS__CONTAINER))
: $container
);
// create form
$form = $this->createFormBuilder(
array(
'url' => $this->getModalParam(self::PARAMS__VALUE),
),
[]
)
->add('url', TextType::class, [])
->getForm();
// just show view
return $this->viewAjax(
array(
'containers' => $containers,
'container' => $container,
'form' => $form->createView(),
)
);
}
/**
* {@inheritdoc}
*/
public function viewAjax($template = null, array $parameters = []): AjaxScene
{
$view = parent::viewAjax($template, $parameters);
$view->setParameters(array_merge(
$view->getParameters(),
array(
'modal' => array_merge(
$this->getModalParams(),
array(
'entity' => ( ! empty($this->getModalParam('container'))) ? $this->getEntityManager()->getRepository(Container::class)->findExact(
$this->getModalParam('container')
) : null,
)
),
)
));
return $view;
}
/**
* @param Container $current
* @return array|Container[]
*/
private function assembleDepartments(Container $current)
{
// query based on class
// get only ones in same root
// and order by the left values
/** @var array|Container[] $containers */
$containers = array_merge(
$this->getEntityManager()->getRepository(ClassUtils::getClass($current))->findBy(
($current instanceof PersonalContainer)
? array(
'account' => $this->getGlobalContext()->getEffectiveAccount(),
)
: [],
array(
'rt' => 'ASC',
'lft' => 'ASC',
'name' => 'ASC',
)
),
($current instanceof IntranetContainer || $current instanceof StorageContainer)
? $this->getEntityManager()->getRepository(GenericContainer::class)->findBy(
[],
array(
'rt' => 'ASC',
'lft' => 'ASC',
'name' => 'ASC',
)
)
: []
);
return $containers;
}
/**
* @return S3Wrapper|object
*/
private function getS3Wrapper(): S3Wrapper
{
return $this->get(__METHOD__);
}
/**
* @return FileManager|object
*/
private function getFileManager(): FileManager
{
return $this->get(__METHOD__);
}
}