]> source.dussan.org Git - nextcloud-server.git/commitdiff
Added external storage list in files app
authorVincent Petry <pvince81@owncloud.com>
Fri, 6 Jun 2014 11:16:47 +0000 (13:16 +0200)
committerVincent Petry <pvince81@owncloud.com>
Fri, 6 Jun 2014 13:06:26 +0000 (15:06 +0200)
apps/files_external/appinfo/app.php
apps/files_external/appinfo/routes.php [new file with mode: 0644]
apps/files_external/js/app.js [new file with mode: 0644]
apps/files_external/js/mountsfilelist.js [new file with mode: 0644]
apps/files_external/lib/api.php [new file with mode: 0644]
apps/files_external/list.php [new file with mode: 0644]
apps/files_external/templates/list.php [new file with mode: 0644]

index ca164784fb011724a4c3578a5367b8b1b11724ab..e88880fe516b994c1700ce779de61607c300bb4a 100644 (file)
@@ -20,12 +20,23 @@ OC::$CLASSPATH['OC\Files\Storage\AmazonS3'] = 'files_external/lib/amazons3.php';
 OC::$CLASSPATH['OC\Files\Storage\Dropbox'] = 'files_external/lib/dropbox.php';
 OC::$CLASSPATH['OC\Files\Storage\SFTP'] = 'files_external/lib/sftp.php';
 OC::$CLASSPATH['OC_Mount_Config'] = 'files_external/lib/config.php';
+OC::$CLASSPATH['OCA\Files\External\Api'] = 'files_external/lib/api.php';
 
 OCP\App::registerAdmin('files_external', 'settings');
 if (OCP\Config::getAppValue('files_external', 'allow_user_mounting', 'yes') == 'yes') {
        OCP\App::registerPersonal('files_external', 'personal');
 }
 
+\OCA\Files\App::getNavigationManager()->add(
+       array(
+               "id" => 'extstoragemounts',
+               "appname" => 'files_external',
+               "script" => 'list.php',
+               "order" => 30,
+               "name" => $l->t('External storage')
+       )
+);
+
 // connecting hooks
 OCP\Util::connectHook('OC_Filesystem', 'post_initMountPoints', '\OC_Mount_Config', 'initMountPointsHook');
 OCP\Util::connectHook('OC_User', 'post_login', 'OC\Files\Storage\SMB_OC', 'login');
@@ -164,3 +175,4 @@ OC_Mount_Config::registerBackend('\OC\Files\Storage\SFTP', array(
                'user' => (string)$l->t('Username'),
                'password' => '*'.$l->t('Password'),
                'root' => '&'.$l->t('Root'))));
+
diff --git a/apps/files_external/appinfo/routes.php b/apps/files_external/appinfo/routes.php
new file mode 100644 (file)
index 0000000..cb95036
--- /dev/null
@@ -0,0 +1,27 @@
+<?php
+/**
+ * ownCloud - External Storage Routes
+ *
+ * @author Vincent Petry
+ * @copyright 2014 Vincent Petry <pvince81@owncloud.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or any later version.
+ *
+ * This library 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 library.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+OC_API::register('get',
+               '/apps/files_external/api/v1/mounts',
+               array('\OCA\Files\External\Api', 'getUserMounts'),
+               'files_external');
+
diff --git a/apps/files_external/js/app.js b/apps/files_external/js/app.js
new file mode 100644 (file)
index 0000000..58ad1a0
--- /dev/null
@@ -0,0 +1,71 @@
+/*
+ * Copyright (c) 2014 Vincent Petry <pvince81@owncloud.com>
+ *
+ * This file is licensed under the Affero General Public License version 3
+ * or later.
+ *
+ * See the COPYING-README file.
+ *
+ */
+
+if (!OCA.External) {
+       OCA.External = {};
+}
+OCA.External.App = {
+
+       fileList: null,
+
+       initList: function($el) {
+               if (this.fileList) {
+                       return this.fileList;
+               }
+
+               this.fileList = new OCA.External.FileList(
+                       $el,
+                       {
+                               scrollContainer: $('#app-content'),
+                               fileActions: this._createFileActions()
+                       }
+               );
+
+               this._extendFileList(this.fileList);
+               this.fileList.appName = t('files_external', 'External storage');
+               return this.fileList;
+       },
+
+       removeList: function() {
+               if (this.fileList) {
+                       this.fileList.$fileList.empty();
+               }
+       },
+
+       _createFileActions: function() {
+               // inherit file actions from the files app
+               var fileActions = new OCA.Files.FileActions();
+               fileActions.registerDefaultActions();
+
+               // when the user clicks on a folder, redirect to the corresponding
+               // folder in the files app instead of opening it directly
+               fileActions.register('dir', 'Open', OC.PERMISSION_READ, '', function (filename, context) {
+                       OCA.Files.App.setActiveView('files', {silent: true});
+                       OCA.Files.App.fileList.changeDirectory(context.$file.attr('data-path') + '/' + filename, true, true);
+               });
+               fileActions.setDefault('dir', 'Open');
+               return fileActions;
+       },
+
+       _extendFileList: function(fileList) {
+               // remove size column from summary
+               fileList.fileSummary.$el.find('.filesize').remove();
+       }
+};
+
+$(document).ready(function() {
+       $('#app-content-extstoragemounts').on('show', function(e) {
+               OCA.External.App.initList($(e.target));
+       });
+       $('#app-content-extstoragemounts').on('hide', function() {
+               OCA.External.App.removeList();
+       });
+});
+
diff --git a/apps/files_external/js/mountsfilelist.js b/apps/files_external/js/mountsfilelist.js
new file mode 100644 (file)
index 0000000..52a9aff
--- /dev/null
@@ -0,0 +1,116 @@
+/*
+ * Copyright (c) 2014 Vincent Petry <pvince81@owncloud.com>
+ *
+ * This file is licensed under the Affero General Public License version 3
+ * or later.
+ *
+ * See the COPYING-README file.
+ *
+ */
+(function() {
+
+       /**
+        * External storage file list
+        */
+       var FileList = function($el, options) {
+               this.initialize($el, options);
+       };
+
+       FileList.prototype = _.extend({}, OCA.Files.FileList.prototype, {
+               appName: 'External storage',
+
+               initialize: function($el, options) {
+                       OCA.Files.FileList.prototype.initialize.apply(this, arguments);
+                       if (this.initialized) {
+                               return;
+                       }
+               },
+
+               _createRow: function(fileData) {
+                       // TODO: hook earlier and render the whole row here
+                       var $tr = OCA.Files.FileList.prototype._createRow.apply(this, arguments);
+                       $tr.find('.filesize,.date').remove();
+                       $tr.find('td.filename').after('<td></td>');
+                       $tr.find('td.filename input:checkbox').remove();
+                       return $tr;
+               },
+
+               updateEmptyContent: function() {
+                       var dir = this.getCurrentDirectory();
+                       if (dir === '/') {
+                               // root has special permissions
+                               this.$el.find('#emptycontent').toggleClass('hidden', !this.isEmpty);
+                               this.$el.find('#filestable thead th').toggleClass('hidden', this.isEmpty);
+                       }
+                       else {
+                               OCA.Files.FileList.prototype.updateEmptyContent.apply(this, arguments);
+                       }
+               },
+
+               getDirectoryPermissions: function() {
+                       return OC.PERMISSION_READ | OC.PERMISSION_DELETE;
+               },
+
+               updateStorageStatistics: function() {
+                       // no op because it doesn't have
+                       // storage info like free space / used space
+               },
+
+               reload: function() {
+                       var self = this;
+                       this.showMask();
+                       if (this._reloadCall) {
+                               this._reloadCall.abort();
+                       }
+                       this._reloadCall = $.ajax({
+                               url: OC.linkToOCS('apps/files_external/api/v1') + 'mounts',
+                               data: {
+                                       format: 'json'
+                               },
+                               type: 'GET',
+                               beforeSend: function(xhr) {
+                                       xhr.setRequestHeader('OCS-APIREQUEST', 'true');
+                               },
+                               error: function(result) {
+                                       self.reloadCallback(result);
+                               },
+                               success: function(result) {
+                                       self.reloadCallback(result);
+                               }
+                       });
+               },
+
+               reloadCallback: function(result) {
+                       delete this._reloadCall;
+                       this.hideMask();
+
+                       if (result.ocs && result.ocs.data) {
+                               this.setFiles(this._makeFiles(result.ocs.data));
+                       }
+                       else {
+                               // TODO: error handling
+                       }
+               },
+
+               /**
+                * Converts the OCS API  response data to a file info
+                * list
+                * @param OCS API mounts array
+                * @return array of file info maps
+                */
+               _makeFiles: function(data) {
+                       var files = _.chain(data)
+                               .map(function(fileData) {
+                                       fileData.icon = OC.imagePath('core', 'filetypes/folder-external');
+                                       return fileData;
+                               })
+                               // Sort by expected sort comparator
+                               .sortBy(this._sortComparator)
+                               .value();
+
+                       return files;
+               }
+       });
+
+       OCA.External.FileList = FileList;
+})();
diff --git a/apps/files_external/lib/api.php b/apps/files_external/lib/api.php
new file mode 100644 (file)
index 0000000..d94dbcf
--- /dev/null
@@ -0,0 +1,64 @@
+<?php
+/**
+ * ownCloud
+ *
+ * @author Vincent Petry
+ * @copyright 2014 Vincent Petry pvince81@owncloud.com
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or any later version.
+ *
+ * This library 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 library.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+namespace OCA\Files\External;
+
+class Api {
+
+       /**
+        * Returns the mount points visible for this user.
+        *
+        * @param array $params
+        * @return \OC_OCS_Result share information
+        */
+       public static function getUserMounts($params) {
+               $entries = array();
+               $user = \OC_User::getUser();
+               $mounts = \OC_Mount_Config::getAbsoluteMountPoints($user);
+
+               foreach ($mounts as $mountPoint => $config) {
+                       // split user name from mount point
+                       $parts = explode('/', ltrim($mountPoint, '/'));
+                       array_shift($parts); // use name
+                       array_shift($parts); // files
+                       $mountPoint = implode('/', $parts);
+
+                       $path = dirname($mountPoint);
+                       if ($path === '.') {
+                               $path = '';
+                       }
+
+                       // TODO: give delete permissions if mount type is personal
+                       $permissions = \OCP\PERMISSION_READ;
+
+                       // TODO: add storageType, might need to use another OC_Mount_Config method
+                       $entries[] = array(
+                               'name' => basename($mountPoint),
+                               'path' => $path,
+                               'type' => 'dir',
+                               'permissions' => $permissions
+                       );
+               }
+
+               return new \OC_OCS_Result($entries);
+       }
+}
diff --git a/apps/files_external/list.php b/apps/files_external/list.php
new file mode 100644 (file)
index 0000000..e951772
--- /dev/null
@@ -0,0 +1,11 @@
+<?php
+
+// Check if we are a user
+OCP\User::checkLoggedIn();
+
+$tmpl = new OCP\Template('files_external', 'list', '');
+
+OCP\Util::addScript('files_external', 'app');
+OCP\Util::addScript('files_external', 'mountsfilelist');
+
+$tmpl->printPage();
diff --git a/apps/files_external/templates/list.php b/apps/files_external/templates/list.php
new file mode 100644 (file)
index 0000000..225616e
--- /dev/null
@@ -0,0 +1,25 @@
+<?php /** @var $l OC_L10N */ ?>
+<div id="controls">
+       <div id="file_action_panel"></div>
+</div>
+<div id='notification'></div>
+
+<div id="emptycontent" class="hidden"><?php p($l->t( 'You don\'t have any external storages' )); ?></div>
+
+<input type="hidden" name="dir" value="" id="dir">
+
+<table id="filestable">
+       <thead>
+               <tr>
+                       <th id='headerName' class="hidden column-name">
+                               <div id="headerName-container">
+                                       <a class="name sort columntitle" data-sort="name"><span><?php p($l->t( 'Name' )); ?></span><span class="sort-indicator"></span></a>
+                               </div>
+                       </th>
+               </tr>
+       </thead>
+       <tbody id="fileList">
+       </tbody>
+       <tfoot>
+       </tfoot>
+</table>