Permalink
Browse files

Fix partial upload

Append md5 to nodesDiff after upload to avoid an additional request.
  • Loading branch information...
1 parent 8d27284 commit 75404652536254c0090e7fd6036a15fc5928bfb7 @cdujeu cdujeu committed Jun 27, 2016
@@ -479,6 +479,7 @@ public function uploadAction(ServerRequestInterface &$request, ResponseInterface
$partialTargetSize = intval($httpVars["partial_target_bytesize"]);
if(!isSet($httpVars["appendto_urlencoded_part"])){
$userfile_name .= ".dlpart";
+ $targetUrl = $destination."/".$userfile_name;
}
}
@@ -495,6 +496,9 @@ public function uploadAction(ServerRequestInterface &$request, ResponseInterface
$this->logDebug("AppendTo FILE".$appendTo);
$already_existed = $this->appendUploadedData($destination, $userfile_name, $appendTo);
$userfile_name = $appendTo;
+ $targetAppended = new AJXP_Node($destination."/".$userfile_name);
+ clearstatcache(true, $targetAppended->getUrl());
+ $targetAppended->loadNodeInfo(true);
if($partialUpload && $partialTargetSize == filesize($destination."/".$userfile_name)){
// This was the last part. We can now rename to the original name.
if(is_file($destination."/".$originalAppendTo)){
@@ -508,6 +512,7 @@ public function uploadAction(ServerRequestInterface &$request, ResponseInterface
$partialUpload = false;
// Send a create event!
$already_existed = false;
+ $lastPartAppended = true;
}
}
@@ -521,20 +526,24 @@ public function uploadAction(ServerRequestInterface &$request, ResponseInterface
if($partialUpload){
$this->logDebug("Return Partial Upload: SUCESS but no event yet");
+ // Make sure to clear cache for parent
+ $createdNode->getParent()->loadNodeInfo(true);
if(isSet($already_existed) && $already_existed === true){
$this->writeUploadSuccess($request, ["PARTIAL_NODE" => $createdNode]);
- return;
+ }else if(isSet($lastPartAppended)){
+ $createdNode->loadHash();
+ $this->writeUploadSuccess($request, ["CREATED_NODE" => $createdNode]);
}
} else {
$this->logDebug("Return success");
+ $createdNode->loadHash();
if(isSet($already_existed) && $already_existed === true){
$this->writeUploadSuccess($request, ["UPDATED_NODE" => $createdNode]);
- return;
}else{
$this->writeUploadSuccess($request, ["CREATED_NODE" => $createdNode]);
- return;
}
}
+ return;
}catch(\Exception $e){
$errorCode = $e->getCode();
@@ -24,6 +24,7 @@
use Pydio\Access\Core\AbstractAccessDriver;
use Pydio\Access\Core\MetaStreamWrapper;
+use Pydio\Access\Meta\Core\IFileHasher;
use Pydio\Core\Model\Context;
use Pydio\Core\Model\ContextInterface;
use Pydio\Core\Model\ContextProviderInterface;
@@ -86,6 +87,10 @@ class AJXP_Node implements \JsonSerializable, ContextProviderInterface
* @var IMetaStoreProvider
*/
private $_metaStore;
+ /**
+ * @var IFileHasher
+ */
+ private $_fileHasher;
/**
* @var String
@@ -219,6 +224,23 @@ protected function getMetaStore()
}
/**
+ * @return IFileHasher
+ */
+ protected function getFileHasher()
+ {
+ if (!isSet($this->_fileHasher)) {
+ $this->getDriver();
+ $hashers = PluginsService::getInstance($this->getContext())->getActivePluginsForType("meta");
+ if(is_array($hashers) && array_key_exists("filehasher", $hashers)){
+ $this->_fileHasher = $hashers["filehasher"];
+ }else{
+ $this->_fileHasher = false;
+ }
+ }
+ return $this->_fileHasher;
+ }
+
+ /**
* Check if there is currently a MetaStore provider set
* @return bool
*/
@@ -346,6 +368,15 @@ public function getParent(){
}
+
+ /**
+ * Search for metadata in parents, recursively
+ * @param $nameSpace
+ * @param bool $private
+ * @param int $scope
+ * @param bool $indexable
+ * @return array|bool
+ */
public function findMetadataInParent($nameSpace, $private = false, $scope=AJXP_METADATA_SCOPE_REPOSITORY, $indexable = false){
$metadata = false;
@@ -410,6 +441,11 @@ public function collectMetadatasInParents($nameSpaces, $private = false, $scope=
}
+ /**
+ * @param $nameSpace
+ * @param $userScope
+ * @return array
+ */
public function collectRepositoryMetadatasInChildren($nameSpace, $userScope){
$result = [];
$metaStore = $this->getMetaStore();
@@ -420,6 +456,15 @@ public function collectRepositoryMetadatasInChildren($nameSpace, $userScope){
}
/**
+ * @return void
+ */
+ public function loadHash(){
+ if($this->getFileHasher() !== false){
+ $this->getFileHasher()->getFileHash($this);
+ }
+ }
+
+ /**
* @param bool $boolean Leaf or Collection?
* @return void
*/
@@ -501,7 +546,7 @@ public function loadNodeInfo($forceRefresh = false, $contextNode = false, $detai
}
}
Controller::applyHook("node.info.start", [&$this, $contextNode, $details, $forceRefresh]);
- if($this->nodeInfoLoaded && !$forceRefresh){
+ if($this->nodeInfoLoaded && !$forceRefresh && isSet($this->_metadata["ajxp_mime"])){
Controller::applyHook("node.info.nocache", [&$this, $contextNode, $details, $forceRefresh]);
return;
}
@@ -0,0 +1,39 @@
+<?php
+/*
+ * Copyright 2007-2016 Abstrium <contact (at) pydio.com>
+ * This file is part of Pydio.
+ *
+ * Pydio is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Pydio is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with Pydio. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * The latest code can be found at <https://pydio.com/>.
+ */
+namespace Pydio\Access\Meta\Core;
+
+use Pydio\Access\Core\Model\AJXP_Node;
+
+defined('AJXP_EXEC') or die('Access not allowed');
+
+/**
+ * Interface IFileHasher
+ * @package Pydio\Access\Meta\Core
+ */
+interface IFileHasher
+{
+ /**
+ * Get a hash and add it to the current node as metadata
+ * @param AJXP_Node $node
+ * @return string md5
+ */
+ public function getFileHash(AJXP_Node $node);
+}
@@ -26,6 +26,7 @@
use Pydio\Access\Core\MetaStreamWrapper;
use Pydio\Access\Core\Model\AJXP_Node;
use Pydio\Access\Core\Model\UserSelection;
+use Pydio\Access\Meta\Core\IFileHasher;
use Pydio\Core\Exception\PydioException;
use Pydio\Core\Model\ContextInterface;
use Pydio\Core\Services\LocalCache;
@@ -44,7 +45,7 @@
* Generates and caches and md5 hash of each file
* @package Pydio\Access\Meta\Hash
*/
-class FileHasher extends AbstractMetaSource
+class FileHasher extends AbstractMetaSource implements IFileHasher
{
const METADATA_HASH_NAMESPACE = "file_hahser";
/**
@@ -159,6 +160,7 @@ public function statAction(ServerRequestInterface $requestInterface, ResponseInt
if ($length + $offset > $fullSize || $length < 0) $length = $fullSize - $offset;
$hash = $this->getPartialHash($node, $offset, $length);
}else{
+ $selection->getUniqueNode()->loadNodeInfo(true);
$hash = $this->getFileHash($selection->getUniqueNode());
}
}
@@ -175,8 +177,12 @@ public function statAction(ServerRequestInterface $requestInterface, ResponseInt
if(!$stat || !is_readable($node->getUrl())) {
$stat = new \stdClass();
} else {
- if(!is_dir($node->getUrl())) $hash = $this->getFileHash($node);
- else $hash = 'directory';
+ if(!is_dir($node->getUrl())) {
+ $node->loadNodeInfo(true);
+ $hash = $this->getFileHash($node);
+ } else {
+ $hash = 'directory';
+ }
$stat[13] = $stat["hash"] = $hash;
}
$responseData[TextEncoder::toUTF8($path)] = $stat;
@@ -248,10 +254,9 @@ public function switchActions($actionName, $httpVars, $fileVars, ContextInterfac
* @param \Pydio\Access\Core\Model\AJXP_Node $node
* @return String md5
*/
- public function getFileHash($node)
+ public function getFileHash(AJXP_Node $node)
{
// Make sure that node is really there
- $node->loadNodeInfo(true);
if ($node->isLeaf()) {
$md5 = null;
if ($this->metaStore != false) {

0 comments on commit 7540465

Please sign in to comment.