Don't load already uploaded files into memory - #756
Conversation
fec3668 to
5499d08
Compare
…y and then into temp files
5499d08 to
45c13b3
Compare
6535835 to
9a46972
Compare
9a46972 to
a0e2175
Compare
|
Marking this as ready for review as it works as intended for post creation; probably worth doing the same for post updates |
|
Thanks, this is an important issue. I don't like hardcoding You identified an issue with
Your code addresses steps 1 and 2 only in the case of "post update with a main content temp token". The writing of temporary files in We still read out the full contents of large uploads into memory when uploading a file directly (e.g. when creating a temp file token). szurubooru/server/szurubooru/rest/app.py Lines 43 to 51 in 0a0e5fc Instead, we can use form[key].file to get a streamed file handle.I think I also identified a potential bug with this code, where duplicate keys will result in weird behavior and likely an exception deeper in szurubooru:
Tangent: The Some functions would have to be updated to work with file handles.
I previously wrote an in-depth review and ran into unfortunate memory corruption that crashed my PC and it got lost... Sorry if I forgot to include some part of my reasoning here. |
I think we should keep the current behavior just like you did. Stale files will automatically get removed. I guess it kind of sucks for non-CoW filesystems though. |
Agree, in that moment I couldn't find a clean way to do this while maintaining backwards compatibility. After reading your comment I think we might implement a
The main problem I have with this is potentially breaking external scripts (mainly thinking about certain extensions I made to
I don't believe this would be much of a problem, as this is only run once on upload and even on large public boards I have rarely seen many postings per minute; I guess the flow most effected by this would be mass-uploading. If downsizing images doesn't severely impair signature quality/duplicates individuation I'm definitely on board with this, but I'd much rather make it a server-side config option tbh.
If this is the only place the cgi module is used I'll gladly remove it to oblivion, otherwise I think this definitely needs to be addressed but deserves its own PR.
I'll put down a quick top-down todo list with this as its base, if you agree with it I'll go ahead and put it in the original post to keep track of it
I'd love to jump on this ASAP but I have just nuked my server by moving the main drive to a different mobo and I can't boot it rn, unless I get it running in the next hour and a half I won't be able to start working on this until tomorrow afternoon (my time). |
|
Here I could just return the result of szurubooru/server/szurubooru/func/net.py Lines 40 to 50 in 0a0e5fc |
I now see a major problem with this approach: how do we read the streams twice? Currently, |
The current methods for post creation/update work using the full
contentas a byte array. When working with large files, such as videos, this can be a problem, as the data ends up being duplicated in a few occasions.The most absurd one is having to create a temporary file for use with ffmpeg, when the original file could have been used all along without even loading it into the python process' memory.
This is a draft that addresses this issue by adding to those methods a new optional parameter,
content_file, which is used ifcontentisNoneor empty. The optimizations are as follows:Methods that need to access the actual contents, such as
mime.get_mime_type, are implemented in a way that severely limits the total data being read (20 bytes).To efficiently implement
util.get_md5andutil.get_sha1, I have introducedutil.get_checksums_from_file, which loads 2M at a time to update both the md5 and sha1 hashes.If
content_fileis set andcontentisNoneor empty,__content_fileis set rather than__content, andshutil.copyfileis used to copy the original file into the correct data location. Another improvement here could have been usingos.rename, but I was not sure I could operate under the assumption temp files obtained via API upload are always meant to be used only once. I'll gladly take suggestions on this one.The parameter ordering for
posts.create_postis quite weird, but I decided against breaking compatibility with the older signature rather than updating it everywhere as I'm not really sure if there are others who have made external scripts using it like me.I'm open to any comments or suggestions, especially please tell me if you have a better name for
_execute_implas I'm not really a fan of this naming convention but the only other name I could think of in that moment was_execute2.