Create a Spotify playlist using spotipy - python

I am trying to create a playlist using the spotipy library. I followed the instructions on their website alongside this solved question Spotipy invalid username? . When running the code provided in this question (fitted to my Spotify developer account) everything works fine. However when trying another scope corresponding to my object of creating a playlist I get the same username error as mentioned in the linked question:
Traceback (most recent call last):
File "C:\Users\d92167\Spotify\Create_Favorites.py", line 23, in <module>
sp.user_playlist_create(cred.user_name, name=playlist_name)
File "C:\Users\d92167\Anaconda3\lib\site-packages\spotipy\client.py", line 784, in user_playlist_create
return self._post("users/%s/playlists" % (user,), payload=data)
File "C:\Users\d92167\Anaconda3\lib\site-packages\spotipy\client.py", line 302, in _post
return self._internal_call("POST", url, payload, kwargs)
File "C:\Users\d92167\Anaconda3\lib\site-packages\spotipy\client.py", line 267, in _internal_call
raise SpotifyException(
SpotifyException: https://api.spotify.com/v1/users/*My Username*/playlists:
Invalid username
My code:
import spotipy
import cred
scope = 'playlist-modify-public'
token = spotipy.util.prompt_for_user_token(cred.user_name,scope,client_id=cred.client_id,client_secret=cred.client_secret,redirect_uri=cred.redirect_url)
sp = spotipy.Spotify(auth=token)
playlist_name = 'Test'
sp.user_playlist_create(cred.user_name, name=playlist_name)
I am using Python 3.8 and Spotipy version 2.20.0

I have 2 possible solutions:
1: You forgot to type user=
sp.user_playlist_create(user=cred.user_name, name=playlist_name)
2: Maybe the user_name in the cred file is wrong. You can get the username with this code:
sp_user = sp.current_user()
user_name = sp_user['uri'].split(":")[2]

Related

Instabot API for Python raises error after running code for the 2nd time

I am currently working with the Instabot API for python and I ran across the following issue:
I wrote a small program:
from instabot import Bot
bot = Bot()
bot.login(username = "[my username]", password = "[my passowrd]")
bot.follow("lego")
which worked fine after running it for the very first time. However, after running the program for a second time, this time following another account, it raised an error ("KeyError: ds_user").
This error can be fixed by deleting the config folder inside the project folder. Unfortunately, this isn't a very sustainable solution, as it makes working on the code really arduous. I therefore would like to know if there is any solution for getting the program to run multiple times without having to delete the config folder over and over again.
I am receiving the following traceback (code is running in an anaconda environment called "Instagram Automation"):
Traceback (most recent call last):
File "e:/Programme/OneDrive/Dokumente/Projekte/Instagram Automation/main.py", line 4, in <module>
bot.login(username = "[my username]", password = "[my password]")
File "E:\Programme\Anaconda\envs\Instagram Automation\lib\site-packages\instabot\bot\bot.py", line 443, in login
if self.api.login(**args) is False:
File "E:\Programme\Anaconda\envs\Instagram Automation\lib\site-packages\instabot\api\api.py", line 240, in login
self.load_uuid_and_cookie(load_cookie=use_cookie, load_uuid=use_uuid)
File "E:\Programme\Anaconda\envs\Instagram Automation\lib\site-packages\instabot\api\api.py", line 199, in load_uuid_and_cookie
return load_uuid_and_cookie(self, load_uuid=load_uuid, load_cookie=load_cookie)
File "E:\Programme\Anaconda\envs\Instagram Automation\lib\site-packages\instabot\api\api_login.py", line 352, in load_uuid_and_cookie
cookie_username = self.cookie_dict["ds_user"]
KeyError: 'ds_user'
As far as I can see, the only way on your side to fight the symptoms is to always delete the JSON file in the config folder, e.g:
import os
if os.path.isfile("path/to/config/file.json"):
os.remove("path/to/config/file.json")
import instabot
# rest of your code goes here
The developers of instabot should fix the source of the problem, for example by using self.cookie_dict.get("ds_user", "some default value") instead of self.cookie_dict["ds_user"]

Bad Request at Authorization Code Flow Spotify

I am trying to built a script that creates a playlist on a user's spotify profile. To learn spotipy I decided to try the examples they have on the documentation page.
The code I run is:
import sys
import spotipy
import spotipy.util as util
token = util.prompt_for_user_token('idxxx',
'user-library-read',
client_id='axxx',
client_secret='Bxxx',
redirect_uri='http://localhost')
scope = 'user-library-read'
if len(sys.argv) > 1:
username = sys.argv[1]
else:
print("Usage: %s username" % (sys.argv[0],))
sys.exit()
token = util.prompt_for_user_token(username, scope)
if token:
sp = spotipy.Spotify(auth=token)
results = sp.current_user_saved_tracks()
for item in results['items']:
track = item['track']
print(track['name'] + ' - ' + track['artists'][0]['name'])
else:
print("Can't get token for", username)
The problem occurs when i run the code. I get redirected on my redirect uri and after i paste it back on the terminal i get this:
Traceback (most recent call last):
File "spot01.py", line 9, in <module>
redirect_uri='http://localhost')
File "/home/user/.local/lib/python3.6/site-packages/spotipy/util.py", line 92, in prompt_for_user_token
token = sp_oauth.get_access_token(code, as_dict=False)
File "/home/user/.local/lib/python3.6/site-packages/spotipy/oauth2.py", line 434, in get_access_token
raise SpotifyOauthError(response.reason)
spotipy.oauth2.SpotifyOauthError: Bad Request
I tried to access the oauth2.py from the File Manager and the terminal but it says that this repository does not exist. Also i tried to install spotipy through the github page they have where the neccessary files exist but still nothing.
Any ideas?
Thanks a lot.
I solved the problem by downloading the required files from here https://github.com/plamere/spotipy/tree/master/spotipy
Then I changed some things inside of each .py file and i run every code I wanted to inside there. It must be another more fancy solution but this one worked for me.
Oh before running any command I typed this set of commands on the terminal:
$ bash
$ export SPOTIPY_CLIENT_ID='xxx'
$ export SPOTIPY_CLIENT_SECRET='xxx'
$ export SPOTIPY_REDIRECT_URI='http://localhost/'
where xxx you put your credentials and at the refirect uri your localhost or your github profile link.

Python - Download files from Share Point | Authentication token error

I am working on a report automation project, where I need to download excel files automatically from a share point location. I tried some examples referring to Python - Download files from SharePoint site but getting below error within imported library function. Please let me know, what I am missing here.
Error:
Traceback (most recent call last):
File "worklod_report.py", line 66, in
if ctxAuth.acquire_token_for_user(username='murali.pandiyan#xyz.com', password=pwd):
File "C:\Users\murali.pandiyan\AppData\Local\Programs\Python\Python37-32\lib\site-
packages\office365\runtime\auth\authentication_context.py", line 18, in acquire_token_for_user
return self.provider.acquire_token()
File "C:\Users\murali.pandiyan\AppData\Local\Programs\Python\Python37-32\lib\site-packages\office365\runtime\auth\saml_token_provider.py", line 57, in acquire_token
self.acquire_service_token(options)
File "C:\Users\murali.pandiyan\AppData\Local\Programs\Python\Python37-32\lib\site-packages\office365\runtime\auth\saml_token_provider.py", line 88, in acquire_service_token
token = self.process_service_token_response(response)
File "C:\Users\murali.pandiyan\AppData\Local\Programs\Python\Python37-32\lib\site-packages\office365\runtime\auth\saml_token_provider.py", line 119, in process_service_token_response
return token.text
AttributeError: 'NoneType' object has no attribute 'text'
Python code:
from office365.runtime.auth.authentication_context import AuthenticationContext
from office365.sharepoint.client_context import ClientContext
import getpass
if __name__ == '__main__':
ctxAuth = AuthenticationContext(url='https://internal.abc.net/sites/Compute/')
print("Enter Password:")
pwd=getpass.getpass()
if ctxAuth.acquire_token_for_user(username='murali.pandiyan#xyz.com', password=pwd):
ctx = ClientContext(settings['url'], ctxAuth)
print("Authentication is success")
else:
print(ctxAuth.get_last_error())
The following code snippet for your reference.
if __name__ == '__main__':
ctxAuth = AuthenticationContext('https://internal.abc.net/sites/Compute/')
print("Enter Password:")
pwd=getpass.getpass()
if ctxAuth.acquire_token_for_user('murali.pandiyan#xyz.com', pwd):
ctx = ClientContext(settings['url'], ctxAuth)
print("Authentication is success")
else:
print(ctxAuth.get_last_error())
Check the authentication source code here: authentication_context.py
And the source code of file download is here: file_operations.py

PyRal getAttachment

I have a fairly simple use-case but i'm not understanding the error message i'm receiving.
I'm using the requests and pyral modules, pyral (http://pyral.readthedocs.io/en/latest/interface.html#) is really just a wrapper for Rally's Restful api. My goal is to get a file (attachment) from a Rally (a CA product) UserStory and store it to a local file system.
For context, here is my environment setup (authenticate to Rally and create an object). I've obviously removed authentication information.
from pyral import Rally, rallyWorkset
options = [arg for arg in sys.argv[1:] if arg.startswith('--')]
args = [arg for arg in sys.argv[1:] if arg not in options]
server, user, password, apikey, workspace, project = rallyWorkset(options)
rally = Rally(server='rally1.rallydev.com',
user='**********', password='***********',
apikey="**************",
workspace='**************', project='**************',
server_ping=False)
After that I get a response object for just one user story (see the query for US845), i do this just to simplify the problem.
r = rally.get('UserStory', fetch = True, projectScopeDown=True, query = 'FormattedID = US845')
and then I use the built-in iterator to get the user story from the RallyRESTResponse object.
us = r.next()
from there it feels like I should be able to easily use the getAttachment() method that accepts a artifact (us) and filename (name of an attachment). I'm able to use getAttachmentNames(us) to return a list of attachment names. The issue arrises when i try something like
attachment_names = rally.getAttachmentNames(us) #get attachments for this UserStory
attachment_file = rally.getAttachment(us, attachment_names[0]) #Try to get the first attachment
returns an error like this
Traceback (most recent call last):
File "<ipython-input-81-a4a342a59c5a>", line 1, in <module>
attachment_file = rally.getAttachment(us, attachment_names[0])
File "C:\Miniconda3\lib\site-packages\pyral\restapi.py", line 1700, in getAttachment
att.Content = base64.decodebytes(att_content.Content) # maybe further txfm to Unicode ?
File "C:\Miniconda3\lib\base64.py", line 552, in decodebytes
_input_type_check(s)
File "C:\Miniconda3\lib\base64.py", line 520, in _input_type_check
raise TypeError(msg) from err
TypeError: expected bytes-like object, not str
I receive a similar error if i try to use
test_obj = rally.getAttachments(us)
Which returns an error like this:
Traceback (most recent call last):
File "<ipython-input-82-06a8cd525177>", line 1, in <module>
rally.getAttachments(us)
File "C:\Miniconda3\lib\site-packages\pyral\restapi.py", line 1721, in getAttachments
attachments = [self.getAttachment(artifact, attachment_name) for attachment_name in attachment_names]
File "C:\Miniconda3\lib\site-packages\pyral\restapi.py", line 1721, in <listcomp>
attachments = [self.getAttachment(artifact, attachment_name) for attachment_name in attachment_names]
File "C:\Miniconda3\lib\site-packages\pyral\restapi.py", line 1700, in getAttachment
att.Content = base64.decodebytes(att_content.Content) # maybe further txfm to Unicode ?
File "C:\Miniconda3\lib\base64.py", line 552, in decodebytes
_input_type_check(s)
File "C:\Miniconda3\lib\base64.py", line 520, in _input_type_check
raise TypeError(msg) from err
TypeError: expected bytes-like object, not str
It seems that i'm fundamentally misunderstanding the parameters that this method requires? Has anyone been able to do this successfully before? For what it's worth i have no issues using the addAttachment() method with a workflow similar to the above. I've tried converting the filename (string) with the bytes() method to utf-8 but that didn't help.
I've also looked at this example in the pyral source, but i receive exactly the same error when trying to execute that.
https://github.com/klehman-rally/pyral/blob/master/examples/get_attachments.py
It looks like the issue in restapi.py script - there is no decodebytes method in base64 library:
att.Content = base64.decodebytes(att_content.Content)
All available methods are described at:
RFC 3548: Base16, Base32, Base64 Data Encodings
So, workaround is to replace decodebytes by base64.b64decode in restapi.py. At least, it works me.
E.g. location at Mac OS X:
/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/pyral/restapi.py
I have used the below code to get all attachment since getAttachments is not working as expected. it will create a file in the current dir with the same name.
import sys
import string
import base64
from pyral import rallyWorkset, Rally,RallyRESTResponse
rally = Rally(server, user=USER_NAME, password=PASSWORD, workspace=workspace, project=project)
criterion = 'FormattedID = US57844'
response = rally.get('HierarchicalRequirement', query=criterion, order="FormattedID",pagesize=200, limit=400, projectScopeDown=True)
artifact = response.next()
context, augments = rally.contextHelper.identifyContext()
for att in artifact.Attachments:
resp = rally._getResourceByOID(context, 'AttachmentContent', att.Content.oid, project=None)
if resp.status_code not in [200, 201, 202]:
break
res = RallyRESTResponse(rally.session, context, "AttachmentContent.x", resp, "full", 1)
if res.errors or res.resultCount != 1:
print("breaking the for loop")
att_content = res.next()
cont = att_content.Content
x = base64.b64decode(cont)
output = open(att.Name, 'wb')
output.write(x)

Pandas / Google Analytics API authentication attempt throws me a weird python error

During my pandas/Google Analytics API setup, I basically did everything as described in this link:
http://blog.yhathq.com/posts/pandas-google-analytics.html
The client_secrets.json is in the pandas/io folder. When i now try to execute a statement of the form
>>>from pandas.io import ga
>>>df = ga.read_ga(metrics, dimensions, start_date)
the following error occurs:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "\Anaconda\lib\site-packages\pandas\io\ga.py", line 110, in read_ga
reader = GAnalytics(**reader_kwds)
File "\Anaconda\lib\site-packages\pandas\io\ga.py", line 179, in __init__
self._service = self._init_service(secrets)
File "\Anaconda\lib\site-packages\pandas\io\ga.py", line 191, in _init_service
http = self.authenticate(secrets)
File "\Anaconda\lib\site-packages\pandas\io\ga.py", line 151, in authenticate
return auth.authenticate(flow, self.token_store)
File "\Anaconda\lib\site-packages\pandas\io\auth.py", line 108, in authenticate
credentials = tools.run(flow, storage)
AttributeError: 'module' object has no attribute 'run'
According to the yhat link, my browser should open for authentication.
Note: I did not not create the Client ID for "installed application", since I did not have this choice in the menu when creating the ID. Instead, i chose "other". This shouldn't be the cause of the error, though.
Second Note: I recently updated my pandas to 0.17.1. When importing pandas.io.ga, i got the message that the .ga module is deprecated. Furthermore, i manually installed the gflags module, because it was needed when I tried to import .io.ga the first time.
Either file a ticket with the owners of Pandas to change (currently) line 108 of pandas/io/auth.py from run() to run_flow(), or make the fix yourself and file a PR. (Yes, it would've been nice if Google had just made run_flow() and alias of run(), but as you can imagine, this is not how this change evolved, so we have to live with it.)
For other developers running into this error: If you have the latest version (as of Feb 2016) of the Google APIs Client Library for Python, just rename your call from tools.run() to tools.run_flow(), and you should be good-to-go. More about this change in a PSA (public service announcement) blogpost I wrote back in mid-2015 but update periodically to stay current.
The fastest way to upgrade your Client Library is with:
pip install -U google-api-python-client # or pip3 for 3.x

Categories

Resources