This commit is contained in:
Dennis Eichhorn 2024-03-10 02:24:56 +00:00
parent 374e22ca15
commit 38565605f7
8 changed files with 244 additions and 60 deletions

View File

@ -29,4 +29,14 @@ return [
], ],
], ],
], ],
'^:tag (\?.*$|$)' => [
[
'dest' => '\Modules\Media\Controller\SearchController:searchTag',
'verb' => RouteVerb::ANY,
'permission' => [
'module' => SearchController::NAME,
'type' => PermissionType::READ,
],
],
],
]; ];

View File

@ -32,10 +32,10 @@ use Modules\Media\Models\PathSettings;
use Modules\Media\Models\PermissionCategory; use Modules\Media\Models\PermissionCategory;
use Modules\Media\Models\Reference; use Modules\Media\Models\Reference;
use Modules\Media\Models\ReferenceMapper; use Modules\Media\Models\ReferenceMapper;
use Modules\Media\Models\Report;
use Modules\Media\Models\UploadFile; use Modules\Media\Models\UploadFile;
use Modules\Media\Models\UploadStatus; use Modules\Media\Models\UploadStatus;
use Modules\Media\Theme\Backend\Components\Media\ElementView; use Modules\Media\Theme\Backend\Components\Media\ElementView;
use Modules\Messages\Models\EmailMapper;
use phpOMS\Account\PermissionType; use phpOMS\Account\PermissionType;
use phpOMS\Ai\Ocr\Tesseract\TesseractOcr; use phpOMS\Ai\Ocr\Tesseract\TesseractOcr;
use phpOMS\Application\ApplicationAbstract; use phpOMS\Application\ApplicationAbstract;
@ -67,6 +67,63 @@ use phpOMS\Views\View;
*/ */
final class ApiController extends Controller final class ApiController extends Controller
{ {
/**
* Api method to create tag
*
* @param RequestAbstract $request Request
* @param ResponseAbstract $response Response
* @param array $data Generic data
*
* @return void
*
* @api
*
* @since 1.0.0
*/
public function apiMediaEmailSend(RequestAbstract $request, ResponseAbstract $response, array $data = []) : void
{
$email = $request->getDataString('email');
$media = $data['media'] ?? MediaMapper::get()
->where('id', (int) $request->getData('id'))
->execute();
/** @var \Model\Setting $template */
$template = $this->app->appSettings->get(
names: (string) $request->getDataString('template')
);
$handler = $this->app->moduleManager->get('Admin', 'Api')->setUpServerMailHandler();
$mail = EmailMapper::get()
->with('l11n')
->where('id', $template)
->where('l11n/language', $response->header->l11n->language)
->execute();
$status = false;
if ($mail->id !== 0) {
$status = $this->app->moduleManager->get('Admin', 'Api')->setupEmailDefaults($mail, $response->header->l11n->language);
}
$mail->addTo($email);
$mail->addAttachment($media->getAbsolutePath(), $media->name);
if ($status) {
$status = $handler->send($mail);
}
if (!$status) {
\phpOMS\Log\FileLogger::getInstance()->error(
\phpOMS\Log\FileLogger::MSG_FULL, [
'message' => 'Couldn\'t send bill media: ' . $media->id,
'line' => __LINE__,
'file' => self::class,
]
);
}
}
/** /**
* Api method to upload media file. * Api method to upload media file.
* *
@ -920,34 +977,42 @@ final class ApiController extends Controller
$status = \is_dir($physicalPath) ? true : \mkdir($physicalPath, 0755, true); $status = \is_dir($physicalPath) ? true : \mkdir($physicalPath, 0755, true);
} }
$path = \trim($path, '/'); $virtualPath = \trim($path, '/');
$paths = \explode('/', $path); $virtualPaths = \explode('/', $virtualPath);
$tempPaths = $paths; $tempVirtualPaths = $virtualPaths;
$length = \count($paths); $length = \count($virtualPaths);
/** @var Collection $parentCollection */ /** @var Collection $parentCollection */
$parentCollection = null; $parentCollection = null;
$temp = ''; $virtual = '';
$real = '';
$newVirtual = '';
for ($i = $length; $i > 0; --$i) { for ($i = $length; $i > 0; --$i) {
$temp = '/' . \implode('/', $tempPaths); $virtual = '/' . \implode('/', $tempVirtualPaths);
/** @var Collection $parentCollection */ /** @var Collection $parentCollection */
$parentCollection = CollectionMapper::getParentCollection($temp)->execute(); $parentCollection = CollectionMapper::getParentCollection($virtual)->execute();
if ($parentCollection->id > 0) { if ($parentCollection->id > 0) {
$real = $parentCollection->getPath();
break; break;
} }
\array_pop($tempPaths); $newVirtual = \array_pop($tempVirtualPaths) . '/' . $newVirtual;
} }
for (; $i < $length; ++$i) { for (; $i < $length; ++$i) {
/* Create collection */ /* Create collection */
$childCollection = new Collection(); $childCollection = new Collection();
$childCollection->name = $paths[$i]; $childCollection->name = $virtualPaths[$i];
$childCollection->createdBy = new NullAccount($account); $childCollection->createdBy = new NullAccount($account);
$childCollection->setVirtualPath('/'. \ltrim($temp, '/')); $childCollection->setVirtualPath('/'. \ltrim($virtual, '/'));
$childCollection->setPath('/Modules/Media/Files' . $temp);
// We assume that the new path is real path of the first found parent directory + the new virtual path
$childCollection->setPath($real . '/' . \ltrim($newVirtual, '/'));
$this->createModel($account, $childCollection, CollectionMapper::class, 'collection', '127.0.0.1'); $this->createModel($account, $childCollection, CollectionMapper::class, 'collection', '127.0.0.1');
$this->createModelRelation( $this->createModelRelation(
@ -961,7 +1026,7 @@ final class ApiController extends Controller
); );
$parentCollection = $childCollection; $parentCollection = $childCollection;
$temp .= '/' . $paths[$i]; $virtual .= '/' . $virtualPaths[$i];
} }
return $parentCollection; return $parentCollection;
@ -1077,6 +1142,13 @@ final class ApiController extends Controller
$media->isAbsolute = false; $media->isAbsolute = false;
$media->setVirtualPath(\dirname($path)); $media->setVirtualPath(\dirname($path));
$media->setPath('/' . \ltrim($path, '\\/')); $media->setPath('/' . \ltrim($path, '\\/'));
} else {
$media = MediaMapper::getAll()
->where('virtualPath', $path)
->limit(1)
->execute();
$filePath = $media->getAbsolutePath();
} }
} }
@ -1210,7 +1282,7 @@ final class ApiController extends Controller
$response->endAllOutputBuffering(); // for large files $response->endAllOutputBuffering(); // for large files
} }
if (($type = $request->getDataString('type')) === null) { if (\in_array($type = $request->getDataString('type'), [null, 'download', 'raw', 'bin'])) {
$view->setTemplate('/Modules/Media/Theme/Api/render'); $view->setTemplate('/Modules/Media/Theme/Api/render');
} elseif ($type === 'html') { } elseif ($type === 'html') {
$head = new Head(); $head = new Head();

View File

@ -30,6 +30,59 @@ use phpOMS\System\MimeType;
*/ */
final class SearchController extends Controller final class SearchController extends Controller
{ {
/**
* Api method to search for tags
*
* @param RequestAbstract $request Request
* @param ResponseAbstract $response Response
* @param array $data Generic data
*
* @return void
*
* @api
*
* @since 1.0.0
*/
public function searchTag(RequestAbstract $request, ResponseAbstract $response, array $data = []) : void
{
$search = $request->getDataString('search') ?? '';
$searchIdStartPos = \stripos($search, ':');
$patternStartPos = $searchIdStartPos === false
? -1
: \stripos($search, ' ', $searchIdStartPos);
$pattern = \substr($search, $patternStartPos + 1);
/** @var \Modules\Media\Models\Media[] $media */
$media = MediaMapper::getAll()
->with('tags')
->with('tags/title')
->where('tags/title/language', $response->header->l11n->language)
->where('tags/title/content', $pattern)
->sort('createdAt', OrderType::DESC)
->limit(8)
->execute();
$results = [];
foreach ($media as $file) {
$results[] = [
'title' => $file->name . ' (' . $file->extension . ')',
'summary' => '',
'link' => '{/base}/media/view?id=' . $file->id,
'account' => '',
'createdAt' => $file->createdAt,
'image' => '',
'tags' => $file->tags,
'type' => 'list_links',
'module' => 'Media',
];
}
$response->header->set('Content-Type', MimeType::M_JSON . '; charset=utf-8', true);
$response->add($request->uri->__toString(), $results);
}
/** /**
* Api method to search for tags * Api method to search for tags
* *

View File

@ -17,6 +17,23 @@ use Modules\Media\Models\NullMedia;
/** @var \Modules\Media\Models\Media $media */ /** @var \Modules\Media\Models\Media $media */
$media = $this->media ?? new NullMedia(); $media = $this->media ?? new NullMedia();
$fp = \fopen(($media->isAbsolute ? '' : __DIR__ . '/../../../../') . $media->getPath(), 'r'); if (\is_file($media->getAbsolutePath())) {
\fpassthru($fp); $fp = \fopen($media->getAbsolutePath(), 'r');
\fclose($fp); if ($fp !== false) {
\fpassthru($fp);
\fclose($fp);
}
} elseif (\is_dir($media->getAbsolutePath())) {
\phpOMS\Utils\IO\Zip\Zip::pack(
$media->getAbsolutePath(),
$tmp = \tempnam(\sys_get_temp_dir(), 'oms_tmp_')
);
$fp = \fopen($tmp, 'r');
if ($fp !== false) {
\fpassthru($fp);
\fclose($fp);
\unlink($tmp);
}
}

View File

@ -33,21 +33,29 @@ use phpOMS\Uri\UriFactory;
<div class="portlet"> <div class="portlet">
<div class="portlet-head"><?= $this->getHtml('CreateCollection'); ?></div> <div class="portlet-head"><?= $this->getHtml('CreateCollection'); ?></div>
<div class="portlet-body"> <div class="portlet-body">
<table class="layout wf-100"> <div class="form-group">
<tr><td><label for="iVirtualPath"><?= $this->getHtml('VirtualPath'); ?></label> <label for="iVirtualPath"><?= $this->getHtml('VirtualPath'); ?></label>
<tr><td><input type="text" id="iVirtualPath" name="virtualPath" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>" disabled> <input type="text" id="iVirtualPath" name="virtualPath" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>" disabled>
<tr><td><label for="iPath"><?= $this->getHtml('Path'); ?></label> </div>
<tr><td><input type="text" id="iPath" name="path" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>">
<tr><td><label><?= $this->getHtml('Settings'); ?></label> <div class="form-group">
<tr><td> <label for="iPath"><?= $this->getHtml('Path'); ?></label>
<label class="checkbox" for="iAddCollection"> <input type="text" id="iPath" name="path" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>">
<input type="checkbox" id="iAddCollection" name="addcollection" checked> </div>
<span class="checkmark"></span>
<?= $this->getHtml('AddToCollection'); ?> <div class="form-group">
</label> <label><?= $this->getHtml('Settings'); ?></label>
<tr><td><label for="iName"><?= $this->getHtml('Name'); ?></label> <label class="checkbox" for="iAddCollection">
<tr><td><input type="text" id="iName" name="name" multiple> <input type="checkbox" id="iAddCollection" name="addcollection" checked>
</table> <span class="checkmark"></span>
<?= $this->getHtml('AddToCollection'); ?>
</label>
</div>
<div class="form-group">
<label for="iName"><?= $this->getHtml('Name'); ?></label>
<input type="text" id="iName" name="name" multiple>
</div>
</div> </div>
<div class="portlet-foot"> <div class="portlet-foot">
<input type="submit" id="iMediaCreate" name="mediaCreateButton" value="<?= $this->getHtml('Create', '0', '0'); ?>"> <input type="submit" id="iMediaCreate" name="mediaCreateButton" value="<?= $this->getHtml('Create', '0', '0'); ?>">

View File

@ -40,9 +40,11 @@ $next = empty($media) ? '{/base}/media/list' : '{/base}/media/list?{?}&id='
<a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/upload?path={?path}'); ?>"> <a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/upload?path={?path}'); ?>">
<?= $this->getHtml('Upload'); ?> <?= $this->getHtml('Upload'); ?>
</a> </a>
<!--
<a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/file/create?path={?path}'); ?>"> <a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/file/create?path={?path}'); ?>">
<?= $this->getHtml('CreateFile'); ?> <?= $this->getHtml('CreateFile'); ?>
</a> </a>
-->
<a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/collection/create?path={?path}'); ?>"> <a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/collection/create?path={?path}'); ?>">
<?= $this->getHtml('CreateCollection'); ?> <?= $this->getHtml('CreateCollection'); ?>
</a> </a>
@ -210,7 +212,7 @@ $next = empty($media) ? '{/base}/media/list' : '{/base}/media/list?{?}&id='
<?php foreach ($value->tags as $tag) : ?> <?php foreach ($value->tags as $tag) : ?>
<a href="<?= $url; ?>"> <a href="<?= $url; ?>">
<span class="tag" style="background: <?= $this->printHtml($tag->color); ?>"> <span class="tag" style="background: <?= $this->printHtml($tag->color); ?>">
<?= empty($tag->icon) ? '' : ''; ?> <?= empty($tag->icon) ? '' : '<i class="g-icon">' . $this->printHtml($tag->icon) . '</i>'; ?>
<?= $this->printHtml($tag->getL11n()); ?> <?= $this->printHtml($tag->getL11n()); ?>
</span> </span>
</a> </a>
@ -238,7 +240,7 @@ $next = empty($media) ? '{/base}/media/list' : '{/base}/media/list?{?}&id='
<div class="portlet-foot"> <div class="portlet-foot">
<a tabindex="0" class="button" href="<?= UriFactory::build($previous); ?>"><?= $this->getHtml('Previous', '0', '0'); ?></a> <a tabindex="0" class="button" href="<?= UriFactory::build($previous); ?>"><?= $this->getHtml('Previous', '0', '0'); ?></a>
<a tabindex="0" class="button" href="<?= UriFactory::build($next); ?>"><?= $this->getHtml('Next', '0', '0'); ?></a> <a tabindex="0" class="button" href="<?= UriFactory::build($next); ?>"><?= $this->getHtml('Next', '0', '0'); ?></a>
<a tabindex="0" class="button rf" href="<?= UriFactory::build('api/media/download'); ?>"> <a tabindex="0" class="button rf" href="<?= UriFactory::build('{/api}media/export?path={?path}&type=download'); ?>">
<?= $this->getHtml('Download'); ?> <?= $this->getHtml('Download'); ?>
</a> </a>
</div> </div>

View File

@ -33,21 +33,29 @@ use phpOMS\Uri\UriFactory;
<div class="portlet"> <div class="portlet">
<div class="portlet-head"><?= $this->getHtml('Upload'); ?></div> <div class="portlet-head"><?= $this->getHtml('Upload'); ?></div>
<div class="portlet-body"> <div class="portlet-body">
<table class="layout wf-100"> <div class="form-group">
<tr><td><label for="iVirtualPath"><?= $this->getHtml('VirtualPath'); ?></label> <label for="iVirtualPath"><?= $this->getHtml('VirtualPath'); ?></label>
<tr><td><input type="text" id="iVirtualPath" name="virtualPath" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>" disabled> <input type="text" id="iVirtualPath" name="virtualPath" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>" disabled>
<tr><td><label for="iPath"><?= $this->getHtml('Path'); ?></label> </div>
<tr><td><input type="text" id="iPath" name="path" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>">
<tr><td><label><?= $this->getHtml('Settings'); ?></label> <div class="form-group">
<tr><td> <label for="iPath"><?= $this->getHtml('Path'); ?></label>
<label class="checkbox" for="iAddCollection"> <input type="text" id="iPath" name="path" value="<?= empty($this->request->uri->getQuery('path')) ? '/' : $this->request->uri->getQuery('path'); ?>">
<input type="checkbox" id="iAddCollection" name="addcollection" checked> </div>
<span class="checkmark"></span>
<?= $this->getHtml('AddToCollection'); ?> <div class="form-group">
</label> <label><?= $this->getHtml('Settings'); ?></label>
<tr><td><label for="iFiles"><?= $this->getHtml('Files'); ?></label> <label class="checkbox" for="iAddCollection">
<tr><td><input type="file" id="iFiles" name="files" multiple> <input type="checkbox" id="iAddCollection" name="addcollection" checked>
</table> <span class="checkmark"></span>
<?= $this->getHtml('AddToCollection'); ?>
</label>
</div>
<div class="form-group">
<label for="iFiles"><?= $this->getHtml('Files'); ?></label>
<input type="file" id="iFiles" name="files" multiple>
</div>
</div> </div>
<div class="portlet-foot"> <div class="portlet-foot">
<input type="submit" id="iMediaCreate" name="mediaCreateButton" value="<?= $this->getHtml('Create', '0', '0'); ?>"> <input type="submit" id="iMediaCreate" name="mediaCreateButton" value="<?= $this->getHtml('Create', '0', '0'); ?>">

View File

@ -37,9 +37,15 @@ echo $this->data['nav']->render();
<div class="col-xs-12"> <div class="col-xs-12">
<div class="box"> <div class="box">
<?php if ($this->request->getData('path') !== null) : ?> <?php if ($this->request->getData('path') !== null) : ?>
<a tabindex="0" class="button" href="<?= UriFactory::build('{/base}/media/list?path=' . ($media->id === 0 ? $media->getVirtualPath() : '{?path}')); ?>"><?= $this->getHtml('Back'); ?></a> <a tabindex="0" class="button"
href="<?= UriFactory::build('{/base}/media/list?path=' . ($media->id === 0 ? $media->getVirtualPath() : '{?path}')); ?>">
<?= $this->getHtml('Back'); ?>
</a>
<?php else: ?> <?php else: ?>
<a tabindex="0" class="button" href="<?= $this->request->getReferer() !== '' ? $this->request->getReferer() : UriFactory::build('{/base}/media/list'); ?>"><?= $this->getHtml('Back'); ?></a> <a tabindex="0" class="button"
href="<?= $this->request->getReferer() !== '' ? $this->request->getReferer() : UriFactory::build('{/base}/media/list'); ?>">
<?= $this->getHtml('Back'); ?>
</a>
<?php endif; ?> <?php endif; ?>
</div> </div>
</div> </div>
@ -94,15 +100,15 @@ echo $this->data['nav']->render();
); ?></a> ); ?></a>
<tr><td><?= $this->getHtml('Tags'); ?><td> <tr><td><?= $this->getHtml('Tags'); ?><td>
<?php foreach ($media->tags as $tag) : ?> <?php foreach ($media->tags as $tag) : ?>
<span class="tag" style="background: <?= $this->printHtml($tag->color); ?>"><?= empty($tag->icon) ? '' : ''; ?><?= $this->printHtml($tag->getL11n()); ?></span> <span class="tag" style="background: <?= $this->printHtml($tag->color); ?>">
<?= empty($tag->icon) ? '' : '<i class="g-icon">' . $this->printHtml($tag->icon) . '</i>'; ?>
<?= $this->printHtml($tag->getL11n()); ?>
</span>
<?php endforeach; ?> <?php endforeach; ?>
<tr><td colspan="2"><?= $this->getHtml('Description'); ?> <tr><td colspan="2"><?= $this->getHtml('Description'); ?>
<tr><td colspan="2"><?= $media->description; ?> <tr><td colspan="2"><?= $media->description; ?>
</table> </table>
</div> </div>
<?php
$path = $this->filePathFunction($media, $this->request->getData('sub') ?? '');
if ($this->isTextFile($media, $path)) : ?>
<div id="iMediaFileUpdate" class="portlet-foot" <div id="iMediaFileUpdate" class="portlet-foot"
data-update-content="#mediaFile .portlet-body" data-update-content="#mediaFile .portlet-body"
data-update-element="#mediaFile .textContent" data-update-element="#mediaFile .textContent"
@ -110,17 +116,25 @@ echo $this->data['nav']->render();
data-tag="form" data-tag="form"
data-method="POST" data-method="POST"
data-uri="<?= UriFactory::build('{/api}media?{?}&csrf={$CSRF}'); ?>"> data-uri="<?= UriFactory::build('{/api}media?{?}&csrf={$CSRF}'); ?>">
<button class="save vh"><?= $this->getHtml('Save', '0', '0'); ?></button> <a tabindex="0"
<button class="cancel vh"><?= $this->getHtml('Cancel', '0', '0'); ?></button> class="button"
<button class="update"><?= $this->getHtml('Edit', '0', '0'); ?></button> href="<?= UriFactory::build('{/api}media/export?id=' . $media->id . '&type=download'); ?>"
><?= $this->getHtml('Download'); ?></a>
<?php
$path = $this->filePathFunction($media, $this->request->getData('sub') ?? '');
if ($this->isTextFile($media, $path)) :
?>
<button class="save vh"><?= $this->getHtml('Save', '0', '0'); ?></button>
<button class="cancel vh"><?= $this->getHtml('Cancel', '0', '0'); ?></button>
<button class="update"><?= $this->getHtml('Edit', '0', '0'); ?></button>
<?php endif; ?>
</div> </div>
<?php endif; ?>
</section> </section>
</div> </div>
</div> </div>
<?php <?php
$media = $media->class === MediaClass::REFERENCE ? $media->source : $media; $media = $media->class === MediaClass::REFERENCE ? $media->source : $media;
?> ?>
<div class="row col-simple"> <div class="row col-simple">