diff options
Diffstat (limited to 'apps')
-rw-r--r-- | apps/dav/lib/Files/Sharing/FilesDropPlugin.php | 30 | ||||
-rw-r--r-- | apps/dav/tests/unit/Files/Sharing/FilesDropPluginTest.php | 179 | ||||
-rw-r--r-- | apps/files/css/detailsView.css | 7 | ||||
-rw-r--r-- | apps/files_sharing/css/sharetabview.css | 17 | ||||
-rw-r--r-- | apps/files_versions/css/versions.css | 4 | ||||
-rw-r--r-- | apps/files_versions/js/versionstabview.js | 8 | ||||
-rw-r--r-- | apps/updatenotification/appinfo/app.php | 5 | ||||
-rw-r--r-- | apps/updatenotification/img/notification.svg | 1 | ||||
-rw-r--r-- | apps/updatenotification/lib/Notification/Notifier.php | 19 | ||||
-rw-r--r-- | apps/updatenotification/tests/Notification/NotifierTest.php | 15 |
10 files changed, 242 insertions, 43 deletions
diff --git a/apps/dav/lib/Files/Sharing/FilesDropPlugin.php b/apps/dav/lib/Files/Sharing/FilesDropPlugin.php index 299427b1634..3485df09d0f 100644 --- a/apps/dav/lib/Files/Sharing/FilesDropPlugin.php +++ b/apps/dav/lib/Files/Sharing/FilesDropPlugin.php @@ -23,6 +23,7 @@ namespace OCA\DAV\Files\Sharing; use OC\Files\View; +use Sabre\DAV\Exception\MethodNotAllowed; use Sabre\DAV\ServerPlugin; use Sabre\HTTP\RequestInterface; use Sabre\HTTP\ResponseInterface; @@ -56,6 +57,7 @@ class FilesDropPlugin extends ServerPlugin { * @param \Sabre\DAV\Server $server Sabre server * * @return void + * @throws MethodNotAllowed */ public function initialize(\Sabre\DAV\Server $server) { $server->on('beforeMethod', [$this, 'beforeMethod'], 999); @@ -64,31 +66,19 @@ class FilesDropPlugin extends ServerPlugin { public function beforeMethod(RequestInterface $request, ResponseInterface $response){ - if (!$this->enabled || $request->getMethod() !== 'PUT') { + if (!$this->enabled) { return; } - $path = $request->getPath(); - - if ($this->view->file_exists($path)) { - $newName = \OC_Helper::buildNotExistingFileNameForView('/', $path, $this->view); - - $url = $request->getBaseUrl() . $newName . '?'; - $parms = $request->getQueryParameters(); - $first = true; - foreach ($parms as $k => $v) { - if ($first) { - $url .= '?'; - $first = false; - } else { - $url .= '&'; - } - $url .= $k . '=' . $v; - } - - $request->setUrl($url); + if ($request->getMethod() !== 'PUT') { + throw new MethodNotAllowed('Only PUT is allowed on files drop'); } + $path = explode('/', $request->getPath()); + $path = array_pop($path); + $newName = \OC_Helper::buildNotExistingFileNameForView('/', $path, $this->view); + $url = $request->getBaseUrl() . $newName; + $request->setUrl($url); } } diff --git a/apps/dav/tests/unit/Files/Sharing/FilesDropPluginTest.php b/apps/dav/tests/unit/Files/Sharing/FilesDropPluginTest.php new file mode 100644 index 00000000000..e2990f27b60 --- /dev/null +++ b/apps/dav/tests/unit/Files/Sharing/FilesDropPluginTest.php @@ -0,0 +1,179 @@ +<?php +/** + * @copyright Copyright (c) 2016, Roeland Jago Douma <roeland@famdouma.nl> + * + * @author Roeland Jago Douma <roeland@famdouma.nl> + * + * @license GNU AGPL version 3 or any later version + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + * + */ +namespace OCA\DAV\Tests\Files\Sharing; + +use OC\Files\View; +use OCA\DAV\Files\Sharing\FilesDropPlugin; +use Sabre\DAV\Exception\MethodNotAllowed; +use Sabre\DAV\Server; +use Sabre\HTTP\RequestInterface; +use Sabre\HTTP\ResponseInterface; +use Test\TestCase; + +class FilesDropPluginTest extends TestCase { + + /** @var View|\PHPUnit_Framework_MockObject_MockObject */ + private $view; + + /** @var Server|\PHPUnit_Framework_MockObject_MockObject */ + private $server; + + /** @var FilesDropPlugin */ + private $plugin; + + /** @var RequestInterface|\PHPUnit_Framework_MockObject_MockObject */ + private $request; + + /** @var ResponseInterface|\PHPUnit_Framework_MockObject_MockObject */ + private $response; + + public function setUp() { + parent::setUp(); + + $this->view = $this->createMock(View::class); + $this->server = $this->createMock(Server::class); + $this->plugin = new FilesDropPlugin(); + + $this->request = $this->createMock(RequestInterface::class); + $this->response = $this->createMock(ResponseInterface::class); + + $this->response->expects($this->never()) + ->method($this->anything()); + } + + public function testInitialize() { + $this->server->expects($this->once()) + ->method('on') + ->with( + $this->equalTo('beforeMethod'), + $this->equalTo([$this->plugin, 'beforeMethod']), + $this->equalTo(999) + ); + + $this->plugin->initialize($this->server); + } + + public function testNotEnabled() { + $this->view->expects($this->never()) + ->method($this->anything()); + + $this->request->expects($this->never()) + ->method($this->anything()); + + $this->plugin->beforeMethod($this->request, $this->response); + } + + public function testValid() { + $this->plugin->enable(); + $this->plugin->setView($this->view); + + $this->request->method('getMethod') + ->willReturn('PUT'); + + $this->request->method('getPath') + ->willReturn('file.txt'); + + $this->request->method('getBaseUrl') + ->willReturn('https://example.com'); + + $this->view->method('file_exists') + ->with('/file.txt') + ->willReturn(false); + + $this->request->expects($this->once()) + ->method('setUrl') + ->with('https://example.com/file.txt'); + + $this->plugin->beforeMethod($this->request, $this->response); + } + + public function testFileAlreadyExistsValid() { + $this->plugin->enable(); + $this->plugin->setView($this->view); + + $this->request->method('getMethod') + ->willReturn('PUT'); + + $this->request->method('getPath') + ->willReturn('file.txt'); + + $this->request->method('getBaseUrl') + ->willReturn('https://example.com'); + + $this->view->method('file_exists') + ->will($this->returnCallback(function($path) { + if ($path === 'file.txt' || $path === '/file.txt') { + return true; + } else { + return false; + } + })); + + $this->request->expects($this->once()) + ->method('setUrl') + ->with($this->equalTo('https://example.com/file (2).txt')); + + $this->plugin->beforeMethod($this->request, $this->response); + } + + public function testNoMKCOL() { + $this->plugin->enable(); + $this->plugin->setView($this->view); + + $this->request->method('getMethod') + ->willReturn('MKCOL'); + + $this->expectException(MethodNotAllowed::class); + + $this->plugin->beforeMethod($this->request, $this->response); + } + + public function testNoSubdirPut() { + $this->plugin->enable(); + $this->plugin->setView($this->view); + + $this->request->method('getMethod') + ->willReturn('PUT'); + + $this->request->method('getPath') + ->willReturn('folder/file.txt'); + + $this->request->method('getBaseUrl') + ->willReturn('https://example.com'); + + $this->view->method('file_exists') + ->will($this->returnCallback(function($path) { + if ($path === 'file.txt' || $path === '/file.txt') { + return true; + } else { + return false; + } + })); + + $this->request->expects($this->once()) + ->method('setUrl') + ->with($this->equalTo('https://example.com/file (2).txt')); + + $this->plugin->beforeMethod($this->request, $this->response); + } +} diff --git a/apps/files/css/detailsView.css b/apps/files/css/detailsView.css index 094f44fdf05..f91fe3319e5 100644 --- a/apps/files/css/detailsView.css +++ b/apps/files/css/detailsView.css @@ -27,11 +27,6 @@ width: 90%; } -#app-sidebar .file-details-container { - display: inline-block; - float: left; -} - #app-sidebar .thumbnailContainer.large { margin-left: -15px; margin-right: -35px; /* 15 + 20 for the close button */ @@ -97,7 +92,7 @@ } #app-sidebar .fileName h3 { - max-width: 300px; + width: calc(100% - 36px); /* 36px is the with of the copy link icon */ display: inline-block; padding: 5px 0; margin: -5px 0; diff --git a/apps/files_sharing/css/sharetabview.css b/apps/files_sharing/css/sharetabview.css index 1ef5ac3fe3c..936e1af246a 100644 --- a/apps/files_sharing/css/sharetabview.css +++ b/apps/files_sharing/css/sharetabview.css @@ -71,7 +71,7 @@ } #shareWithList .unshare { - padding: 4px; + padding: 1px 6px; vertical-align: text-bottom; } #shareWithList .unshare .icon { @@ -81,6 +81,11 @@ #shareWithList .unshare .icon-delete { padding-right: 4px; background-position-x: 0; + display: inline-block; +} + +#shareWithList .sharingOptionsGroup .popovermenu:after { + right: 3px; } #shareWithList label input[type=checkbox] { @@ -104,12 +109,14 @@ .shareTabView .icon-loading-small { display: inline-block; z-index: 1; - padding: 2px 0; + margin-right: 4px; + vertical-align: text-top; } -.shareTabView .shareWithList .icon-loading-small, -.shareTabView .linkShareView .icon-loading-small { - position: absolute; +.shareTabView .shareWithList .icon-loading-small:not(.hidden) + span, +.shareTabView .linkShareView .icon-loading-small:not(.hidden) + input + label:before { + /* Hide if loader is visible */ + display: none !important; } .linkShareView { diff --git a/apps/files_versions/css/versions.css b/apps/files_versions/css/versions.css index cd63a90ab51..e749854a942 100644 --- a/apps/files_versions/css/versions.css +++ b/apps/files_versions/css/versions.css @@ -68,3 +68,7 @@ float: right; margin-right: -10px; } + +.versionsTabView .emptycontent { + margin-top: 10px; +} diff --git a/apps/files_versions/js/versionstabview.js b/apps/files_versions/js/versionstabview.js index a91366fd40a..e5ca115ecfa 100644 --- a/apps/files_versions/js/versionstabview.js +++ b/apps/files_versions/js/versionstabview.js @@ -38,7 +38,11 @@ var TEMPLATE = '<ul class="versions"></ul>' + '<div class="clear-float"></div>' + - '<div class="empty hidden">{{emptyResultLabel}}</div>' + + '<div class="empty hidden">' + + '<div class="emptycontent">' + + '<div class="icon-history"></div>' + + '<p>{{emptyResultLabel}}</p>' + + '</div></div>' + '<input type="button" class="showMoreVersions hidden" value="{{moreVersionsLabel}}"' + ' name="show-more-versions" id="show-more-versions" />' + '<div class="loading hidden" style="height: 50px"></div>'; @@ -225,7 +229,7 @@ */ render: function() { this.$el.html(this.template({ - emptyResultLabel: t('files_versions', 'No other versions available'), + emptyResultLabel: t('files_versions', 'No versions available'), moreVersionsLabel: t('files_versions', 'More versions...') })); this.$el.find('.has-tooltip').tooltip(); diff --git a/apps/updatenotification/appinfo/app.php b/apps/updatenotification/appinfo/app.php index f5bcf345669..e3010d418bb 100644 --- a/apps/updatenotification/appinfo/app.php +++ b/apps/updatenotification/appinfo/app.php @@ -43,10 +43,7 @@ if(\OC::$server->getConfig()->getSystemValue('updatechecker', true) === true) { $manager = \OC::$server->getNotificationManager(); $manager->registerNotifier(function() use ($manager) { - return new \OCA\UpdateNotification\Notification\Notifier( - $manager, - \OC::$server->getL10NFactory() - ); + return \OC::$server->query(\OCA\UpdateNotification\Notification\Notifier::class); }, function() { $l = \OC::$server->getL10N('updatenotification'); return [ diff --git a/apps/updatenotification/img/notification.svg b/apps/updatenotification/img/notification.svg new file mode 100644 index 00000000000..7a3f6270cbd --- /dev/null +++ b/apps/updatenotification/img/notification.svg @@ -0,0 +1 @@ +<svg xmlns="http://www.w3.org/2000/svg" height="16" width="16" viewbox="0 0 16 16"><path d="M6.938 0A.43.43 0 0 0 6.5.438v1.25a5.818 5.818 0 0 0-1.53.656l-.907-.906a.436.436 0 0 0-.625 0l-1.5 1.5a.436.436 0 0 0 0 .624l.906.907c-.285.48-.514.976-.656 1.53H.938a.43.43 0 0 0-.438.438v2.125C.5 8.81.69 9 .938 9h1.25a5.82 5.82 0 0 0 .656 1.53l-.907.908a.436.436 0 0 0 0 .625l1.5 1.5c.176.176.45.176.625 0l.907-.907c.48.285.976.514 1.53.656v1.25c0 .25.19.438.437.438h2.125a.43.43 0 0 0 .438-.438v-1.25a5.82 5.82 0 0 0 1.53-.657l.907.907c.176.175.45.175.625 0l1.5-1.5a.436.436 0 0 0 0-.625l-.906-.906A5.79 5.79 0 0 0 13.812 9h1.25a.43.43 0 0 0 .438-.438V6.437A.43.43 0 0 0 15.062 6h-1.25a5.79 5.79 0 0 0-.656-1.532l.906-.906a.436.436 0 0 0 0-.625l-1.5-1.5a.436.436 0 0 0-.625 0l-.906.906a5.816 5.816 0 0 0-1.53-.656V.437A.43.43 0 0 0 9.063 0zM8 4.157a3.344 3.344 0 0 1 0 6.686 3.344 3.344 0 0 1 0-6.686z" display="block"/></svg> diff --git a/apps/updatenotification/lib/Notification/Notifier.php b/apps/updatenotification/lib/Notification/Notifier.php index 3e1bc94425f..00cc94095ca 100644 --- a/apps/updatenotification/lib/Notification/Notifier.php +++ b/apps/updatenotification/lib/Notification/Notifier.php @@ -24,6 +24,7 @@ namespace OCA\UpdateNotification\Notification; +use OCP\IURLGenerator; use OCP\L10N\IFactory; use OCP\Notification\IManager; use OCP\Notification\INotification; @@ -31,6 +32,9 @@ use OCP\Notification\INotifier; class Notifier implements INotifier { + /** @var IURLGenerator */ + protected $url; + /** @var IManager */ protected $notificationManager; @@ -43,10 +47,12 @@ class Notifier implements INotifier { /** * Notifier constructor. * + * @param IURLGenerator $url * @param IManager $notificationManager * @param IFactory $l10NFactory */ - public function __construct(IManager $notificationManager, IFactory $l10NFactory) { + public function __construct(IURLGenerator $url, IManager $notificationManager, IFactory $l10NFactory) { + $this->url = $url; $this->notificationManager = $notificationManager; $this->l10NFactory = $l10NFactory; $this->appVersions = $this->getAppVersions(); @@ -78,9 +84,18 @@ class Notifier implements INotifier { $this->updateAlreadyInstalledCheck($notification, $this->appVersions[$notification->getObjectType()]); } - $notification->setParsedSubject($l->t('Update for %1$s to version %2$s is available.', [$appName, $notification->getObjectId()])); + $notification->setParsedSubject($l->t('Update for %1$s to version %2$s is available.', [$appName, $notification->getObjectId()])) + ->setRichSubject($l->t('Update for {app} to version %s is available.', $notification->getObjectId()), [ + 'app' => [ + 'type' => 'app', + 'id' => $notification->getObjectType(), + 'name' => $appName, + ] + ]); } + $notification->setIcon($this->url->getAbsoluteURL($this->url->imagePath('updatenotification', 'notification.svg'))); + return $notification; } diff --git a/apps/updatenotification/tests/Notification/NotifierTest.php b/apps/updatenotification/tests/Notification/NotifierTest.php index e5ccb291b5c..421fcada689 100644 --- a/apps/updatenotification/tests/Notification/NotifierTest.php +++ b/apps/updatenotification/tests/Notification/NotifierTest.php @@ -24,12 +24,16 @@ namespace OCA\UpdateNotification\Tests\Notification; use OCA\UpdateNotification\Notification\Notifier; +use OCP\IURLGenerator; use OCP\L10N\IFactory; use OCP\Notification\IManager; +use OCP\Notification\INotification; use Test\TestCase; class NotifierTest extends TestCase { + /** @var IURLGenerator|\PHPUnit_Framework_MockObject_MockObject */ + protected $urlGenerator; /** @var IManager|\PHPUnit_Framework_MockObject_MockObject */ protected $notificationManager; /** @var IFactory|\PHPUnit_Framework_MockObject_MockObject */ @@ -38,8 +42,9 @@ class NotifierTest extends TestCase { public function setUp() { parent::setUp(); - $this->notificationManager = $this->getMockBuilder('OCP\Notification\IManager')->getMock(); - $this->l10nFactory = $this->getMockBuilder('OCP\L10n\IFactory')->getMock(); + $this->urlGenerator = $this->createMock(IURLGenerator::class); + $this->notificationManager = $this->createMock(IManager::class); + $this->l10nFactory = $this->createMock(IFactory::class); } /** @@ -49,12 +54,14 @@ class NotifierTest extends TestCase { protected function getNotifier(array $methods = []) { if (empty($methods)) { return new Notifier( + $this->urlGenerator, $this->notificationManager, $this->l10nFactory ); } { - return $this->getMockBuilder('OCA\UpdateNotification\Notification\Notifier') + return $this->getMockBuilder(Notifier::class) ->setConstructorArgs([ + $this->urlGenerator, $this->notificationManager, $this->l10nFactory, ]) @@ -81,7 +88,7 @@ class NotifierTest extends TestCase { public function testUpdateAlreadyInstalledCheck($versionNotification, $versionInstalled, $exception) { $notifier = $this->getNotifier(); - $notification = $this->getMockBuilder('OCP\Notification\INotification')->getMock(); + $notification = $this->createMock(INotification::class); $notification->expects($this->once()) ->method('getObjectId') ->willReturn($versionNotification); |