Image gets uploaded to Media but not with proper content type

I have been successfully uploading PDFs using similar code below but not sure why it does not work if I try to upload images they look like this

Here is my Python code

import requests,json

h = {
'X-Api-Version': '3',
'Authorization': 'Bearer ABC',
'Accept': 'application/json',
'Content-Type': 'application/json'
}

image_file=requests.get('https://upload.wikimedia.org/wikipedia/commons/c/c6/Kimi_Raikkonen_2006_test.jpg', 
                      stream=True).content

upload_requests = json.loads(requests.post("https://site-api.datocms.com/upload-requests", headers=h, data=json.dumps({
  "data": {
    "type": "upload_request",
    "attributes": {
      "filename": "Kimi_Raikkonen_2006_test.jpg",
    }
  }
})).text)

print(upload_requests)

requests.put(upload_requests['data']['attributes']['url'], files={'file': image_file}).text

final_upload_resp = requests.post("https://site-api.datocms.com/uploads", headers=h, data=json.dumps({
  "data": {
    "type": "upload",
    "attributes": {
      "path": upload_requests['data']['id'],
      "author": "Me",
      "copyright": "2020 DatoCMS",
      "default_field_metadata": {
        "en": {
          "alt": "Test",
          "title": "Test",
          "custom_data": {}
        }
      }
    }
  }
})).text

final_upload_resp = json.loads(final_upload_resp)
print(final_upload_resp)
if final_upload_resp['data']['type'] == "job":
    final_upload_resp = json.loads(requests.get("https://site-api.datocms.com/job-results/%s" % final_upload_resp['data']['id'], headers=h).text)

requests.get("https://site-api.datocms.com/job-results/upload_id/%s"%(final_upload_resp['data']['id']), headers=h).text

As I said, file gets uploaded to Media and correct size, but it does not have proper content type

hello @mohammadayub6565 and welcome to Community!

Are you sure that the image that you are uploading is not corrupted? Can you please share the picture here after you have downloaded?

@mat_jack1

This is real image url as also shown in my question

Here is the download url of the image that actually got to dato after I ran my code, I have tried other images as well, I get same results each time

@mohammadayub6565 sorry I’m not a Python expert, but looks like you are not downloading the image correctly with requests. I’m not sure why though :frowning:

If you are still stuck with this please get in touch, I might try to spend some more time on this tomorrow.

I should have also mentioned that I also tried to upload image file by reading directly from my computer

requests.put(upload_requests['data']['attributes']['url'], files={'file': open('image.jpg', 'rb')}).text

That did not work too, but at the same time, uploading PDF file works perfectly :frowning:

Hey @mohammadayub6565! Just found the issue!

Using requests.put() with the files parameter sends a multipart/form-data encoded request which is not what you should do. As the docs says:

Use the obtained URL to perform a PUT request directly to AWS, uploading the raw content of the file as the request body;

Here’s a corrected version of your script:

import requests,json

h = {
'X-Api-Version': '3',
'Authorization': 'Bearer API-TOKEN',
'Accept': 'application/json',
'Content-Type': 'application/json'
}

image_file=requests.get('https://upload.wikimedia.org/wikipedia/commons/c/c6/Kimi_Raikkonen_2006_test.jpg',
                      stream=True).content

upload_requests = json.loads(requests.post("https://site-api.datocms.com/upload-requests", headers=h, data=json.dumps({
  "data": {
    "type": "upload_request",
    "attributes": {
      "filename": "Kimi_Raikkonen_2006_test.jpg",
    }
  }
})).text)

print(upload_requests)

requests.put(upload_requests['data']['attributes']['url'], data=image_file).text

final_upload_resp = requests.post("https://site-api.datocms.com/uploads", headers=h, data=json.dumps({
  "data": {
    "type": "upload",
    "attributes": {
      "path": upload_requests['data']['id'],
      "author": "Me",
      "copyright": "2020 DatoCMS",
      "default_field_metadata": {
        "en": {
          "alt": "Test",
          "title": "Test",
          "custom_data": {}
        }
      }
    }
  }
})).text

final_upload_resp = json.loads(final_upload_resp)

print(final_upload_resp)

if final_upload_resp['data']['type'] == "job":
    while True:
      response = requests.get("https://site-api.datocms.com/job-results/%s" % final_upload_resp['data']['id'], headers=h)
      print(response)

      if response.status_code == 200:
          print(response.text)
          final_upload_resp = json.loads(response.text)
          upload = final_upload_resp['data']['attributes']['payload']['data']
          print(upload)
          break