Skip to content

Commit

Permalink
Merge pull request #60 from CS222-UIUC/aden/oauth
Browse files Browse the repository at this point in the history
added google oauth
  • Loading branch information
akrakman authored Dec 6, 2022
2 parents 9d01d15 + 08be118 commit f92e514
Show file tree
Hide file tree
Showing 10 changed files with 144 additions and 602 deletions.
2 changes: 2 additions & 0 deletions .github/workflows/pylint.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ jobs:
pip install flask-cors
pip install BeautifulSoup4
pip install Flask-Session2
pip install Authlib
pip install requests
- name: Analysing the code with pylint
run: |
pylint $(git ls-files '*.py')
Expand Down
506 changes: 0 additions & 506 deletions package-lock.json

This file was deleted.

6 changes: 0 additions & 6 deletions package.json

This file was deleted.

59 changes: 51 additions & 8 deletions src/backend/app.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,34 +2,76 @@
import json
import dataclasses
from werkzeug.datastructures import MultiDict
from flask import Flask, request, session
from flask import Flask, request, session, url_for, redirect
from flask_cors import CORS
from authlib.integrations.flask_client import OAuth
from flask_session import Session
from pages.login import Login
from pages.mainpage import MainPage
from pages.userpage import UserPage
from dataholders.mainpage_get import GetRequestType, GetRequestParams


app = Flask(__name__)
SECRET_KEY = b"xe47Wxcdx86Wxac(mKlxa5xa2,xb3axc6xf1x86Fxc25x94xfc"
SESSION_TYPE = "filesystem"
app.config.from_object(__name__)
Session(app)
CORS(app, resources={r"/*": {"origins": "*"}}, supports_credentials=True)
oauth = OAuth(app)

google = oauth.register(
name="google",
client_id="410902541459-t10u2h0s4v2bnksbtq6futvmm2lke57k.apps.googleusercontent.com",
client_secret="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",
access_token_url="https://accounts.google.com/o/oauth2/token",
authorize_url="https://accounts.google.com/o/oauth2/auth",
api_base_url="https://www.googleapis.com/oauth2/v1/",
userinfo_endpoint="https://openidconnect.googleapis.com/v1/userinfo",
client_kwargs={"scope": "email"},
server_metadata_url="https://accounts.google.com/.well-known/openid-configuration",
)


@app.route("/googlelogin", methods=["GET", "POST"])
def googlelogin():
"""Handles google oauth login"""
google_client = oauth.create_client("google")
redirect_uri = url_for("authorize", _external=True) # move to the /authorize route
return google_client.authorize_redirect(redirect_uri)


@app.route("/authorize")
def authorize():
"""Authorization with google"""
google_client = oauth.create_client("google")
token = google_client.authorize_access_token()
resp = google_client.get("userinfo", token=token) # userinfo contains email
resp.raise_for_status() # check status code
user_info = resp.json() # convert to json
# query database for username and create session
page = UserPage(user_info["email"])
session["username"] = page.get_user(user_info["email"]).username
return (
redirect("http://localhost:3000"),
301,
) # necessary status code for Flask to auto-redirect


@app.route("/login", methods=["GET", "POST"])
def login():
"""Handles login routing"""
user_login = Login()
json_form = request.get_json(force=True)

if isinstance(json_form, dict):
username = json_form.get("user", "")
password = json_form.get("password", "")
remember = json_form.get("remember_me", False)
if user_login.login(username, password):
# session object makes User accessible in the backend
# A session object makes the User accessible in the backend
session["username"] = username
if remember:
session.permanent = True # Flask probably does this automatically
return f"welcome {username}", 200
return "User not found, please try again", 401
return "", 400
Expand Down Expand Up @@ -62,7 +104,7 @@ def userpage():
page = UserPage(name)
if request.method == "POST":
json_form = request.get_json(force=True) or {} # deserialize data
# see which field was True and therefore should be changed
# see which field is True and should be changed
is_password = json_form.get("is_password", False)
is_email = json_form.get("is_email", False)
is_phone = json_form.get("is_phone", False)
Expand All @@ -80,23 +122,24 @@ def userpage():
if not result:
return "invalid request", 400
return "success", 201
user = page.get_user(name) # request.method == "GET"
# request.method == "GET"
user = page.get_user(name)
data_dict = dataclasses.asdict(user)
return json.dumps(data_dict), 200


@app.route("/logout")
def logout():
"""Removes session object"""
session.pop("username", None) # remove session object
return "", 201
session.pop("username", None)
return "logout success", 201


@app.route("/api/whoami")
def whoami():
"""Shows whether a user is logged in and returns session username"""
if session.get("username") is None:
return "user logged out", 403
return "user is logged out", 403
username = session.get("username", "")
return str(username), 201

Expand Down
1 change: 0 additions & 1 deletion src/backend/pages/userpage.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ def get_user(self, query_sql: str) -> User:
@use_database
def update_password(self, password: str) -> bool:
"""Updates password based on username"""
# can use Flask-Hashing if we want
if not validate_password(password):
return False
if self.user.password == password:
Expand Down
4 changes: 3 additions & 1 deletion src/backend/requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,6 @@ pylint==2.15.2
coverage==6.4.4
black==22.8.0
Flask_Cors==3.0.10
Flask-Session2==1.3.1
Flask-Session2==1.3.1
Authlib==1.1.0
requests
13 changes: 12 additions & 1 deletion src/backend/tests/test_app.py
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ def test_login_valid(client):
)
connection.commit()

log_info = {"user": "big_finger", "password": "123456789"}
log_info = {"user": "big_finger", "password": "123456789", "remember_me": "True"}
res = client.post("/login", json=log_info)
cursor.execute("DELETE FROM Users WHERE username = ?", ("big_finger",))
connection.commit()
Expand Down Expand Up @@ -415,3 +415,14 @@ def test_whoami():
session["username"] = "Mike"
res = whoami()
assert res[0] == "Mike" and res[1] == 201


@use_test
def test_google_oauth_success(client):
"""Successful oauth login"""
res = client.get("/googlelogin")
print(res)
assert len(res.history) == 0
assert res.request.path == "/googlelogin"
# don't know how to test /authorize
# res2 = client.get("/authorize")
Loading

3 comments on commit f92e514

@github-actions
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Coverage

Coverage Report
FileStmtsMissCoverMissing
app.py171895%47–55
auth.py90100% 
config.py10100% 
decorators.py270100% 
dataholders
   apt.py90100% 
   mainpage_get.py160100% 
   review.py70100% 
   user.py80100% 
pages
   login.py290100% 
   mainpage.py1200100% 
   userpage.py530100% 
TOTAL450898% 

Tests Skipped Failures Errors Time
54 0 💤 0 ❌ 0 🔥 1.383s ⏱️

@github-actions
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Coverage

Coverage Report
FileStmtsMissCoverMissing
app.py171895%47–55
auth.py90100% 
config.py10100% 
decorators.py270100% 
dataholders
   apt.py90100% 
   mainpage_get.py160100% 
   review.py70100% 
   user.py80100% 
pages
   login.py290100% 
   mainpage.py1200100% 
   userpage.py530100% 
TOTAL450898% 

Tests Skipped Failures Errors Time
54 0 💤 0 ❌ 0 🔥 1.565s ⏱️

@github-actions
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Coverage

Coverage Report
FileStmtsMissCoverMissing
app.py171895%47–55
auth.py90100% 
config.py10100% 
decorators.py270100% 
dataholders
   apt.py90100% 
   mainpage_get.py160100% 
   review.py70100% 
   user.py80100% 
pages
   login.py290100% 
   mainpage.py1200100% 
   userpage.py530100% 
TOTAL450898% 

Tests Skipped Failures Errors Time
54 0 💤 0 ❌ 0 🔥 1.620s ⏱️

Please sign in to comment.