Firebase Admin SDK credentials certificate not validating - python

After creating a chatbot in Dialogflow I want to connect this to my PyCharm environment, my end goal is to create a GUI within Python and allow it to connect through Dialogflow back-end, I also have a Firestore database and a few API's set up.
I have read to connect PyCharm to the Dialogflow (and, the Google Cloud platform) I need to use the Firebase-Admin SDK, which has been installed through PIP.
import dialogflow_v2beta1
from google.cloud import firestore
import firebase_admin
from firebase_admin import credentials
#Initialize the Admin SDK
cred = credentials.Certificate('C:Users\folder1\folder2\chatbot.json')
default_app = firebase_admin.initialize_app(cred)
#The below is a default test hoping to write a new document to the Firestore Database to check the connection works.
doc_ref = db.collection(u'users').document(u'alovelace')
doc_ref.set({
u'first': u'Ada',
u'last': u'Lovelace',
u'born': 1815
})
So, with the above I simply hope to connect my environment to my chatbot through the Google platform and when I run this code I hope for some data to be created in my Firestore database.
The error I get when I run the above is:
C:\Users\Me\PycharmProjects\Chatbot\venv\Scripts\python.exe C:/Users/Me/PycharmProjects/Chatbot/venv/Chatbot.py
Traceback (most recent call last):
File "C:/Users/Me/PycharmProjects/Chatbot/venv/Chatbot.py", line 12, in <module>
cred = credentials.Certificate('C:Users\folder1\folder2\chatbot.json')
File "C:\Users\Me\PycharmProjects\Chatbot\venv\lib\site-packages\firebase_admin\credentials.py", line 83, in __init__
with open(cert) as json_file:
IOError: [Errno 2] No such file or directory: 'C:Users\\folder1\\folder2\\chatbot.json'
Process finished with exit code 1
In short, I've checked the line 83 error in the credentials.py file where the default comment suggests means the file can't be found, but is correct as far as I can tell. The only thing I notice are the two \ in the error.
Any help would be much appreciated.
UPDATE
This has erased that error, but now being shown another three:
SNIMissingWarning: An HTTPS request has been made, but the SNI (Subject Name Indication) extension to TLS is not available on this platform. This may cause the server to present an incorrect TLS certificate, which can cause validation failures. You can upgrade to a newer version of Python to solve this. For more information, see https://urllib3.readthedocs.io/en/latest/advanced-usage.html#ssl-warnings
InsecurePlatformWarning: A true SSLContext object is not available. This prevents urllib3 from configuring SSL appropriately and may cause certain SSL connections to fail. You can upgrade to a newer version of Python to solve this. For more information, see https://urllib3.readthedocs.io/en/latest/advanced-usage.html#ssl-warnings
google.api_core.exceptions.PermissionDenied: 403 Missing or insufficient permissions.

That path is wrong as far as I can tell. Should be C:\Users\folder1\folder2\chatbot.json. You're missing \ after C:.

Solved the additional errors by;
import requests.packages.urllib3
requests.packages.urllib3.disable_warnings()

I had this problem too. It was caused by an old Python version (2.7.6) on Ubuntu 14.04.
Firebase requires SSLContext which was introduced in 2.7.9. I fixed it using this howto.

be careful
use this C:/../ instead c:\ ... \
don't forget:
cred = credentials.Certificate('C:/Users/ASPIREone/PycharmProjects/amazon/tester/serviceAccountKey.json')
firebase_admin.initialize_app(cred, {
'databaseURL': 'https://hrd-line.firebaseio.com'
})
db = firestore.client()
doc_ref = db.collection(u'users').document(u'president')
doc_ref.set({
u'first': u'Barrack',
u'last': u'Obama',
u'born': 1815
})

I got the same error (MAC USER)
Code fb_test.py
import firebase_admin
from firebase_admin import db
from firebase_admin import credentials
cred = credentials.Certificate("<dir>cred.json")
firebase_admin.initialize_app(cred, {'databaseURL':'https://<URL>'})
I ended adding the verify=False parameter on
/Users/<user>/.pyenv/versions/3.9.11/lib/python3.9/site-packages/google/auth/transport/requests.py
response = self.session.request(method, url, data=body, headers=headers,
timeout=timeout, verify=False, **kwargs)

Related

access ADFS/OIDC protected webapi with curl or python

I would like to access a webapi by a script(bash or python), which is protected by mod_openidc/apache2 and an self-hosted ADFS.
For the authentication, a certificate from a smartcard or locally stored certificate is required.
I already tried several approaches with python or curl, but got no nearly working script.
approach at python:
from oauthlib.oauth2 import BackendApplicationClient
from requests_oauthlib import OAuth2Session
client_id="abcdef-abcd-abcd-abcd-abcdefghijk"
client = BackendApplicationClient(client_id=client_id)
#client = BackendApplicationClient()
oauth = OAuth2Session(client=client)
protected_url="https://protectedurl/page/"
oauth.fetch_token(token_url='https://sts.myserver.net/adfs/oauth2/token/', include_client_id=True, cert=('/home/user/cert.pem', '/home/user/server.key'))
which lead to: "oauthlib.oauth2.rfc6749.errors.InvalidClientError: (invalid_client) MSIS9627: Received invalid OAuth client credentials request. Client credentials are missing or found empty"
curl:
curl --cert /home/user/cert.pem --key /home/user/server.key
https://sts.example.net/adfs/oauth2/authorize/?response_type=code&scope=openid%20email%20profile%20allatclaims&client_id=XXX&state=XXXredirect_uri=https%3A%2F%2Fexample.net%2Fpage%2Fredirect_uri&nonceXXX
Which gives the sts page in html
So I think I dont have some small bug, but a wrong approach
Since it works in a browser, I dont suggest a issue on server side
Any approaches and examples are warmly welcome

Trying to connect to Google cloud storage (GCS) using python

I've build the following script:
import boto
import sys
import gcs_oauth2_boto_plugin
def check_size_lzo(ds):
# URI scheme for Cloud Storage.
CLIENT_ID = 'myclientid'
CLIENT_SECRET = 'mysecret'
GOOGLE_STORAGE = 'gs'
dir_file= 'date_id={ds}/apollo_export_{ds}.lzo'.format(ds=ds)
gcs_oauth2_boto_plugin.SetFallbackClientIdAndSecret(CLIENT_ID, CLIENT_SECRET)
uri = boto.storage_uri('my_bucket/data/apollo/prod/'+ dir_file, GOOGLE_STORAGE)
key = uri.get_key()
if key.size < 45379959:
raise ValueError('umg lzo file is too small, investigate')
else:
print('umg lzo file is %sMB' % round((key.size/1e6),2))
if __name__ == "__main__":
check_size_lzo(sys.argv[1])
It works fine locally but when I try and run on kubernetes cluster I get the following error:
boto.exception.GSResponseError: GSResponseError: 403 Access denied to 'gs://my_bucket/data/apollo/prod/date_id=20180628/apollo_export_20180628.lzo'
I have updated the .boto file on my cluster and added my oauth client id and secret but still having the same issue.
Would really appreciate help resolving this issue.
Many thanks!
If it works in one environment and fails in another, I assume that you're getting your auth from a .boto file (or possibly from the OAUTH2_CLIENT_ID environment variable), but your kubernetes instance is lacking such a file. That you got a 403 instead of a 401 says that your remote server is correctly authenticating as somebody, but that somebody is not authorized to access the object, so presumably you're making the call as a different user.
Unless you've changed something, I'm guessing that you're getting the default Kubernetes Engine auth, with means a service account associated with your project. That service account probably hasn't been granted read permission for your object, which is why you're getting a 403. Grant it read/write permission for your GCS resources, and that should solve the problem.
Also note that by default the default credentials aren't scoped to include GCS, so you'll need to add that as well and then restart the instance.

Verifying firebase auth token permission denied

Following the directions in the google docs for using firebase for auth in GAE, I am sending an authorization token from Android to my backend python server. Reading that token using the following code:
import google.auth.transport.requests
import google.oauth2.id_token
HTTP_REQUEST = google.auth.transport.requests.Request()
id_token = headers['authorization'].split(' ').pop()
user_info = google.oauth2.id_token.verify_firebase_token(
id_token, HTTP_REQUEST)
results in the following stack trace:
File "/Users/alex/projects/don/don_server/mobile/main.py", line 61, in get_video
user_id = get_user_id(self.request_state.headers)
File "/Users/alex/projects/don/don_server/mobile/main.py", line 37, in get_user_id
id_token, HTTP_REQUEST)
File "/Users/alex/projects/don/don_server/mobile/lib/google/oauth2/id_token.py", line 115, in verify_firebase_token
id_token, request, audience=audience, certs_url=_GOOGLE_APIS_CERTS_URL)
File "/Users/alex/projects/don/don_server/mobile/lib/google/oauth2/id_token.py", line 76, in verify_token
certs = _fetch_certs(request, certs_url)
File "/Users/alex/projects/don/don_server/mobile/lib/google/oauth2/id_token.py", line 50, in _fetch_certs
response = request(certs_url, method='GET')
File "/Users/alex/projects/don/don_server/mobile/lib/google/auth/transport/requests.py", line 111, in __call__
raise exceptions.TransportError(exc)
TransportError: ('Connection aborted.', error(13, 'Permission denied'))
I've double checked my firebase project settings and localhost is listed as an authorized domain in the authentication sign-in section (I'm running this on the GAE local dev server).
As far as I can recall this was working a couple weeks ago. Any ideas?
UPDATE:
I implemented the same authentication using a service account as recommended in the firebase docs but am getting the same error message:
from firebase_admin import auth, credentials
import firebase_admin
fpath = os.path.join(os.path.dirname(__file__), 'shared', 'firebase-admin-private-key.json')
cred = credentials.Certificate(fpath)
firebase_admin.initialize_app(cred)
Then to process an incoming token
id_token = headers['authorization'].split(' ').pop()
user_info = auth.verify_id_token(id_token)
At some point I upgraded my requests library. Because requests doesn't play well with GAE, the calls to the firebase server failed. By downgrading to version 2.3.0 this now works.
pip install -t lib requests==2.3.0
Alternatively monkeypatching requests as suggested in this answer works as well!
import requests_toolbelt.adapters.appengine
requests_toolbelt.adapters.appengine.monkeypatch()

How to use Python requests to perform NTLM SSPI authentication?

My goal is to authenticate my client that uses the requests library (2.11.1) in Python 3.5.2 through NTLM with SSPI so that the user does not have to manually enter her domain credentials (used to login to the PC).
I have found the following possibilities, but none work for me:
HttpNtlmSspiAuth provokes an exception in requests:
import requests
from requests_ntlm import HttpNtlmAuth, HttpNtlmSspiAuth
requests.get(site_url, auth=HttpNtlmSspiAuth())
requests-sspi-ntlm always gets a 401:
import requests
from requests_sspi_ntlm import HttpNtlmAuth
session = requests.Session()
session.auth = HttpNtlmAuth()
session.get("http://ntlm_protected_site.com")
And requests-negotiate-sspi also triggers an exception in requests:
import requests
from requests_negotiate_sspi import HttpNegotiateAuth
r = requests.get('https://iis.contoso.com', auth=HttpNegotiateAuth())
Am I doing something wrong?
The package requests-negotiate-sspi works for me.
I probably had the same issue with PO, but I was too lazy to try PO's solution and integrate PO's code into mine. And Google helped me out. In case anyone encounters the same exception raised from sspi.py ValueError: year 30828 is out of range, it's a known issue for python 3.6 of requests-negotiate-sspi. See here: Github-Issue
I solved this by creating a new conda environment with python 3.4. Then reinstall some dependencies as well as requests-negotiate-sspi, boom, all works.
Same issue here but solved when I realized I was in a adm account that doesn’t have authorization to that resource uri.

Basic authentication with jira-python

I'm new to Python, new to the jira-python library, and new to network programming, though I do have quite a bit of experience with application and integration programming and database queries (though it's been a while).
Using Python 2.7 and requests 1.0.3
I'm trying to use this library - http://jira-python.readthedocs.org/en/latest/ to query Jira 5.1 using Python. I successfully connected using an unauthenticated query, though I had to make a change to a line in client.py, changing
I changed
self._session = requests.session(verify=verify, hooks={'args': self._add_content_type})
to
self._session = requests.session()
I didn't know what I was doing exactly but before the change I got an error and after the change I got a successful list of project names returned.
Then I tried basic authentication so I can take advantage of my Jira permissions and do reporting. That failed initially too. And I made the same change to
def _create_http_basic_session
in client.py , but now I just get another error. So problem not solved. Now I get a different error:
HTTP Status 415 - Unsupported Media Type
type Status report
message Unsupported Media Type
description The server refused this request because the request entity is in
a format not` `supported by the requested resource for the requested method
(Unsupported Media Type).
So then I decided to do a super simple test just using the requests module, which I believe is being used by the jira-python module and this code seemed to log me in. I got a good response:
import requests
r = requests.get(the_url, auth=(my username , password))
print r.text
Any suggestions?
Here's how I use the jira module with authentication in a Python script:
from jira.client import JIRA
import logging
# Defines a function for connecting to Jira
def connect_jira(log, jira_server, jira_user, jira_password):
'''
Connect to JIRA. Return None on error
'''
try:
log.info("Connecting to JIRA: %s" % jira_server)
jira_options = {'server': jira_server}
jira = JIRA(options=jira_options, basic_auth=(jira_user, jira_password))
# ^--- Note the tuple
return jira
except Exception,e:
log.error("Failed to connect to JIRA: %s" % e)
return None
# create logger
log = logging.getLogger(__name__)
# NOTE: You put your login details in the function call connect_jira(..) below!
# create a connection object, jc
jc = connect_jira(log, "https://myjira.mydom.com", "myusername", "mypassword")
# print names of all projects
projects = jc.projects()
for v in projects:
print v
Below Python script connects to Jira and does basic authentication and lists all projects.
from jira.client import JIRA
options = {'server': 'Jira-URL'}
jira = JIRA(options, basic_auth=('username', 'password'))
projects = jira.projects()
for v in projects:
print v
It prints a list of all the project's available within your instance of Jira.
Problem:
As of June 2019, Atlassian Cloud users who are using a REST endpoint in Jira or Confluence Cloud with basic or cookie-based authentication will need to update their app or integration processes to use an API token, OAuth, or Atlassian Connect.
After June 5th, 2019 attempts to authenticate via basic auth with an Atlassian account password will return an invalid credentials error.
Reference: Deprecation of basic authentication with passwords for Jira and Confluence APIs
Solution to the Above-mentioned Problem:
You can use an API token to authenticate a script or other process with an Atlassian cloud product. You generate the token from your Atlassian account, then copy and paste it to the script.
If you use two-step verification to authenticate, your script will need to use a REST API token to authenticate.
Steps to Create an API Token from your Atlassian Account:
Log in to https://id.atlassian.com/manage/api-tokens
Click Create API token.
From the dialog that appears, enter a memorable and concise Label for your token and click Create.
Click Copy to clipboard, then paste the token to your script.
Reference: API tokens
Python 3.8 Code Reference
from jira.client import JIRA
jira_client = JIRA(options={'server': JIRA_URL}, basic_auth=(JIRA_USERNAME, JIRA_TOKEN))
issue = jira_client.issue('PLAT-8742')
print(issue.fields.summary)
Don't change the library, instead put your credentials inside the ~/.netrc file.
If you put them there you will also be able to test your calls using curl or wget.
I am not sure anymore about compatibility with Jira 5.x, only 7.x and 6.4 are currently tested. If you setup an instance for testing I could modify the integration tests to run against it, too.
My lucky guess is that you broke it with that change.
As of 2019 Atlassian has deprecated authorizing with passwords.
You can easily replace the password with an API Token created here.
Here's a minimalistic example:
pip install jira
from jira import JIRA
jira = JIRA("YOUR-JIRA-URL", basic_auth=("YOUR-EMAIL", "YOUR-API-TOKEN"))
issue = jira.issue("YOUR-ISSUE-KEY (e.g. ABC-13)")
print(issue.fields.summary)
I recommend storing your API Token as an environment variable and accessing it with os.environ[key].

Categories