Can't Move DriveItem in Mocrosoft Graph - python-requests

I am using Python to download PDF files from OneDrive to a local folder, and also moving the files to a different folder in OneDrive after they have been downloaded.
I am able to download the files from OneDrive to a local folder, however, I get a 400 response when trying to move (PATCH) the files to another OneDrive Folder.
Here is my successful code to download the files:
download_url = 'https://graph.microsoft.com/v1.0/me/drive/items/{item-id}/content'
headers = {'Authorization': 'Bearer ' + json_response['access_token']}
download_url_data = requests.get(download_url, headers=headers)
with open('/Users/Name/Folder/file_name, 'wb') as f:
f.write(download_url_data.content)
Here is my unsuccessful PATCH request to move the files:
move_url = 'https://graph.microsoft.com/v1.0/me/drive/items/{item-id}
move_headers = {'Authorization': 'Bearer ' + json_response['access_token'],
'Content-Type' : 'application/json'}
move_body = {'parentReference' : {'id' : '01EV3NG2F6Y2GOVW7775BZO354PUSELRRZ'}}
move_file = requests.patch(move_url, headers=move_headers, data=move_body)
return move_file.status_code
I have followed the documentation here https://learn.microsoft.com/en-us/graph/api/driveitem-move?view=graph-rest-1.0&tabs=http and I have tried different parentReference id's, but no luck.
Please help! Cheers.

What is the response you're getting (the actual content beside the 400 status code)?
I believe that requests.patch should receive it's data as a string, not a dictionary (json).
Try:
move_file = requests.patch(move_url, headers=move_headers, data=json.dumps(move_body))
And of course don't forget to import json

Related

Passing files in POST using Requests in Python

I'm getting below error when making a requests call post method
{'detail': [{'loc': ['body', 'files'], 'msg': 'field required', 'type': 'value_error.missing'}]}
I tried
response = requests.post("url",headers={mytoken},params=p,files=files)
files = { "file 1": open("sample.pdf",'rb'), "file 2":open("sample11.pdf",'rb')}
I want to get 200 status but I'm getting 422 validation error. Any Idea Why? Its for API Testing purpose, Im new to this I've been debugging this for whole day but still couldn't figure out.
It is not clear from the question what kind of a request the server is expecting. Also, its not clear the exact code snippet you are using too.
From the question, the snippet looks like as follows,
response = requests.post("url",headers={mytoken},params=p,files=files)
files = { "file 1": open("sample.pdf",'rb'), "file 2":open("sample11.pdf",'rb')}
if so, that means you are reading files after you send the request, may be thats why the server complained about missing files field.
See the below example on how you can send two files to an endpoint expecting files.
import requests
import logging
logger = logging.getLogger(__name__)
post_url = "https://exampledomain.local/upload"
file1 = open("sample1.pdf", "rb")
file2 = open("sample2.pdf", "rb")
files = {"file1": file1, "file2": file2}
headers = {"Authorization": "Bearer <your_token_here>"}
params = {"file_type": "pdf"}
response = requests.post(post_url, files=files, headers=headers, params=params)
file1.close()
file2.close()
logger.debug(response.text)

Receiving <Fault -32700: 'parse error. not well formed'> when trying to upload video to WordPress using xmlrpc.client

Pretty much the title, attaching the python code below.
I'm trying to download files from a specific source and upload them to a WordPress site.
Photos work great, and videos return the following message on wp.call(UploadFile(data)):
<Fault -32700: 'parse error. not well formed'>
Tried using different methods for encoding to base64, reading Wordpress_xmlrpc documentation, nothing.
It's worth mentioning that this method did work on the "Demo" site, and now on once we moved to the "real" site it returns this error.
Any ideas?
def UploadPicture(PathOfFile, Type):
wp = Client(url ,user, password)
filename = PathOfFile #pathofvideo
#Setup
if Type == "jpg":
data = {
'name': 'picture.jpg',
'type': 'image/jpeg', # mimetype
}
if Type == "mp4":
data = {
'name': 'clip.mp4',
'type': 'video/mp4', # mimetype
}
# read the binary file and let the XMLRPC library encode it into base64
with open(filename, 'rb') as img:
data['bits'] = xmlrpc_client.Binary(img.read())
#upload and return ID
response = wp.call(media.UploadFile(data))
attachment_id = response['id']
return(attachment_id)

Download a static file with strict name via Nginx [duplicate]

I'm writing a web application that, among other things, allows users to upload files to my server. In order to prevent name clashes and to organize the files, I rename them once they are put on my server. By keeping track of the original file name I can communicate with the file's owner without them ever knowing I changed the file name on the back end. That is, until they go do download the file. In that case they're prompted to download a file with a unfamiliar name.
My question is, is there any way to specify the name of a file to be downloaded using just HTML? So a user uploads a file named 'abc.txt' and I rename it to 'xyz.txt', but when they download it I want the browser to save the file as 'abc.txt' by default. If this isn't possible with just HTML, is there any way to do it?
When they click a button to download the file, you can add the HTML5 attribute download where you can set the default filename.
That's what I did, when I created a xlsx file and the browser want to save it as zip file.
Download
Download Export
Can't find a way in HTML. I think you'll need a server-side script which will output a content-disposition header. In php this is done like this:
header('Content-Disposition: attachment; filename="downloaded.pdf"');
if you wish to provide a default filename, but not automatic download, this seems to work.
header('Content-Disposition: inline; filename="filetodownload.jpg"');
In fact, it is the server that is directly serving your files, so you have no way to interact with it from HTML, as HTML is not involved at all.
just need to use HTML5 a tag download attribute
codepen live demo
https://codepen.io/xgqfrms/full/GyEGzG/
my screen shortcut.
update answer
whether a file is downloadable depends on the server's response config, such as Content-Type, Content-Disposition;
download file's extensions are optional, depending on the server's config, too.
'Content-Type': 'application/octet-stream',
// it means unknown binary file,
// browsers usually don't execute it, or even ask if it should be executed.
'Content-Disposition': `attachment; filename=server_filename.filetype`,
// if the header specifies a filename,
// it takes priority over a filename specified in the download attribute.
download blob url file
function generatorBlobVideo(url, type, dom, link) {
var xhr = new XMLHttpRequest();
xhr.open('GET', url);
xhr.responseType = 'arraybuffer';
xhr.onload = function(res) {
// console.log('res =', res);
var blob = new Blob(
[xhr.response],
{'type' : type},
);
// create blob url
var urlBlob = URL.createObjectURL(blob);
dom.src = urlBlob;
// download file using `a` tag
link.href = urlBlob;
};
xhr.send();
}
(function() {
var type = 'image/png';
var url = 'https://cdn.xgqfrms.xyz/logo/icon.png';
var dom = document.querySelector('#img');
var link = document.querySelector('#img-link');
generatorBlobVideo(url, type, dom, link);
})();
https://cdn.xgqfrms.xyz/HTML5/Blob/index.html
refs
https://developer.mozilla.org/en-US/docs/Web/HTML/Element/a#download
https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Disposition
https://developer.mozilla.org/en-US/docs/Web/HTTP/Basics_of_HTTP/MIME_types#important_mime_types_for_web_developers
Sometimes #Mephiztopheles answer won't work on blob storages and some browsers.
For this you need to use a custom function to convert the file to blob and download it
const coverntFiletoBlobAndDownload = async (file, name) => {
const blob = await fetch(file).then(r => r.blob())
const url = URL.createObjectURL(blob)
const a = document.createElement('a')
a.style.display = 'none'
a.href = url
a.download = name // add custom extension here
document.body.appendChild(a)
a.click()
window.URL.revokeObjectURL(url)
}
Same code as #Hillkim Henry but with a.remove() improvement
This forces the document to remove the a tag from the body and avoid multiple elements
const coverntFiletoBlobAndDownload = async (file, name) => {
const blob = await fetch(file).then(r => r.blob())
const url = URL.createObjectURL(blob)
const a = document.createElement('a')
a.style.display = 'none'
a.href = url
a.download = name // add custom extension here
document.body.appendChild(a)
a.click()
window.URL.revokeObjectURL(url)
// Remove "a" tag from the body
a.remove()
}
Well, #Palantir's answer is, for me, the most correct way!
If you plan to use that with multiple files, then i suggest you to use (or make one) PHP Download Manager.
BUT, if you want to make that to one or two files, I will suggest you the mod_rewrite option:
You have to create or edit your .htaccess file on htdocs folder and add this:
RewriteEngine on
RewriteRule ^abc\.txt$ xyz.txt
With this code, users will download xyz.txt data with the name abc.txt
NOTE: Verify if you have already the "RewriteEngine on " on your file, if yes, add only the second for each file you wish to redirect.
Good Luck ;)
(Sorry for my english)

Wordpress says, "rest_upload_sideload_error" for a recognized type in an image upload from Google Apps Script. Why?

Context: uploading images to WordPress.
I've been digging around on this for a while. There are lots of StackOverflow postings about the issue, including this one from which I have derived the code below.
function test3() {
const png = DriveApp.getFileById('id of a png file');
const parm = {};
parm.method = "post";
parm.headers = {
"Authorization": "Basic " + Utilities.base64Encode('user' + ':' + 'application password'),
"Content-Disposition": "attachment; filename=" + "name of file.png",
"Content-Type": "image/png",
"Accept": "application/json",
"cache-control": "no-cache"
};
parm.payload = Utilities.base64Encode(png.getBlob().getBytes());
parm.muteHttpExceptions = false;
const x = UrlFetchApp.fetch("https://client.domain/wp-json/wp/v2/media", parm);
Logger.log(x.getContentText());
}
The response from this is
Exception: Request failed for https://client.domain returned code 500.
Truncated server response:
{"code":"rest_upload_sideload_error","message":"Sorry, this file type is not permitted for security reasons.","data":{"status":500}}
(use muteHttpExceptions option to examine full response)
test3 # Tests.gs:15
One of the suggestions, at Kinsta suggesting installing the WP Extra File Types plugin. No effect. Even selecting Check only file extensions had no effect (and 'png' is one of the standard accepted types.)
Where to now?
In this case, the "problem" was with Sucuri which needed to be told to whitelist googlecontent IP addresses, namely 107.178.0.0/16. Once Sucuri stopped blocking the traffic, the image was uploaded.

upload binary file using python requests

I am uploading a file using requests library below is the code:
files = {'file': open(full_file_name, 'rb')}
headers = {"content-type": 'application/x-www-form-urlencoded'}
final_resp = requests.put(loc, files=files, headers=headers)
The problem is some extra contents have been added to the file's start and end point.
The contents added to the start point is:
--b16010ae7646a031a5adc64ac0661e72
Content-Disposition: form-data; name="file"; filename="1016064585-65769268.csv"
The contents added to the endpoint is:
--b16010ae7646a031a5adc64ac0661e72--
But when the same file is uploaded through the postman these problems are not arising.
here is the screenshot of the postman .
The header of the postman is:
application/x-www-form-urlencoded
it may because you use multipart/form to upload file.try use data like code below
data = open(localFilePath, 'rb').read()
headers = {
"Content-Type":"application/binary",
}
upload = requests.put(uploadUrl,data=data,headers=headers)

Resources