i'm trying to upload a zip file to Team Google Drive, but the file appears in my own Google drive, and not in the Team's folder. I have a permissions for the team's (shared) folder and I can upload files there manually. I'm able to obtain the access_token.This is my code:
import json
import requests
def get_token():
oauth = 'https://www.googleapis.com/oauth2/v4/token' # Google API oauth url
headers = {'content-type': 'application/x-www-form-urlencoded'}
data = {
'grant_type': 'refresh_token',
'client_id': '{CLIENT_ID}',
'client_secret': '{CLIENT_SECRET}',
'refresh_token': '{REFRESH_TOKEN}',
}
token = requests.post(oauth, headers=headers, data=data)
_key = json.loads(token.text)
return _key['access_token']
# Upload files to google drive using access token
def upload_to_drive(files):
token_key = get_token()
headers = {"Authorization": "Bearer " + token_key}
upload = requests.post(
"https://www.googleapis.com/upload/drive/v3/files?uploadType=multipart",
headers=headers,
files=files
)
print(upload.text)
if __name__ == '__main__':
file = "my_folder.zip"
para = {
"name": file,
# "parents": [FOLDER_ID],
"parents": [{
"kind": "drive#file",
"driveId": "{TEAM_DRIVE_ID}",
"id": "{FOLDER_ID}",
"supportsAllDrives": True
}],
}
files_for_upload = {
'data': ('metadata', json.dumps(para), 'application/json; charset=UTF-8'),
'file': ('application/zip', open("./" + file, "rb"))
}
upload_to_drive(files_for_upload)
Any help is much appreciated!
Find a solution:
import json
import requests
def get_token():
oauth = 'https://www.googleapis.com/oauth2/v4/token' # Google API oauth url
headers = {'content-type': 'application/x-www-form-urlencoded'}
data = {
'grant_type': 'refresh_token',
'client_id': '{CL}',
'client_secret': '{CLIENT_SECRET}',
'refresh_token': '{REFRESH_TOKEN}',
}
token = requests.post(oauth, headers=headers, data=data)
_key = json.loads(token.text)
return _key['access_token']
# Upload files to google drive using access token
def upload_to_drive(files):
token_key = get_token()
headers = {"Authorization": "Bearer " + token_key}
upload = requests.post(
"https://www.googleapis.com/upload/drive/v3/files?uploadType=multipart&supportsAllDrives=true",
headers=headers,
files=files
)
print(upload.text)
if __name__ == '__main__':
file = "my_file.zip"
para = {
"name": file,
"parents": ['{FOLDER_ID}'],
}
files_for_upload = {
'data': ('metadata', json.dumps(para), 'application/json; charset=UTF-8'),
'file': ('application/zip', open("./" + file, "rb"))
}
upload_to_drive(files_for_upload)
supportsAllDrives should not be a part of metadata!
Related
Trying to understand how it works oauth
How to get authorized user details using Blizzard api?
import json
import requests
client_id = ""
client_secret = ""
region = "eu"
data = {
'grant_type': 'client_credentials'
}
access_token_response = requests.post(f"https://{region}.battle.net/oauth/token", data=data, allow_redirects=False, auth=(client_id, client_secret))
access_token = json.loads(access_token_response.text)["access_token"]
api_call_headers = {
'Authorization': 'Bearer ' + access_token
}
api_call_response = requests.get(f"https://{region}.battle.net/oauth/userinfo", headers=api_call_headers)
I want to trigger the cloud functions with a self-signed JWT for a Google-signed ID token. However, it produces the response Your client does not have permission to the requested URL. I am sure that that account has "Cloud Functions Invoker" access and I also get the token successfully.
import time
import jwt
import json
# import http.client
# payload
private_key = "\n-----END PRIVATE KEY-----\n"
token_dict = {
"iss": "het-query-function#smarter-poc.iam.gserviceaccount.com",
"scope": "https://www.googleapis.com/auth/cloud-platform",
"aud": "https://www.googleapis.com/oauth2/v4/token",
# "aud": "https://europe-central2-smarter-poc.cloudfunctions.net/query_soc_ota_information",
"exp": time.time()+3600,
'iat': time.time(), # 时间戳
"sub":"het-query-function#smarter-poc.iam.gserviceaccount.com"
}
"""payload 中一些固定参数名称的意义, 同时可以在payload中自定义参数"""
# iss 【issuer】发布者的url地址
# sub 【subject】该JWT所面向的用户,用于处理特定应用,不是常用的字段
# aud 【audience】接受者的url地址
# exp 【expiration】 该jwt销毁的时间;unix时间戳
# nbf 【not before】 该jwt的使用时间不能早于该时间;unix时间戳
# iat 【issued at】 该jwt的发布时间;unix 时间戳
# jti 【JWT ID】 该jwt的唯一ID编号
# headers
headers = {
'alg': "RS256", # 声明所使用的算法
'typ': 'JWT'
}
# 调用jwt库,生成json web token
jwt_token = jwt.encode(token_dict, # payload, 有效载体
private_key, # 进行加密签名的密钥
algorithm="RS256", # 指明签名算法方式, 默认也是HS256
headers=headers # json web token 数据结构包含两部分, payload(有效载体), headers(标头)
).decode('ascii') # python3 编码后得到 bytes, 再进行解码(指明解码的格式), 得到一个str
print(jwt_token)
import http.client
conn = http.client.HTTPSConnection("www.googleapis.com")
# payload = 'grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&assertion=eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IjllN2Q5ZTk1YjZkNTdiY2NiZjBhYmM2NzgzYzc2N2RhYjE2MzFjOWIiLCJ0eXAiOiJKV1QifQ.eyJpYXQiOjE2NDMwMDUwMzAsImV4cCI6MTY0MzAwNTYzMCwic3ViIjoiZ2NwLXN0b3JhZ2VAc21hcnRlci1wb2MuaWFtLmdzZXJ2aWNlYWNjb3VudC5jb20iLCJpc3MiOiJnY3Atc3RvcmFnZUBzbWFydGVyLXBvYy5pYW0uZ3NlcnZpY2VhY2NvdW50LmNvbSIsImF1ZCI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL29hdXRoMi92NC90b2tlbiIsInNjb3BlIjoiaHR0cHM6Ly93d3cuZ29vZ2xlYXBpcy5jb20vYXV0aC9jbG91ZC1wbGF0Zm9ybSJ9.eAgCd5JbliFLoggcE9z7Ybhrd0GO3vb3zBW9N48iDe9tGBkQKaFdgAeANutoYLmLuvQM4m4NSavIKFHWYJHiZ6-ioehUvrs0qHZFe2bBkbNYAMQTW73ERr1XjufnZkgK6u1TUTpcX9u2EiJyMHIuku4PBYlhv8aniIsYojVfA_wVcmKhN0dVeBQzixZ_mhJsIZRPKYDPkJKn4H4oOXgy_ymbvKmguZyYLuPGezgycZpKwhFOvQQTbVSuoKikow9v4JIISXlt0fuspFLlsaEVWRx4468GUJ1SNyYThkXARRFxQAWMsgAJ2Z25I38Z3i-owWDnFKJl8KrtjSGG52sa8w'
payload = 'grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&assertion='+jwt_token
headers = {
'Authorization': 'Bearer '+jwt_token,
'Content-Type': 'application/x-www-form-urlencoded'
}
conn.request("POST", "/oauth2/v4/token", payload, headers)
res = conn.getresponse()
data = res.read()
jwt = data.decode("utf-8")
print(jwt)
jwt_list = json.loads(jwt)
print(jwt_list['access_token'])
for v in range(len(jwt_list['access_token'])-1,-1,-1):
# print(jwt_list['access_token'][v])
if jwt_list['access_token'][v]!='.':
break
print(jwt_list['access_token'][v])
print("!!!!!!!")
jwt_str = jwt_list['access_token'][0:v+1]
print(jwt_str)
conn = http.client.HTTPSConnection("europe-central2-smarter-poc.cloudfunctions.net")
headers = {
'Authorization': 'bearer '+jwt_str
}
payload = ""
conn.request("GET", "/query_soc_ota_information/?hello=hello", payload, headers)
res = conn.getresponse()
data = res.read()
re = data.decode("utf-8")
print(re)
OK, your code works for me but with several changes.
It would be helpful to include which JWT you're library; I assume PyJWT
You need to include target_audience
ALG="RS256"
PROJECT=os.getenv("PROJECT")
REGION=os.getenv("REGION")
ACCOUNT=os.getenv("ACCOUNT")
FUNCTION=os.getenv("FUNCTION")
EMAIL="{account}#{project}.iam.gserviceaccount.com".format(
account=ACCOUNT,
project=PROJECT,
)
ROOT="{region}-{project}.cloudfunctions.net".format(
region=REGION,
project=PROJECT,
)
ENDPOINT="https://{root}/{function}".format(
root=ROOT,
function=FUNCTION,
)
token_dict = {
"target_audience": ENDPOINT,
"iss": EMAIL,
"sub": EMAIL,
"exp": time.time()+3600,
"iat": time.time(),
"aud": "https://www.googleapis.com/oauth2/v4/token",
}
NOTE I think exp and iat should be integers but your code works as-is.
The .decode("ascii") appended to jwt.encode().decode("ascii") is incorrect.
The payload should not be URL-encoded:
payload = "grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer&assertion={jwt}".format(
jwt=jwt_token,
)
The /oauth2/v4/token endpoint does not return an access_token per #john-hanley comment. It returns an id_token (as described by Google in the doc you reference).
jwt = data.decode("utf-8")
jwt_list = json.loads(jwt)
id_token=jwt_list["id_token"]
conn = http.client.HTTPSConnection(ROOT)
headers = {
"Authorization": "Bearer {token}".format(token=id_token),
}
conn.request("GET", "/{function}".format(function=FUNCTION), headers=headers)
NOTE No payload (null) not ""
main.py:
import http.client
import json
import jwt
import os
import time
ALG="RS256"
# Use GOOGLE_APPLICATION_CREDENTIALS for consistency
CREDENTIALS=os.getenv("GOOGLE_APPLICATION_CREDENTIALS")
f=open(CREDENTIALS)
key=json.load(f)
PRIVATE_KEY=key["private_key"]
PROJECT=os.getenv("PROJECT")
REGION=os.getenv("REGION")
ACCOUNT=os.getenv("ACCOUNT")
FUNCTION=os.getenv("FUNCTION")
EMAIL="{account}#{project}.iam.gserviceaccount.com".format(
account=ACCOUNT,
project=PROJECT,
)
ROOT="{region}-{project}.cloudfunctions.net".format(
region=REGION,
project=PROJECT,
)
ENDPOINT="https://{root}/{function}".format(
root=ROOT,
function=FUNCTION,
)
token_dict = {
"target_audience": ENDPOINT,
"iss": EMAIL,
"sub": EMAIL,
"exp": time.time()+3600,
"iat": time.time(),
"aud": "https://www.googleapis.com/oauth2/v4/token",
}
headers = {
'alg': ALG,
'typ': 'JWT'
}
jwt_token = jwt.encode(
token_dict,
PRIVATE_KEY,
algorithm=ALG,
headers=headers,
)
payload = "grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer&assertion={jwt}".format(
jwt=jwt_token,
)
headers = {
"Authorization": "Bearer {token}".format(
token=jwt_token,
),
"Content-Type": 'application/x-www-form-urlencoded'
}
conn = http.client.HTTPSConnection("www.googleapis.com")
conn.request("POST", "/oauth2/v4/token", payload, headers)
res = conn.getresponse()
data = res.read()
jwt = data.decode("utf-8")
jwt_list = json.loads(jwt)
id_token=jwt_list["id_token"]
conn = http.client.HTTPSConnection(ROOT)
headers = {
"Authorization": "Bearer {token}".format(token=id_token),
}
conn.request("GET", "/{function}".format(function=FUNCTION), headers=headers)
res = conn.getresponse()
data = res.read()
re = data.decode("utf-8")
print(re)
I am following documentation to post on my company linkedin page (i am superadministrator) so i used GET https://www.linkedin.com/oauth/v2/authorization?response_type=code&client_id={your_client_id}&redirect_uri={your_callback_url}&state=foobar&scope=r_liteprofile%20r_emailaddress%20w_member_social to get code then I got access_token using this https://linkedin.com/oauth/v2/accessToken?client_id={client_id}&client_secret={client_Secret}&grant_type=authorization_code&redirect_uri={url}&code={code}
Also i got approved on Marketing program so I dont have any problem at this point but When i try to post using credentials i get nothing in console and nothing appears on my company page.
Here is my code
I have a json with creds gotten from api
{
"client_id": "",
"client_secret": "",
"redirect_uri": "https://www.exampleuri.com",
"access_token": "",
"page_id":"73482979"
}
Then read json
def headers(access_token):
headers = {
'Authorization': f'Bearer {access_token}',
'cache-control': 'no-cache',
'X-Restli-Protocol-Version': '2.0.0'
}
return headers
def auth(credentials):
creds = read_creds(credentials)
#print(creds)
client_id, client_secret = creds['client_id'], creds['client_secret']
redirect_uri = creds['redirect_uri']
api_url = 'https://www.linkedin.com/oauth/v2'
if 'access_token' not in creds.keys():
args = client_id,client_secret,redirect_uri
auth_code = authorize(api_url,*args)
access_token = refresh_token(auth_code,*args)
creds.update({'access_token':access_token})
save_token(credentials,creds)
else:
access_token = creds['access_token']
return access_token
if __name__ == '__main__':
credentials = 'credentials.json'
access_token = auth(credentials)
Finally call functions above
import requests
from linked_credentials import auth,headers
credentials = 'credentials.json'
access_token = auth(credentials)
headers = headers(access_token)
def user_info(headers):
response = requests.get('https://api.linkedin.com/v2/organizations', headers = headers)
user_info = response.json()
return user_info
# Get user id to make a UGC post
user_info = user_info(headers)
urn = user_info['page_id']
api_url = 'https://api.linkedin.com/v2/ugcPosts'
author = f'urn:li:organization:{urn}'
message = '''
Testing post on LinkedIn with python
'''
link = 'https://www.example.com/'
link_text = 'Example!'
post_data = {
"owner": author,
"lifecycleState": "PUBLISHED",
"specificContent": {
"com.linkedin.ugc.ShareContent": {
"shareCommentary": {
"text": message
},
"shareMediaCategory": "ARTICLE",
"media": [
{
"status": "READY",
"description": {
"text": message
},
"originalUrl": link,
"title": {
"text": link_text
}
}
]
}
},
"visibility": {
"com.linkedin.ugc.MemberNetworkVisibility": "CONNECTIONS"
}
}
if __name__ == '__main__':
r = requests.post(api_url, headers=headers, json=post_data)
r.json()
This is what i have in my app
I'm trying to automate a process in which i have to download some brazilian fund quotes from Anbima (Brazil regulator). I have been able to work around the first steps to retrieve the access token but i don't know how to use the token in order to make requests. Here is the tutorial website https://developers.anbima.com.br/en/como-acessar-nossas-apis/.
I have tried a lot of thing but all i get from the request is 'Could not find a required APP in the request, identified by HEADER client_id.'
If someone could share some light. Thank you in advance.
import requests
import base64
import json
requests.get("https://api.anbima.com.br/feed/fundos/v1/fundos")
ClientID = '2Xy1ey11****'
ClientSecret = 'faStF1Hc****'
codeString = ClientID + ":" + ClientSecret
codeStringBytes = codeString.encode('ascii')
base64CodeBytes = base64.b64encode(codeStringBytes)
base64CodeString = base64CodeBytes.decode('ascii')
url = "https://api.anbima.com.br/oauth/access-token"
headers = {
'content-type': 'application/json'
,'authorization': f'Basic {base64CodeString}'
}
body = {
"grant_type": "client_credentials"
}
r = requests.post(url=url, data=json.dumps(body), headers=headers, allow_redirects=True)
jsonDict = r.json()
##################
urlFundos = "https://api-sandbox.anbima.com.br/feed/precos-indices/v1/titulos-publicos/mercado-secundario-TPF"
token = jsonDict['access_token']
headers2 = {
'content-type': 'application/json'
,'authorization': f'Bearer {token}'
}
r2 = requests.get(url=urlFundos, headers=headers2)
r2.status_code
r2.text
I was having the same problem, but today I could advance. I believe you need to adjust some parameters in the header.
Follows the piece of code I developed.
from bs4 import BeautifulSoup
import requests
PRODUCTION_URL = 'https://api.anbima.com.br'
SANDBOX_URL = 'https://api-sandbox.anbima.com.br'
API_URL = '/feed/fundos/v1/fundos/'
CODIGO_FUNDO = '594733'
PRODUCTION = False
if PRODUCTION:
URL = PRODUCTION_URL
else:
URL = SANDBOX_URL
URL = URL + API_URL + CODIGO_FUNDO
HEADER = {'access_token': 'your token',
'client_id' : 'your client ID'}
html = requests.get(URL, headers=HEADER).content
soup = BeautifulSoup(html, 'html.parser')
print(soup.prettify())
The sandbox API will return a dummy JSON. To access the production API you will need to request access (I'm trying to do this just now).
url = 'https://api.anbima.com.br/oauth/access-token'
http = 'https://api-sandbox.anbima.com.br/feed/precos-indices/v1/titulos-publicos/pu-intradiario'
client_id = "oLRa*******"
client_secret = "6U2nefG*****"
client_credentials = "oLRa*******:6U2nefG*****"
client_credentials = client_credentials.encode('ascii')
senhabytes = base64.b64encode(client_credentials)
senha = base64.b64decode(senhabytes)
print(senhabytes, senha)
body = {
"grant_type": "client_credentials"
}
headers = {
'content-type': 'application/json',
'Authorization': 'Basic b0xSYTJFSUlOMWR*********************'
}
request = requests.post(url, headers=headers, json=body, allow_redirects=True)
informacoes = request.json()
token = informacoes['access_token']
headers2 = {
"content-type": "application/json",
"client_id": f"{client_id}",
"access_token": f"{token}"
}
titulos = requests.get(http, headers=headers2)
titulos = fundos.json()
I used your code as a model, then I've made some changes. I've printed the encode client_id:client_secret and then I've copied and pasted in the headers.
I've changed the data for json.
I am trying to upload a photo (jpg image) using the new Google Photos API.
I am able to get an uploadToken but when I try to create the media item I get the following error:
{
"newMediaItemResults": [
{
"uploadToken": "CAIS+QIAkor2Yr4JcvYMMx..... ",
"status": {
"code": 3,
"message": "NOT_IMAGE: There was an error while trying to create this media item."
}
}
]
}
Here is a snippet of my code:
import sys
import json
import requests
pic = 'image.jpg'
fname = 'read_write_token_creds.json'
with open(fname) as f:
data = json.load(f)
tok = data['access_token']
# Step 1 get an upload token
URL = 'https://photoslibrary.googleapis.com/v1/uploads'
headers = {
'Content-type': 'application/octet-stream',
'X-Goog-Upload-File-Name': pic,
'X-Goog-Upload-Protocol': 'raw',
'Authorization': 'Bearer ' + tok,
}
files = {'file': open(pic, 'rb')}
r = requests.post(URL, headers=headers, files=files)
upload_token = r.text
# Step 2
album_id = 'AG.....7u'
URL = 'https://photoslibrary.googleapis.com/v1/mediaItems:batchCreate'
header = {
'Content-type': 'application/json',
'Authorization': 'Bearer ' + tok
}
payload = {
'albumId': album_id,
'newMediaItems': [
{
'description': 'Desc.',
'simpleMediaItem': { 'uploadToken': upload_token }
}
]
}
r = requests.post(URL, headers=header, data=json.dumps(payload))
When I look at r.text from the requests module, I receive the error message which was given at the top of he message.
This worked for me.
How to authenticate user see here https://developers.google.com/photos/library/guides/upload-media
def upload(service, file):
f = open(file, 'rb').read();
url = 'https://photoslibrary.googleapis.com/v1/uploads'
headers = {
'Authorization': "Bearer " + service._http.request.credentials.access_token,
'Content-Type': 'application/octet-stream',
'X-Goog-Upload-File-Name': file,
'X-Goog-Upload-Protocol': "raw",
}
r = requests.post(url, data=f, headers=headers)
print '\nUpload token: %s' % r.content
return r.content
def createItem(service, upload_token, albumId):
url = 'https://photoslibrary.googleapis.com/v1/mediaItems:batchCreate'
body = {
'newMediaItems' : [
{
"description": "test upload",
"simpleMediaItem": {
"uploadToken": upload_token
}
}
]
}
if albumId is not None:
body['albumId'] = albumId;
bodySerialized = json.dumps(body);
headers = {
'Authorization': "Bearer " + service._http.request.credentials.access_token,
'Content-Type': 'application/json',
}
r = requests.post(url, data=bodySerialized, headers=headers)
print '\nCreate item response: %s' % r.content
return r.content
# authenticate user and build service
upload_token = upload(service, './path_to_image.png')
response = createItem(service, upload_token, album['id'])