PRAW gives 401 exception when fetching subreddit in read-only mode - python

I am using PRAW package to read information from reddit. PS: The client_id, client_secret and user_agent values are passed correctly.
import praw
from prawcore.exceptions import ResponseException
reddit = praw.Reddit(
client_id="xxxxxxx",
client_secret="xxxxxxxxxxxxxxx",
user_agent="xxxxxxxxxxxxxx",
)
print (reddit.read_only)
subreddit = reddit.subreddit("redditdev")
print(subreddit.display_name) # output: redditdev
print(subreddit.title) # output: reddit development
print(subreddit.description)
The instance reddit seems to get created successfully as I can print the value of the read_only attribute and the display_name attributes. However, when printing the title attribute, I get a 401 HTTP response error.
True
redditdev
Traceback (most recent call last):
File "/Users/sanjose/PycharmProjects/pubReddit/prawC/prawMain.py", line 13, in <module>
print(subreddit.title) # output: reddit development
............
............
File "/Users/sanjose/PycharmProjects/pubReddit/venv/lib/python3.7/site-packages/prawcore/auth.py", line 36, in _post
raise ResponseException(response)
prawcore.exceptions.ResponseException: received 401 HTTP response
I am intentionally not passing the user id and password as I wish to use it only in the read-only mode. Have I missed some setup or does the title attribute require authentication?

I had the same issue, I'm pretty sure it was because I made a web app rather than a script. I solved the issue by making a new reddit app (you can make a reddit app here) and selecting the script option instead of the web app option.

Related

python sharepoint - Error validating credentials due to invalid username or password

I want to automate downloading a zipfile on another organization's sharepoint site that they have shared with my organization, inviting us as a guest using a generic company email address so we can access the files. To gain access, I provide the company email address as username and its associated AD password which authenticates access through our MS 365 organization account.
This works fine manually, but when attempting to do it through shareplum I get a credentials error.
Here is my code:
from shareplum import Site
from shareplum import Office365
from shareplum.site import Version
sharepointUsername = 'elvis.presley#suspiciousminds.org'
sharepointPassword = 'oogabooga123'
sharepointSite = 'https://abc.sharepoint.com/sites/ClientLogin/Shared Documents/Graceland/'
authcookie = Office365(website, username=sharepointUsername,
password=sharepointPassword).GetCookies()
site = Site(sharepointSite, version=Version.v365, authcookie=authcookie)
And here is the error:
Traceback (most recent call last):
File "<string>", line 11, in <module>
File "C:\arcgispro-py3-clone2\lib\site-packages\shareplum\office365.py", line 88, in get_cookies
sectoken = self.get_security_token(self.username, self.password)
File "C:\arcgispro-py3-clone2\lib\site-packages\shareplum\office365.py", line 80, in get_security_token
raise Exception('Error authenticating against Office 365. Error from Office 365:', message[0].text)
Exception: ('Error authenticating against Office 365. Error from Office 365:', 'AADSTS50126: Error validating credentials due to invalid username or password.')
Any clue as why this is not working? I've checked the credentials several times using them to log in manually and it works every time (obviously the example does not have the real username/password)?
You’re not alone, this seems to be a common issue with shareplum over the past 6 months. There’s an open issue on GitHub. The code owner is aware and is having difficulty debugging the issue.
GitHub issue: https://github.com/jasonrollins/shareplum/issues/84
I recommend working closely with the code owner to debug and resolve the issue on GitHub, or using a different library/solution altogether. Another user commented on the issue and referenced a solution that utilizes the requests library to retrieve a file that you may find useful: https://github.com/jasonrollins/shareplum/issues/84#issuecomment-627986466 .

API GET request returns 404

I'm currently developing a Django web application which is supposed to add some functionality to online shops based on InSales (a popular Russian web platform). I use the official InSales lib for Python called pyinsales to get objects like orders and products from registered shops.
The InSales API is based on REST requests with XML. I use the code below to get information about orders in the Django shell:
from install.models import Shop
from insales import InSalesApi
shop = Shop.objects.get(shop_url='shop-url.myinsales.ru')
api = InSalesApi(shop.shop_url, 'trackpost', shop.password)
orders = api.get_orders()
Here shop.shop_url is the shop URL ("oh, really?"), trackpost is the name of my app and shop.password is the password needed to connect. Password is generated by MD5 (that's an InSales rule). And here I get an error:
Traceback (most recent call last):
File "<console>", line 1, in <module>
File "/usr/local/lib/python3.5/site-packages/insales/api.py", line 32, in get_orders
return self._get('/admin/orders.xml', {'per_page': per_page, 'page': page}) or []
File "/usr/local/lib/python3.5/site-packages/insales/api.py", line 291, in _get
return self._req('get', endpoint, qargs)
File "/usr/local/lib/python3.5/site-packages/insales/api.py", line 307, in _req
response = getattr(self.connection, method)(*args, **kwargs)
File "/usr/local/lib/python3.5/site-packages/insales/connection.py", line 85, in get
return self.request('GET', path, qargs=qargs)
File "/usr/local/lib/python3.5/site-packages/insales/connection.py", line 70, in request
(method, path, resp.status, body), resp.status)
insales.connection.ApiError: GET request to /admin/orders.xml?page=1&per_page=25 returned: 404
b'<?xml version="1.0" encoding="UTF-8"?>\n<errors>\n <error></error>\n</errors>\n'
I've already checked everything for mistakes. Password is generated properly (according to official documentation), shop URL is correct and all the methods from the lib are used correctly. InSales tech support doesn't response, so now I have no idea about what is happening.
I don't want you to debug this issue, but I'd like to know what can cause the 404 error (except obvious things, like incorrect URL or password). Thanks everybody who tries to answer.
404 mean that the server couldn't find what you requested.
https://en.wikipedia.org/wiki/HTTP_404
So it's not an authentication issue, it seems like there are no orders at that particular endpoint.
Have you tried using the python "requests" package instead of using the "pyinsales" module to request data from the endpoint directly? That way you can customize your own headers, etc.
You might also try testing the endpoints in a program like postman to ensure that the endpoints are valid before you try to hit them programmatically.
Analysing the pyinsales code on github, I realised that url should be a subdomain name on myinsales domain, so if the full url is http://shop.myinsales.ru/ then the first argument in pyinsales should be shop. That's a pity no one working on the module pointed that in readme, but such things happen

BadParametersError: Invalid signature when using OVH Python wrapper

I'm using OVH API along with python wrapper:
https://pypi.python.org/pypi/ovh
When trying to execute this code:
import ovh
client = ovh.Client()
# Print nice welcome message
print "Welcome", client.get('/me')['firstname']
I get this error:
Traceback (most recent call last):
File "index.py", line 6, in <module>
print "Welcome", client.get('/me')['firstname']
File "/home/rubinhozzz/.local/lib/python2.7/site-packages/ovh/client.py", line 290, in get
return self.call('GET', _target, None, _need_auth)
File "/home/rubinhozzz/.local/lib/python2.7/site-packages/ovh/client.py", line 419, in call
raise BadParametersError(json_result.get('message'))
ovh.exceptions.BadParametersError: Invalid signature
My info is saved in the ovh.conf as the documentation suggests.
[default]
; general configuration: default endpoint
endpoint=ovh-eu
[ovh-eu]
application_key=XXXlVy5SE7dY7Gc5
application_secret=XXXdTEBKHweS5F0P0tb0lfOa8GoQPy4l
consumer_key=pscg79fXXX8ESMIXXX7dR9ckpDR7Pful
It looks that I can connect but when trying to use the services like for instance "/me", the error raises!
It is difficult to reproduce the issue because it requires an application key and it seems that it is only granted to existing customers of OVH. I couldn't even see a link to an account registration page on their site.
By looking at the code of the call() method in /ovh/client.py, it seems that their server doesn't recognise the format or the content off the signature sent by your script. According to the inline documentation the signature is generated from these parameters:
application_secret
consumer_key
METHOD
full request url
body
server current time (takes time delta into account)
Since your call is identical to the example code provided on the OVH Python package web page, the last four parameters should be valid. In that case it looks like either the application secret or the customer key (or both) in your config file are not correct.
See also the documentation on OVH site under the 'Signing requests' heading. They explain how the signature is made and what it should look like.
Perhaps try to re-create a new application API to obtain new key and secret and make sure you copy them without any additional character.

Dropbox API request token not working with Python 3?

I'm maintaining a Python application using the official Dropbox API. To ask the users to let my application use their Dropbox account, I use a small script using the DropboxSession class, which is clearly the same as the one we can find on this blog post :
# Include the Dropbox SDK libraries
from dropbox import client, rest, session
# Get your app key and secret from the Dropbox developer website
APP_KEY = '******'
APP_SECRET = '******'
# ACCESS_TYPE should be 'dropbox' or 'app_folder' as configured for your app
ACCESS_TYPE = 'app_folder'
sess = session.DropboxSession(APP_KEY, APP_SECRET, ACCESS_TYPE)
request_token = sess.obtain_request_token()
url = sess.build_authorize_url(request_token)
# Make the user sign in and authorize this token
print "url:", url
print "Please visit this website and press the 'Allow' button, then hit 'Enter' here."
# Python 2/3 compatibility
try:
raw_input()
except NameError:
input()
# This will fail if the user didn't visit the above URL
access_token = sess.obtain_access_token(request_token)
#Print the token for future reference
print access_token
While it's perfectly working with Python 2.7.6, it seems to fail because of Dropbox code in Python 3.4 (the raw_input problem having been dealt with). I get this error :
Traceback (most recent call last):
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/session.py", line 285, in _parse_token
key = params['oauth_token'][0]
KeyError: 'oauth_token'
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "get_access_token.py", line 12, in <module>
request_token = sess.obtain_request_token()
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/session.py", line 185, in obtain_request_token
self.request_token = self._parse_token(response.read())
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/session.py", line 287, in _parse_token
raise ValueError("'oauth_token' not found in OAuth request.")
ValueError: 'oauth_token' not found in OAuth request.
Long story short, after having studied the faulty code, it seems that the Dropbox code searches for a string dictionary key, despite the fact that in Python 3, those keys become bytestrings (i.e. it lookups 'oauth_token', which isn't here, instead of b'oauth_token', which is here).
However, even after having fixed the code to see if that's the only issue, no luck, I get another error further in the procedure:
Traceback (most recent call last):
File "get_access_token.py", line 25, in <module>
access_token = sess.obtain_access_token(request_token)
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/session.py", line 214, in obtain_access_token
response = self.rest_client.POST(url, headers=headers, params=params, raw_response=True)
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/rest.py", line 316, in POST
return cls.IMPL.POST(*n, **kw)
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/rest.py", line 254, in POST
post_params=params, headers=headers, raw_response=raw_response)
File "/home/scylardor/.virtualenvs/onitu3/lib/python3.4/site-packages/dropbox/rest.py", line 227, in request
raise ErrorResponse(r, r.read())
dropbox.rest.ErrorResponse: [401] 'Unauthorized'
So the faulty functions are sess.obtain_request_token() and sess.obtain_access_token(request_token). And the Python 2.7 version works fine, but I'd like to keep Python 3 compatibility.
So, does anyone know how one's supposed to make it work in Python 3 ? Could it be deliberately broken in order to make people move on to new procedures ? I could have sworn it was working with Python 3, some time ago.
Thank you for your time if you have an idea :)
edit: It seems the Dropbox SDK just isn't fully Python 3-compatible yet. So, I guess there's nothing else to do than to wait for them to update the SDK.
Try to use version 1.6
$ pip install dropbox==1.6
Better than waiting for the SDK to be compatible, you can use (or contribute to and use) the "community" fork, dropbox-py3 (here on github).
(Those quotes are big quotes. For now it's just me coding this, and just the part I need, but everyone's welcome to help. I think it's mainly identifying the few parts that are missing a ".encode" because it's mixing bytes and strings.)

Google app engine send mail raises ApplicationError: 1 Internal Error

Years back I built a simple mail form that has been working like a champ, but in the last couple months the logs show I'm getting an error when EmailMessage's send() method gets called.
I wrote a quick test to see if a stripped down version of an EmailMessage would work without error:
class TestEmail(webapp.RequestHandler):
def get(self):
fromAddress = "APPOWNEREMAIL#gmail.com"
email = mail.EmailMessage(sender=fromAddress)
email.to = self.request.get('to') + '#gmail.com'
email.subject = "Test Email"
email.body = "Testing the email system"
email.html = "<strong>Testing the <em>email</em> system</strong>"
email.check_initialized()
email.send()
Simple enough, but if I call that with:
http://MYAPPNAME.appspot.com/test-email?to=TOTALLYLEGITEMAIL
I still get the same error (note check_initialized() isn't throwing an error):
Traceback (most recent call last):
File "/base/python_runtime/python_lib/versions/1/google/appengine/ext/webapp/_webapp25.py", line 701, in __call__
handler.get(*groups)
File "/base/data/home/apps/s~myappname/3.354527616249361817/myappname.py", line 370, in get
email.send()
File "/base/python_runtime/python_lib/versions/1/google/appengine/api/mail.py", line 895, in send
raise e
ApplicationError: ApplicationError: 1 Internal error
I haven't made any recent changes to the app, it's a lightly used app well below quota, it's sending as the email associated with the app owner and after spending a few hours scrutinizing the code, I'm still no closer to an answer.
Even more distressing, every Google search I come up with offers no new help. The best I could find was this question: Google app engine send mail service raises exception which sounds exactly like my problem, but in that case there wasn't a solution, the problem just went away.
Any idea how I can track this one down? Let me know if I need to clarify anything. Thanks!
What is your appid?
There is currently an issue that sending mail from an application whose appid is the same as the owner's gmail name will fail. eg, I have a gmail address "moishel at gmail dot com"; if I created an app whose appid is 'moishel' (before version 1.6.0) it will fail when trying to send mail. Note that this problem does not exist for apps created with version 1.6.0 or after.
Here's the issue: http://code.google.com/p/googleappengine/issues/detail?id=5320

Categories