Python- flask digest auth with POSTMAN - python

So, I am trying to understand the digest authentication implementation with Python- Flask.
I did a simple test, I took the below code from the documentation,
from flask import Flask
from flask_httpauth import HTTPDigestAuth
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret key here'
auth = HTTPDigestAuth()
users = {
"john": "hello",
"susan": "bye"
}
#auth.get_password
def get_pw(username):
if username in users:
return users.get(username)
return None
#app.route('/', methods=['HEAD'])
#auth.login_required
def index():
return "Hello, %s!" % auth.username()
if __name__ == '__main__':
app.run()
The code runs.
I paste this URL(host:port) in same in POSTMAN(head method), it always returns 401.
I am lost and am trying to get it work.
What am I doing wrong here?

OK so here is what the problem is, the URL works fine in the browser but not in POSTMAN.
This is happening due to the name resolution in your case, e.g. 9mxlhm2
You need to make sure that it resolved that name, try and see if you can ping that name mentioned or else easiest fix just use **0.0.0.0**, if this is local.
Make sure the authorization info is mentioned when you are doing a HTTP request via postman. Under the request section there will be a Authorization section. See this image as an example.
To reproduce the problem i used localhost but it didn't work and it gives me an error with 401, as soon as i try 0.0.0.0 in the GET request via postman, it starts to work again. Hope this fixes your problem. Although the hostname for me works(as in my own hostname, e.g rajlocal)

Related

Python slackclient oauth.access call returning 'invalid_code' error

I am using ngrok + flask + python slackclient to respond to Slack API's OAuth Flow and I am receiving an invalid_code error.
I am following steps described in slackclient docs and my code is pretty simple so far:
import os
import slack
from flask import Flask, request
app = Flask(__name__)
SLACK_CLIENT_ID = os.environ['SLACK_CLIENT_ID']
SLACK_CLIENT_SECRET = os.environ['SLACK_CLIENT_SECRET']
#app.route('/install', methods=['GET', 'POST'])
def install():
# Retrieve the auth code from the request params
auth_code = request.args['code']
# An empty string is a valid token for this request
client = slack.WebClient(token='')
# Request the auth tokens from Slack
response = client.oauth_access(
client_id=SLACK_CLIENT_ID,
client_secret=SLACK_CLIENT_SECRET,
code=auth_code
)
print(response)
if __name__ == '__main__':
app.run()
I initiate the App installation from the "Add" button in my Slack workspace's Manage Apps page. I can confirm that I am receiving a code as expected once the installation is initiated, and it is being correctly passed through to the slack.BaseClient.api_call() function that eventually sends the request to https://slack.com/api/oauth.access.
I expect the response from the oauth_access call to be a JSON object containing my access tokens, however, I get:
slack.errors.SlackApiError: The request to the Slack API failed.
The server responded with: {'ok': False, 'error': 'invalid_code', 'warning': 'superfluous_charset', 'response_metadata': {'warnings': ['superfluous_charset']}}
I tried to send a POST with curl to Slack's endpoint with the required parameters and it worked as expected. I also tried with requests.post() and that also worked as expected. So I suspect that I am using slackclient incorrectly or have misunderstood something. Can anyone help point me in the right direction?
It seems to be a problem with the Python SDK. I think this pull request fixes this
https://github.com/slackapi/python-slackclient/pull/527
In the meantime it may be easier to revert to version 2.1.0
This issue is solved in v2.2.1 of slackclient
See changelog:
[WebClient] Oauth previously failed to pass along credentials properly. This is fixed now. #527

How to deal with Facebook's Verification requests on flask app

Im setting up a flask app on Heroku to set up web hooks for phishing certificates pulling from Facebook's certificate transparency api. I am trying to get pass facebook's verification requests (facebook sending a GET request asking for hub.challenge) however I do not understand how to give them the required information. Before suggesting I use facebook's prebuilt Heroku app, I am doing this to learn.
I tried looking up more information on GET requests however this hasn't helped me solve this problem.
This is facebook's website on this. https://developers.facebook.com/docs/graph-api/webhooks/getting-started#verification-requests
#app.route("/facebook", methods=['GET', 'POST'])
if request.method == 'GET':
def get_facebook(mode, challenge, verify_token):
#not sure what to put in here
After reviewing the docs, a few pointers:
You'll receive the request as a GET, so you won't need the 'POST' value in methods
The values sent from Facebook will be request args, and can be accessed using request.args.get('e.g.')
Facebook is expecting an int to be returned, which is up to you to decide what this is.
The result (disclaimer: this is untested!):
import datetime
from flask import jsonify
#app.route("/facebook", methods=['GET'])
def get_facebook():
my_token = 'abc123' # The token you setup on the App dashboard
if request.args.get('hub.verify_token') == my_token:
# The token is valid, return the (current datetime as an int)
# Assuming facebook is expecting a JSON result value
return jsonify({'hub.challenge': int(datetime.datetime.now().timestamp())})
return 'invalid', 403

Why am I getting a response from the wrong API endpoint?

I am following this tutorial initially I was trying to get a response using postman with the url
ec2-x-x-xxx-xx.eu-west-2.compute.amazonaws.com/:8080
but it would not return a response, so then I tried without the / at the end and it returned what I wanted, why is this happening as my flask route clearly has a / in it
My flask app looks like this
from flask import Flask
application = Flask(__name__)
#application.route("/")
def hello():
return "<h1 style='color:blue'>Hello There!</h1>"
if __name__ == '__main__':
application.run(host="0.0.0.0", port="8080")
The order of the parts of a URL is important.
The URL
ec2-x-x-xxx-xx.eu-west-2.compute.amazonaws.com/:8080
Is going to attempt port 80, and look for a path /:8080.
ec2-x-x-xxx-xx.eu-west-2.compute.amazonaws.com:8080/
Will attempt port 8080 and look for a path /
There are two different concepts that you are getting mixed up on here.
The line #application.route("/") defines the root of your site. That is the default entry point or path if you enter your site address in a browser without e.g /about at the end.
The address ec2-x-x-xxx-xx.eu-west-2.compute.amazonaws.com:8080 is a combination of the web server address and port, separated by a colon. You will not get a response if you alter this address. You could add a "/" after the 8080 to get to a particular page.

Python Flask local server not updating

I am starting to learn Flask, so I am a noob in this stuff, but I have ran out of ideas to implement, that is why I came here to ask. I have python script that makes a GET request to the API and it returns me a QRcode, after that I get the QRcode and add it to my html, everything works fine.
But I have this code checking for the JSON response that the API gives me, it haves three responses: "loading", "authenticated" & "got qr code".
req = requests.get('this is the link with my API token')
json_content = req.content
# parsed JSON content, ready to use
parsed_json = json.loads(json_content)
#app.route("/")
def index():
if parsed_json["accountStatus"] == "loading":
print(parsed_json["accountStatus"])
print(req.status_code)
return render_template("loading.html")
if parsed_json["accountStatus"] == "got qr code":
print(parsed_json["accountStatus"])
str_parsed_json = yaml.safe_load(parsed_json["qrCode"])
print(req.status_code)
return render_template("qrcodePage.html", str_parsed_json=str_parsed_json)
if parsed_json["accountStatus"] == "authenticated":
print(parsed_json["accountStatus"])
print(req.status_code)
return render_template("index.html")
if __name__ == "__main__":
app.run(host="0.0.0.0", port=8000, debug=True)
The response I am getting is a 200
I have searched all over the internet to see if someone else has the same issue as me, but I haven't found one person with this problem.
I have tried restarting the following
Restart my local server
Making True the debug thing in the app.run()
Check in PostMan the server response but it always return me the expected result, but changes are not seen in the page.
The only way it seems to work is when I make some changes to my code, and restart the server, that is when I can refresh the page and redirect me to the expected template file.
Thanks in advance.
Move your requests.get and all subsequent object based on that inside your index():
#app.route("/")
def index():
req = requests.get('this is the link with my API token')
json_content = req.content
# parsed JSON content, ready to use
parsed_json = json.loads(json_content)
if parsed_json["accountStatus"] == "loading":
print(parsed_json["accountStatus"])
return render_template("loading.html")
... rest of your code
Currently your requests is not being refreshed past the point of your server starting. But if you move it inside your #app.route("/") each time you visit the site's root page, it will do a new requests.get() to refresh your data.

Heroku - Python simple POST api, only can do GET (cannot do POST)

I want to do a web API which consist only POST. Currently I need to run python script on the web, so I am building a python web server from flask in Heroku. However, my issue is, whenever I send POST request from POSTMAN, what I will receive is the return data which is actually from GET request. Below is my code:
from flask import Flask
from flask import request
import os
app = Flask(__name__)
#app.route("/", methods=['GET', 'POST'])
def api_grab_key():
if request.method == 'POST':
if request.headers['Content-Type'] == 'application/json':
return request.json["imgUrl"]
else:
return "Request must be in JSON"
if request.method == 'GET':
return "Hello World! GET request"
if __name__ == "__main__":
port = int(os.environ.get('PORT', 33507))
app.run(host='0.0.0.0', port=port)
It works when I run locally, but not on Heroku. On Heroku, the output is always "Hello World! GET request" Thanks!
Sorry, apparently my issue is in the URL. So in Heroku, it has xxx.heroku.com and xxx.herokuapp.com.
I don't know why, requests sent to xxx.heroku.com turns into GET request. So, I had to change it to xxx.herokuapp.com for POST request.
I don't see anything jumping out, have you tried enabling debugging mode in Flask?
app.run(debug=True)
Then:
heroku logs --tail

Categories

Resources