From 2bafe9102c7bc696262cd14ec60e6c47712b0fb4 Mon Sep 17 00:00:00 2001 From: Sorrel Bri Date: Tue, 8 Oct 2019 16:56:28 -0700 Subject: [PATCH 1/5] add room endpoints --- api/api.py | 22 ++++++++++++++++++---- api/rooms/room.py | 7 ------- api/rooms/room_endpoint.py | 9 +++++++++ websockets/socket.py | 12 ++++++++++-- 4 files changed, 37 insertions(+), 13 deletions(-) delete mode 100644 api/rooms/room.py create mode 100644 api/rooms/room_endpoint.py diff --git a/api/api.py b/api/api.py index 78efbbb..3a88fc3 100644 --- a/api/api.py +++ b/api/api.py @@ -1,5 +1,6 @@ from flask import Blueprint, request, jsonify, session from .users.user_endpoint import UserEndpoint +from .users.room_endpoint import RoomEndpoint api = Blueprint('api', __name__, url_prefix='/api') @@ -8,10 +9,23 @@ def api_home(): response = {"message": "home page"} return jsonify(response) -@api.route('/users') -def api_users(): +@api.route('/users', methods=['GET']) +def api_get_users(): return jsonify(UserEndpoint.users()) -@api.route('/user') -def api_user(): +@api.route('/user', methods=['GET']) +def api_get_user(): return jsonify(UserEndpoint.user()) + +@api.route('/rooms', methods=['GET']) +def api_get_rooms(): + return RoomEndpoint.get_rooms() + +@api.route('/room', methods=['GET']) +def api_get_room(): + return RoomEndpoint.get_room() + +# protected route +@api.route('/room', methods=['POST']) +def api_post_room(): + return pass \ No newline at end of file diff --git a/api/rooms/room.py b/api/rooms/room.py deleted file mode 100644 index 13081d1..0000000 --- a/api/rooms/room.py +++ /dev/null @@ -1,7 +0,0 @@ -from flask import Blueprint - -room = Blueprint('rooms', __name__) - -@room.route('/') -def func(): - pass \ No newline at end of file diff --git a/api/rooms/room_endpoint.py b/api/rooms/room_endpoint.py new file mode 100644 index 0000000..5ba537d --- /dev/null +++ b/api/rooms/room_endpoint.py @@ -0,0 +1,9 @@ +from models.User import User, user_schema, users_schema +from models.Room import Room +from flask import request, jsonify, Response, json + +class RoomEndpoint(object): + def get_rooms(): + pass + def get_room(): + pass \ No newline at end of file diff --git a/websockets/socket.py b/websockets/socket.py index 5de2d8c..12c5e9d 100644 --- a/websockets/socket.py +++ b/websockets/socket.py @@ -9,9 +9,17 @@ def handle_connection(): cool ''') - send({'data':'connection'}) + emit('message', {'data':'connection'}) @socketio.on('message') def handle_message(message): print(message) - emit('message return', {'data':'a message was sent'}) \ No newline at end of file + emit('message return', {'message':'a message was sent'}, broadcast=True) + +@socketio.on('connect', namespace='/newroom') +def handle_connection(): + print(''' + + look cool a namespaced socketio connection! + + ''') \ No newline at end of file From 33584d6147e65edda878c377b7ab241d259cea4f Mon Sep 17 00:00:00 2001 From: Sorrel Bri Date: Tue, 8 Oct 2019 17:18:40 -0700 Subject: [PATCH 2/5] refactor api endpoints --- api/api.py | 29 ++++++++--------------------- api/rooms/api_rooms.py | 19 +++++++++++++++++++ api/rooms/room_endpoint.py | 9 --------- api/users/api_users.py | 25 +++++++++++++++++++++++++ api/users/user_endpoint.py | 15 --------------- server.py | 5 ++--- 6 files changed, 54 insertions(+), 48 deletions(-) create mode 100644 api/rooms/api_rooms.py delete mode 100644 api/rooms/room_endpoint.py create mode 100644 api/users/api_users.py delete mode 100644 api/users/user_endpoint.py diff --git a/api/api.py b/api/api.py index 3a88fc3..8703d27 100644 --- a/api/api.py +++ b/api/api.py @@ -1,31 +1,18 @@ from flask import Blueprint, request, jsonify, session -from .users.user_endpoint import UserEndpoint -from .users.room_endpoint import RoomEndpoint +from .users.api_users import api_users +from .rooms.api_rooms import api_rooms api = Blueprint('api', __name__, url_prefix='/api') +def register_api_endpoints(app): + app.register_blueprint(api_users) + app.register_blueprint(api_rooms) + app.register_blueprint(api) + return app + @api.route('/home', methods=['GET']) def api_home(): response = {"message": "home page"} return jsonify(response) -@api.route('/users', methods=['GET']) -def api_get_users(): - return jsonify(UserEndpoint.users()) -@api.route('/user', methods=['GET']) -def api_get_user(): - return jsonify(UserEndpoint.user()) - -@api.route('/rooms', methods=['GET']) -def api_get_rooms(): - return RoomEndpoint.get_rooms() - -@api.route('/room', methods=['GET']) -def api_get_room(): - return RoomEndpoint.get_room() - -# protected route -@api.route('/room', methods=['POST']) -def api_post_room(): - return pass \ No newline at end of file diff --git a/api/rooms/api_rooms.py b/api/rooms/api_rooms.py new file mode 100644 index 0000000..19c3346 --- /dev/null +++ b/api/rooms/api_rooms.py @@ -0,0 +1,19 @@ +from models.User import User, user_schema, users_schema +from models.GameRoom import GameRoom +from flask import Blueprint, request, jsonify, session + +api_rooms = Blueprint('api_rooms', __name__, url_prefix='/api/rooms') + +@api_rooms.route('/', methods=['GET']) +def get_room(): + pass + +@api_rooms.route('/', methods=['GET']) +def get_rooms(): + response = {"status" : "success"} + return jsonify(response) + +# protected route +@api_rooms.route('/', methods=['POST']) +def post_room(): + pass \ No newline at end of file diff --git a/api/rooms/room_endpoint.py b/api/rooms/room_endpoint.py deleted file mode 100644 index 5ba537d..0000000 --- a/api/rooms/room_endpoint.py +++ /dev/null @@ -1,9 +0,0 @@ -from models.User import User, user_schema, users_schema -from models.Room import Room -from flask import request, jsonify, Response, json - -class RoomEndpoint(object): - def get_rooms(): - pass - def get_room(): - pass \ No newline at end of file diff --git a/api/users/api_users.py b/api/users/api_users.py new file mode 100644 index 0000000..e6d4183 --- /dev/null +++ b/api/users/api_users.py @@ -0,0 +1,25 @@ +from models.User import User, user_schema, users_schema +from flask import Blueprint, request, json, session, jsonify + +api_users = Blueprint('api_users', __name__, url_prefix='/api') + +@api_users.route('/users/', methods=['GET']) +def api_get_users(): + print('called one') + users = User.query.all() + response = users_schema.dumps(users) + return jsonify(response) + +@api_users.route('/users/account', methods=['GET']) +def api_get_user(): + print('called') + auth_header = request.headers.get('Authorization') or None + if auth_header: + auth_token = auth_header.split(" ")[1] + user = User.decode_auth_token(auth_token) or None + response = json.dumps(user) + else: + response = { + 'status': 'failed', + 'message': 'Please Log In'} + return jsonify(response) diff --git a/api/users/user_endpoint.py b/api/users/user_endpoint.py deleted file mode 100644 index c5413ab..0000000 --- a/api/users/user_endpoint.py +++ /dev/null @@ -1,15 +0,0 @@ -from models.User import User, user_schema, users_schema -from flask import request, jsonify, Response, json - -class UserEndpoint(object): - def users(): - users = User.query.all() - response = users_schema.dumps(users) - return response - def user(): - - auth_header = request.headers.get('Authorization') or None - auth_token = auth_header.split(" ")[1] - user = User.decode_auth_token(auth_token) or None - response = json.dumps(user) - return response \ No newline at end of file diff --git a/server.py b/server.py index bebf6c1..226bf96 100644 --- a/server.py +++ b/server.py @@ -1,7 +1,7 @@ from app import create_app, db # Blueprints -from api.api import api +from api.api import register_api_endpoints from auth.auth import auth # Web sockets @@ -14,7 +14,6 @@ from flask_migrate import Migrate if __name__ == '__main__': app = create_app() - app.register_blueprint(api) - app.register_blueprint(auth) + register_api_endpoints(app) migrate = Migrate(app, db) socketio.run(app, debug=True) \ No newline at end of file From 34182fdc23b1af0fb515ee48cebfcd857f479592 Mon Sep 17 00:00:00 2001 From: Sorrel Bri Date: Tue, 8 Oct 2019 18:03:46 -0700 Subject: [PATCH 3/5] stub jwt_required decorator to protect routes --- api/decorators.py | 13 +++++++++++++ api/users/api_users.py | 3 +++ 2 files changed, 16 insertions(+) create mode 100644 api/decorators.py diff --git a/api/decorators.py b/api/decorators.py new file mode 100644 index 0000000..a34620f --- /dev/null +++ b/api/decorators.py @@ -0,0 +1,13 @@ +from flask import Blueprint, request, jsonify, session + +def jwt_required(): + def decorator(func): + def authorized(*args, **kwargs): + auth_header = request.headers.get('Authorization') or None + if auth_header: + # check secret on auth header + return func(*args, **kwargs) + else: + abort(401) + return authorized + return decorator \ No newline at end of file diff --git a/api/users/api_users.py b/api/users/api_users.py index e6d4183..d4f3f17 100644 --- a/api/users/api_users.py +++ b/api/users/api_users.py @@ -1,5 +1,6 @@ from models.User import User, user_schema, users_schema from flask import Blueprint, request, json, session, jsonify +from ..decorators import jwt_required api_users = Blueprint('api_users', __name__, url_prefix='/api') @@ -10,7 +11,9 @@ def api_get_users(): response = users_schema.dumps(users) return jsonify(response) + @api_users.route('/users/account', methods=['GET']) +@jwt_required() def api_get_user(): print('called') auth_header = request.headers.get('Authorization') or None From 8cd08567281b53c3fd24e48dfd849e7db9d1292c Mon Sep 17 00:00:00 2001 From: Sorrel Bri Date: Tue, 8 Oct 2019 22:53:37 -0700 Subject: [PATCH 4/5] add rooms post route --- api/decorators.py | 10 ++++++++-- api/rooms/api_rooms.py | 26 +++++++++++++++++++++++++- models/GameRoom.py | 23 ++++++++++++++++++++--- models/User.py | 6 ++---- 4 files changed, 55 insertions(+), 10 deletions(-) diff --git a/api/decorators.py b/api/decorators.py index a34620f..58f1a65 100644 --- a/api/decorators.py +++ b/api/decorators.py @@ -1,12 +1,18 @@ from flask import Blueprint, request, jsonify, session +import os +import jwt def jwt_required(): def decorator(func): def authorized(*args, **kwargs): auth_header = request.headers.get('Authorization') or None + print(User.decode_auth_token(auth_header.split(" ")[1])) if auth_header: - # check secret on auth header - return func(*args, **kwargs) + auth_token = auth_header.split(" ")[1] + if jwt.decode(auth_token, os.environ.get('SECRET_KEY')): + return func(*args, **kwargs) + else: + abort(401) else: abort(401) return authorized diff --git a/api/rooms/api_rooms.py b/api/rooms/api_rooms.py index 19c3346..f470349 100644 --- a/api/rooms/api_rooms.py +++ b/api/rooms/api_rooms.py @@ -1,6 +1,7 @@ from models.User import User, user_schema, users_schema from models.GameRoom import GameRoom from flask import Blueprint, request, jsonify, session +from ..decorators import jwt_required api_rooms = Blueprint('api_rooms', __name__, url_prefix='/api/rooms') @@ -15,5 +16,28 @@ def get_rooms(): # protected route @api_rooms.route('/', methods=['POST']) +@jwt_required() def post_room(): - pass \ No newline at end of file + data = request.get_json() + try: + room = GameRoom( + name = data['name'], + description = data['description'], + private = data['private'], + language = data['language'] + ) + db.session.add(room) + db.session.commit() + response = { + 'status': 'success', + 'message': 'Succesfully registered.', + 'gameRoom': room.id + } + return jsonify(response), 201 + except Exception as e: + print(e.__dict__) + response = { + 'status': 'fail', + 'message': 'There was an error. Please try again.' + } + return jsonify(response), 401 \ No newline at end of file diff --git a/models/GameRoom.py b/models/GameRoom.py index 3e5239c..0a83fb3 100644 --- a/models/GameRoom.py +++ b/models/GameRoom.py @@ -1,8 +1,14 @@ from app import db, ma +# TODO User >---< GameRoom import enum +game_rooms_users = db.Table('game_rooms_users', + db.Column('user_id', db.Integer, db.ForeignKey('users.id'), primary_key=True), + db.Column('game_rooms_id', db.Integer, db.ForeignKey('game_rooms.id'), primary_key=True) +) + class Languages(enum.Enum): - EN: "English" + EN = "English" class GameRoom(db.Model): __tablename__ = "game_rooms" @@ -14,5 +20,16 @@ class GameRoom(db.Model): private = db.Column(db.Boolean(), nullable=False, default=False) language = db.Column(db.Enum(Languages), nullable=False) - def __init__(self): - pass \ No newline at end of file + # ! Foreign Keys + users = db.relationship( + 'User', + secondary=game_rooms_users, + lazy='subquery', + backref=db.backref('game_rooms', lazy=True) + ) + + def __init__(self, name, description, private=False, language=Languages.EN): + self.name = name + self.description = description + self.private = private + self.language = language diff --git a/models/User.py b/models/User.py index 917df4c..73c6bea 100644 --- a/models/User.py +++ b/models/User.py @@ -46,7 +46,7 @@ class Ranks(enum.Enum): # with minimal Elo rating K28 = "Twenty-Eight Kyu" K29 = "Twenty-Nine Kyu" K30 = "Thirty Kyu" # Elo -900 - RU = "Unknown Rank" + UR = "Unknown Rank" class User(db.Model): __tablename__ = "users" @@ -61,9 +61,7 @@ class User(db.Model): elo = db.Column(db.Integer) rank_certainty = db.Column(db.Boolean, nullable=False, default=False) - def __init__(self, username, email, password, rank=Ranks.K1, admin=False): - print(rank) - print(Ranks) + def __init__(self, username, email, password, rank=Ranks.UR, admin=False): self.username = username self.email = email self.password = bcrypt.generate_password_hash( From 9380f0485cbb4c5fb5e7a16283086dea3c5a5f64 Mon Sep 17 00:00:00 2001 From: Sorrel Bri Date: Wed, 9 Oct 2019 00:08:37 -0700 Subject: [PATCH 5/5] debug auth --- api/api.py | 3 +++ api/decorators.py | 1 - api/rooms/api_rooms.py | 2 +- auth/auth.py | 1 + 4 files changed, 5 insertions(+), 2 deletions(-) diff --git a/api/api.py b/api/api.py index 8703d27..c1b926a 100644 --- a/api/api.py +++ b/api/api.py @@ -2,12 +2,15 @@ from flask import Blueprint, request, jsonify, session from .users.api_users import api_users from .rooms.api_rooms import api_rooms +from auth.auth import auth + api = Blueprint('api', __name__, url_prefix='/api') def register_api_endpoints(app): app.register_blueprint(api_users) app.register_blueprint(api_rooms) app.register_blueprint(api) + app.register_blueprint(auth) return app @api.route('/home', methods=['GET']) diff --git a/api/decorators.py b/api/decorators.py index 58f1a65..e971bec 100644 --- a/api/decorators.py +++ b/api/decorators.py @@ -6,7 +6,6 @@ def jwt_required(): def decorator(func): def authorized(*args, **kwargs): auth_header = request.headers.get('Authorization') or None - print(User.decode_auth_token(auth_header.split(" ")[1])) if auth_header: auth_token = auth_header.split(" ")[1] if jwt.decode(auth_token, os.environ.get('SECRET_KEY')): diff --git a/api/rooms/api_rooms.py b/api/rooms/api_rooms.py index f470349..37ac0ff 100644 --- a/api/rooms/api_rooms.py +++ b/api/rooms/api_rooms.py @@ -5,7 +5,7 @@ from ..decorators import jwt_required api_rooms = Blueprint('api_rooms', __name__, url_prefix='/api/rooms') -@api_rooms.route('/', methods=['GET']) +@api_rooms.route('/', methods=['GET']) def get_room(): pass diff --git a/auth/auth.py b/auth/auth.py index 1ead3fb..c263c6e 100644 --- a/auth/auth.py +++ b/auth/auth.py @@ -52,6 +52,7 @@ def auth_login(): try: # fetch the user data print('getting here') + print(data) user = User.query.filter_by(email=data['email']).first() print(user.username) auth_token = user.encode_auth_token(user.id)