105

I am currently uploading images pasted from the clipboard with the following code:

// Turns out getAsFile will return a blob, not a file
var blob = event.clipboardData.items[0].getAsFile(), 
    form = new FormData(),
    request = new XMLHttpRequest();
form.append("blob",blob);
request.open(
            "POST",
            "/upload",
            true
        );
request.send(form);

Turns out the uploaded form field with receive a name similar to this: Blob157fce71535b4f93ba92ac6053d81e3a

Is there any way to set this or receive this file name client side, without doing any server side communication?

jontro
  • 10,241
  • 6
  • 46
  • 71

8 Answers8

188

For Chrome, Safari and Firefox, just use this:

form.append("blob", blob, filename);

(see MDN documentation)

Derzu
  • 7,011
  • 3
  • 57
  • 60
Chiguireitor
  • 3,186
  • 1
  • 20
  • 26
  • Where did you notice about this??? This is great! Is there any link regarding chrome versions' support of this? – Dmitrii Sorin Apr 29 '12 at 11:24
  • BTW, this is in the spec: http://www.w3.org/TR/XMLHttpRequest2/#interface-formdata – Dmitrii Sorin Apr 29 '12 at 11:27
  • 1
    Also, i'm working on the firefox bug to fix this issue, i have already fixed it but i have some "style issues" https://bugzilla.mozilla.org/show_bug.cgi?id=690659 (i'm currently out of time to fix this patch, so if anyone wants to pick it up i'm more than happy with it) – Chiguireitor Apr 30 '12 at 12:52
  • @Chiguireitor its still not fixed? – Will Dec 15 '12 at 10:55
  • AFAIK not, my time has been lately a very scarce resource. As i said earlier, anyone who wants to pick up the slack is welcome. – Chiguireitor Jan 14 '13 at 19:20
  • 3
    Here is the "compatibility table" from MDN. Notice that as of this post, append with filename has shaky support on all browsers except Chrome and FF: https://developer.mozilla.org/en-US/docs/Web/API/FormData#compat-desktop – Adam Sep 06 '13 at 19:02
48

Adding this here as it doesn't seem to be here.

Aside from the excellent solution of form.append("blob",blob, filename); you can also turn the blob into a File instance:

var blob = new Blob([JSON.stringify([0,1,2])], {type : 'application/json'});
var fileOfBlob = new File([blob], 'aFileName.json');
form.append("upload", fileOfBlob);
Noitidart
  • 35,443
  • 37
  • 154
  • 323
  • 1
    Problem is that you get the file/blob from the clipboard. What you're describing is related to this question: http://stackoverflow.com/questions/27251953/how-to-create-file-object-from-blob – jontro Feb 04 '16 at 13:56
  • 9
    doesn't work on IE cause it still doesn't support File constructor. – Mahib Mar 23 '17 at 19:54
  • @Mahib [MDN's documentation on the `File` constructor](https://developer.mozilla.org/en-US/docs/Web/API/File/File) suggests that it's supported from IE10 and up. – Robert K. Bell May 15 '17 at 03:08
  • 2
    @RobertK.Bell, I practically checked on Edge and it didn't work :(, then I had to change back to blob constructor. – Mahib May 15 '17 at 16:32
  • 1
    @Mahib You're right ― [issue #9551546 on Edge's tracker](https://developer.microsoft.com/en-us/microsoft-edge/platform/issues/9551546/) `File` constructor throws `Function Expected` exception – Robert K. Bell May 23 '17 at 05:13
  • 1
    @Mahib IE doesn't like to support stuff very much, so we have dropped support for it post-2022. – Syed M. Sannan Mar 14 '23 at 20:10
4

Since you're getting the data pasted to clipboard, there is no reliable way of knowing the origin of the file and its properties (including name).

Your best bet is to come up with a file naming scheme of your own and send along with the blob.

form.append("filename",getFileName());
form.append("blob",blob);

function getFileName() {
 // logic to generate file names
}
Mrchief
  • 75,126
  • 20
  • 142
  • 189
  • 1
    The question does not ask for the original filename. This answer is completely off target. – Niels Abildgaard Jun 16 '14 at 13:44
  • 3
    @NielsAbildgaard: Really? It is asking about assigning a filename, and doesn't the original filename qualify as a valid filename? – Mrchief Jun 16 '14 at 13:55
  • 1
    The answer does not answer the original question (other than "here's an alternative") and provides an answer to something that is not asked, and, frankly, off-topic. – Niels Abildgaard Jun 16 '14 at 14:00
2

That name looks derived from an object URL GUID. Do the following to get the object URL that the name was derived from.

var URL = self.URL || self.webkitURL || self;
var object_url = URL.createObjectURL(blob);
URL.revokeObjectURL(object_url);

object_url will be formatted as blob:{origin}{GUID} in Google Chrome and moz-filedata:{GUID} in Firefox. An origin is the protocol+host+non-standard port for the protocol. For example, blob:http://stackoverflow.com/e7bc644d-d174-4d5e-b85d-beeb89c17743 or blob:http://[::1]:123/15111656-e46c-411d-a697-a09d23ec9a99. You probably want to extract the GUID and strip any dashes.

Eli Grey
  • 35,104
  • 14
  • 75
  • 93
1

Haven't tested it, but that should alert the blobs data url:

var blob = event.clipboardData.items[0].getAsFile(), 
    form = new FormData(),
    request = new XMLHttpRequest();

var reader = new FileReader();
reader.onload = function(event) {
  alert(event.target.result); // <-- data url
};
reader.readAsDataURL(blob);
JochenJung
  • 7,183
  • 12
  • 64
  • 113
  • This will alert blob as a data url indeed. What I want to receive/set is the file name attached to the form field when doing a form post upload. – jontro Jul 18 '11 at 09:08
  • Then I don't know of a way Without server side communication. – JochenJung Jul 18 '11 at 10:36
0

It really depends on how the server on the other side is configured and with what modules for how it handles a blob post. You can try putting the desired name in the path for your post.

request.open(
    "POST",
    "/upload/myname.bmp",
    true
);
mbarnes
  • 455
  • 2
  • 7
0

Are you using Google App Engine? You could use cookies (made with JavaScript) to maintain a relationship between filenames and the name received from the server.

Bogdacutu
  • 763
  • 7
  • 24
0

When you are using Google Chrome you can use/abuse the Google Filesystem API for this. Here you can create a file with a specified name and write the content of a blob to it. Then you can return the result to the user.

I have not found a good way for Firefox yet; probably a small piece of Flash like downloadify is required to name a blob.

IE10 has a msSaveBlob() function in the BlobBuilder.

Maybe this is more for downloading a blob, but it is related.

Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278
Gijs Molenaar
  • 405
  • 1
  • 3
  • 9