aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorkondou <kondou@ts.unde.re>2013-09-02 07:58:06 +0200
committerkondou <kondou@ts.unde.re>2013-09-02 07:58:06 +0200
commite5fc7b9dbeb01ac116bb132903c562c8f7d3c5b3 (patch)
treeb7d8d913cdf7f4d1ce42f3027918ad0f5fbe5c3b /lib
parent8dd93c8c0288a11f04816bea2a58aee661ef9e97 (diff)
parentf038cb9aea7c9a1513ab14d0df002773b17d5333 (diff)
downloadnextcloud-server-e5fc7b9dbeb01ac116bb132903c562c8f7d3c5b3.tar.gz
nextcloud-server-e5fc7b9dbeb01ac116bb132903c562c8f7d3c5b3.zip
Merge branch 'master' into clean_up_util
Conflicts: lib/base.php
Diffstat (limited to 'lib')
-rw-r--r--lib/app.php17
-rw-r--r--lib/base.php66
-rw-r--r--lib/connector/sabre/directory.php6
-rw-r--r--lib/connector/sabre/quotaplugin.php91
-rw-r--r--lib/files/storage/mappedlocal.php2
-rw-r--r--lib/files/view.php1
-rw-r--r--lib/group/group.php38
-rw-r--r--lib/helper.php88
-rw-r--r--lib/image.php306
-rw-r--r--lib/installer.php53
-rw-r--r--lib/l10n/ca.php22
-rw-r--r--lib/l10n/cs_CZ.php14
-rw-r--r--lib/l10n/da.php14
-rw-r--r--lib/l10n/de.php14
-rw-r--r--lib/l10n/de_CH.php12
-rw-r--r--lib/l10n/de_DE.php14
-rw-r--r--lib/l10n/en_GB.php69
-rw-r--r--lib/l10n/es.php11
-rw-r--r--lib/l10n/et_EE.php22
-rw-r--r--lib/l10n/eu.php8
-rw-r--r--lib/l10n/fi_FI.php7
-rw-r--r--lib/l10n/gl.php14
-rw-r--r--lib/l10n/he.php8
-rw-r--r--lib/l10n/it.php22
-rw-r--r--lib/l10n/ja_JP.php13
-rw-r--r--lib/l10n/ko.php36
-rw-r--r--lib/l10n/lt_LT.php6
-rw-r--r--lib/l10n/nl.php1
-rw-r--r--lib/l10n/pt_BR.php14
-rw-r--r--lib/l10n/sk_SK.php22
-rw-r--r--lib/l10n/sv.php14
-rw-r--r--lib/l10n/tr.php14
-rw-r--r--lib/l10n/ug.php1
-rw-r--r--lib/l10n/zh_CN.GB2312.php32
-rw-r--r--lib/l10n/zh_CN.php7
-rw-r--r--lib/l10n/zh_TW.php26
-rw-r--r--lib/log/rotate.php35
-rw-r--r--lib/ocs/cloud.php46
-rwxr-xr-xlib/preview.php627
-rw-r--r--lib/preview/image.php36
-rw-r--r--lib/preview/movies.php47
-rw-r--r--lib/preview/mp3.php48
-rw-r--r--lib/preview/office-cl.php134
-rw-r--r--lib/preview/office-fallback.php142
-rw-r--r--lib/preview/office.php22
-rw-r--r--lib/preview/pdf.php40
-rw-r--r--lib/preview/provider.php19
-rw-r--r--lib/preview/svg.php46
-rw-r--r--lib/preview/txt.php73
-rw-r--r--lib/preview/unknown.php27
-rw-r--r--lib/public/preview.php34
-rw-r--r--lib/public/share.php16
-rw-r--r--lib/public/template.php19
-rw-r--r--lib/template/functions.php16
-rwxr-xr-xlib/util.php2
55 files changed, 2197 insertions, 337 deletions
diff --git a/lib/app.php b/lib/app.php
index 1b5979107db..1a0a7e6f9a9 100644
--- a/lib/app.php
+++ b/lib/app.php
@@ -210,7 +210,8 @@ class OC_App{
/**
* @brief enables an app
* @param mixed $app app
- * @return bool
+ * @throws \Exception
+ * @return void
*
* This function set an app as enabled in appconfig.
*/
@@ -228,25 +229,25 @@ class OC_App{
}
}
}
+ $l = OC_L10N::get('core');
if($app!==false) {
// check if the app is compatible with this version of ownCloud
$info=OC_App::getAppInfo($app);
$version=OC_Util::getVersion();
if(!isset($info['require']) or !self::isAppVersionCompatible($version, $info['require'])) {
- OC_Log::write('core',
- 'App "'.$info['name'].'" can\'t be installed because it is'
- .' not compatible with this version of ownCloud',
- OC_Log::ERROR);
- return false;
+ throw new \Exception(
+ $l->t("App \"%s\" can't be installed because it is not compatible with this version of ownCloud.",
+ array($info['name'])
+ )
+ );
}else{
OC_Appconfig::setValue( $app, 'enabled', 'yes' );
if(isset($appdata['id'])) {
OC_Appconfig::setValue( $app, 'ocsid', $appdata['id'] );
}
- return true;
}
}else{
- return false;
+ throw new \Exception($l->t("No app name specified"));
}
}
diff --git a/lib/base.php b/lib/base.php
index a59fe8b7a48..fe160f73652 100644
--- a/lib/base.php
+++ b/lib/base.php
@@ -257,20 +257,22 @@ class OC {
OC_Util::addScript("compatibility");
OC_Util::addScript("jquery.ocdialog");
OC_Util::addScript("oc-dialogs");
- OC_Util::addScript("octemplate");
OC_Util::addScript("js");
+ OC_Util::addScript("octemplate");
OC_Util::addScript("eventsource");
OC_Util::addScript("config");
//OC_Util::addScript( "multiselect" );
OC_Util::addScript('search', 'result');
OC_Util::addScript('router');
+ OC_Util::addScript("oc-requesttoken");
OC_Util::addStyle("styles");
+ OC_Util::addStyle("apps");
+ OC_Util::addStyle("fixes");
OC_Util::addStyle("multiselect");
OC_Util::addStyle("jquery-ui-1.10.0.custom");
OC_Util::addStyle("jquery-tipsy");
OC_Util::addStyle("jquery.ocdialog");
- OC_Util::addScript("oc-requesttoken");
}
public static function initSession() {
@@ -490,7 +492,9 @@ class OC {
self::registerCacheHooks();
self::registerFilesystemHooks();
+ self::registerPreviewHooks();
self::registerShareHooks();
+ self::registerLogRotate();
//make sure temporary files are cleaned up
register_shutdown_function(array('OC_Helper', 'cleanTmp'));
@@ -553,6 +557,21 @@ class OC {
}
/**
+ * register hooks for the cache
+ */
+ public static function registerLogRotate() {
+ if (OC_Config::getValue('installed', false) && OC_Config::getValue('log_rotate_size', false)) {
+ //don't try to do this before we are properly setup
+ // register cache cleanup jobs
+ try { //if this is executed before the upgrade to the new backgroundjob system is completed it will throw an exception
+ \OCP\BackgroundJob::registerJob('OC\Log\Rotate', OC_Config::getValue("datadirectory", OC::$SERVERROOT.'/data').'/owncloud.log');
+ } catch (Exception $e) {
+
+ }
+ }
+ }
+
+ /**
* register hooks for the filesystem
*/
public static function registerFilesystemHooks() {
@@ -562,6 +581,14 @@ class OC {
}
/**
+ * register hooks for previews
+ */
+ public static function registerPreviewHooks() {
+ OC_Hook::connect('OC_Filesystem', 'post_write', 'OC\Preview', 'post_write');
+ OC_Hook::connect('OC_Filesystem', 'delete', 'OC\Preview', 'post_delete');
+ }
+
+ /**
* register hooks for sharing
*/
public static function registerShareHooks() {
@@ -669,12 +696,15 @@ class OC {
$app = $param['app'];
$file = $param['file'];
$app_path = OC_App::getAppPath($app);
- $file = $app_path . '/' . $file;
- unset($app, $app_path);
- if (file_exists($file)) {
- require_once $file;
- return true;
+ if (OC_App::isEnabled($app) && $app_path !== false) {
+ $file = $app_path . '/' . $file;
+ unset($app, $app_path);
+ if (file_exists($file)) {
+ require_once $file;
+ return true;
+ }
}
+ header('HTTP/1.0 404 Not Found');
return false;
}
@@ -772,14 +802,15 @@ class OC {
self::$session->set('timezone', $_POST['timezone-offset']);
}
- self::cleanupLoginTokens($_POST['user']);
+ $userid = OC_User::getUser();
+ self::cleanupLoginTokens($userid);
if (!empty($_POST["remember_login"])) {
if (defined("DEBUG") && DEBUG) {
OC_Log::write('core', 'Setting remember login to cookie', OC_Log::DEBUG);
}
$token = OC_Util::generateRandomBytes(32);
- OC_Preferences::setValue($_POST['user'], 'login_token', $token, time());
- OC_User::setMagicInCookie($_POST["user"], $token);
+ OC_Preferences::setValue($userid, 'login_token', $token, time());
+ OC_User::setMagicInCookie($userid, $token);
} else {
OC_User::unsetMagicInCookie();
}
@@ -795,11 +826,16 @@ class OC {
) {
return false;
}
- OC_App::loadApps(array('authentication'));
- if (OC_User::login($_SERVER["PHP_AUTH_USER"], $_SERVER["PHP_AUTH_PW"])) {
- //OC_Log::write('core',"Logged in with HTTP Authentication", OC_Log::DEBUG);
- OC_User::unsetMagicInCookie();
- $_SERVER['HTTP_REQUESTTOKEN'] = OC_Util::callRegister();
+ // don't redo authentication if user is already logged in
+ // otherwise session would be invalidated in OC_User::login with
+ // session_regenerate_id at every page load
+ if (!OC_User::isLoggedIn()) {
+ OC_App::loadApps(array('authentication'));
+ if (OC_User::login($_SERVER["PHP_AUTH_USER"], $_SERVER["PHP_AUTH_PW"])) {
+ //OC_Log::write('core',"Logged in with HTTP Authentication", OC_Log::DEBUG);
+ OC_User::unsetMagicInCookie();
+ $_SERVER['HTTP_REQUESTTOKEN'] = OC_Util::callRegister();
+ }
}
return true;
}
diff --git a/lib/connector/sabre/directory.php b/lib/connector/sabre/directory.php
index ed8d085462d..3181a4b310f 100644
--- a/lib/connector/sabre/directory.php
+++ b/lib/connector/sabre/directory.php
@@ -233,10 +233,10 @@ class OC_Connector_Sabre_Directory extends OC_Connector_Sabre_Node implements Sa
* @return array
*/
public function getQuotaInfo() {
- $rootInfo=\OC\Files\Filesystem::getFileInfo('');
+ $storageInfo = OC_Helper::getStorageInfo($this->path);
return array(
- $rootInfo['size'],
- \OC\Files\Filesystem::free_space()
+ $storageInfo['used'],
+ $storageInfo['free']
);
}
diff --git a/lib/connector/sabre/quotaplugin.php b/lib/connector/sabre/quotaplugin.php
index 34d4b676157..ea2cb81d1f7 100644
--- a/lib/connector/sabre/quotaplugin.php
+++ b/lib/connector/sabre/quotaplugin.php
@@ -3,58 +3,95 @@
/**
* This plugin check user quota and deny creating files when they exceeds the quota.
*
- * @copyright Copyright (C) 2012 entreCables S.L. All rights reserved.
* @author Sergio Cambra
+ * @copyright Copyright (C) 2012 entreCables S.L. All rights reserved.
* @license http://code.google.com/p/sabredav/wiki/License Modified BSD License
*/
class OC_Connector_Sabre_QuotaPlugin extends Sabre_DAV_ServerPlugin {
/**
- * Reference to main server object
- *
- * @var Sabre_DAV_Server
- */
+ * Reference to main server object
+ *
+ * @var Sabre_DAV_Server
+ */
private $server;
/**
- * This initializes the plugin.
- *
- * This function is called by Sabre_DAV_Server, after
- * addPlugin is called.
- *
- * This method should set up the requires event subscriptions.
- *
- * @param Sabre_DAV_Server $server
- * @return void
- */
+ * is kept public to allow overwrite for unit testing
+ *
+ * @var \OC\Files\View
+ */
+ public $fileView;
+
+ /**
+ * This initializes the plugin.
+ *
+ * This function is called by Sabre_DAV_Server, after
+ * addPlugin is called.
+ *
+ * This method should set up the requires event subscriptions.
+ *
+ * @param Sabre_DAV_Server $server
+ * @return void
+ */
public function initialize(Sabre_DAV_Server $server) {
- $this->server = $server;
- $this->server->subscribeEvent('beforeWriteContent', array($this, 'checkQuota'), 10);
- $this->server->subscribeEvent('beforeCreateFile', array($this, 'checkQuota'), 10);
+ $this->server = $server;
+ $server->subscribeEvent('beforeWriteContent', array($this, 'checkQuota'), 10);
+ $server->subscribeEvent('beforeCreateFile', array($this, 'checkQuota'), 10);
}
/**
- * This method is called before any HTTP method and forces users to be authenticated
- *
- * @param string $method
- * @throws Sabre_DAV_Exception
- * @return bool
- */
+ * This method is called before any HTTP method and validates there is enough free space to store the file
+ *
+ * @param string $method
+ * @throws Sabre_DAV_Exception
+ * @return bool
+ */
public function checkQuota($uri, $data = null) {
- $expected = $this->server->httpRequest->getHeader('X-Expected-Entity-Length');
- $length = $expected ? $expected : $this->server->httpRequest->getHeader('Content-Length');
+ $length = $this->getLength();
if ($length) {
if (substr($uri, 0, 1)!=='/') {
$uri='/'.$uri;
}
list($parentUri, $newName) = Sabre_DAV_URLUtil::splitPath($uri);
- $freeSpace = \OC\Files\Filesystem::free_space($parentUri);
+ $freeSpace = $this->getFreeSpace($parentUri);
if ($freeSpace !== \OC\Files\SPACE_UNKNOWN && $length > $freeSpace) {
throw new Sabre_DAV_Exception_InsufficientStorage();
}
}
return true;
}
+
+ public function getLength()
+ {
+ $req = $this->server->httpRequest;
+ $length = $req->getHeader('X-Expected-Entity-Length');
+ if (!$length) {
+ $length = $req->getHeader('Content-Length');
+ }
+
+ $ocLength = $req->getHeader('OC-Total-Length');
+ if ($length && $ocLength) {
+ return max($length, $ocLength);
+ }
+
+ return $length;
+ }
+
+ /**
+ * @param $parentUri
+ * @return mixed
+ */
+ public function getFreeSpace($parentUri)
+ {
+ if (is_null($this->fileView)) {
+ // initialize fileView
+ $this->fileView = \OC\Files\Filesystem::getView();
+ }
+
+ $freeSpace = $this->fileView->free_space($parentUri);
+ return $freeSpace;
+ }
}
diff --git a/lib/files/storage/mappedlocal.php b/lib/files/storage/mappedlocal.php
index cf5d9b3ef4f..fbf1b4ebf96 100644
--- a/lib/files/storage/mappedlocal.php
+++ b/lib/files/storage/mappedlocal.php
@@ -65,7 +65,7 @@ class MappedLocal extends \OC\Files\Storage\Common{
$logicalPath = $this->mapper->physicalToLogic($physicalPath);
$dh = opendir($physicalPath);
- while ($file = readdir($dh)) {
+ while (($file = readdir($dh)) !== false) {
if ($file === '.' or $file === '..') {
continue;
}
diff --git a/lib/files/view.php b/lib/files/view.php
index bb737f19ef8..8aee12bf6fe 100644
--- a/lib/files/view.php
+++ b/lib/files/view.php
@@ -249,6 +249,7 @@ class View {
$hooks = array('touch');
if (!$this->file_exists($path)) {
+ $hooks[] = 'create';
$hooks[] = 'write';
}
$result = $this->basicOperation('touch', $path, $hooks, $mtime);
diff --git a/lib/group/group.php b/lib/group/group.php
index a752c4311c1..bcd2419b309 100644
--- a/lib/group/group.php
+++ b/lib/group/group.php
@@ -62,7 +62,6 @@ class Group {
return $this->users;
}
- $users = array();
$userIds = array();
foreach ($this->backends as $backend) {
$diff = array_diff(
@@ -74,11 +73,8 @@ class Group {
}
}
- foreach ($userIds as $userId) {
- $users[] = $this->userManager->get($userId);
- }
- $this->users = $users;
- return $users;
+ $this->users = $this->getVerifiedUsers($userIds);
+ return $this->users;
}
/**
@@ -113,7 +109,7 @@ class Group {
if ($backend->implementsActions(OC_GROUP_BACKEND_ADD_TO_GROUP)) {
$backend->addToGroup($user->getUID(), $this->gid);
if ($this->users) {
- $this->users[] = $user;
+ $this->users[$user->getUID()] = $user;
}
if ($this->emitter) {
$this->emitter->emit('\OC\Group', 'postAddUser', array($this, $user));
@@ -172,9 +168,7 @@ class Group {
if (!is_null($offset)) {
$offset -= count($userIds);
}
- foreach ($userIds as $userId) {
- $users[$userId] = $this->userManager->get($userId);
- }
+ $users += $this->getVerifiedUsers($userIds);
if (!is_null($limit) and $limit <= 0) {
return array_values($users);
}
@@ -191,7 +185,6 @@ class Group {
* @return \OC\User\User[]
*/
public function searchDisplayName($search, $limit = null, $offset = null) {
- $users = array();
foreach ($this->backends as $backend) {
if ($backend->implementsActions(OC_GROUP_BACKEND_GET_DISPLAYNAME)) {
$userIds = array_keys($backend->displayNamesInGroup($this->gid, $search, $limit, $offset));
@@ -204,9 +197,7 @@ class Group {
if (!is_null($offset)) {
$offset -= count($userIds);
}
- foreach ($userIds as $userId) {
- $users[$userId] = $this->userManager->get($userId);
- }
+ $users = $this->getVerifiedUsers($userIds);
if (!is_null($limit) and $limit <= 0) {
return array_values($users);
}
@@ -235,4 +226,23 @@ class Group {
}
return $result;
}
+
+ /**
+ * @brief returns all the Users from an array that really exists
+ * @param $userIds an array containing user IDs
+ * @return an Array with the userId as Key and \OC\User\User as value
+ */
+ private function getVerifiedUsers($userIds) {
+ if(!is_array($userIds)) {
+ return array();
+ }
+ $users = array();
+ foreach ($userIds as $userId) {
+ $user = $this->userManager->get($userId);
+ if(!is_null($user)) {
+ $users[$userId] = $user;
+ }
+ }
+ return $users;
+ }
}
diff --git a/lib/helper.php b/lib/helper.php
index 1024a570e36..5fb8fed3459 100644
--- a/lib/helper.php
+++ b/lib/helper.php
@@ -185,7 +185,38 @@ class OC_Helper {
* Returns the path to the image of this file type.
*/
public static function mimetypeIcon($mimetype) {
- $alias = array('application/xml' => 'code/xml');
+ $alias = array(
+ 'application/xml' => 'code/xml',
+ 'application/msword' => 'x-office/document',
+ 'application/vnd.openxmlformats-officedocument.wordprocessingml.document' => 'x-office/document',
+ 'application/vnd.openxmlformats-officedocument.wordprocessingml.template' => 'x-office/document',
+ 'application/vnd.ms-word.document.macroEnabled.12' => 'x-office/document',
+ 'application/vnd.ms-word.template.macroEnabled.12' => 'x-office/document',
+ 'application/vnd.oasis.opendocument.text' => 'x-office/document',
+ 'application/vnd.oasis.opendocument.text-template' => 'x-office/document',
+ 'application/vnd.oasis.opendocument.text-web' => 'x-office/document',
+ 'application/vnd.oasis.opendocument.text-master' => 'x-office/document',
+ 'application/vnd.ms-powerpoint' => 'x-office/presentation',
+ 'application/vnd.openxmlformats-officedocument.presentationml.presentation' => 'x-office/presentation',
+ 'application/vnd.openxmlformats-officedocument.presentationml.template' => 'x-office/presentation',
+ 'application/vnd.openxmlformats-officedocument.presentationml.slideshow' => 'x-office/presentation',
+ 'application/vnd.ms-powerpoint.addin.macroEnabled.12' => 'x-office/presentation',
+ 'application/vnd.ms-powerpoint.presentation.macroEnabled.12' => 'x-office/presentation',
+ 'application/vnd.ms-powerpoint.template.macroEnabled.12' => 'x-office/presentation',
+ 'application/vnd.ms-powerpoint.slideshow.macroEnabled.12' => 'x-office/presentation',
+ 'application/vnd.oasis.opendocument.presentation' => 'x-office/presentation',
+ 'application/vnd.oasis.opendocument.presentation-template' => 'x-office/presentation',
+ 'application/vnd.ms-excel' => 'x-office/spreadsheet',
+ 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet' => 'x-office/spreadsheet',
+ 'application/vnd.openxmlformats-officedocument.spreadsheetml.template' => 'x-office/spreadsheet',
+ 'application/vnd.ms-excel.sheet.macroEnabled.12' => 'x-office/spreadsheet',
+ 'application/vnd.ms-excel.template.macroEnabled.12' => 'x-office/spreadsheet',
+ 'application/vnd.ms-excel.addin.macroEnabled.12' => 'x-office/spreadsheet',
+ 'application/vnd.ms-excel.sheet.binary.macroEnabled.12' => 'x-office/spreadsheet',
+ 'application/vnd.oasis.opendocument.spreadsheet' => 'x-office/spreadsheet',
+ 'application/vnd.oasis.opendocument.spreadsheet-template' => 'x-office/spreadsheet',
+ );
+
if (isset($alias[$mimetype])) {
$mimetype = $alias[$mimetype];
}
@@ -220,6 +251,21 @@ class OC_Helper {
}
/**
+ * @brief get path to preview of file
+ * @param string $path path
+ * @return string the url
+ *
+ * Returns the path to the preview of the file.
+ */
+ public static function previewIcon($path) {
+ return self::linkToRoute( 'core_ajax_preview', array('x' => 36, 'y' => 36, 'file' => urlencode($path) ));
+ }
+
+ public static function publicPreviewIcon( $path, $token ) {
+ return self::linkToRoute( 'core_ajax_public_preview', array('x' => 36, 'y' => 36, 'file' => urlencode($path), 't' => $token));
+ }
+
+ /**
* @brief Make a human file size
* @param int $bytes file size in bytes
* @return string a human readable file size
@@ -591,9 +637,26 @@ class OC_Helper {
* remove all files in PHP /oc-noclean temp dir
*/
public static function cleanTmpNoClean() {
- $tmpDirNoCleanFile = get_temp_dir() . '/oc-noclean/';
- if (file_exists($tmpDirNoCleanFile)) {
- self::rmdirr($tmpDirNoCleanFile);
+ $tmpDirNoCleanName=get_temp_dir() . '/oc-noclean/';
+ if(file_exists($tmpDirNoCleanName) && is_dir($tmpDirNoCleanName)) {
+ $files=scandir($tmpDirNoCleanName);
+ foreach($files as $file) {
+ $fileName = $tmpDirNoCleanName . $file;
+ if (!\OC\Files\Filesystem::isIgnoredDir($file) && filemtime($fileName) + 600 < time()) {
+ unlink($fileName);
+ }
+ }
+ // if oc-noclean is empty delete it
+ $isTmpDirNoCleanEmpty = true;
+ $tmpDirNoClean = opendir($tmpDirNoCleanName);
+ while (false !== ($file = readdir($tmpDirNoClean))) {
+ if (!\OC\Files\Filesystem::isIgnoredDir($file)) {
+ $isTmpDirNoCleanEmpty = false;
+ }
+ }
+ if ($isTmpDirNoCleanEmpty) {
+ rmdir($tmpDirNoCleanName);
+ }
}
}
@@ -824,24 +887,25 @@ class OC_Helper {
}
/**
- * Calculate the disc space
+ * Calculate the disc space for the given path
+ *
+ * @param string $path
+ * @return array
*/
- public static function getStorageInfo() {
- $rootInfo = \OC\Files\Filesystem::getFileInfo('/');
+ public static function getStorageInfo($path) {
+ $rootInfo = \OC\Files\Filesystem::getFileInfo($path);
$used = $rootInfo['size'];
if ($used < 0) {
$used = 0;
}
- $free = \OC\Files\Filesystem::free_space();
+ $free = \OC\Files\Filesystem::free_space($path);
if ($free >= 0) {
$total = $free + $used;
} else {
$total = $free; //either unknown or unlimited
}
- if ($total == 0) {
- $total = 1; // prevent division by zero
- }
- if ($total >= 0) {
+ if ($total > 0) {
+ // prevent division by zero or error codes (negative values)
$relative = round(($used / $total) * 10000) / 100;
} else {
$relative = 0;
diff --git a/lib/image.php b/lib/image.php
index 4bc38e20e56..7761a3c7737 100644
--- a/lib/image.php
+++ b/lib/image.php
@@ -25,24 +25,27 @@
*/
class OC_Image {
protected $resource = false; // tmp resource.
- protected $imagetype = IMAGETYPE_PNG; // Default to png if file type isn't evident.
- protected $bit_depth = 24;
- protected $filepath = null;
+ protected $imageType = IMAGETYPE_PNG; // Default to png if file type isn't evident.
+ protected $mimeType = "image/png"; // Default to png
+ protected $bitDepth = 24;
+ protected $filePath = null;
+
+ private $fileInfo;
/**
* @brief Get mime type for an image file.
* @param $filepath The path to a local image file.
* @returns string The mime type if the it could be determined, otherwise an empty string.
*/
- static public function getMimeTypeForFile($filepath) {
+ static public function getMimeTypeForFile($filePath) {
// exif_imagetype throws "read error!" if file is less than 12 byte
- if (filesize($filepath) > 11) {
- $imagetype = exif_imagetype($filepath);
+ if (filesize($filePath) > 11) {
+ $imageType = exif_imagetype($filePath);
}
else {
- $imagetype = false;
+ $imageType = false;
}
- return $imagetype ? image_type_to_mime_type($imagetype) : '';
+ return $imageType ? image_type_to_mime_type($imageType) : '';
}
/**
@@ -50,14 +53,19 @@ class OC_Image {
* @param $imageref The path to a local file, a base64 encoded string or a resource created by an imagecreate* function.
* @returns bool False on error
*/
- public function __construct($imageref = null) {
+ public function __construct($imageRef = null) {
//OC_Log::write('core',__METHOD__.'(): start', OC_Log::DEBUG);
if(!extension_loaded('gd') || !function_exists('gd_info')) {
OC_Log::write('core', __METHOD__.'(): GD module not installed', OC_Log::ERROR);
return false;
}
- if(!is_null($imageref)) {
- $this->load($imageref);
+
+ if (\OC_Util::fileInfoLoaded()) {
+ $this->fileInfo = new finfo(FILEINFO_MIME_TYPE);
+ }
+
+ if(!is_null($imageRef)) {
+ $this->load($imageRef);
}
}
@@ -74,7 +82,7 @@ class OC_Image {
* @returns int
*/
public function mimeType() {
- return $this->valid() ? image_type_to_mime_type($this->imagetype) : '';
+ return $this->valid() ? $this->mimeType : '';
}
/**
@@ -157,30 +165,30 @@ class OC_Image {
* @returns bool
*/
- public function save($filepath=null) {
- if($filepath === null && $this->filepath === null) {
+ public function save($filePath=null) {
+ if($filePath === null && $this->filePath === null) {
OC_Log::write('core', __METHOD__.'(): called with no path.', OC_Log::ERROR);
return false;
- } elseif($filepath === null && $this->filepath !== null) {
- $filepath = $this->filepath;
+ } elseif($filePath === null && $this->filePath !== null) {
+ $filePath = $this->filePath;
}
- return $this->_output($filepath);
+ return $this->_output($filePath);
}
/**
* @brief Outputs/saves the image.
*/
- private function _output($filepath=null) {
- if($filepath) {
- if (!file_exists(dirname($filepath)))
- mkdir(dirname($filepath), 0777, true);
- if(!is_writable(dirname($filepath))) {
+ private function _output($filePath=null) {
+ if($filePath) {
+ if (!file_exists(dirname($filePath)))
+ mkdir(dirname($filePath), 0777, true);
+ if(!is_writable(dirname($filePath))) {
OC_Log::write('core',
- __METHOD__.'(): Directory \''.dirname($filepath).'\' is not writable.',
+ __METHOD__.'(): Directory \''.dirname($filePath).'\' is not writable.',
OC_Log::ERROR);
return false;
- } elseif(is_writable(dirname($filepath)) && file_exists($filepath) && !is_writable($filepath)) {
- OC_Log::write('core', __METHOD__.'(): File \''.$filepath.'\' is not writable.', OC_Log::ERROR);
+ } elseif(is_writable(dirname($filePath)) && file_exists($filePath) && !is_writable($filePath)) {
+ OC_Log::write('core', __METHOD__.'(): File \''.$filePath.'\' is not writable.', OC_Log::ERROR);
return false;
}
}
@@ -188,30 +196,30 @@ class OC_Image {
return false;
}
- $retval = false;
- switch($this->imagetype) {
+ $retVal = false;
+ switch($this->imageType) {
case IMAGETYPE_GIF:
- $retval = imagegif($this->resource, $filepath);
+ $retVal = imagegif($this->resource, $filePath);
break;
case IMAGETYPE_JPEG:
- $retval = imagejpeg($this->resource, $filepath);
+ $retVal = imagejpeg($this->resource, $filePath);
break;
case IMAGETYPE_PNG:
- $retval = imagepng($this->resource, $filepath);
+ $retVal = imagepng($this->resource, $filePath);
break;
case IMAGETYPE_XBM:
- $retval = imagexbm($this->resource, $filepath);
+ $retVal = imagexbm($this->resource, $filePath);
break;
case IMAGETYPE_WBMP:
- $retval = imagewbmp($this->resource, $filepath);
+ $retVal = imagewbmp($this->resource, $filePath);
break;
case IMAGETYPE_BMP:
- $retval = imagebmp($this->resource, $filepath, $this->bit_depth);
+ $retVal = imagebmp($this->resource, $filePath, $this->bitDepth);
break;
default:
- $retval = imagepng($this->resource, $filepath);
+ $retVal = imagepng($this->resource, $filePath);
}
- return $retval;
+ return $retVal;
}
/**
@@ -233,7 +241,21 @@ class OC_Image {
*/
function data() {
ob_start();
- $res = imagepng($this->resource);
+ switch ($this->mimeType) {
+ case "image/png":
+ $res = imagepng($this->resource);
+ break;
+ case "image/jpeg":
+ $res = imagejpeg($this->resource);
+ break;
+ case "image/gif":
+ $res = imagegif($this->resource);
+ break;
+ default:
+ $res = imagepng($this->resource);
+ OC_Log::write('core', 'OC_Image->data. Couldn\'t guess mimetype, defaulting to png', OC_Log::INFO);
+ break;
+ }
if (!$res) {
OC_Log::write('core', 'OC_Image->data. Error getting image data.', OC_Log::ERROR);
}
@@ -261,11 +283,11 @@ class OC_Image {
OC_Log::write('core', 'OC_Image->fixOrientation() No image loaded.', OC_Log::DEBUG);
return -1;
}
- if(is_null($this->filepath) || !is_readable($this->filepath)) {
+ if(is_null($this->filePath) || !is_readable($this->filePath)) {
OC_Log::write('core', 'OC_Image->fixOrientation() No readable file path set.', OC_Log::DEBUG);
return -1;
}
- $exif = @exif_read_data($this->filepath, 'IFD0');
+ $exif = @exif_read_data($this->filePath, 'IFD0');
if(!$exif) {
return -1;
}
@@ -351,19 +373,19 @@ class OC_Image {
* @param $imageref The path to a local file, a base64 encoded string or a resource created by an imagecreate* function or a file resource (file handle ).
* @returns An image resource or false on error
*/
- public function load($imageref) {
- if(is_resource($imageref)) {
- if(get_resource_type($imageref) == 'gd') {
- $this->resource = $imageref;
+ public function load($imageRef) {
+ if(is_resource($imageRef)) {
+ if(get_resource_type($imageRef) == 'gd') {
+ $this->resource = $imageRef;
return $this->resource;
- } elseif(in_array(get_resource_type($imageref), array('file', 'stream'))) {
- return $this->loadFromFileHandle($imageref);
+ } elseif(in_array(get_resource_type($imageRef), array('file', 'stream'))) {
+ return $this->loadFromFileHandle($imageRef);
}
- } elseif($this->loadFromFile($imageref) !== false) {
+ } elseif($this->loadFromFile($imageRef) !== false) {
return $this->resource;
- } elseif($this->loadFromBase64($imageref) !== false) {
+ } elseif($this->loadFromBase64($imageRef) !== false) {
return $this->resource;
- } elseif($this->loadFromData($imageref) !== false) {
+ } elseif($this->loadFromData($imageRef) !== false) {
return $this->resource;
} else {
OC_Log::write('core', __METHOD__.'(): couldn\'t load anything. Giving up!', OC_Log::DEBUG);
@@ -390,62 +412,62 @@ class OC_Image {
* @param $imageref The path to a local file.
* @returns An image resource or false on error
*/
- public function loadFromFile($imagepath=false) {
+ public function loadFromFile($imagePath=false) {
// exif_imagetype throws "read error!" if file is less than 12 byte
- if(!@is_file($imagepath) || !file_exists($imagepath) || filesize($imagepath) < 12 || !is_readable($imagepath)) {
+ if(!@is_file($imagePath) || !file_exists($imagePath) || filesize($imagePath) < 12 || !is_readable($imagePath)) {
// Debug output disabled because this method is tried before loadFromBase64?
- OC_Log::write('core', 'OC_Image->loadFromFile, couldn\'t load: '.$imagepath, OC_Log::DEBUG);
+ OC_Log::write('core', 'OC_Image->loadFromFile, couldn\'t load: '.$imagePath, OC_Log::DEBUG);
return false;
}
- $itype = exif_imagetype($imagepath);
- switch($itype) {
+ $iType = exif_imagetype($imagePath);
+ switch ($iType) {
case IMAGETYPE_GIF:
if (imagetypes() & IMG_GIF) {
- $this->resource = imagecreatefromgif($imagepath);
+ $this->resource = imagecreatefromgif($imagePath);
} else {
OC_Log::write('core',
- 'OC_Image->loadFromFile, GIF images not supported: '.$imagepath,
+ 'OC_Image->loadFromFile, GIF images not supported: '.$imagePath,
OC_Log::DEBUG);
}
break;
case IMAGETYPE_JPEG:
if (imagetypes() & IMG_JPG) {
- $this->resource = imagecreatefromjpeg($imagepath);
+ $this->resource = imagecreatefromjpeg($imagePath);
} else {
OC_Log::write('core',
- 'OC_Image->loadFromFile, JPG images not supported: '.$imagepath,
+ 'OC_Image->loadFromFile, JPG images not supported: '.$imagePath,
OC_Log::DEBUG);
}
break;
case IMAGETYPE_PNG:
if (imagetypes() & IMG_PNG) {
- $this->resource = imagecreatefrompng($imagepath);
+ $this->resource = imagecreatefrompng($imagePath);
} else {
OC_Log::write('core',
- 'OC_Image->loadFromFile, PNG images not supported: '.$imagepath,
+ 'OC_Image->loadFromFile, PNG images not supported: '.$imagePath,
OC_Log::DEBUG);
}
break;
case IMAGETYPE_XBM:
if (imagetypes() & IMG_XPM) {
- $this->resource = imagecreatefromxbm($imagepath);
+ $this->resource = imagecreatefromxbm($imagePath);
} else {
OC_Log::write('core',
- 'OC_Image->loadFromFile, XBM/XPM images not supported: '.$imagepath,
+ 'OC_Image->loadFromFile, XBM/XPM images not supported: '.$imagePath,
OC_Log::DEBUG);
}
break;
case IMAGETYPE_WBMP:
if (imagetypes() & IMG_WBMP) {
- $this->resource = imagecreatefromwbmp($imagepath);
+ $this->resource = imagecreatefromwbmp($imagePath);
} else {
OC_Log::write('core',
- 'OC_Image->loadFromFile, WBMP images not supported: '.$imagepath,
+ 'OC_Image->loadFromFile, WBMP images not supported: '.$imagePath,
OC_Log::DEBUG);
}
break;
case IMAGETYPE_BMP:
- $this->resource = $this->imagecreatefrombmp($imagepath);
+ $this->resource = $this->imagecreatefrombmp($imagePath);
break;
/*
case IMAGETYPE_TIFF_II: // (intel byte order)
@@ -474,14 +496,15 @@ class OC_Image {
default:
// this is mostly file created from encrypted file
- $this->resource = imagecreatefromstring(\OC\Files\Filesystem::file_get_contents(\OC\Files\Filesystem::getLocalPath($imagepath)));
- $itype = IMAGETYPE_PNG;
+ $this->resource = imagecreatefromstring(\OC\Files\Filesystem::file_get_contents(\OC\Files\Filesystem::getLocalPath($imagePath)));
+ $iType = IMAGETYPE_PNG;
OC_Log::write('core', 'OC_Image->loadFromFile, Default', OC_Log::DEBUG);
break;
}
if($this->valid()) {
- $this->imagetype = $itype;
- $this->filepath = $imagepath;
+ $this->imageType = $iType;
+ $this->mimeType = image_type_to_mime_type($iType);
+ $this->filePath = $imagePath;
}
return $this->resource;
}
@@ -496,6 +519,14 @@ class OC_Image {
return false;
}
$this->resource = @imagecreatefromstring($str);
+ if ($this->fileInfo) {
+ $this->mimeType = $this->fileInfo->buffer($str);
+ }
+ if(is_resource($this->resource)) {
+ imagealphablending($this->resource, false);
+ imagesavealpha($this->resource, true);
+ }
+
if(!$this->resource) {
OC_Log::write('core', 'OC_Image->loadFromData, couldn\'t load', OC_Log::DEBUG);
return false;
@@ -515,6 +546,9 @@ class OC_Image {
$data = base64_decode($str);
if($data) { // try to load from string data
$this->resource = @imagecreatefromstring($data);
+ if ($this->fileInfo) {
+ $this->mimeType = $this->fileInfo->buffer($data);
+ }
if(!$this->resource) {
OC_Log::write('core', 'OC_Image->loadFromBase64, couldn\'t load', OC_Log::DEBUG);
return false;
@@ -534,16 +568,16 @@ class OC_Image {
* </p>
* @return resource an image resource identifier on success, <b>FALSE</b> on errors.
*/
- private function imagecreatefrombmp($filename) {
- if (!($fh = fopen($filename, 'rb'))) {
- trigger_error('imagecreatefrombmp: Can not open ' . $filename, E_USER_WARNING);
+ private function imagecreatefrombmp($fileName) {
+ if (!($fh = fopen($fileName, 'rb'))) {
+ trigger_error('imagecreatefrombmp: Can not open ' . $fileName, E_USER_WARNING);
return false;
}
// read file header
$meta = unpack('vtype/Vfilesize/Vreserved/Voffset', fread($fh, 14));
// check for bitmap
if ($meta['type'] != 19778) {
- trigger_error('imagecreatefrombmp: ' . $filename . ' is not a bitmap!', E_USER_WARNING);
+ trigger_error('imagecreatefrombmp: ' . $fileName . ' is not a bitmap!', E_USER_WARNING);
return false;
}
// read image header
@@ -554,7 +588,7 @@ class OC_Image {
}
// set bytes and padding
$meta['bytes'] = $meta['bits'] / 8;
- $this->bit_depth = $meta['bits']; //remember the bit depth for the imagebmp call
+ $this->bitDepth = $meta['bits']; //remember the bit depth for the imagebmp call
$meta['decal'] = 4 - (4 * (($meta['width'] * $meta['bytes'] / 4)- floor($meta['width'] * $meta['bytes'] / 4)));
if ($meta['decal'] == 4) {
$meta['decal'] = 0;
@@ -590,7 +624,7 @@ class OC_Image {
$p = 0;
$vide = chr(0);
$y = $meta['height'] - 1;
- $error = 'imagecreatefrombmp: ' . $filename . ' has not enough data!';
+ $error = 'imagecreatefrombmp: ' . $fileName . ' has not enough data!';
// loop through the image data beginning with the lower left corner
while ($y >= 0) {
$x = 0;
@@ -653,7 +687,7 @@ class OC_Image {
break;
default:
trigger_error('imagecreatefrombmp: '
- . $filename . ' has ' . $meta['bits'] . ' bits and this is not supported!',
+ . $fileName . ' has ' . $meta['bits'] . ' bits and this is not supported!',
E_USER_WARNING);
return false;
}
@@ -673,24 +707,24 @@ class OC_Image {
* @param $maxsize The maximum size of either the width or height.
* @returns bool
*/
- public function resize($maxsize) {
+ public function resize($maxSize) {
if(!$this->valid()) {
OC_Log::write('core', __METHOD__.'(): No image loaded', OC_Log::ERROR);
return false;
}
- $width_orig=imageSX($this->resource);
- $height_orig=imageSY($this->resource);
- $ratio_orig = $width_orig/$height_orig;
+ $widthOrig=imageSX($this->resource);
+ $heightOrig=imageSY($this->resource);
+ $ratioOrig = $widthOrig/$heightOrig;
- if ($ratio_orig > 1) {
- $new_height = round($maxsize/$ratio_orig);
- $new_width = $maxsize;
+ if ($ratioOrig > 1) {
+ $newHeight = round($maxSize/$ratioOrig);
+ $newWidth = $maxSize;
} else {
- $new_width = round($maxsize*$ratio_orig);
- $new_height = $maxsize;
+ $newWidth = round($maxSize*$ratioOrig);
+ $newHeight = $maxSize;
}
- $this->preciseResize(round($new_width), round($new_height));
+ $this->preciseResize(round($newWidth), round($newHeight));
return true;
}
@@ -699,8 +733,8 @@ class OC_Image {
OC_Log::write('core', __METHOD__.'(): No image loaded', OC_Log::ERROR);
return false;
}
- $width_orig=imageSX($this->resource);
- $height_orig=imageSY($this->resource);
+ $widthOrig=imageSX($this->resource);
+ $heightOrig=imageSY($this->resource);
$process = imagecreatetruecolor($width, $height);
if ($process == false) {
@@ -710,13 +744,13 @@ class OC_Image {
}
// preserve transparency
- if($this->imagetype == IMAGETYPE_GIF or $this->imagetype == IMAGETYPE_PNG) {
+ if($this->imageType == IMAGETYPE_GIF or $this->imageType == IMAGETYPE_PNG) {
imagecolortransparent($process, imagecolorallocatealpha($process, 0, 0, 0, 127));
imagealphablending($process, false);
imagesavealpha($process, true);
}
- imagecopyresampled($process, $this->resource, 0, 0, 0, 0, $width, $height, $width_orig, $height_orig);
+ imagecopyresampled($process, $this->resource, 0, 0, 0, 0, $width, $height, $widthOrig, $heightOrig);
if ($process == false) {
OC_Log::write('core', __METHOD__.'(): Error resampling process image '.$width.'x'.$height, OC_Log::ERROR);
imagedestroy($process);
@@ -737,19 +771,19 @@ class OC_Image {
OC_Log::write('core', 'OC_Image->centerCrop, No image loaded', OC_Log::ERROR);
return false;
}
- $width_orig=imageSX($this->resource);
- $height_orig=imageSY($this->resource);
- if($width_orig === $height_orig and $size==0) {
+ $widthOrig=imageSX($this->resource);
+ $heightOrig=imageSY($this->resource);
+ if($widthOrig === $heightOrig and $size==0) {
return true;
}
- $ratio_orig = $width_orig/$height_orig;
- $width = $height = min($width_orig, $height_orig);
+ $ratioOrig = $widthOrig/$heightOrig;
+ $width = $height = min($widthOrig, $heightOrig);
- if ($ratio_orig > 1) {
- $x = ($width_orig/2) - ($width/2);
+ if ($ratioOrig > 1) {
+ $x = ($widthOrig/2) - ($width/2);
$y = 0;
} else {
- $y = ($height_orig/2) - ($height/2);
+ $y = ($heightOrig/2) - ($height/2);
$x = 0;
}
if($size>0) {
@@ -767,7 +801,7 @@ class OC_Image {
}
// preserve transparency
- if($this->imagetype == IMAGETYPE_GIF or $this->imagetype == IMAGETYPE_PNG) {
+ if($this->imageType == IMAGETYPE_GIF or $this->imageType == IMAGETYPE_PNG) {
imagecolortransparent($process, imagecolorallocatealpha($process, 0, 0, 0, 127));
imagealphablending($process, false);
imagesavealpha($process, true);
@@ -827,9 +861,9 @@ class OC_Image {
OC_Log::write('core', __METHOD__.'(): No image loaded', OC_Log::ERROR);
return false;
}
- $width_orig=imageSX($this->resource);
- $height_orig=imageSY($this->resource);
- $ratio = $width_orig/$height_orig;
+ $widthOrig=imageSX($this->resource);
+ $heightOrig=imageSY($this->resource);
+ $ratio = $widthOrig/$heightOrig;
$newWidth = min($maxWidth, $ratio*$maxHeight);
$newHeight = min($maxHeight, $maxWidth/$ratio);
@@ -863,7 +897,7 @@ if ( ! function_exists( 'imagebmp') ) {
* @param int $compression [optional]
* @return bool <b>TRUE</b> on success or <b>FALSE</b> on failure.
*/
- function imagebmp($im, $filename='', $bit=24, $compression=0) {
+ function imagebmp($im, $fileName='', $bit=24, $compression=0) {
if (!in_array($bit, array(1, 4, 8, 16, 24, 32))) {
$bit = 24;
}
@@ -874,14 +908,14 @@ if ( ! function_exists( 'imagebmp') ) {
imagetruecolortopalette($im, true, $bits);
$width = imagesx($im);
$height = imagesy($im);
- $colors_num = imagecolorstotal($im);
- $rgb_quad = '';
+ $colorsNum = imagecolorstotal($im);
+ $rgbQuad = '';
if ($bit <= 8) {
- for ($i = 0; $i < $colors_num; $i++) {
+ for ($i = 0; $i < $colorsNum; $i++) {
$colors = imagecolorsforindex($im, $i);
- $rgb_quad .= chr($colors['blue']) . chr($colors['green']) . chr($colors['red']) . "\0";
+ $rgbQuad .= chr($colors['blue']) . chr($colors['green']) . chr($colors['red']) . "\0";
}
- $bmp_data = '';
+ $bmpData = '';
if ($compression == 0 || $bit < 8) {
$compression = 0;
$extra = '';
@@ -899,35 +933,35 @@ if ( ! function_exists( 'imagebmp') ) {
$bin |= $index << $k;
$i++;
}
- $bmp_data .= chr($bin);
+ $bmpData .= chr($bin);
}
- $bmp_data .= $extra;
+ $bmpData .= $extra;
}
}
// RLE8
else if ($compression == 1 && $bit == 8) {
for ($j = $height - 1; $j >= 0; $j--) {
- $last_index = "\0";
- $same_num = 0;
+ $lastIndex = "\0";
+ $sameNum = 0;
for ($i = 0; $i <= $width; $i++) {
$index = imagecolorat($im, $i, $j);
- if ($index !== $last_index || $same_num > 255) {
- if ($same_num != 0) {
- $bmp_data .= chr($same_num) . chr($last_index);
+ if ($index !== $lastIndex || $sameNum > 255) {
+ if ($sameNum != 0) {
+ $bmpData .= chr($same_num) . chr($lastIndex);
}
- $last_index = $index;
- $same_num = 1;
+ $lastIndex = $index;
+ $sameNum = 1;
}
else {
- $same_num++;
+ $sameNum++;
}
}
- $bmp_data .= "\0\0";
+ $bmpData .= "\0\0";
}
- $bmp_data .= "\0\1";
+ $bmpData .= "\0\1";
}
- $size_quad = strlen($rgb_quad);
- $size_data = strlen($bmp_data);
+ $sizeQuad = strlen($rgbQuad);
+ $sizeData = strlen($bmpData);
}
else {
$extra = '';
@@ -935,7 +969,7 @@ if ( ! function_exists( 'imagebmp') ) {
if ($padding % 4 != 0) {
$extra = str_repeat("\0", $padding);
}
- $bmp_data = '';
+ $bmpData = '';
for ($j = $height - 1; $j >= 0; $j--) {
for ($i = 0; $i < $width; $i++) {
$index = imagecolorat($im, $i, $j);
@@ -945,27 +979,27 @@ if ( ! function_exists( 'imagebmp') ) {
$bin |= ($colors['red'] >> 3) << 10;
$bin |= ($colors['green'] >> 3) << 5;
$bin |= $colors['blue'] >> 3;
- $bmp_data .= pack("v", $bin);
+ $bmpData .= pack("v", $bin);
}
else {
- $bmp_data .= pack("c*", $colors['blue'], $colors['green'], $colors['red']);
+ $bmpData .= pack("c*", $colors['blue'], $colors['green'], $colors['red']);
}
}
- $bmp_data .= $extra;
+ $bmpData .= $extra;
}
- $size_quad = 0;
- $size_data = strlen($bmp_data);
- $colors_num = 0;
- }
- $file_header = 'BM' . pack('V3', 54 + $size_quad + $size_data, 0, 54 + $size_quad);
- $info_header = pack('V3v2V*', 0x28, $width, $height, 1, $bit, $compression, $size_data, 0, 0, $colors_num, 0);
- if ($filename != '') {
- $fp = fopen($filename, 'wb');
- fwrite($fp, $file_header . $info_header . $rgb_quad . $bmp_data);
+ $sizeQuad = 0;
+ $sizeData = strlen($bmpData);
+ $colorsNum = 0;
+ }
+ $fileHeader = 'BM' . pack('V3', 54 + $sizeQuad + $sizeData, 0, 54 + $sizeQuad);
+ $infoHeader = pack('V3v2V*', 0x28, $width, $height, 1, $bit, $compression, $sizeData, 0, 0, $colorsNum, 0);
+ if ($fileName != '') {
+ $fp = fopen($fileName, 'wb');
+ fwrite($fp, $fileHeader . $infoHeader . $rgbQuad . $bmpData);
fclose($fp);
return true;
}
- echo $file_header . $info_header. $rgb_quad . $bmp_data;
+ echo $fileHeader . $infoHeader. $rgbQuad . $bmpData;
return true;
}
}
@@ -977,8 +1011,8 @@ if ( ! function_exists( 'exif_imagetype' ) ) {
* @param string $filename
* @return string|boolean
*/
- function exif_imagetype ( $filename ) {
- if ( ( $info = getimagesize( $filename ) ) !== false ) {
+ function exif_imagetype ( $fileName ) {
+ if ( ( $info = getimagesize( $fileName ) ) !== false ) {
return $info[2];
}
return false;
diff --git a/lib/installer.php b/lib/installer.php
index c29f9ec8982..b9684eaeea0 100644
--- a/lib/installer.php
+++ b/lib/installer.php
@@ -27,6 +27,7 @@ class OC_Installer{
/**
* @brief Installs an app
* @param $data array with all information
+ * @throws \Exception
* @returns integer
*
* This function installs an app. All information needed are passed in the
@@ -56,23 +57,22 @@ class OC_Installer{
* needed to get the app working.
*/
public static function installApp( $data = array()) {
+ $l = \OC_L10N::get('lib');
+
if(!isset($data['source'])) {
- OC_Log::write('core', 'No source specified when installing app', OC_Log::ERROR);
- return false;
+ throw new \Exception($l->t("No source specified when installing app"));
}
//download the file if necesary
if($data['source']=='http') {
$path=OC_Helper::tmpFile();
if(!isset($data['href'])) {
- OC_Log::write('core', 'No href specified when installing app from http', OC_Log::ERROR);
- return false;
+ throw new \Exception($l->t("No href specified when installing app from http"));
}
copy($data['href'], $path);
}else{
if(!isset($data['path'])) {
- OC_Log::write('core', 'No path specified when installing app from local file', OC_Log::ERROR);
- return false;
+ throw new \Exception($l->t("No path specified when installing app from local file"));
}
$path=$data['path'];
}
@@ -86,8 +86,7 @@ class OC_Installer{
rename($path, $path.'.tgz');
$path.='.tgz';
}else{
- OC_Log::write('core', 'Archives of type '.$mime.' are not supported', OC_Log::ERROR);
- return false;
+ throw new \Exception($l->t("Archives of type %s are not supported", array($mime)));
}
//extract the archive in a temporary folder
@@ -97,12 +96,11 @@ class OC_Installer{
if($archive=OC_Archive::open($path)) {
$archive->extract($extractDir);
} else {
- OC_Log::write('core', 'Failed to open archive when installing app', OC_Log::ERROR);
OC_Helper::rmdirr($extractDir);
if($data['source']=='http') {
unlink($path);
}
- return false;
+ throw new \Exception($l->t("Failed to open archive when installing app"));
}
//load the info.xml file of the app
@@ -118,62 +116,48 @@ class OC_Installer{
}
}
if(!is_file($extractDir.'/appinfo/info.xml')) {
- OC_Log::write('core', 'App does not provide an info.xml file', OC_Log::ERROR);
OC_Helper::rmdirr($extractDir);
if($data['source']=='http') {
unlink($path);
}
- return false;
+ throw new \Exception($l->t("App does not provide an info.xml file"));
}
$info=OC_App::getAppInfo($extractDir.'/appinfo/info.xml', true);
// check the code for not allowed calls
if(!OC_Installer::checkCode($info['id'], $extractDir)) {
- OC_Log::write('core', 'App can\'t be installed because of not allowed code in the App', OC_Log::ERROR);
OC_Helper::rmdirr($extractDir);
- return false;
+ throw new \Exception($l->t("App can't be installed because of not allowed code in the App"));
}
// check if the app is compatible with this version of ownCloud
if(
- !isset($info['require'])
- or !OC_App::isAppVersionCompatible(OC_Util::getVersion(), $info['require'])
- ) {
- OC_Log::write('core',
- 'App can\'t be installed because it is not compatible with this version of ownCloud',
- OC_Log::ERROR);
+ !isset($info['require'])
+ or !OC_App::isAppVersionCompatible(OC_Util::getVersion(), $info['require'])
+ ) {
OC_Helper::rmdirr($extractDir);
- return false;
+ throw new \Exception($l->t("App can't be installed because it is not compatible with this version of ownCloud"));
}
// check if shipped tag is set which is only allowed for apps that are shipped with ownCloud
if(isset($info['shipped']) and ($info['shipped']=='true')) {
- OC_Log::write('core',
- 'App can\'t be installed because it contains the <shipped>true</shippe>'
- .' tag which is not allowed for non shipped apps',
- OC_Log::ERROR);
OC_Helper::rmdirr($extractDir);
- return false;
+ throw new \Exception($l->t("App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps"));
}
// check if the ocs version is the same as the version in info.xml/version
if(!isset($info['version']) or ($info['version']<>$data['appdata']['version'])) {
- OC_Log::write('core',
- 'App can\'t be installed because the version in info.xml/version is not the same'
- .' as the version reported from the app store',
- OC_Log::ERROR);
OC_Helper::rmdirr($extractDir);
- return false;
+ throw new \Exception($l->t("App can't be installed because the version in info.xml/version is not the same as the version reported from the app store"));
}
$basedir=OC_App::getInstallPath().'/'.$info['id'];
//check if the destination directory already exists
if(is_dir($basedir)) {
- OC_Log::write('core', 'App directory already exists', OC_Log::WARN);
OC_Helper::rmdirr($extractDir);
if($data['source']=='http') {
unlink($path);
}
- return false;
+ throw new \Exception($l->t("App directory already exists"));
}
if(isset($data['pretent']) and $data['pretent']==true) {
@@ -182,12 +166,11 @@ class OC_Installer{
//copy the app to the correct place
if(@!mkdir($basedir)) {
- OC_Log::write('core', 'Can\'t create app folder. Please fix permissions. ('.$basedir.')', OC_Log::ERROR);
OC_Helper::rmdirr($extractDir);
if($data['source']=='http') {
unlink($path);
}
- return false;
+ throw new \Exception($l->t("Can't create app folder. Please fix permissions. %s", array($basedir)));
}
OC_Helper::copyr($extractDir, $basedir);
diff --git a/lib/l10n/ca.php b/lib/l10n/ca.php
index 67ccdabc636..166455e652c 100644
--- a/lib/l10n/ca.php
+++ b/lib/l10n/ca.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "L'aplicació \"%s\" no es pot instal·lar perquè no és compatible amb aquesta versió d'ownCloud.",
+"No app name specified" => "No heu especificat cap nom d'aplicació",
"Help" => "Ajuda",
"Personal" => "Personal",
"Settings" => "Configuració",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Torna a Fitxers",
"Selected files too large to generate zip file." => "Els fitxers seleccionats son massa grans per generar un fitxer zip.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Baixeu els fitxers en trossos petits, de forma separada, o pregunteu a l'administrador.",
+"No source specified when installing app" => "No heu especificat la font en instal·lar l'aplicació",
+"No href specified when installing app from http" => "No heu especificat href en instal·lar l'aplicació des de http",
+"No path specified when installing app from local file" => "No heu seleccionat el camí en instal·lar una aplicació des d'un fitxer local",
+"Archives of type %s are not supported" => "Els fitxers del tipus %s no són compatibles",
+"Failed to open archive when installing app" => "Ha fallat l'obertura del fitxer en instal·lar l'aplicació",
+"App does not provide an info.xml file" => "L'aplicació no proporciona un fitxer info.xml",
+"App can't be installed because of not allowed code in the App" => "L'aplicació no es pot instal·lar perquè hi ha codi no autoritzat en l'aplicació",
+"App can't be installed because it is not compatible with this version of ownCloud" => "L'aplicació no es pot instal·lar perquè no és compatible amb aquesta versió d'ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "L'aplicació no es pot instal·lar perquè conté l'etiqueta <shipped>vertader</shipped> que no es permet per aplicacions no enviades",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "L'aplicació no es pot instal·lar perquè la versió a info.xml/version no és la mateixa que la versió indicada des de la botiga d'aplicacions",
+"App directory already exists" => "La carpeta de l'aplicació ja existeix",
+"Can't create app folder. Please fix permissions. %s" => "No es pot crear la carpeta de l'aplicació. Arregleu els permisos. %s",
"Application is not enabled" => "L'aplicació no està habilitada",
"Authentication error" => "Error d'autenticació",
"Token expired. Please reload page." => "El testimoni ha expirat. Torneu a carregar la pàgina.",
@@ -40,13 +54,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "El servidor web no està configurat correctament per permetre la sincronització de fitxers perquè la interfície WebDAV sembla no funcionar correctament.",
"Please double check the <a href='%s'>installation guides</a>." => "Comproveu les <a href='%s'>guies d'instal·lació</a>.",
"seconds ago" => "segons enrere",
-"_%n minute ago_::_%n minutes ago_" => array("",""),
-"_%n hour ago_::_%n hours ago_" => array("",""),
+"_%n minute ago_::_%n minutes ago_" => array("fa %n minut","fa %n minuts"),
+"_%n hour ago_::_%n hours ago_" => array("fa %n hora","fa %n hores"),
"today" => "avui",
"yesterday" => "ahir",
-"_%n day go_::_%n days ago_" => array("",""),
+"_%n day go_::_%n days ago_" => array("fa %n dia","fa %n dies"),
"last month" => "el mes passat",
-"_%n month ago_::_%n months ago_" => array("",""),
+"_%n month ago_::_%n months ago_" => array("fa %n mes","fa %n mesos"),
"last year" => "l'any passat",
"years ago" => "anys enrere",
"Caused by:" => "Provocat per:",
diff --git a/lib/l10n/cs_CZ.php b/lib/l10n/cs_CZ.php
index 1a80fc78bb6..fed9ad03c01 100644
--- a/lib/l10n/cs_CZ.php
+++ b/lib/l10n/cs_CZ.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Aplikace \"%s\" nemůže být nainstalována, protože není kompatibilní s touto verzí ownCloud.",
+"No app name specified" => "Nebyl zadan název aplikace",
"Help" => "Nápověda",
"Personal" => "Osobní",
"Settings" => "Nastavení",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Zpět k souborům",
"Selected files too large to generate zip file." => "Vybrané soubory jsou příliš velké pro vytvoření ZIP souboru.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Stáhněte soubory po menších částech, samostatně, nebo se obraťte na správce.",
+"No source specified when installing app" => "Nebyl zadán zdroj při instalaci aplikace",
+"No href specified when installing app from http" => "Nebyl zadán odkaz pro instalaci aplikace z HTTP",
+"No path specified when installing app from local file" => "Nebyla zadána cesta pro instalaci aplikace z místního souboru",
+"Archives of type %s are not supported" => "Archivy typu %s nejsou podporovány",
+"Failed to open archive when installing app" => "Chyba při otevírání archivu během instalace aplikace",
+"App does not provide an info.xml file" => "Aplikace neposkytuje soubor info.xml",
+"App can't be installed because of not allowed code in the App" => "Aplikace nemůže být nainstalována, protože obsahuje nepovolený kód",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Aplikace nemůže být nainstalována, protože není kompatibilní s touto verzí ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Aplikace nemůže být nainstalována, protože obsahuje značku\n<shipped>\n\ntrue\n</shipped>\n\ncož není povoleno pro nedodávané aplikace",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Aplikace nemůže být nainstalována, protože verze uvedená v info.xml/version nesouhlasí s verzí oznámenou z úložiště aplikací.",
+"App directory already exists" => "Adresář aplikace již existuje",
+"Can't create app folder. Please fix permissions. %s" => "Nelze vytvořit složku aplikace. Opravte práva souborů. %s",
"Application is not enabled" => "Aplikace není povolena",
"Authentication error" => "Chyba ověření",
"Token expired. Please reload page." => "Token vypršel. Obnovte prosím stránku.",
diff --git a/lib/l10n/da.php b/lib/l10n/da.php
index 78859b08745..26903142763 100644
--- a/lib/l10n/da.php
+++ b/lib/l10n/da.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "App'en \"%s\" kan ikke blive installeret, da den ikke er kompatibel med denne version af ownCloud.",
+"No app name specified" => "Intet app-navn angivet",
"Help" => "Hjælp",
"Personal" => "Personligt",
"Settings" => "Indstillinger",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Tilbage til Filer",
"Selected files too large to generate zip file." => "De markerede filer er for store til at generere en ZIP-fil.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Download filerne i små bider, seperat, eller kontakt venligst din administrator.",
+"No source specified when installing app" => "Ingen kilde angivet under installation af app",
+"No href specified when installing app from http" => "Ingen href angivet under installation af app via http",
+"No path specified when installing app from local file" => "Ingen sti angivet under installation af app fra lokal fil",
+"Archives of type %s are not supported" => "Arkiver af type %s understøttes ikke",
+"Failed to open archive when installing app" => "Kunne ikke åbne arkiv under installation af appen",
+"App does not provide an info.xml file" => "Der følger ingen info.xml-fil med appen",
+"App can't be installed because of not allowed code in the App" => "Appen kan ikke installeres, da den indeholder ikke-tilladt kode",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Appen kan ikke installeres, da den ikke er kompatibel med denne version af ownCloud.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Appen kan ikke installeres, da den indeholder taget\n<shipped>\n\ntrue\n</shipped>\n\nhvilket ikke er tilladt for ikke-medfølgende apps",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "App kan ikke installeres, da versionen i info.xml/version ikke er den samme som versionen rapporteret fra app-storen",
+"App directory already exists" => "App-mappe findes allerede",
+"Can't create app folder. Please fix permissions. %s" => "Kan ikke oprette app-mappe. Ret tilladelser. %s",
"Application is not enabled" => "Programmet er ikke aktiveret",
"Authentication error" => "Adgangsfejl",
"Token expired. Please reload page." => "Adgang er udløbet. Genindlæs siden.",
diff --git a/lib/l10n/de.php b/lib/l10n/de.php
index 01fe5ee0583..7a3e2c43e6b 100644
--- a/lib/l10n/de.php
+++ b/lib/l10n/de.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Applikation \"%s\" kann nicht installiert werden, da sie mit dieser ownCloud Version nicht kompatibel ist.",
+"No app name specified" => "Es wurde kein Applikation-Name angegeben",
"Help" => "Hilfe",
"Personal" => "Persönlich",
"Settings" => "Einstellungen",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Zurück zu \"Dateien\"",
"Selected files too large to generate zip file." => "Die gewählten Dateien sind zu groß, um eine ZIP-Datei zu erstellen.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Lade die Dateien in kleineren, separaten, Stücken herunter oder bitte deinen Administrator.",
+"No source specified when installing app" => "Für die Installation der Applikation wurde keine Quelle angegeben",
+"No href specified when installing app from http" => "Der Link (href) wurde nicht angegeben um die Applikation per http zu installieren",
+"No path specified when installing app from local file" => "Bei der Installation der Applikation aus einer lokalen Datei wurde kein Pfad angegeben",
+"Archives of type %s are not supported" => "Archive vom Typ %s werden nicht unterstützt",
+"Failed to open archive when installing app" => "Das Archiv konnte bei der Installation der Applikation nicht geöffnet werden",
+"App does not provide an info.xml file" => "Die Applikation enthält keine info,xml Datei",
+"App can't be installed because of not allowed code in the App" => "Die Applikation kann auf Grund von unerlaubten Code nicht installiert werden",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Die Anwendung konnte nicht installiert werden, weil Sie nicht mit dieser Version von ownCloud kompatibel ist.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Die Applikation konnte nicht installiert werden, da diese das <shipped>true</shipped> Tag beinhaltet und dieses, bei nicht mitausgelieferten Applikationen, nicht erlaubt ist ist",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Die Applikation konnte nicht installiert werden, da die Version in der info.xml nicht die gleiche Version wie im App-Store ist",
+"App directory already exists" => "Das Applikationsverzeichnis existiert bereits",
+"Can't create app folder. Please fix permissions. %s" => "Es kann kein Applikationsordner erstellt werden. Bitte passen sie die Berechtigungen an. %s",
"Application is not enabled" => "Die Anwendung ist nicht aktiviert",
"Authentication error" => "Fehler bei der Anmeldung",
"Token expired. Please reload page." => "Token abgelaufen. Bitte lade die Seite neu.",
diff --git a/lib/l10n/de_CH.php b/lib/l10n/de_CH.php
index 188ea4e2fc0..33f3446a693 100644
--- a/lib/l10n/de_CH.php
+++ b/lib/l10n/de_CH.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Anwendung \"%s\" kann nicht installiert werden, da sie mit dieser Version von ownCloud nicht kompatibel ist.",
+"No app name specified" => "Kein App-Name spezifiziert",
"Help" => "Hilfe",
"Personal" => "Persönlich",
"Settings" => "Einstellungen",
@@ -13,6 +15,8 @@ $TRANSLATIONS = array(
"Back to Files" => "Zurück zu \"Dateien\"",
"Selected files too large to generate zip file." => "Die gewählten Dateien sind zu gross, um eine ZIP-Datei zu erstellen.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Laden Sie die Dateien in kleineren, separaten, Stücken herunter oder bitten Sie Ihren Administrator.",
+"App can't be installed because of not allowed code in the App" => "Anwendung kann wegen nicht erlaubten Codes nicht installiert werden",
+"App directory already exists" => "Anwendungsverzeichnis existiert bereits",
"Application is not enabled" => "Die Anwendung ist nicht aktiviert",
"Authentication error" => "Authentifizierungs-Fehler",
"Token expired. Please reload page." => "Token abgelaufen. Bitte laden Sie die Seite neu.",
@@ -40,13 +44,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "Ihr Web-Server ist noch nicht für eine Datei-Synchronisation konfiguriert, weil die WebDAV-Schnittstelle vermutlich defekt ist.",
"Please double check the <a href='%s'>installation guides</a>." => "Bitte prüfen Sie die <a href='%s'>Installationsanleitungen</a>.",
"seconds ago" => "Gerade eben",
-"_%n minute ago_::_%n minutes ago_" => array("",""),
-"_%n hour ago_::_%n hours ago_" => array("",""),
+"_%n minute ago_::_%n minutes ago_" => array("","Vor %n Minuten"),
+"_%n hour ago_::_%n hours ago_" => array("","Vor %n Stunden"),
"today" => "Heute",
"yesterday" => "Gestern",
-"_%n day go_::_%n days ago_" => array("",""),
+"_%n day go_::_%n days ago_" => array("","Vor %n Tagen"),
"last month" => "Letzten Monat",
-"_%n month ago_::_%n months ago_" => array("",""),
+"_%n month ago_::_%n months ago_" => array("","Vor %n Monaten"),
"last year" => "Letztes Jahr",
"years ago" => "Vor Jahren",
"Caused by:" => "Verursacht durch:",
diff --git a/lib/l10n/de_DE.php b/lib/l10n/de_DE.php
index 9fd319b7e1b..0a72f443e4d 100644
--- a/lib/l10n/de_DE.php
+++ b/lib/l10n/de_DE.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Applikation \"%s\" kann nicht installiert werden, da sie mit dieser ownCloud Version nicht kompatibel ist.",
+"No app name specified" => "Es wurde kein Applikation-Name angegeben",
"Help" => "Hilfe",
"Personal" => "Persönlich",
"Settings" => "Einstellungen",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Zurück zu \"Dateien\"",
"Selected files too large to generate zip file." => "Die gewählten Dateien sind zu groß, um eine ZIP-Datei zu erstellen.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Laden Sie die Dateien in kleineren, separaten, Stücken herunter oder bitten Sie Ihren Administrator.",
+"No source specified when installing app" => "Für die Installation der Applikation wurde keine Quelle angegeben",
+"No href specified when installing app from http" => "Der Link (href) wurde nicht angegeben um die Applikation per http zu installieren",
+"No path specified when installing app from local file" => "Bei der Installation der Applikation aus einer lokalen Datei wurde kein Pfad angegeben",
+"Archives of type %s are not supported" => "Archive des Typs %s werden nicht unterstützt.",
+"Failed to open archive when installing app" => "Das Archiv konnte bei der Installation der Applikation nicht geöffnet werden",
+"App does not provide an info.xml file" => "Die Applikation enthält keine info,xml Datei",
+"App can't be installed because of not allowed code in the App" => "Die Applikation kann auf Grund von unerlaubten Code nicht installiert werden",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Die Anwendung konnte nicht installiert werden, weil Sie nicht mit dieser Version von ownCloud kompatibel ist.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Die Applikation konnte nicht installiert werden, da diese das <shipped>true</shipped> Tag beinhaltet und dieses, bei nicht mitausgelieferten Applikationen, nicht erlaubt ist ist",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Die Applikation konnte nicht installiert werden, da die Version in der info.xml nicht die gleiche Version wie im App-Store ist",
+"App directory already exists" => "Der Ordner für die Anwendung existiert bereits.",
+"Can't create app folder. Please fix permissions. %s" => "Der Ordner für die Anwendung konnte nicht angelegt werden. Bitte überprüfen Sie die Ordner- und Dateirechte und passen Sie diese entsprechend an. %s",
"Application is not enabled" => "Die Anwendung ist nicht aktiviert",
"Authentication error" => "Authentifizierungs-Fehler",
"Token expired. Please reload page." => "Token abgelaufen. Bitte laden Sie die Seite neu.",
diff --git a/lib/l10n/en_GB.php b/lib/l10n/en_GB.php
new file mode 100644
index 00000000000..f799c071c76
--- /dev/null
+++ b/lib/l10n/en_GB.php
@@ -0,0 +1,69 @@
+<?php
+$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "App \"%s\" can't be installed because it is not compatible with this version of ownCloud.",
+"No app name specified" => "No app name specified",
+"Help" => "Help",
+"Personal" => "Personal",
+"Settings" => "Settings",
+"Users" => "Users",
+"Admin" => "Admin",
+"Failed to upgrade \"%s\"." => "Failed to upgrade \"%s\".",
+"web services under your control" => "web services under your control",
+"cannot open \"%s\"" => "cannot open \"%s\"",
+"ZIP download is turned off." => "ZIP download is turned off.",
+"Files need to be downloaded one by one." => "Files need to be downloaded one by one.",
+"Back to Files" => "Back to Files",
+"Selected files too large to generate zip file." => "Selected files too large to generate zip file.",
+"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Download the files in smaller chunks, seperately or kindly ask your administrator.",
+"No source specified when installing app" => "No source specified when installing app",
+"No href specified when installing app from http" => "No href specified when installing app from http",
+"No path specified when installing app from local file" => "No path specified when installing app from local file",
+"Archives of type %s are not supported" => "Archives of type %s are not supported",
+"Failed to open archive when installing app" => "Failed to open archive when installing app",
+"App does not provide an info.xml file" => "App does not provide an info.xml file",
+"App can't be installed because of not allowed code in the App" => "App can't be installed because of unallowed code in the App",
+"App can't be installed because it is not compatible with this version of ownCloud" => "App can't be installed because it is not compatible with this version of ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "App can't be installed because the version in info.xml/version is not the same as the version reported from the app store",
+"App directory already exists" => "App directory already exists",
+"Can't create app folder. Please fix permissions. %s" => "Can't create app folder. Please fix permissions. %s",
+"Application is not enabled" => "Application is not enabled",
+"Authentication error" => "Authentication error",
+"Token expired. Please reload page." => "Token expired. Please reload page.",
+"Files" => "Files",
+"Text" => "Text",
+"Images" => "Images",
+"%s enter the database username." => "%s enter the database username.",
+"%s enter the database name." => "%s enter the database name.",
+"%s you may not use dots in the database name" => "%s you may not use dots in the database name",
+"MS SQL username and/or password not valid: %s" => "MS SQL username and/or password not valid: %s",
+"You need to enter either an existing account or the administrator." => "You need to enter either an existing account or the administrator.",
+"MySQL username and/or password not valid" => "MySQL username and/or password not valid",
+"DB Error: \"%s\"" => "DB Error: \"%s\"",
+"Offending command was: \"%s\"" => "Offending command was: \"%s\"",
+"MySQL user '%s'@'localhost' exists already." => "MySQL user '%s'@'localhost' exists already.",
+"Drop this user from MySQL" => "Drop this user from MySQL",
+"MySQL user '%s'@'%%' already exists" => "MySQL user '%s'@'%%' already exists",
+"Drop this user from MySQL." => "Drop this user from MySQL.",
+"Oracle connection could not be established" => "Oracle connection could not be established",
+"Oracle username and/or password not valid" => "Oracle username and/or password not valid",
+"Offending command was: \"%s\", name: %s, password: %s" => "Offending command was: \"%s\", name: %s, password: %s",
+"PostgreSQL username and/or password not valid" => "PostgreSQL username and/or password not valid",
+"Set an admin username." => "Set an admin username.",
+"Set an admin password." => "Set an admin password.",
+"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "Your web server is not yet properly setup to allow files synchronisation because the WebDAV interface seems to be broken.",
+"Please double check the <a href='%s'>installation guides</a>." => "Please double check the <a href='%s'>installation guides</a>.",
+"seconds ago" => "seconds ago",
+"_%n minute ago_::_%n minutes ago_" => array("","%n minutes ago"),
+"_%n hour ago_::_%n hours ago_" => array("","%n hours ago"),
+"today" => "today",
+"yesterday" => "yesterday",
+"_%n day go_::_%n days ago_" => array("","%n days ago"),
+"last month" => "last month",
+"_%n month ago_::_%n months ago_" => array("","%n months ago"),
+"last year" => "last year",
+"years ago" => "years ago",
+"Caused by:" => "Caused by:",
+"Could not find category \"%s\"" => "Could not find category \"%s\""
+);
+$PLURAL_FORMS = "nplurals=2; plural=(n != 1);";
diff --git a/lib/l10n/es.php b/lib/l10n/es.php
index 14bbf6f6a13..7a82f8f6a19 100644
--- a/lib/l10n/es.php
+++ b/lib/l10n/es.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "La aplicación \"%s\" no puede ser instalada porque no es compatible con esta versión de ownCloud",
+"No app name specified" => "No se ha especificado nombre de la aplicación",
"Help" => "Ayuda",
"Personal" => "Personal",
"Settings" => "Ajustes",
@@ -13,6 +15,15 @@ $TRANSLATIONS = array(
"Back to Files" => "Volver a Archivos",
"Selected files too large to generate zip file." => "Los archivos seleccionados son demasiado grandes para generar el archivo zip.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Descargue los archivos en trozos más pequeños, por separado o solicítelos amablemente su administrador.",
+"No source specified when installing app" => "No se ha especificado origen cuando se ha instalado la aplicación",
+"No href specified when installing app from http" => "No href especificado cuando se ha instalado la aplicación",
+"No path specified when installing app from local file" => "Sin path especificado cuando se ha instalado la aplicación desde el fichero local",
+"Archives of type %s are not supported" => "Ficheros de tipo %s no son soportados",
+"Failed to open archive when installing app" => "Fallo de apertura de fichero mientras se instala la aplicación",
+"App does not provide an info.xml file" => "La aplicación no suministra un fichero info.xml",
+"App can't be installed because of not allowed code in the App" => "La aplicación no puede ser instalada por tener código no autorizado en la aplicación",
+"App can't be installed because it is not compatible with this version of ownCloud" => "La aplicación no se puede instalar porque no es compatible con esta versión de ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "La aplicación no se puede instalar porque contiene la etiqueta\n<shipped>\ntrue\n</shipped>\nque no está permitida para aplicaciones no distribuidas",
"Application is not enabled" => "La aplicación no está habilitada",
"Authentication error" => "Error de autenticación",
"Token expired. Please reload page." => "Token expirado. Por favor, recarga la página.",
diff --git a/lib/l10n/et_EE.php b/lib/l10n/et_EE.php
index 912ef37a935..8e3aa55c4ed 100644
--- a/lib/l10n/et_EE.php
+++ b/lib/l10n/et_EE.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Rakendit \"%s\" ei saa paigaldada, kuna see pole ühilduv selle ownCloud versiooniga.",
+"No app name specified" => "Ühegi rakendi nime pole määratletud",
"Help" => "Abiinfo",
"Personal" => "Isiklik",
"Settings" => "Seaded",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Tagasi failide juurde",
"Selected files too large to generate zip file." => "Valitud failid on ZIP-faili loomiseks liiga suured.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Laadi failid alla eraldi väiksemate osadena või küsi nõu oma süsteemiadminstraatorilt.",
+"No source specified when installing app" => "Ühegi lähteallikat pole rakendi paigalduseks määratletud",
+"No href specified when installing app from http" => "Ühtegi aadressi pole määratletud rakendi paigalduseks veebist",
+"No path specified when installing app from local file" => "Ühtegi teed pole määratletud paigaldamaks rakendit kohalikust failist",
+"Archives of type %s are not supported" => "%s tüüpi arhiivid pole toetatud",
+"Failed to open archive when installing app" => "Arhiivi avamine ebaõnnestus rakendi paigalduse käigus",
+"App does not provide an info.xml file" => "Rakend ei paku ühtegi info.xml faili",
+"App can't be installed because of not allowed code in the App" => "Rakendit ei saa paigaldada, kuna sisaldab lubamatud koodi",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Rakendit ei saa paigaldada, kuna see pole ühilduv selle ownCloud versiooniga.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Rakendit ei saa paigaldada, kuna see sisaldab \n<shipped>\n\ntrue\n</shipped>\nmärgendit, mis pole lubatud mitte veetud (non shipped) rakendites",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Rakendit ei saa paigaldada, kuna selle versioon info.xml/version pole sama, mis on märgitud rakendite laos.",
+"App directory already exists" => "Rakendi kataloog on juba olemas",
+"Can't create app folder. Please fix permissions. %s" => "Ei saa luua rakendi kataloogi. Palun korrigeeri õigusi. %s",
"Application is not enabled" => "Rakendus pole sisse lülitatud",
"Authentication error" => "Autentimise viga",
"Token expired. Please reload page." => "Kontrollkood aegus. Paelun lae leht uuesti.",
@@ -40,13 +54,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "Veebiserveri ei ole veel korralikult seadistatud võimaldamaks failide sünkroniseerimist, kuna WebDAV liides näib olevat mittetoimiv.",
"Please double check the <a href='%s'>installation guides</a>." => "Palun tutvu veelkord <a href='%s'>paigalduse juhenditega</a>.",
"seconds ago" => "sekundit tagasi",
-"_%n minute ago_::_%n minutes ago_" => array("",""),
-"_%n hour ago_::_%n hours ago_" => array("",""),
+"_%n minute ago_::_%n minutes ago_" => array("","%n minutit tagasi"),
+"_%n hour ago_::_%n hours ago_" => array("","%n tundi tagasi"),
"today" => "täna",
"yesterday" => "eile",
-"_%n day go_::_%n days ago_" => array("",""),
+"_%n day go_::_%n days ago_" => array("","%n päeva tagasi"),
"last month" => "viimasel kuul",
-"_%n month ago_::_%n months ago_" => array("",""),
+"_%n month ago_::_%n months ago_" => array("","%n kuud tagasi"),
"last year" => "viimasel aastal",
"years ago" => "aastat tagasi",
"Caused by:" => "Põhjustaja:",
diff --git a/lib/l10n/eu.php b/lib/l10n/eu.php
index 8f967314f4b..413819f4f94 100644
--- a/lib/l10n/eu.php
+++ b/lib/l10n/eu.php
@@ -40,13 +40,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "Zure web zerbitzaria ez dago oraindik ongi konfiguratuta fitxategien sinkronizazioa egiteko, WebDAV interfazea ongi ez dagoela dirudi.",
"Please double check the <a href='%s'>installation guides</a>." => "Mesedez begiratu <a href='%s'>instalazio gidak</a>.",
"seconds ago" => "segundu",
-"_%n minute ago_::_%n minutes ago_" => array("",""),
-"_%n hour ago_::_%n hours ago_" => array("",""),
+"_%n minute ago_::_%n minutes ago_" => array("orain dela minutu %n","orain dela %n minutu"),
+"_%n hour ago_::_%n hours ago_" => array("orain dela ordu %n","orain dela %n ordu"),
"today" => "gaur",
"yesterday" => "atzo",
-"_%n day go_::_%n days ago_" => array("",""),
+"_%n day go_::_%n days ago_" => array("orain dela egun %n","orain dela %n egun"),
"last month" => "joan den hilabetean",
-"_%n month ago_::_%n months ago_" => array("",""),
+"_%n month ago_::_%n months ago_" => array("orain dela hilabete %n","orain dela %n hilabete"),
"last year" => "joan den urtean",
"years ago" => "urte",
"Caused by:" => "Honek eraginda:",
diff --git a/lib/l10n/fi_FI.php b/lib/l10n/fi_FI.php
index 4552d4627c0..2e69df43ad2 100644
--- a/lib/l10n/fi_FI.php
+++ b/lib/l10n/fi_FI.php
@@ -1,5 +1,6 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Sovellusta \"%s\" ei voi asentaa, koska se ei ole yhteensopiva käytössä olevan ownCloud-version kanssa.",
"Help" => "Ohje",
"Personal" => "Henkilökohtainen",
"Settings" => "Asetukset",
@@ -10,6 +11,12 @@ $TRANSLATIONS = array(
"Files need to be downloaded one by one." => "Tiedostot on ladattava yksittäin.",
"Back to Files" => "Takaisin tiedostoihin",
"Selected files too large to generate zip file." => "Valitut tiedostot ovat liian suurikokoisia mahtuakseen zip-tiedostoon.",
+"No source specified when installing app" => "Lähdettä ei määritelty sovellusta asennettaessa",
+"No path specified when installing app from local file" => "Polkua ei määritelty sovellusta asennettaessa paikallisesta tiedostosta",
+"Archives of type %s are not supported" => "Tyypin %s arkistot eivät ole tuettuja",
+"App does not provide an info.xml file" => "Sovellus ei sisällä info.xml-tiedostoa",
+"App directory already exists" => "Sovelluskansio on jo olemassa",
+"Can't create app folder. Please fix permissions. %s" => "Sovelluskansion luominen ei onnistu. Korjaa käyttöoikeudet. %s",
"Application is not enabled" => "Sovellusta ei ole otettu käyttöön",
"Authentication error" => "Tunnistautumisvirhe",
"Token expired. Please reload page." => "Valtuutus vanheni. Lataa sivu uudelleen.",
diff --git a/lib/l10n/gl.php b/lib/l10n/gl.php
index 4d92e89ebba..a8fee3b1bc1 100644
--- a/lib/l10n/gl.php
+++ b/lib/l10n/gl.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Non é posíbel instalar o aplicativo «%s» por non seren compatíbel con esta versión do ownCloud.",
+"No app name specified" => "Non se especificou o nome do aplicativo",
"Help" => "Axuda",
"Personal" => "Persoal",
"Settings" => "Axustes",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Volver aos ficheiros",
"Selected files too large to generate zip file." => "Os ficheiros seleccionados son demasiado grandes como para xerar un ficheiro zip.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Descargue os ficheiros en cachos máis pequenos e por separado, ou pídallos amabelmente ao seu administrador.",
+"No source specified when installing app" => "Non foi especificada ningunha orixe ao instalar aplicativos",
+"No href specified when installing app from http" => "Non foi especificada ningunha href ao instalar aplicativos",
+"No path specified when installing app from local file" => "Non foi especificada ningunha ruta ao instalar aplicativos desde un ficheiro local",
+"Archives of type %s are not supported" => "Os arquivos do tipo %s non están admitidos",
+"Failed to open archive when installing app" => "Non foi posíbel abrir o arquivo ao instalar aplicativos",
+"App does not provide an info.xml file" => "O aplicativo non fornece un ficheiro info.xml",
+"App can't be installed because of not allowed code in the App" => "Non é posíbel instalar o aplicativo por mor de conter código non permitido",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Non é posíbel instalar o aplicativo por non seren compatíbel con esta versión do ownCloud.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Non é posíbel instalar o aplicativo por conter a etiqueta\n<shipped>\n\ntrue\n</shipped>\nque non está permitida para os aplicativos non enviados",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Non é posíbel instalar o aplicativo xa que a versión en info.xml/version non é a mesma que a versión informada desde a App Store",
+"App directory already exists" => "Xa existe o directorio do aplicativo",
+"Can't create app folder. Please fix permissions. %s" => "Non é posíbel crear o cartafol de aplicativos. Corrixa os permisos. %s",
"Application is not enabled" => "O aplicativo non está activado",
"Authentication error" => "Produciuse un erro de autenticación",
"Token expired. Please reload page." => "Testemuña caducada. Recargue a páxina.",
diff --git a/lib/l10n/he.php b/lib/l10n/he.php
index bab1a6ff424..ced6244ee91 100644
--- a/lib/l10n/he.php
+++ b/lib/l10n/he.php
@@ -19,13 +19,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "שרת האינטרנט שלך אינו מוגדר לצורכי סנכרון קבצים עדיין כיוון שמנשק ה־WebDAV כנראה אינו תקין.",
"Please double check the <a href='%s'>installation guides</a>." => "נא לעיין שוב ב<a href='%s'>מדריכי ההתקנה</a>.",
"seconds ago" => "שניות",
-"_%n minute ago_::_%n minutes ago_" => array("",""),
-"_%n hour ago_::_%n hours ago_" => array("",""),
+"_%n minute ago_::_%n minutes ago_" => array("","לפני %n דקות"),
+"_%n hour ago_::_%n hours ago_" => array("","לפני %n שעות"),
"today" => "היום",
"yesterday" => "אתמול",
-"_%n day go_::_%n days ago_" => array("",""),
+"_%n day go_::_%n days ago_" => array("","לפני %n ימים"),
"last month" => "חודש שעבר",
-"_%n month ago_::_%n months ago_" => array("",""),
+"_%n month ago_::_%n months ago_" => array("","לפני %n חודשים"),
"last year" => "שנה שעברה",
"years ago" => "שנים",
"Could not find category \"%s\"" => "לא ניתן למצוא את הקטגוריה „%s“"
diff --git a/lib/l10n/it.php b/lib/l10n/it.php
index e734fbdbb9b..c3a040048ec 100644
--- a/lib/l10n/it.php
+++ b/lib/l10n/it.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "L'applicazione \"%s\" non può essere installata poiché non è compatibile con questa versione di ownCloud.",
+"No app name specified" => "Il nome dell'applicazione non è specificato",
"Help" => "Aiuto",
"Personal" => "Personale",
"Settings" => "Impostazioni",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Torna ai file",
"Selected files too large to generate zip file." => "I file selezionati sono troppo grandi per generare un file zip.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Scarica i file in blocchi più piccoli, separatamente o chiedi al tuo amministratore.",
+"No source specified when installing app" => "Nessuna fonte specificata durante l'installazione dell'applicazione",
+"No href specified when installing app from http" => "Nessun href specificato durante l'installazione dell'applicazione da http",
+"No path specified when installing app from local file" => "Nessun percorso specificato durante l'installazione dell'applicazione da file locale",
+"Archives of type %s are not supported" => "Gli archivi di tipo %s non sono supportati",
+"Failed to open archive when installing app" => "Apertura archivio non riuscita durante l'installazione dell'applicazione",
+"App does not provide an info.xml file" => "L'applicazione non fornisce un file info.xml",
+"App can't be installed because of not allowed code in the App" => "L'applicazione non può essere installata a causa di codice non consentito al suo interno",
+"App can't be installed because it is not compatible with this version of ownCloud" => "L'applicazione non può essere installata poiché non è compatibile con questa versione di ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "L'applicazione non può essere installata poiché contiene il tag <shipped>true<shipped> che non è permesso alle applicazioni non shipped",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "L'applicazione non può essere installata poiché la versione in info.xml/version non è la stessa riportata dall'app store",
+"App directory already exists" => "La cartella dell'applicazione esiste già",
+"Can't create app folder. Please fix permissions. %s" => "Impossibile creare la cartella dell'applicazione. Correggi i permessi. %s",
"Application is not enabled" => "L'applicazione non è abilitata",
"Authentication error" => "Errore di autenticazione",
"Token expired. Please reload page." => "Token scaduto. Ricarica la pagina.",
@@ -40,13 +54,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "Il tuo server web non è configurato correttamente per consentire la sincronizzazione dei file poiché l'interfaccia WebDAV sembra essere danneggiata.",
"Please double check the <a href='%s'>installation guides</a>." => "Leggi attentamente le <a href='%s'>guide d'installazione</a>.",
"seconds ago" => "secondi fa",
-"_%n minute ago_::_%n minutes ago_" => array("",""),
-"_%n hour ago_::_%n hours ago_" => array("",""),
+"_%n minute ago_::_%n minutes ago_" => array("%n minuto fa","%n minuti fa"),
+"_%n hour ago_::_%n hours ago_" => array("%n ora fa","%n ore fa"),
"today" => "oggi",
"yesterday" => "ieri",
-"_%n day go_::_%n days ago_" => array("",""),
+"_%n day go_::_%n days ago_" => array("%n giorno fa","%n giorni fa"),
"last month" => "mese scorso",
-"_%n month ago_::_%n months ago_" => array("",""),
+"_%n month ago_::_%n months ago_" => array("%n mese fa","%n mesi fa"),
"last year" => "anno scorso",
"years ago" => "anni fa",
"Caused by:" => "Causato da:",
diff --git a/lib/l10n/ja_JP.php b/lib/l10n/ja_JP.php
index 902170524b9..e2b67e76187 100644
--- a/lib/l10n/ja_JP.php
+++ b/lib/l10n/ja_JP.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => " \"%s\" アプリは、このバージョンのownCloudと互換性がない為、インストールできません。",
+"No app name specified" => "アプリ名が未指定",
"Help" => "ヘルプ",
"Personal" => "個人",
"Settings" => "設定",
@@ -13,6 +15,17 @@ $TRANSLATIONS = array(
"Back to Files" => "ファイルに戻る",
"Selected files too large to generate zip file." => "選択したファイルはZIPファイルの生成には大きすぎます。",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "ファイルは、小さいファイルに分割されてダウンロードされます。もしくは、管理者にお尋ねください。",
+"No source specified when installing app" => "アプリインストール時のソースが未指定",
+"No href specified when installing app from http" => "アプリインストール時のhttpの URL が未指定",
+"No path specified when installing app from local file" => "アプリインストール時のローカルファイルのパスが未指定",
+"Archives of type %s are not supported" => "\"%s\"タイプのアーカイブ形式は未サポート",
+"Failed to open archive when installing app" => "アプリをインストール中にアーカイブファイルを開けませんでした。",
+"App does not provide an info.xml file" => "アプリにinfo.xmlファイルが入っていません",
+"App can't be installed because of not allowed code in the App" => "アプリで許可されないコードが入っているのが原因でアプリがインストールできません",
+"App can't be installed because it is not compatible with this version of ownCloud" => "アプリは、このバージョンのownCloudと互換性がない為、インストールできません。",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "info.xml/versionのバージョンがアプリストアのバージョンと合っていない為、アプリはインストールされません",
+"App directory already exists" => "アプリディレクトリは既に存在します",
+"Can't create app folder. Please fix permissions. %s" => "アプリフォルダを作成出来ませんでした。%s のパーミッションを修正してください。",
"Application is not enabled" => "アプリケーションは無効です",
"Authentication error" => "認証エラー",
"Token expired. Please reload page." => "トークンが無効になりました。ページを再読込してください。",
diff --git a/lib/l10n/ko.php b/lib/l10n/ko.php
index 4dab8b816bf..eec5be65abd 100644
--- a/lib/l10n/ko.php
+++ b/lib/l10n/ko.php
@@ -1,15 +1,31 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "현재 ownCloud 버전과 호환되지 않기 때문에 \"%s\" 앱을 설치할 수 없습니다.",
+"No app name specified" => "앱 이름이 지정되지 않았습니다.",
"Help" => "도움말",
"Personal" => "개인",
"Settings" => "설정",
"Users" => "사용자",
"Admin" => "관리자",
+"Failed to upgrade \"%s\"." => "\"%s\" 업그레이드에 실패했습니다.",
"web services under your control" => "내가 관리하는 웹 서비스",
+"cannot open \"%s\"" => "\"%s\"을(를) 열 수 없습니다.",
"ZIP download is turned off." => "ZIP 다운로드가 비활성화되었습니다.",
"Files need to be downloaded one by one." => "파일을 개별적으로 다운로드해야 합니다.",
"Back to Files" => "파일로 돌아가기",
"Selected files too large to generate zip file." => "선택한 파일들은 ZIP 파일을 생성하기에 너무 큽니다.",
+"No source specified when installing app" => "앱을 설치할 때 소스가 지정되지 않았습니다.",
+"No href specified when installing app from http" => "http에서 앱을 설치할 대 href가 지정되지 않았습니다.",
+"No path specified when installing app from local file" => "로컬 파일에서 앱을 설치할 때 경로가 지정되지 않았습니다.",
+"Archives of type %s are not supported" => "%s 타입 아카이브는 지원되지 않습니다.",
+"Failed to open archive when installing app" => "앱을 설치할 때 아카이브를 열지 못했습니다.",
+"App does not provide an info.xml file" => "앱에서 info.xml 파일이 제공되지 않았습니다.",
+"App can't be installed because of not allowed code in the App" => "앱에 허용되지 않는 코드가 있어서 앱을 설치할 수 없습니다. ",
+"App can't be installed because it is not compatible with this version of ownCloud" => "현재 ownCloud 버전과 호환되지 않기 때문에 앱을 설치할 수 없습니다.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "출하되지 않은 앱에 허용되지 않는 <shipped>true</shipped> 태그를 포함하고 있기 때문에 앱을 설치할 수 없습니다.",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "info.xml/version에 포함된 버전과 앱 스토어에 보고된 버전이 같지 않아서 앱을 설치할 수 없습니다. ",
+"App directory already exists" => "앱 디렉토리가 이미 존재합니다. ",
+"Can't create app folder. Please fix permissions. %s" => "앱 폴더를 만들 수 없습니다. 권한을 수정하십시오. %s ",
"Application is not enabled" => "앱이 활성화되지 않았습니다",
"Authentication error" => "인증 오류",
"Token expired. Please reload page." => "토큰이 만료되었습니다. 페이지를 새로 고치십시오.",
@@ -19,22 +35,34 @@ $TRANSLATIONS = array(
"%s enter the database username." => "데이터베이스 사용자 명을 %s 에 입력해주십시오",
"%s enter the database name." => "데이터베이스 명을 %s 에 입력해주십시오",
"%s you may not use dots in the database name" => "%s 에 적으신 데이터베이스 이름에는 점을 사용할수 없습니다",
+"MS SQL username and/or password not valid: %s" => "MS SQL 사용자 이름이나 암호가 잘못되었습니다: %s",
+"You need to enter either an existing account or the administrator." => "기존 계정이나 administrator(관리자)를 입력해야 합니다.",
+"MySQL username and/or password not valid" => "MySQL 사용자 이름이나 암호가 잘못되었습니다.",
"DB Error: \"%s\"" => "DB 오류: \"%s\"",
+"Offending command was: \"%s\"" => "잘못된 명령: \"%s\"",
+"MySQL user '%s'@'localhost' exists already." => "MySQL 사용자 '%s'@'localhost'이(가) 이미 존재합니다.",
+"Drop this user from MySQL" => "이 사용자를 MySQL에서 뺍니다.",
+"MySQL user '%s'@'%%' already exists" => "MySQL 사용자 '%s'@'%%'이(가) 이미 존재합니다. ",
+"Drop this user from MySQL." => "이 사용자를 MySQL에서 뺍니다.",
+"Oracle connection could not be established" => "Oracle 연결을 수립할 수 없습니다.",
+"Oracle username and/or password not valid" => "Oracle 사용자 이름이나 암호가 잘못되었습니다.",
+"Offending command was: \"%s\", name: %s, password: %s" => "잘못된 명령: \"%s\", 이름: %s, 암호: %s",
"PostgreSQL username and/or password not valid" => "PostgreSQL의 사용자 명 혹은 비밀번호가 잘못되었습니다",
"Set an admin username." => "관리자 이름 설정",
"Set an admin password." => "관리자 비밀번호 설정",
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "WebDAV 인터페이스가 제대로 작동하지 않습니다. 웹 서버에서 파일 동기화를 사용할 수 있도록 설정이 제대로 되지 않은 것 같습니다.",
"Please double check the <a href='%s'>installation guides</a>." => "<a href='%s'>설치 가이드</a>를 다시 한 번 확인하십시오.",
"seconds ago" => "초 전",
-"_%n minute ago_::_%n minutes ago_" => array(""),
-"_%n hour ago_::_%n hours ago_" => array(""),
+"_%n minute ago_::_%n minutes ago_" => array("%n분 전 "),
+"_%n hour ago_::_%n hours ago_" => array("%n시간 전 "),
"today" => "오늘",
"yesterday" => "어제",
-"_%n day go_::_%n days ago_" => array(""),
+"_%n day go_::_%n days ago_" => array("%n일 전 "),
"last month" => "지난 달",
-"_%n month ago_::_%n months ago_" => array(""),
+"_%n month ago_::_%n months ago_" => array("%n달 전 "),
"last year" => "작년",
"years ago" => "년 전",
+"Caused by:" => "원인: ",
"Could not find category \"%s\"" => "분류 \"%s\"을(를) 찾을 수 없습니다."
);
$PLURAL_FORMS = "nplurals=1; plural=0;";
diff --git a/lib/l10n/lt_LT.php b/lib/l10n/lt_LT.php
index fb109b86339..242b0a23106 100644
--- a/lib/l10n/lt_LT.php
+++ b/lib/l10n/lt_LT.php
@@ -17,13 +17,13 @@ $TRANSLATIONS = array(
"Text" => "Žinučių",
"Images" => "Paveikslėliai",
"seconds ago" => "prieš sekundę",
-"_%n minute ago_::_%n minutes ago_" => array("","",""),
-"_%n hour ago_::_%n hours ago_" => array("","",""),
+"_%n minute ago_::_%n minutes ago_" => array("",""," prieš %n minučių"),
+"_%n hour ago_::_%n hours ago_" => array("","","prieš %n valandų"),
"today" => "šiandien",
"yesterday" => "vakar",
"_%n day go_::_%n days ago_" => array("","",""),
"last month" => "praeitą mėnesį",
-"_%n month ago_::_%n months ago_" => array("","",""),
+"_%n month ago_::_%n months ago_" => array("","","prieš %n mėnesių"),
"last year" => "praeitais metais",
"years ago" => "prieš metus"
);
diff --git a/lib/l10n/nl.php b/lib/l10n/nl.php
index 338c3673c5b..e546c1f3179 100644
--- a/lib/l10n/nl.php
+++ b/lib/l10n/nl.php
@@ -1,5 +1,6 @@
<?php
$TRANSLATIONS = array(
+"No app name specified" => "De app naam is niet gespecificeerd.",
"Help" => "Help",
"Personal" => "Persoonlijk",
"Settings" => "Instellingen",
diff --git a/lib/l10n/pt_BR.php b/lib/l10n/pt_BR.php
index 52329667174..a2379ca4883 100644
--- a/lib/l10n/pt_BR.php
+++ b/lib/l10n/pt_BR.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "O aplicativo \"%s\" não pode ser instalado porque não é compatível com esta versão do ownCloud.",
+"No app name specified" => "O nome do aplicativo não foi especificado.",
"Help" => "Ajuda",
"Personal" => "Pessoal",
"Settings" => "Ajustes",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Voltar para Arquivos",
"Selected files too large to generate zip file." => "Arquivos selecionados são muito grandes para gerar arquivo zip.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Baixe os arquivos em pedaços menores, separadamente ou solicite educadamente ao seu administrador.",
+"No source specified when installing app" => "Nenhuma fonte foi especificada enquanto instalava o aplicativo",
+"No href specified when installing app from http" => "Nenhuma href foi especificada enquanto instalava o aplicativo de httml",
+"No path specified when installing app from local file" => "Nenhum caminho foi especificado enquanto instalava o aplicativo do arquivo local",
+"Archives of type %s are not supported" => "Arquivos do tipo %s não são suportados",
+"Failed to open archive when installing app" => "Falha para abrir o arquivo enquanto instalava o aplicativo",
+"App does not provide an info.xml file" => "O aplicativo não fornece um arquivo info.xml",
+"App can't be installed because of not allowed code in the App" => "O aplicativo não pode ser instalado por causa do código não permitido no Aplivativo",
+"App can't be installed because it is not compatible with this version of ownCloud" => "O aplicativo não pode ser instalado porque não é compatível com esta versão do ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "O aplicativo não pode ser instalado porque ele contém a marca <shipped>verdadeiro</shipped> que não é permitido para aplicações não embarcadas",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "O aplicativo não pode ser instalado porque a versão em info.xml /versão não é a mesma que a versão relatada na App Store",
+"App directory already exists" => "Diretório App já existe",
+"Can't create app folder. Please fix permissions. %s" => "Não é possível criar pasta app. Corrija as permissões. %s",
"Application is not enabled" => "Aplicação não está habilitada",
"Authentication error" => "Erro de autenticação",
"Token expired. Please reload page." => "Token expirou. Por favor recarregue a página.",
diff --git a/lib/l10n/sk_SK.php b/lib/l10n/sk_SK.php
index 43a4b4a0bee..13487b039d6 100644
--- a/lib/l10n/sk_SK.php
+++ b/lib/l10n/sk_SK.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Aplikácia \"%s\" nemôže byť nainštalovaná kvôli nekompatibilite z danou verziou ownCloudu.",
+"No app name specified" => "Nešpecifikované meno aplikácie",
"Help" => "Pomoc",
"Personal" => "Osobné",
"Settings" => "Nastavenia",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Späť na súbory",
"Selected files too large to generate zip file." => "Zvolené súbory sú príliš veľké na vygenerovanie zip súboru.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Stiahnite súbory po menších častiach, samostatne, alebo sa obráťte na správcu.",
+"No source specified when installing app" => "Nešpecifikovaný zdroj pri inštalácii aplikácie",
+"No href specified when installing app from http" => "Nešpecifikovaný atribút \"href\" pri inštalácii aplikácie pomocou protokolu \"http\"",
+"No path specified when installing app from local file" => "Nešpecifikovaná cesta pri inštalácii aplikácie z lokálneho súboru",
+"Archives of type %s are not supported" => "Typ archívu %s nie je podporovaný",
+"Failed to open archive when installing app" => "Zlyhanie pri otváraní archívu počas inštalácie aplikácie",
+"App does not provide an info.xml file" => "Aplikácia neposkytuje súbor info.xml",
+"App can't be installed because of not allowed code in the App" => "Aplikácia nemôže byť inštalovaná pre nepovolený kód v aplikácii",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Aplikácia nemôže byť inštalovaná pre nekompatibilitu z danou verziou ownCloudu",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Aplikácia nemôže byť inštalovaná pretože obsahuje <shipped>pravý</shipped> štítok, ktorý nie je povolený pre zaslané \"shipped\" aplikácie",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Aplikácia nemôže byť inštalovaná pretože verzia v info.xml/version nezodpovedá verzii špecifikovanej v aplikačnom obchode",
+"App directory already exists" => "Aplikačný adresár už existuje",
+"Can't create app folder. Please fix permissions. %s" => "Nemožno vytvoriť aplikačný priečinok. Prosím upravte povolenia. %s",
"Application is not enabled" => "Aplikácia nie je zapnutá",
"Authentication error" => "Chyba autentifikácie",
"Token expired. Please reload page." => "Token vypršal. Obnovte, prosím, stránku.",
@@ -40,13 +54,13 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "Váš webový server nie je správne nastavený na synchronizáciu, pretože rozhranie WebDAV je poškodené.",
"Please double check the <a href='%s'>installation guides</a>." => "Prosím skontrolujte <a href='%s'>inštalačnú príručku</a>.",
"seconds ago" => "pred sekundami",
-"_%n minute ago_::_%n minutes ago_" => array("","",""),
-"_%n hour ago_::_%n hours ago_" => array("","",""),
+"_%n minute ago_::_%n minutes ago_" => array("","","pred %n minútami"),
+"_%n hour ago_::_%n hours ago_" => array("","","pred %n hodinami"),
"today" => "dnes",
"yesterday" => "včera",
-"_%n day go_::_%n days ago_" => array("","",""),
+"_%n day go_::_%n days ago_" => array("","","pred %n dňami"),
"last month" => "minulý mesiac",
-"_%n month ago_::_%n months ago_" => array("","",""),
+"_%n month ago_::_%n months ago_" => array("","","pred %n mesiacmi"),
"last year" => "minulý rok",
"years ago" => "pred rokmi",
"Caused by:" => "Príčina:",
diff --git a/lib/l10n/sv.php b/lib/l10n/sv.php
index dd54e6ca5d3..e7c3420a85b 100644
--- a/lib/l10n/sv.php
+++ b/lib/l10n/sv.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Appen \"%s\" kan inte installeras eftersom att den inte är kompatibel med denna version av ownCloud.",
+"No app name specified" => "Inget appnamn angivet",
"Help" => "Hjälp",
"Personal" => "Personligt",
"Settings" => "Inställningar",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Tillbaka till Filer",
"Selected files too large to generate zip file." => "Valda filer är för stora för att skapa zip-fil.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Ladda ner filerna i mindre bitar, separat eller fråga din administratör.",
+"No source specified when installing app" => "Ingen källa angiven vid installation av app ",
+"No href specified when installing app from http" => "Ingen href angiven vid installation av app från http",
+"No path specified when installing app from local file" => "Ingen sökväg angiven vid installation av app från lokal fil",
+"Archives of type %s are not supported" => "Arkiv av typen %s stöds ej",
+"Failed to open archive when installing app" => "Kunde inte öppna arkivet när appen skulle installeras",
+"App does not provide an info.xml file" => "Appen har ingen info.xml fil",
+"App can't be installed because of not allowed code in the App" => "Appen kan inte installeras eftersom att den innehåller otillåten kod",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Appen kan inte installeras eftersom att den inte är kompatibel med denna version av ownCloud",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Appen kan inte installeras eftersom att den innehåller etiketten <shipped>true</shipped> vilket inte är tillåtet för icke inkluderade appar",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Appen kan inte installeras eftersom versionen i info.xml inte är samma som rapporteras från app store",
+"App directory already exists" => "Appens mapp finns redan",
+"Can't create app folder. Please fix permissions. %s" => "Kan inte skapa appens mapp. Var god åtgärda rättigheterna. %s",
"Application is not enabled" => "Applikationen är inte aktiverad",
"Authentication error" => "Fel vid autentisering",
"Token expired. Please reload page." => "Ogiltig token. Ladda om sidan.",
diff --git a/lib/l10n/tr.php b/lib/l10n/tr.php
index 498469ea8b1..b63c37c7240 100644
--- a/lib/l10n/tr.php
+++ b/lib/l10n/tr.php
@@ -1,5 +1,7 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "Owncloud yazılımının bu sürümü ile uyumlu olmadığı için \"%s\" uygulaması kurulamaz.",
+"No app name specified" => "Uygulama adı belirtimedli",
"Help" => "Yardım",
"Personal" => "Kişisel",
"Settings" => "Ayarlar",
@@ -13,6 +15,18 @@ $TRANSLATIONS = array(
"Back to Files" => "Dosyalara dön",
"Selected files too large to generate zip file." => "Seçilen dosyalar bir zip dosyası oluşturmak için fazla büyüktür.",
"Download the files in smaller chunks, seperately or kindly ask your administrator." => "Dosyaları ayrı ayrı, küçük parçalar halinde indirin ya da yöneticinizden yardım isteyin. ",
+"No source specified when installing app" => "Uygulama kurulurken bir kaynak belirtilmedi",
+"No href specified when installing app from http" => "Uygulama kuruluyorken http'de href belirtilmedi.",
+"No path specified when installing app from local file" => "Uygulama yerel dosyadan kuruluyorken dosya yolu belirtilmedi",
+"Archives of type %s are not supported" => "%s arşiv tipi desteklenmiyor",
+"Failed to open archive when installing app" => "Uygulama kuruluyorken arşiv dosyası açılamadı",
+"App does not provide an info.xml file" => "Uygulama info.xml dosyası sağlamıyor",
+"App can't be installed because of not allowed code in the App" => "Uygulamada izin verilmeyeden kodlar olduğu için kurulamıyor.",
+"App can't be installed because it is not compatible with this version of ownCloud" => "Owncloud versiyonunuz ile uyumsuz olduğu için uygulama kurulamıyor.",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "Uygulama kurulamıyor. Çünkü \"non shipped\" uygulamalar için <shipped>true</shipped> tag içermektedir.",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "Uygulama kurulamıyor çünkü info.xml/version ile uygulama marketde belirtilen sürüm aynı değil.",
+"App directory already exists" => "App dizini zaten mevcut",
+"Can't create app folder. Please fix permissions. %s" => "app dizini oluşturulamıyor. Lütfen izinleri düzeltin. %s",
"Application is not enabled" => "Uygulama etkinleştirilmedi",
"Authentication error" => "Kimlik doğrulama hatası",
"Token expired. Please reload page." => "Jetonun süresi geçti. Lütfen sayfayı yenileyin.",
diff --git a/lib/l10n/ug.php b/lib/l10n/ug.php
index 731ad904d7e..e2cf38ecc8c 100644
--- a/lib/l10n/ug.php
+++ b/lib/l10n/ug.php
@@ -8,6 +8,7 @@ $TRANSLATIONS = array(
"Files" => "ھۆججەتلەر",
"Text" => "قىسقا ئۇچۇر",
"Images" => "سۈرەتلەر",
+"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "سىزنىڭ تور مۇلازىمېتىرىڭىز ھۆججەت قەدەمداشلاشقا يول قويىدىغان قىلىپ توغرا تەڭشەلمەپتۇ، چۈنكى WebDAV نىڭ ئېغىزى بۇزۇلغاندەك تۇرىدۇ.",
"_%n minute ago_::_%n minutes ago_" => array(""),
"_%n hour ago_::_%n hours ago_" => array(""),
"today" => "بۈگۈن",
diff --git a/lib/l10n/zh_CN.GB2312.php b/lib/l10n/zh_CN.GB2312.php
deleted file mode 100644
index bc81ff8fe1b..00000000000
--- a/lib/l10n/zh_CN.GB2312.php
+++ /dev/null
@@ -1,32 +0,0 @@
-<?php
-$TRANSLATIONS = array(
-"Help" => "帮助",
-"Personal" => "私人",
-"Settings" => "设置",
-"Users" => "用户",
-"Admin" => "管理员",
-"web services under your control" => "您控制的网络服务",
-"ZIP download is turned off." => "ZIP 下载已关闭",
-"Files need to be downloaded one by one." => "需要逐个下载文件。",
-"Back to Files" => "返回到文件",
-"Selected files too large to generate zip file." => "选择的文件太大而不能生成 zip 文件。",
-"Application is not enabled" => "应用未启用",
-"Authentication error" => "验证错误",
-"Token expired. Please reload page." => "会话过期。请刷新页面。",
-"Files" => "文件",
-"Text" => "文本",
-"Images" => "图片",
-"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "因WebDAV接口故障,您的网络服务器好像并未允许文件同步。",
-"Please double check the <a href='%s'>installation guides</a>." => "请双击<a href='%s'>安装向导</a>。",
-"seconds ago" => "秒前",
-"_%n minute ago_::_%n minutes ago_" => array("%n 分钟以前"),
-"_%n hour ago_::_%n hours ago_" => array("%n 小时以前"),
-"today" => "今天",
-"yesterday" => "昨天",
-"_%n day go_::_%n days ago_" => array("%n 天以前"),
-"last month" => "上个月",
-"_%n month ago_::_%n months ago_" => array("%n 个月以前"),
-"last year" => "去年",
-"years ago" => "年前"
-);
-$PLURAL_FORMS = "nplurals=1; plural=0;";
diff --git a/lib/l10n/zh_CN.php b/lib/l10n/zh_CN.php
index 03bd48de74b..2c34356ea10 100644
--- a/lib/l10n/zh_CN.php
+++ b/lib/l10n/zh_CN.php
@@ -10,6 +10,7 @@ $TRANSLATIONS = array(
"Files need to be downloaded one by one." => "需要逐一下载文件",
"Back to Files" => "回到文件",
"Selected files too large to generate zip file." => "选择的文件太大,无法生成 zip 文件。",
+"App does not provide an info.xml file" => "应用未提供 info.xml 文件",
"Application is not enabled" => "应用程序未启用",
"Authentication error" => "认证出错",
"Token expired. Please reload page." => "Token 过期,请刷新页面。",
@@ -38,12 +39,12 @@ $TRANSLATIONS = array(
"Please double check the <a href='%s'>installation guides</a>." => "请认真检查<a href='%s'>安装指南</a>.",
"seconds ago" => "秒前",
"_%n minute ago_::_%n minutes ago_" => array("%n 分钟前"),
-"_%n hour ago_::_%n hours ago_" => array(""),
+"_%n hour ago_::_%n hours ago_" => array("%n 小时前"),
"today" => "今天",
"yesterday" => "昨天",
-"_%n day go_::_%n days ago_" => array(""),
+"_%n day go_::_%n days ago_" => array("%n 天前"),
"last month" => "上月",
-"_%n month ago_::_%n months ago_" => array(""),
+"_%n month ago_::_%n months ago_" => array("%n 月前"),
"last year" => "去年",
"years ago" => "年前",
"Could not find category \"%s\"" => "无法找到分类 \"%s\""
diff --git a/lib/l10n/zh_TW.php b/lib/l10n/zh_TW.php
index f405eb88ae9..210c766aa59 100644
--- a/lib/l10n/zh_TW.php
+++ b/lib/l10n/zh_TW.php
@@ -1,15 +1,32 @@
<?php
$TRANSLATIONS = array(
+"App \"%s\" can't be installed because it is not compatible with this version of ownCloud." => "無法安裝應用程式 %s 因為它和此版本的 ownCloud 不相容。",
+"No app name specified" => "沒有指定應用程式名稱",
"Help" => "說明",
"Personal" => "個人",
"Settings" => "設定",
"Users" => "使用者",
"Admin" => "管理",
+"Failed to upgrade \"%s\"." => "升級失敗:%s",
"web services under your control" => "由您控制的網路服務",
+"cannot open \"%s\"" => "無法開啓 %s",
"ZIP download is turned off." => "ZIP 下載已關閉。",
"Files need to be downloaded one by one." => "檔案需要逐一下載。",
"Back to Files" => "回到檔案列表",
"Selected files too large to generate zip file." => "選擇的檔案太大以致於無法產生壓縮檔。",
+"Download the files in smaller chunks, seperately or kindly ask your administrator." => "以小分割下載您的檔案,請詢問您的系統管理員。",
+"No source specified when installing app" => "沒有指定應用程式安裝來源",
+"No href specified when installing app from http" => "從 http 安裝應用程式,找不到 href 屬性",
+"No path specified when installing app from local file" => "從本地檔案安裝應用程式時沒有指定路徑",
+"Archives of type %s are not supported" => "不支援 %s 格式的壓縮檔",
+"Failed to open archive when installing app" => "安裝應用程式時無法開啓壓縮檔",
+"App does not provide an info.xml file" => "應用程式沒有提供 info.xml 檔案",
+"App can't be installed because of not allowed code in the App" => "無法安裝應用程式因為在當中找到危險的代碼",
+"App can't be installed because it is not compatible with this version of ownCloud" => "無法安裝應用程式因為它和此版本的 ownCloud 不相容。",
+"App can't be installed because it contains the <shipped>true</shipped> tag which is not allowed for non shipped apps" => "無法安裝應用程式,因為它包含了 <shipped>true</shipped> 標籤,在未發行的應用程式當中這是不允許的",
+"App can't be installed because the version in info.xml/version is not the same as the version reported from the app store" => "無法安裝應用程式,因為它在 info.xml/version 宣告的版本與 app store 當中記載的版本不同",
+"App directory already exists" => "應用程式目錄已經存在",
+"Can't create app folder. Please fix permissions. %s" => "無法建立應用程式目錄,請檢查權限:%s",
"Application is not enabled" => "應用程式未啟用",
"Authentication error" => "認證錯誤",
"Token expired. Please reload page." => "Token 過期,請重新整理頁面。",
@@ -37,15 +54,16 @@ $TRANSLATIONS = array(
"Your web server is not yet properly setup to allow files synchronization because the WebDAV interface seems to be broken." => "您的網頁伺服器尚未被正確設定來進行檔案同步,因為您的 WebDAV 界面似乎無法使用。",
"Please double check the <a href='%s'>installation guides</a>." => "請參考<a href='%s'>安裝指南</a>。",
"seconds ago" => "幾秒前",
-"_%n minute ago_::_%n minutes ago_" => array(""),
-"_%n hour ago_::_%n hours ago_" => array(""),
+"_%n minute ago_::_%n minutes ago_" => array("%n 分鐘前"),
+"_%n hour ago_::_%n hours ago_" => array("%n 小時前"),
"today" => "今天",
"yesterday" => "昨天",
-"_%n day go_::_%n days ago_" => array(""),
+"_%n day go_::_%n days ago_" => array("%n 天前"),
"last month" => "上個月",
-"_%n month ago_::_%n months ago_" => array(""),
+"_%n month ago_::_%n months ago_" => array("%n 個月前"),
"last year" => "去年",
"years ago" => "幾年前",
+"Caused by:" => "原因:",
"Could not find category \"%s\"" => "找不到分類:\"%s\""
);
$PLURAL_FORMS = "nplurals=1; plural=0;";
diff --git a/lib/log/rotate.php b/lib/log/rotate.php
new file mode 100644
index 00000000000..bf23ad588b3
--- /dev/null
+++ b/lib/log/rotate.php
@@ -0,0 +1,35 @@
+<?php
+/**
+ * Copyright (c) 2013 Bart Visscher <bartv@thisnet.nl>
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+
+namespace OC\Log;
+
+/**
+ * This rotates the current logfile to a new name, this way the total log usage
+ * will stay limited and older entries are available for a while longer.
+ * For more professional log management set the 'logfile' config to a different
+ * location and manage that with your own tools.
+ */
+class Rotate extends \OC\BackgroundJob\Job {
+ private $max_log_size;
+ public function run($logFile) {
+ $this->max_log_size = \OC_Config::getValue('log_rotate_size', false);
+ if ($this->max_log_size) {
+ $filesize = @filesize($logFile);
+ if ($filesize >= $this->max_log_size) {
+ $this->rotate($logFile);
+ }
+ }
+ }
+
+ protected function rotate($logfile) {
+ $rotatedLogfile = $logfile.'.1';
+ rename($logfile, $rotatedLogfile);
+ $msg = 'Log file "'.$logfile.'" was over '.$this->max_log_size.' bytes, moved to "'.$rotatedLogfile.'"';
+ \OC_Log::write('OC\Log\Rotate', $msg, \OC_Log::WARN);
+ }
+}
diff --git a/lib/ocs/cloud.php b/lib/ocs/cloud.php
index 132d923d960..2dd99319057 100644
--- a/lib/ocs/cloud.php
+++ b/lib/ocs/cloud.php
@@ -35,13 +35,49 @@ class OC_OCS_Cloud {
'edition' => OC_Util::getEditionString(),
);
- $result['capabilities'] = array(
- 'core' => array(
- 'pollinterval' => OC_Config::getValue('pollinterval', 60),
- ),
- );
+ $result['capabilities'] = array(
+ 'core' => array(
+ 'pollinterval' => OC_Config::getValue('pollinterval', 60),
+ ),
+ );
+
return new OC_OCS_Result($result);
}
+
+ /**
+ * gets user info
+ *
+ * exposes the quota of an user:
+ * <data>
+ * <quota>
+ * <free>1234</free>
+ * <used>4321</used>
+ * <total>5555</total>
+ * <ralative>0.78</ralative>
+ * </quota>
+ * </data>
+ *
+ * @param $parameters object should contain parameter 'userid' which identifies
+ * the user from whom the information will be returned
+ */
+ public static function getUser($parameters) {
+ // Check if they are viewing information on themselves
+ if($parameters['userid'] === OC_User::getUser()) {
+ // Self lookup
+ $quota = array();
+ $storage = OC_Helper::getStorageInfo();
+ $quota = array(
+ 'free' => $storage['free'],
+ 'used' => $storage['used'],
+ 'total' => $storage['total'],
+ 'relative' => $storage['relative'],
+ );
+ return new OC_OCS_Result(array('quota' => $quota));
+ } else {
+ // No permission to view this user data
+ return new OC_OCS_Result(null, 997);
+ }
+ }
public static function getUserPublickey($parameters) {
diff --git a/lib/preview.php b/lib/preview.php
new file mode 100755
index 00000000000..b40ba191fba
--- /dev/null
+++ b/lib/preview.php
@@ -0,0 +1,627 @@
+<?php
+/**
+ * Copyright (c) 2013 Frank Karlitschek frank@owncloud.org
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ *
+ * Thumbnails:
+ * structure of filename:
+ * /data/user/thumbnails/pathhash/x-y.png
+ *
+ */
+namespace OC;
+
+require_once 'preview/image.php';
+require_once 'preview/movies.php';
+require_once 'preview/mp3.php';
+require_once 'preview/pdf.php';
+require_once 'preview/svg.php';
+require_once 'preview/txt.php';
+require_once 'preview/unknown.php';
+require_once 'preview/office.php';
+
+class Preview {
+ //the thumbnail folder
+ const THUMBNAILS_FOLDER = 'thumbnails';
+
+ //config
+ private $maxScaleFactor;
+ private $configMaxX;
+ private $configMaxY;
+
+ //fileview object
+ private $fileView = null;
+ private $userView = null;
+
+ //vars
+ private $file;
+ private $maxX;
+ private $maxY;
+ private $scalingup;
+
+ //preview images object
+ private $preview;
+
+ //preview providers
+ static private $providers = array();
+ static private $registeredProviders = array();
+
+ /**
+ * @brief check if thumbnail or bigger version of thumbnail of file is cached
+ * @param string $user userid - if no user is given, OC_User::getUser will be used
+ * @param string $root path of root
+ * @param string $file The path to the file where you want a thumbnail from
+ * @param int $maxX The maximum X size of the thumbnail. It can be smaller depending on the shape of the image
+ * @param int $maxY The maximum Y size of the thumbnail. It can be smaller depending on the shape of the image
+ * @param bool $scalingUp Disable/Enable upscaling of previews
+ * @return mixed (bool / string)
+ * false if thumbnail does not exist
+ * path to thumbnail if thumbnail exists
+ */
+ public function __construct($user='', $root='/', $file='', $maxX=1, $maxY=1, $scalingUp=true) {
+ //set config
+ $this->configMaxX = \OC_Config::getValue('preview_max_x', null);
+ $this->configMaxY = \OC_Config::getValue('preview_max_y', null);
+ $this->maxScaleFactor = \OC_Config::getValue('preview_max_scale_factor', 2);
+
+ //save parameters
+ $this->setFile($file);
+ $this->setMaxX($maxX);
+ $this->setMaxY($maxY);
+ $this->setScalingUp($scalingUp);
+
+ //init fileviews
+ if($user === ''){
+ $user = \OC_User::getUser();
+ }
+ $this->fileView = new \OC\Files\View('/' . $user . '/' . $root);
+ $this->userView = new \OC\Files\View('/' . $user);
+
+ $this->preview = null;
+
+ //check if there are preview backends
+ if(empty(self::$providers)) {
+ self::initProviders();
+ }
+
+ if(empty(self::$providers)) {
+ \OC_Log::write('core', 'No preview providers exist', \OC_Log::ERROR);
+ throw new \Exception('No preview providers');
+ }
+ }
+
+ /**
+ * @brief returns the path of the file you want a thumbnail from
+ * @return string
+ */
+ public function getFile() {
+ return $this->file;
+ }
+
+ /**
+ * @brief returns the max width of the preview
+ * @return integer
+ */
+ public function getMaxX() {
+ return $this->maxX;
+ }
+
+ /**
+ * @brief returns the max height of the preview
+ * @return integer
+ */
+ public function getMaxY() {
+ return $this->maxY;
+ }
+
+ /**
+ * @brief returns whether or not scalingup is enabled
+ * @return bool
+ */
+ public function getScalingUp() {
+ return $this->scalingup;
+ }
+
+ /**
+ * @brief returns the name of the thumbnailfolder
+ * @return string
+ */
+ public function getThumbnailsFolder() {
+ return self::THUMBNAILS_FOLDER;
+ }
+
+ /**
+ * @brief returns the max scale factor
+ * @return integer
+ */
+ public function getMaxScaleFactor() {
+ return $this->maxScaleFactor;
+ }
+
+ /**
+ * @brief returns the max width set in ownCloud's config
+ * @return integer
+ */
+ public function getConfigMaxX() {
+ return $this->configMaxX;
+ }
+
+ /**
+ * @brief returns the max height set in ownCloud's config
+ * @return integer
+ */
+ public function getConfigMaxY() {
+ return $this->configMaxY;
+ }
+
+ /**
+ * @brief set the path of the file you want a thumbnail from
+ * @param string $file
+ * @return $this
+ */
+ public function setFile($file) {
+ $this->file = $file;
+ return $this;
+ }
+
+ /**
+ * @brief set the the max width of the preview
+ * @param int $maxX
+ * @return $this
+ */
+ public function setMaxX($maxX=1) {
+ if($maxX <= 0) {
+ throw new \Exception('Cannot set width of 0 or smaller!');
+ }
+ $configMaxX = $this->getConfigMaxX();
+ if(!is_null($configMaxX)) {
+ if($maxX > $configMaxX) {
+ \OC_Log::write('core', 'maxX reduced from ' . $maxX . ' to ' . $configMaxX, \OC_Log::DEBUG);
+ $maxX = $configMaxX;
+ }
+ }
+ $this->maxX = $maxX;
+ return $this;
+ }
+
+ /**
+ * @brief set the the max height of the preview
+ * @param int $maxY
+ * @return $this
+ */
+ public function setMaxY($maxY=1) {
+ if($maxY <= 0) {
+ throw new \Exception('Cannot set height of 0 or smaller!');
+ }
+ $configMaxY = $this->getConfigMaxY();
+ if(!is_null($configMaxY)) {
+ if($maxY > $configMaxY) {
+ \OC_Log::write('core', 'maxX reduced from ' . $maxY . ' to ' . $configMaxY, \OC_Log::DEBUG);
+ $maxY = $configMaxY;
+ }
+ }
+ $this->maxY = $maxY;
+ return $this;
+ }
+
+ /**
+ * @brief set whether or not scalingup is enabled
+ * @param bool $scalingUp
+ * @return $this
+ */
+ public function setScalingup($scalingUp) {
+ if($this->getMaxScaleFactor() === 1) {
+ $scalingUp = false;
+ }
+ $this->scalingup = $scalingUp;
+ return $this;
+ }
+
+ /**
+ * @brief check if all parameters are valid
+ * @return bool
+ */
+ public function isFileValid() {
+ $file = $this->getFile();
+ if($file === '') {
+ \OC_Log::write('core', 'No filename passed', \OC_Log::DEBUG);
+ return false;
+ }
+
+ if(!$this->fileView->file_exists($file)) {
+ \OC_Log::write('core', 'File:"' . $file . '" not found', \OC_Log::DEBUG);
+ return false;
+ }
+
+ return true;
+ }
+
+ /**
+ * @brief deletes previews of a file with specific x and y
+ * @return bool
+ */
+ public function deletePreview() {
+ $file = $this->getFile();
+
+ $fileInfo = $this->fileView->getFileInfo($file);
+ $fileId = $fileInfo['fileid'];
+
+ $previewPath = $this->getThumbnailsFolder() . '/' . $fileId . '/' . $this->getMaxX() . '-' . $this->getMaxY() . '.png';
+ $this->userView->unlink($previewPath);
+ return !$this->userView->file_exists($previewPath);
+ }
+
+ /**
+ * @brief deletes all previews of a file
+ * @return bool
+ */
+ public function deleteAllPreviews() {
+ $file = $this->getFile();
+
+ $fileInfo = $this->fileView->getFileInfo($file);
+ $fileId = $fileInfo['fileid'];
+
+ $previewPath = $this->getThumbnailsFolder() . '/' . $fileId . '/';
+ $this->userView->deleteAll($previewPath);
+ $this->userView->rmdir($previewPath);
+ return !$this->userView->is_dir($previewPath);
+ }
+
+ /**
+ * @brief check if thumbnail or bigger version of thumbnail of file is cached
+ * @return mixed (bool / string)
+ * false if thumbnail does not exist
+ * path to thumbnail if thumbnail exists
+ */
+ private function isCached() {
+ $file = $this->getFile();
+ $maxX = $this->getMaxX();
+ $maxY = $this->getMaxY();
+ $scalingUp = $this->getScalingUp();
+ $maxScaleFactor = $this->getMaxScaleFactor();
+
+ $fileInfo = $this->fileView->getFileInfo($file);
+ $fileId = $fileInfo['fileid'];
+
+ if(is_null($fileId)) {
+ return false;
+ }
+
+ $previewPath = $this->getThumbnailsFolder() . '/' . $fileId . '/';
+ if(!$this->userView->is_dir($previewPath)) {
+ return false;
+ }
+
+ //does a preview with the wanted height and width already exist?
+ if($this->userView->file_exists($previewPath . $maxX . '-' . $maxY . '.png')) {
+ return $previewPath . $maxX . '-' . $maxY . '.png';
+ }
+
+ $wantedAspectRatio = (float) ($maxX / $maxY);
+
+ //array for usable cached thumbnails
+ $possibleThumbnails = array();
+
+ $allThumbnails = $this->userView->getDirectoryContent($previewPath);
+ foreach($allThumbnails as $thumbnail) {
+ $name = rtrim($thumbnail['name'], '.png');
+ $size = explode('-', $name);
+ $x = (int) $size[0];
+ $y = (int) $size[1];
+
+ $aspectRatio = (float) ($x / $y);
+ if($aspectRatio !== $wantedAspectRatio) {
+ continue;
+ }
+
+ if($x < $maxX || $y < $maxY) {
+ if($scalingUp) {
+ $scalefactor = $maxX / $x;
+ if($scalefactor > $maxScaleFactor) {
+ continue;
+ }
+ }else{
+ continue;
+ }
+ }
+ $possibleThumbnails[$x] = $thumbnail['path'];
+ }
+
+ if(count($possibleThumbnails) === 0) {
+ return false;
+ }
+
+ if(count($possibleThumbnails) === 1) {
+ return current($possibleThumbnails);
+ }
+
+ ksort($possibleThumbnails);
+
+ if(key(reset($possibleThumbnails)) > $maxX) {
+ return current(reset($possibleThumbnails));
+ }
+
+ if(key(end($possibleThumbnails)) < $maxX) {
+ return current(end($possibleThumbnails));
+ }
+
+ foreach($possibleThumbnails as $width => $path) {
+ if($width < $maxX) {
+ continue;
+ }else{
+ return $path;
+ }
+ }
+ }
+
+ /**
+ * @brief return a preview of a file
+ * @return \OC_Image
+ */
+ public function getPreview() {
+ if(!is_null($this->preview) && $this->preview->valid()){
+ return $this->preview;
+ }
+
+ $this->preview = null;
+ $file = $this->getFile();
+ $maxX = $this->getMaxX();
+ $maxY = $this->getMaxY();
+ $scalingUp = $this->getScalingUp();
+
+ $fileInfo = $this->fileView->getFileInfo($file);
+ $fileId = $fileInfo['fileid'];
+
+ $cached = $this->isCached();
+
+ if($cached) {
+ $image = new \OC_Image($this->userView->file_get_contents($cached, 'r'));
+ $this->preview = $image->valid() ? $image : null;
+ $this->resizeAndCrop();
+ }
+
+ if(is_null($this->preview)) {
+ $mimetype = $this->fileView->getMimeType($file);
+ $preview = null;
+
+ foreach(self::$providers as $supportedMimetype => $provider) {
+ if(!preg_match($supportedMimetype, $mimetype)) {
+ continue;
+ }
+
+ \OC_Log::write('core', 'Generating preview for "' . $file . '" with "' . get_class($provider) . '"', \OC_Log::DEBUG);
+
+ $preview = $provider->getThumbnail($file, $maxX, $maxY, $scalingUp, $this->fileView);
+
+ if(!($preview instanceof \OC_Image)) {
+ continue;
+ }
+
+ $this->preview = $preview;
+ $this->resizeAndCrop();
+
+ $previewPath = $this->getThumbnailsFolder() . '/' . $fileId . '/';
+ $cachePath = $previewPath . $maxX . '-' . $maxY . '.png';
+
+ if($this->userView->is_dir($this->getThumbnailsFolder() . '/') === false) {
+ $this->userView->mkdir($this->getThumbnailsFolder() . '/');
+ }
+
+ if($this->userView->is_dir($previewPath) === false) {
+ $this->userView->mkdir($previewPath);
+ }
+
+ $this->userView->file_put_contents($cachePath, $preview->data());
+
+ break;
+ }
+ }
+
+ if(is_null($this->preview)) {
+ $this->preview = new \OC_Image();
+ }
+
+ return $this->preview;
+ }
+
+ /**
+ * @brief show preview
+ * @return void
+ */
+ public function showPreview() {
+ \OCP\Response::enableCaching(3600 * 24); // 24 hours
+ if(is_null($this->preview)) {
+ $this->getPreview();
+ }
+ $this->preview->show();
+ return;
+ }
+
+ /**
+ * @brief show preview
+ * @return void
+ */
+ public function show() {
+ $this->showPreview();
+ return;
+ }
+
+ /**
+ * @brief resize, crop and fix orientation
+ * @return void
+ */
+ private function resizeAndCrop() {
+ $image = $this->preview;
+ $x = $this->getMaxX();
+ $y = $this->getMaxY();
+ $scalingUp = $this->getScalingUp();
+ $maxscalefactor = $this->getMaxScaleFactor();
+
+ if(!($image instanceof \OC_Image)) {
+ \OC_Log::write('core', '$this->preview is not an instance of OC_Image', \OC_Log::DEBUG);
+ return;
+ }
+
+ $image->fixOrientation();
+
+ $realx = (int) $image->width();
+ $realy = (int) $image->height();
+
+ if($x === $realx && $y === $realy) {
+ $this->preview = $image;
+ return;
+ }
+
+ $factorX = $x / $realx;
+ $factorY = $y / $realy;
+
+ if($factorX >= $factorY) {
+ $factor = $factorX;
+ }else{
+ $factor = $factorY;
+ }
+
+ if($scalingUp === false) {
+ if($factor > 1) {
+ $factor = 1;
+ }
+ }
+
+ if(!is_null($maxscalefactor)) {
+ if($factor > $maxscalefactor) {
+ \OC_Log::write('core', 'scalefactor reduced from ' . $factor . ' to ' . $maxscalefactor, \OC_Log::DEBUG);
+ $factor = $maxscalefactor;
+ }
+ }
+
+ $newXsize = (int) ($realx * $factor);
+ $newYsize = (int) ($realy * $factor);
+
+ $image->preciseResize($newXsize, $newYsize);
+
+ if($newXsize === $x && $newYsize === $y) {
+ $this->preview = $image;
+ return;
+ }
+
+ if($newXsize >= $x && $newYsize >= $y) {
+ $cropX = floor(abs($x - $newXsize) * 0.5);
+ //don't crop previews on the Y axis, this sucks if it's a document.
+ //$cropY = floor(abs($y - $newYsize) * 0.5);
+ $cropY = 0;
+
+ $image->crop($cropX, $cropY, $x, $y);
+
+ $this->preview = $image;
+ return;
+ }
+
+ if($newXsize < $x || $newYsize < $y) {
+ if($newXsize > $x) {
+ $cropX = floor(($newXsize - $x) * 0.5);
+ $image->crop($cropX, 0, $x, $newYsize);
+ }
+
+ if($newYsize > $y) {
+ $cropY = floor(($newYsize - $y) * 0.5);
+ $image->crop(0, $cropY, $newXsize, $y);
+ }
+
+ $newXsize = (int) $image->width();
+ $newYsize = (int) $image->height();
+
+ //create transparent background layer
+ $backgroundlayer = imagecreatetruecolor($x, $y);
+ $white = imagecolorallocate($backgroundlayer, 255, 255, 255);
+ imagefill($backgroundlayer, 0, 0, $white);
+
+ $image = $image->resource();
+
+ $mergeX = floor(abs($x - $newXsize) * 0.5);
+ $mergeY = floor(abs($y - $newYsize) * 0.5);
+
+ imagecopy($backgroundlayer, $image, $mergeX, $mergeY, 0, 0, $newXsize, $newYsize);
+
+ //$black = imagecolorallocate(0,0,0);
+ //imagecolortransparent($transparentlayer, $black);
+
+ $image = new \OC_Image($backgroundlayer);
+
+ $this->preview = $image;
+ return;
+ }
+ }
+
+ /**
+ * @brief register a new preview provider to be used
+ * @param string $provider class name of a Preview_Provider
+ * @param array $options
+ * @return void
+ */
+ public static function registerProvider($class, $options=array()) {
+ self::$registeredProviders[]=array('class'=>$class, 'options'=>$options);
+ }
+
+ /**
+ * @brief create instances of all the registered preview providers
+ * @return void
+ */
+ private static function initProviders() {
+ if(!\OC_Config::getValue('enable_previews', true)) {
+ $provider = new Preview\Unknown(array());
+ self::$providers = array($provider->getMimeType() => $provider);
+ return;
+ }
+
+ if(count(self::$providers)>0) {
+ return;
+ }
+
+ foreach(self::$registeredProviders as $provider) {
+ $class=$provider['class'];
+ $options=$provider['options'];
+
+ $object = new $class($options);
+
+ self::$providers[$object->getMimeType()] = $object;
+ }
+
+ $keys = array_map('strlen', array_keys(self::$providers));
+ array_multisort($keys, SORT_DESC, self::$providers);
+ }
+
+ public static function post_write($args) {
+ self::post_delete($args);
+ }
+
+ public static function post_delete($args) {
+ $path = $args['path'];
+ if(substr($path, 0, 1) === '/') {
+ $path = substr($path, 1);
+ }
+ $preview = new Preview(\OC_User::getUser(), 'files/', $path);
+ $preview->deleteAllPreviews();
+ }
+
+ public static function isMimeSupported($mimetype) {
+ if(!\OC_Config::getValue('enable_previews', true)) {
+ return false;
+ }
+
+ //check if there are preview backends
+ if(empty(self::$providers)) {
+ self::initProviders();
+ }
+
+ //remove last element because it has the mimetype *
+ $providers = array_slice(self::$providers, 0, -1);
+ foreach($providers as $supportedMimetype => $provider) {
+ if(preg_match($supportedMimetype, $mimetype)) {
+ return true;
+ }
+ }
+ return false;
+ }
+} \ No newline at end of file
diff --git a/lib/preview/image.php b/lib/preview/image.php
new file mode 100644
index 00000000000..9aec967282d
--- /dev/null
+++ b/lib/preview/image.php
@@ -0,0 +1,36 @@
+<?php
+/**
+ * Copyright (c) 2013 Frank Karlitschek frank@owncloud.org
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+class Image extends Provider {
+
+ public function getMimeType() {
+ return '/image\/.*/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ //get fileinfo
+ $fileInfo = $fileview->getFileInfo($path);
+ if(!$fileInfo) {
+ return false;
+ }
+
+ //check if file is encrypted
+ if($fileInfo['encrypted'] === true) {
+ $image = new \OC_Image(stream_get_contents($fileview->fopen($path, 'r')));
+ }else{
+ $image = new \OC_Image();
+ $image->loadFromFile($fileview->getLocalFile($path));
+ }
+
+ return $image->valid() ? $image : false;
+ }
+}
+
+\OC\Preview::registerProvider('OC\Preview\Image'); \ No newline at end of file
diff --git a/lib/preview/movies.php b/lib/preview/movies.php
new file mode 100644
index 00000000000..e2a1b8edddc
--- /dev/null
+++ b/lib/preview/movies.php
@@ -0,0 +1,47 @@
+<?php
+/**
+ * Copyright (c) 2013 Frank Karlitschek frank@owncloud.org
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+$isShellExecEnabled = !in_array('shell_exec', explode(', ', ini_get('disable_functions')));
+$whichFFMPEG = shell_exec('which ffmpeg');
+$isFFMPEGAvailable = !empty($whichFFMPEG);
+
+if($isShellExecEnabled && $isFFMPEGAvailable) {
+
+ class Movie extends Provider {
+
+ public function getMimeType() {
+ return '/video\/.*/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ $absPath = \OC_Helper::tmpFile();
+ $tmpPath = \OC_Helper::tmpFile();
+
+ $handle = $fileview->fopen($path, 'rb');
+
+ $firstmb = stream_get_contents($handle, 1048576); //1024 * 1024 = 1048576
+ file_put_contents($absPath, $firstmb);
+
+ //$cmd = 'ffmpeg -y -i ' . escapeshellarg($absPath) . ' -f mjpeg -vframes 1 -ss 1 -s ' . escapeshellarg($maxX) . 'x' . escapeshellarg($maxY) . ' ' . $tmpPath;
+ $cmd = 'ffmpeg -an -y -i ' . escapeshellarg($absPath) . ' -f mjpeg -vframes 1 -ss 1 ' . escapeshellarg($tmpPath);
+
+ shell_exec($cmd);
+
+ $image = new \OC_Image($tmpPath);
+
+ unlink($absPath);
+ unlink($tmpPath);
+
+ return $image->valid() ? $image : false;
+ }
+ }
+
+ \OC\Preview::registerProvider('OC\Preview\Movie');
+} \ No newline at end of file
diff --git a/lib/preview/mp3.php b/lib/preview/mp3.php
new file mode 100644
index 00000000000..1eed566315c
--- /dev/null
+++ b/lib/preview/mp3.php
@@ -0,0 +1,48 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+class MP3 extends Provider {
+
+ public function getMimeType() {
+ return '/audio\/mpeg/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ require_once('getid3/getid3.php');
+
+ $getID3 = new \getID3();
+
+ $tmpPath = $fileview->toTmpFile($path);
+
+ $tags = $getID3->analyze($tmpPath);
+ \getid3_lib::CopyTagsToComments($tags);
+ if(isset($tags['id3v2']['APIC'][0]['data'])) {
+ $picture = @$tags['id3v2']['APIC'][0]['data'];
+ unlink($tmpPath);
+ $image = new \OC_Image($picture);
+ return $image->valid() ? $image : $this->getNoCoverThumbnail();
+ }
+
+ return $this->getNoCoverThumbnail();
+ }
+
+ private function getNoCoverThumbnail() {
+ $icon = \OC::$SERVERROOT . '/core/img/filetypes/audio.png';
+
+ if(!file_exists($icon)) {
+ return false;
+ }
+
+ $image = new \OC_Image($icon);
+ return $image->valid() ? $image : false;
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\MP3'); \ No newline at end of file
diff --git a/lib/preview/office-cl.php b/lib/preview/office-cl.php
new file mode 100644
index 00000000000..112909d6523
--- /dev/null
+++ b/lib/preview/office-cl.php
@@ -0,0 +1,134 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+//we need imagick to convert
+class Office extends Provider {
+
+ private $cmd;
+
+ public function getMimeType() {
+ return null;
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ $this->initCmd();
+ if(is_null($this->cmd)) {
+ return false;
+ }
+
+ $absPath = $fileview->toTmpFile($path);
+
+ $tmpDir = get_temp_dir();
+
+ $defaultParameters = ' --headless --nologo --nofirststartwizard --invisible --norestore -convert-to pdf -outdir ';
+ $clParameters = \OCP\Config::getSystemValue('preview_office_cl_parameters', $defaultParameters);
+
+ $exec = $this->cmd . $clParameters . escapeshellarg($tmpDir) . ' ' . escapeshellarg($absPath);
+ $export = 'export HOME=/' . $tmpDir;
+
+ shell_exec($export . "\n" . $exec);
+
+ //create imagick object from pdf
+ try{
+ $pdf = new \imagick($absPath . '.pdf' . '[0]');
+ $pdf->setImageFormat('jpg');
+ } catch (\Exception $e) {
+ unlink($absPath);
+ unlink($absPath . '.pdf');
+ \OC_Log::write('core', $e->getmessage(), \OC_Log::ERROR);
+ return false;
+ }
+
+ $image = new \OC_Image($pdf);
+
+ unlink($absPath);
+ unlink($absPath . '.pdf');
+
+ return $image->valid() ? $image : false;
+ }
+
+ private function initCmd() {
+ $cmd = '';
+
+ if(is_string(\OC_Config::getValue('preview_libreoffice_path', null))) {
+ $cmd = \OC_Config::getValue('preview_libreoffice_path', null);
+ }
+
+ $whichLibreOffice = shell_exec('which libreoffice');
+ if($cmd === '' && !empty($whichLibreOffice)) {
+ $cmd = 'libreoffice';
+ }
+
+ $whichOpenOffice = shell_exec('which openoffice');
+ if($cmd === '' && !empty($whichOpenOffice)) {
+ $cmd = 'openoffice';
+ }
+
+ if($cmd === '') {
+ $cmd = null;
+ }
+
+ $this->cmd = $cmd;
+ }
+}
+
+//.doc, .dot
+class MSOfficeDoc extends Office {
+
+ public function getMimeType() {
+ return '/application\/msword/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\MSOfficeDoc');
+
+//.docm, .dotm, .xls(m), .xlt(m), .xla(m), .ppt(m), .pot(m), .pps(m), .ppa(m)
+class MSOffice2003 extends Office {
+
+ public function getMimeType() {
+ return '/application\/vnd.ms-.*/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\MSOffice2003');
+
+//.docx, .dotx, .xlsx, .xltx, .pptx, .potx, .ppsx
+class MSOffice2007 extends Office {
+
+ public function getMimeType() {
+ return '/application\/vnd.openxmlformats-officedocument.*/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\MSOffice2007');
+
+//.odt, .ott, .oth, .odm, .odg, .otg, .odp, .otp, .ods, .ots, .odc, .odf, .odb, .odi, .oxt
+class OpenDocument extends Office {
+
+ public function getMimeType() {
+ return '/application\/vnd.oasis.opendocument.*/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\OpenDocument');
+
+//.sxw, .stw, .sxc, .stc, .sxd, .std, .sxi, .sti, .sxg, .sxm
+class StarOffice extends Office {
+
+ public function getMimeType() {
+ return '/application\/vnd.sun.xml.*/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\StarOffice'); \ No newline at end of file
diff --git a/lib/preview/office-fallback.php b/lib/preview/office-fallback.php
new file mode 100644
index 00000000000..e69ab0ab8cb
--- /dev/null
+++ b/lib/preview/office-fallback.php
@@ -0,0 +1,142 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+/* //There is no (good) php-only solution for converting 2003 word documents to pdfs / pngs ...
+class DOC extends Provider {
+
+ public function getMimeType() {
+ return '/application\/msword/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ require_once('');
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\DOC');
+*/
+
+class DOCX extends Provider {
+
+ public function getMimeType() {
+ return '/application\/vnd.openxmlformats-officedocument.wordprocessingml.document/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ require_once('phpdocx/classes/TransformDoc.inc');
+
+ $tmpDoc = $fileview->toTmpFile($path);
+
+ $transformdoc = new \TransformDoc();
+ $transformdoc->setStrFile($tmpDoc);
+ $transformdoc->generatePDF($tmpDoc);
+
+ $pdf = new \imagick($tmpDoc . '[0]');
+ $pdf->setImageFormat('jpg');
+
+ unlink($tmpDoc);
+
+ $image = new \OC_Image($pdf);
+
+ return $image->valid() ? $image : false;
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\DOCX');
+
+class MSOfficeExcel extends Provider {
+
+ public function getMimeType() {
+ return null;
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ require_once('PHPExcel/Classes/PHPExcel.php');
+ require_once('PHPExcel/Classes/PHPExcel/IOFactory.php');
+
+ $absPath = $fileview->toTmpFile($path);
+ $tmpPath = \OC_Helper::tmpFile();
+
+ $rendererName = \PHPExcel_Settings::PDF_RENDERER_DOMPDF;
+ $rendererLibraryPath = \OC::$THIRDPARTYROOT . '/3rdparty/dompdf';
+
+ \PHPExcel_Settings::setPdfRenderer($rendererName, $rendererLibraryPath);
+
+ $phpexcel = new \PHPExcel($absPath);
+ $excel = \PHPExcel_IOFactory::createWriter($phpexcel, 'PDF');
+ $excel->save($tmpPath);
+
+ $pdf = new \imagick($tmpPath . '[0]');
+ $pdf->setImageFormat('jpg');
+
+ unlink($absPath);
+ unlink($tmpPath);
+
+ $image = new \OC_Image($pdf);
+
+ return $image->valid() ? $image : false;
+ }
+
+}
+
+class XLS extends MSOfficeExcel {
+
+ public function getMimeType() {
+ return '/application\/vnd.ms-excel/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\XLS');
+
+class XLSX extends MSOfficeExcel {
+
+ public function getMimeType() {
+ return '/application\/vnd.openxmlformats-officedocument.spreadsheetml.sheet/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\XLSX');
+
+/* //There is no (good) php-only solution for converting powerpoint documents to pdfs / pngs ...
+class MSOfficePowerPoint extends Provider {
+
+ public function getMimeType() {
+ return null;
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ return false;
+ }
+
+}
+
+class PPT extends MSOfficePowerPoint {
+
+ public function getMimeType() {
+ return '/application\/vnd.ms-powerpoint/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\PPT');
+
+class PPTX extends MSOfficePowerPoint {
+
+ public function getMimeType() {
+ return '/application\/vnd.openxmlformats-officedocument.presentationml.presentation/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\PPTX');
+*/ \ No newline at end of file
diff --git a/lib/preview/office.php b/lib/preview/office.php
new file mode 100644
index 00000000000..5287bbd6ac1
--- /dev/null
+++ b/lib/preview/office.php
@@ -0,0 +1,22 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+//both, libreoffice backend and php fallback, need imagick
+if (extension_loaded('imagick')) {
+ $isShellExecEnabled = !in_array('shell_exec', explode(', ', ini_get('disable_functions')));
+ $whichLibreOffice = shell_exec('which libreoffice');
+ $isLibreOfficeAvailable = !empty($whichLibreOffice);
+ $whichOpenOffice = shell_exec('which libreoffice');
+ $isOpenOfficeAvailable = !empty($whichOpenOffice);
+ //let's see if there is libreoffice or openoffice on this machine
+ if($isShellExecEnabled && ($isLibreOfficeAvailable || $isOpenOfficeAvailable || is_string(\OC_Config::getValue('preview_libreoffice_path', null)))) {
+ require_once('office-cl.php');
+ }else{
+ //in case there isn't, use our fallback
+ require_once('office-fallback.php');
+ }
+} \ No newline at end of file
diff --git a/lib/preview/pdf.php b/lib/preview/pdf.php
new file mode 100644
index 00000000000..cc974b68818
--- /dev/null
+++ b/lib/preview/pdf.php
@@ -0,0 +1,40 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+if (extension_loaded('imagick')) {
+
+ class PDF extends Provider {
+
+ public function getMimeType() {
+ return '/application\/pdf/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ $tmpPath = $fileview->toTmpFile($path);
+
+ //create imagick object from pdf
+ try{
+ $pdf = new \imagick($tmpPath . '[0]');
+ $pdf->setImageFormat('jpg');
+ } catch (\Exception $e) {
+ \OC_Log::write('core', $e->getmessage(), \OC_Log::ERROR);
+ return false;
+ }
+
+ unlink($tmpPath);
+
+ //new image object
+ $image = new \OC_Image($pdf);
+ //check if image object is valid
+ return $image->valid() ? $image : false;
+ }
+ }
+
+ \OC\Preview::registerProvider('OC\Preview\PDF');
+}
diff --git a/lib/preview/provider.php b/lib/preview/provider.php
new file mode 100644
index 00000000000..e4a730bafc8
--- /dev/null
+++ b/lib/preview/provider.php
@@ -0,0 +1,19 @@
+<?php
+namespace OC\Preview;
+
+abstract class Provider {
+ private $options;
+
+ public function __construct($options) {
+ $this->options=$options;
+ }
+
+ abstract public function getMimeType();
+
+ /**
+ * search for $query
+ * @param string $query
+ * @return
+ */
+ abstract public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview);
+}
diff --git a/lib/preview/svg.php b/lib/preview/svg.php
new file mode 100644
index 00000000000..b49e51720fa
--- /dev/null
+++ b/lib/preview/svg.php
@@ -0,0 +1,46 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+if (extension_loaded('imagick')) {
+
+ class SVG extends Provider {
+
+ public function getMimeType() {
+ return '/image\/svg\+xml/';
+ }
+
+ public function getThumbnail($path,$maxX,$maxY,$scalingup,$fileview) {
+ try{
+ $svg = new \Imagick();
+ $svg->setBackgroundColor(new \ImagickPixel('transparent'));
+
+ $content = stream_get_contents($fileview->fopen($path, 'r'));
+ if(substr($content, 0, 5) !== '<?xml') {
+ $content = '<?xml version="1.0" encoding="UTF-8" standalone="no"?>' . $content;
+ }
+
+ $svg->readImageBlob($content);
+ $svg->setImageFormat('png32');
+ } catch (\Exception $e) {
+ \OC_Log::write('core', $e->getmessage(), \OC_Log::ERROR);
+ return false;
+ }
+
+
+ //new image object
+ $image = new \OC_Image();
+ $image->loadFromData($svg);
+ //check if image object is valid
+ return $image->valid() ? $image : false;
+ }
+ }
+
+ \OC\Preview::registerProvider('OC\Preview\SVG');
+
+} \ No newline at end of file
diff --git a/lib/preview/txt.php b/lib/preview/txt.php
new file mode 100644
index 00000000000..a487330691e
--- /dev/null
+++ b/lib/preview/txt.php
@@ -0,0 +1,73 @@
+<?php
+/**
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+class TXT extends Provider {
+
+ public function getMimeType() {
+ return '/text\/.*/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ $content = $fileview->fopen($path, 'r');
+ $content = stream_get_contents($content);
+
+ //don't create previews of empty text files
+ if(trim($content) === '') {
+ return false;
+ }
+
+ $lines = preg_split("/\r\n|\n|\r/", $content);
+
+ $fontSize = 5; //5px
+ $lineSize = ceil($fontSize * 1.25);
+
+ $image = imagecreate($maxX, $maxY);
+ imagecolorallocate($image, 255, 255, 255);
+ $textColor = imagecolorallocate($image, 0, 0, 0);
+
+ foreach($lines as $index => $line) {
+ $index = $index + 1;
+
+ $x = (int) 1;
+ $y = (int) ($index * $lineSize) - $fontSize;
+
+ imagestring($image, 1, $x, $y, $line, $textColor);
+
+ if(($index * $lineSize) >= $maxY) {
+ break;
+ }
+ }
+
+ $image = new \OC_Image($image);
+
+ return $image->valid() ? $image : false;
+ }
+}
+
+\OC\Preview::registerProvider('OC\Preview\TXT');
+
+class PHP extends TXT {
+
+ public function getMimeType() {
+ return '/application\/x-php/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\PHP');
+
+class JavaScript extends TXT {
+
+ public function getMimeType() {
+ return '/application\/javascript/';
+ }
+
+}
+
+\OC\Preview::registerProvider('OC\Preview\JavaScript'); \ No newline at end of file
diff --git a/lib/preview/unknown.php b/lib/preview/unknown.php
new file mode 100644
index 00000000000..9e6cd68d401
--- /dev/null
+++ b/lib/preview/unknown.php
@@ -0,0 +1,27 @@
+<?php
+/**
+ * Copyright (c) 2013 Frank Karlitschek frank@owncloud.org
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OC\Preview;
+
+class Unknown extends Provider {
+
+ public function getMimeType() {
+ return '/.*/';
+ }
+
+ public function getThumbnail($path, $maxX, $maxY, $scalingup, $fileview) {
+ $mimetype = $fileview->getMimeType($path);
+
+ $path = \OC_Helper::mimetypeIcon($mimetype);
+ $path = \OC::$SERVERROOT . substr($path, strlen(\OC::$WEBROOT));
+
+ return new \OC_Image($path);
+ }
+}
+
+\OC\Preview::registerProvider('OC\Preview\Unknown'); \ No newline at end of file
diff --git a/lib/public/preview.php b/lib/public/preview.php
new file mode 100644
index 00000000000..7588347eccb
--- /dev/null
+++ b/lib/public/preview.php
@@ -0,0 +1,34 @@
+<?php
+/**
+ * Copyright (c) 2013 Frank Karlitschek frank@owncloud.org
+ * Copyright (c) 2013 Georg Ehrke georg@ownCloud.com
+ * This file is licensed under the Affero General Public License version 3 or
+ * later.
+ * See the COPYING-README file.
+ */
+namespace OCP;
+
+/**
+ * This class provides functions to render and show thumbnails and previews of files
+ */
+class Preview {
+
+ /**
+ * @brief return a preview of a file
+ * @param $file The path to the file where you want a thumbnail from
+ * @param $maxX The maximum X size of the thumbnail. It can be smaller depending on the shape of the image
+ * @param $maxY The maximum Y size of the thumbnail. It can be smaller depending on the shape of the image
+ * @param $scaleup Scale smaller images up to the thumbnail size or not. Might look ugly
+ * @return image
+ */
+ public static function show($file,$maxX=100,$maxY=75,$scaleup=false) {
+ return(\OC\Preview::show($file,$maxX,$maxY,$scaleup));
+ }
+
+
+
+ public static function isMimeSupported($mimetype='*') {
+ return \OC\Preview::isMimeSupported($mimetype);
+ }
+
+}
diff --git a/lib/public/share.php b/lib/public/share.php
index 7714837769d..fe996dbe266 100644
--- a/lib/public/share.php
+++ b/lib/public/share.php
@@ -209,7 +209,7 @@ class Share {
}
}
}
-
+
// let's get the parent for the next round
$meta = $cache->get((int)$source);
if($meta !== false) {
@@ -840,7 +840,11 @@ class Share {
// Get filesystem root to add it to the file target and remove from the
// file source, match file_source with the file cache
if ($itemType == 'file' || $itemType == 'folder') {
- $root = \OC\Files\Filesystem::getRoot();
+ if(!is_null($uidOwner)) {
+ $root = \OC\Files\Filesystem::getRoot();
+ } else {
+ $root = '';
+ }
$where = 'INNER JOIN `*PREFIX*filecache` ON `file_source` = `*PREFIX*filecache`.`fileid`';
if (!isset($item)) {
$where .= ' WHERE `file_target` IS NOT NULL';
@@ -1303,11 +1307,11 @@ class Share {
'run' => &$run,
'error' => &$error
));
-
+
if ($run === false) {
throw new \Exception($error);
}
-
+
if (isset($fileSource)) {
if ($parentFolder) {
if ($parentFolder === true) {
@@ -1398,11 +1402,11 @@ class Share {
'run' => &$run,
'error' => &$error
));
-
+
if ($run === false) {
throw new \Exception($error);
}
-
+
if (isset($fileSource)) {
if ($parentFolder) {
if ($parentFolder === true) {
diff --git a/lib/public/template.php b/lib/public/template.php
index ab1089c332d..3b1a4ed4906 100644
--- a/lib/public/template.php
+++ b/lib/public/template.php
@@ -54,6 +54,25 @@ function mimetype_icon( $mimetype ) {
return(\mimetype_icon( $mimetype ));
}
+/**
+ * @brief make preview_icon available as a simple function
+ * Returns the path to the preview of the image.
+ * @param $path path of file
+ * @returns link to the preview
+ */
+function preview_icon( $path ) {
+ return(\preview_icon( $path ));
+}
+
+/**
+ * @brief make publicpreview_icon available as a simple function
+ * Returns the path to the preview of the image.
+ * @param $path path of file
+ * @returns link to the preview
+ */
+function publicPreview_icon ( $path, $token ) {
+ return(\publicPreview_icon( $path, $token ));
+}
/**
* @brief make OC_Helper::humanFileSize available as a simple function
diff --git a/lib/template/functions.php b/lib/template/functions.php
index 717e197c1cb..501f8081bff 100644
--- a/lib/template/functions.php
+++ b/lib/template/functions.php
@@ -59,6 +59,22 @@ function mimetype_icon( $mimetype ) {
}
/**
+ * @brief make preview_icon available as a simple function
+ * Returns the path to the preview of the image.
+ * @param $path path of file
+ * @returns link to the preview
+ *
+ * For further information have a look at OC_Helper::previewIcon
+ */
+function preview_icon( $path ) {
+ return OC_Helper::previewIcon( $path );
+}
+
+function publicPreview_icon ( $path, $token ) {
+ return OC_Helper::publicPreviewIcon( $path, $token );
+}
+
+/**
* @brief make OC_Helper::humanFileSize available as a simple function
* @param int $bytes size in bytes
* @return string size as string
diff --git a/lib/util.php b/lib/util.php
index f343e783206..0777643a952 100755
--- a/lib/util.php
+++ b/lib/util.php
@@ -108,7 +108,7 @@ class OC_Util {
public static function getVersion() {
// hint: We only can count up. Reset minor/patchlevel when
// updating major/minor version number.
- return array(5, 80, 05);
+ return array(5, 80, 07);
}
/**