-
-
Notifications
You must be signed in to change notification settings - Fork 78
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
TUS temporary file optimization (mv instead of read on same filesystem) #1690
Draft
JeffersonBledsoe
wants to merge
11
commits into
plone:main
Choose a base branch
from
pretagov:tus_tmp_file_rename
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Draft
Changes from 10 commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
d893353
Rename tus temporary file to temporary blob location instead of itera…
instification 31d5b0a
black/flake8 fixes
instification 36eee20
Use zodb rename_or_copy blob to handle final blob move
instification a5ae68f
Move the blob after validation to save time/memory. Move blob-move c…
instification 18e98bc
use storage adapter and put in test that shows validation reads file …
djay 833cbe6
fix pep8
djay c2ec9ec
format with black
djay a559fca
more black
djay 90bd5c4
zpretty
djay dabf6d9
fix lint
djay 0792e47
use mock
djay File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -13,6 +13,7 @@ parts = | |
sphinx-python | ||
deploy-to-heroku | ||
omelette | ||
vscode | ||
zpretty | ||
develop = . | ||
sources-dir = extras | ||
|
@@ -172,6 +173,14 @@ input = inline: | |
output = ${buildout:directory}/bin/zpretty-run | ||
mode = 755 | ||
|
||
[vscode] | ||
recipe = collective.recipe.vscode >= 0.1.8 | ||
eggs = | ||
Plone | ||
Pillow | ||
plone.app.debugtoolbar | ||
plone.restapi [test] | ||
|
||
[sources] | ||
plone.rest = git git://github.com/plone/plone.rest.git [email protected]:plone/plone.rest.git branch=master | ||
plone.schema = git git://github.com/plone/plone.schema.git [email protected]:plone/plone.schema.git branch=master | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -51,7 +51,6 @@ def _prepare_metadata(filename, content_type): | |
|
||
|
||
class TestTUS(unittest.TestCase): | ||
|
||
layer = PLONE_RESTAPI_DX_FUNCTIONAL_TESTING | ||
|
||
def setUp(self): | ||
|
@@ -395,6 +394,60 @@ def test_tus_can_upload_text_file(self): | |
) | ||
self.assertEqual(response.status_code, 204) | ||
|
||
def test_tus_can_upload_with_rereading(self): | ||
# if tmp dir is on the same filesystem then we shouldn't have delay caused by reading and writing large file | ||
|
||
import ZODB.blob | ||
|
||
old_open = ZODB.blob.Blob.open | ||
blob_read = 0 | ||
blob_write = 0 | ||
|
||
def count_open(self, mode="r"): | ||
nonlocal blob_read, blob_write | ||
blob_read += 1 if "r" in mode else 0 | ||
blob_write += 1 if "w" in mode else 0 | ||
return old_open(self, mode) | ||
|
||
ZODB.blob.Blob.open = count_open | ||
|
||
pdf_file_path = os.path.join(os.path.dirname(__file__), UPLOAD_PDF_FILENAME) | ||
pdf_file_size = os.path.getsize(pdf_file_path) | ||
metadata = _prepare_metadata(UPLOAD_PDF_FILENAME, UPLOAD_PDF_MIMETYPE) | ||
response = self.api_session.post( | ||
self.upload_url, | ||
headers={ | ||
"Tus-Resumable": "1.0.0", | ||
"Upload-Length": str(pdf_file_size), | ||
"Upload-Metadata": metadata, | ||
}, | ||
) | ||
self.assertEqual(response.status_code, 201) | ||
location = response.headers["Location"] | ||
|
||
# upload the data with PATCH | ||
with open(pdf_file_path, "rb") as pdf_file: | ||
response = self.api_session.patch( | ||
location, | ||
headers={ | ||
"Content-Type": "application/offset+octet-stream", | ||
"Upload-Offset": "0", | ||
"Tus-Resumable": "1.0.0", | ||
}, | ||
data=pdf_file, | ||
) | ||
self.assertEqual(response.status_code, 204) | ||
|
||
self.assertEqual( | ||
blob_write, | ||
1, | ||
"Slow write to blob instead of os rename. Should be only 1 on init", | ||
) | ||
self.assertEqual(blob_read, 0, "Validation is reading the whole blob in memory") | ||
# TODO: would be better test to patch file read instead and ensure its not called? | ||
|
||
ZODB.blob.Blob.open = old_open | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This should go in a finally block in case there's an error during the test. |
||
|
||
def test_tus_can_replace_pdf_file(self): | ||
# Create a test file | ||
self.file = api.content.create( | ||
|
@@ -568,7 +621,6 @@ class CORSTestPolicy(CORSPolicy): | |
|
||
|
||
class TestTUSUploadWithCORS(unittest.TestCase): | ||
|
||
layer = PLONE_RESTAPI_DX_FUNCTIONAL_TESTING | ||
|
||
def setUp(self): | ||
|
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@djay Now that I'm looking at things more carefully, I'm wondering if this special storage adapter is really needed.
Previously, an open file was passed into the NamedBlobFile constructor. This should end up using the FileDescriptorStorable which uses blob.consumeFile, which is already using rename_or_copy_blob.