0

I am attempting to send some binary data from a client via a blob to a django rest server, but the content of the received file ends up being "{}" independently of the content of the blob. I do not want to upload using base64 encoding.

sample client code:

    fetch("myserver/upload/file", {
        headers: {
            'Authorization': 'Token mytoken',
            'Content-Disposition': 'attachment; filename="filename.dat"'
        },
        method: "POST",
        body: new Blob(Array.from(Array(10000).keys()))
    ); 

On the server side I have a view class:


    from rest_framework import generics
    from rest_framework.parsers import FileUploadParser
    from rest_framework.response import Response

    class MyView(generics.GenericAPIView):
        parser_classes = (FileUploadParser,)

        def post(self, request):
            f = request.data.get('file')

            # some processing of file...

            return Response(
                {"response_info_key": "response_info_value"},
                status = 201
            )

What I observe independently of whether I send the post using jquery, fetch or xhr, and independently of blob content, what is received on server side is a file object whose only content is the two characters "{" and "}". I am required to add the Content-Disposition header, but not confident that this is the form it should have.

If I on the other hand set a "binary" body using Postman and the same headers, and specify file, the server successfully receives the file. How should I correct my POST request to make it work in a Javascript client?

Python version: 2.7.6

Django==1.11

requests==2.22.0

djangorestframework==3.6.2

EDIT: It seems like request header has 'HTTP_CONTENT_LENGTH': 2 on the server side, while the CONTENT-LENGTH on client side of the request is ~10^4

2 Answers 2

1

You can send the binary blob using FormData without it being modified.

const formData = new FormData();
formData.append('content', new Blob(Array.from(Array(10000).keys())));

fetch("myserver/upload/file", {
  headers: {
    'Authorization': 'Token mytoken',
    'Content-Disposition': 'attachment; filename="filename.dat"'
  },
  method: "POST",
  body: formData
); 
Sign up to request clarification or add additional context in comments.

1 Comment

When I try this, I the content-type changes to 'multipart/form-data; boundary=----WebKitFormBoundary8npSGzGOP99U6W2N', but otherwise the result is the same. When combined with changing "FileUploadParser" with "MultiPartParser", then request.data is just an empty querydict. Any ideas?
1

I think data from the frontend should be send in data not in body and the data you are expecting should look something like this:

data = {
    "file": new Blob(Array.from(Array(10000).keys()))
}

Now you can send the about data as

body: JSON.stringify(data), // data can be string or {object}!

7 Comments

fetch does not seem to have a data field. Do you have any documentation for this?
Yes fetch doesn't have data, you need to send data in the body itself, Read developer.mozilla.org/en-US/docs/Web/API/Fetch_API/Using_Fetch
If i set body: {data: {"file": new Blob(Array.from(Array(10000).keys()))}}, then on the server-side the content changes to the string "[object Object]".
Send data as: body: JSON.stringify(data), // data can be string` or {object}!`, Please go through the shared documentation.
This way, all i get is the string {"data":{"file":{}}}, which i interpret as JSON.stringify is not intended for binary data. I have read the documentation, and what you are referring to seems to be how to use fetch to post JSON-data?
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.