Open paul-freeman opened 5 years ago
I will also add that this issue can be summarized as an attempt to complete the example listed in the documentation for Http.Body.bytesBody
.
For example, you could create an
archive.zip
file and send it along like this
Afterwards, sample code is provided, but makes no mention as to how those bytes come to be named archive.zip
(presumably through server-side code).
I'm having trouble understanding the thing you want to do, so I am going to try to say what I understand.
There are a couple ways to create Part
values right now:
File
into a Part
with filePart
Bytes
into a Part
with bytesPart
I believe the difference in the HTTP request produced is whether a file name is associated with the part in the body. You want to send a file you made in browser though, so it is annoying that there is not an easy way to create a part with custom bytes and a custom file name.
Is that correct?
If so, I think the path would be to add functions to the File
module for creating files locally. Something like File.fromBytes : String -> String -> Bytes -> File
and an equivalent one for fromString
. I'll need to get back into the whole File
API in JS to see exactly what information is needed to make this reliable, but that's the direction that jumps out to me.
Note: I'm not sure when HTTP and files will get another batch of work, so I recommend using ports in the meantime.
You want to send a file you made in browser though, so it is annoying that there is not an easy way to create a part with custom bytes and a custom file name.
Absolutely correct.
Something like
File.fromBytes : String -> String -> Bytes -> File
and an equivalent one forfromString
.
Yes. I think this would be ideal and simple to understand.
This SO post seems to indicate that a Blob
and a File
are nearly identical, suggesting this (slightly edited by me) JS transformation:
function blobToFile(theBlob, fileName){
theBlob.lastModified = new Date();
theBlob.name = fileName;
return theBlob;
}
Basically, you just add the filename and date. Technically, the definition of File
lists 4 fields not inherited from Blob
, but 1 is deprecated and 1 is non-standardized. I think the change would be straightforward.
More than happy to use ports in the meantime. And would be happy to submit a PR if requested. :)
As background, I'm working for a decentralized messaging app startup Sylo. The browser version of our app is being written in Elm (we've got about 10K LOC) and will be released soon. My need for a resolution to this issue stems from my desire to give back to the Elm community. We use many Web RPC services, and if I can turn some of them into Elm packages, I would enjoy being able to do that for everyone. Specifically blocked are a number of improvements to the paul-freeman/elm-ipfs
package.
The https://github.com/elm/file package provides methods for downloading strings and bytes as files, but similar methods are not included with this package. This makes it difficult for an application to generate files that can be posted with
Http.multipartBody
.Expected behavior would be to shortcut these (UX-poor) steps:
File.Download.bytes
(have user download file)File.Select.file
(have user select the same file)Http.filePart
(create a file part)Http.post
(post to server)The net result of the above steps is essentially nothing more than attaching a
name
to aBlob
, resulting in aFile
. Similar steps would be used for string data.One possible solution might be to add a function:
bytesPartToFilePart : String -> Part -> Part
to explicitly name a bytes blob.A second solution might be to add functions to go directly from strings and bytes to file bodies.
I am proposing this change as I feel it is a relatively simple change that will open up a large variety of HTTP-based storage options for future Elm applications. I am personally exploring decentralized application file storage via IPFS and have hit a few walls from not having this feature.