Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dev/#107 Authentication tokens for APIs #153

Merged
merged 39 commits into from
Oct 10, 2022
Merged
Show file tree
Hide file tree
Changes from 37 commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
5d3384a
testing flask db commands
tuz666 Jun 8, 2022
9559477
revert
tuz666 Jun 8, 2022
ff274af
first steps for testing flask-praetorian
tuz666 Jul 27, 2022
cfb206f
token generation is working now
tuz666 Aug 11, 2022
0d15cf3
test with flask-securitys auth token handling
tuz666 Aug 15, 2022
28182ee
hotfix
tuz666 Aug 15, 2022
8d5380e
working endpoint for the API token
tuz666 Aug 15, 2022
b358a6e
testing how it works with the CI
tuz666 Aug 15, 2022
9c09241
fixx
tuz666 Aug 15, 2022
ce55652
fix postman test
tuz666 Aug 15, 2022
c7de9ea
get_api_token working fine, show_all still returns 401
tuz666 Aug 15, 2022
1d88c33
added extra log into the postman tests
tuz666 Aug 15, 2022
8cf1583
set api_token before newman tests
tuz666 Aug 16, 2022
f39734d
we don't have to install curl
tuz666 Aug 16, 2022
3c14361
initialize api_token in separate newman run
tuz666 Aug 16, 2022
fce9b31
working hashed password
tuz666 Aug 16, 2022
a48c366
fixed arcsi view to handle tokens
tuz666 Aug 16, 2022
a2b6de9
fixed views
tuz666 Aug 16, 2022
881b47d
refining draft commit
tuz666 Aug 16, 2022
e1c33c0
fixxx
tuz666 Aug 16, 2022
097d223
added headers to some missing places
tuz666 Aug 16, 2022
3df654f
roles_required not working yet
tuz666 Aug 16, 2022
edaae1f
testing separate arcsi and api endpoint for adding shows
tuz666 Aug 24, 2022
8a26aa0
example for protected API used by a view function
tuz666 Aug 24, 2022
e184352
fixx
tuz666 Aug 24, 2022
36013d2
browser and API endpoints for show POST requests
tuz666 Aug 27, 2022
8c90e9b
add and edit helper functions for items
tuz666 Aug 27, 2022
16e25e2
separate browser and API endpoints for items
tuz666 Aug 27, 2022
2fcc1ce
fixed item edit APIs
tuz666 Aug 27, 2022
6c6b00c
fix postman test, edit item's id was not passed
tuz666 Aug 27, 2022
5da1406
removed some early dev usecases
tuz666 Aug 27, 2022
3e1df13
added token protection to the GET requests
tuz666 Aug 27, 2022
f904e55
added token headers for Postman's GET requests
tuz666 Aug 27, 2022
847a0bd
Merge branch 'master' into dev/#107-praetorian_authentication
tuz666 Aug 27, 2022
3165e93
added API token to user profile view
tuz666 Aug 28, 2022
56c8ea9
Merge branch 'dev/#107-praetorian_authentication' of github.com:mmmnm…
tuz666 Aug 28, 2022
da0220a
Add auth token for preflight mode in proxy
gammaw Sep 23, 2022
2c96300
reverting _add/_edit_show/item functions
tuz666 Oct 9, 2022
84e0973
updated Swagger docs
tuz666 Oct 9, 2022
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
162 changes: 90 additions & 72 deletions arcsi/api/item.py
Original file line number Diff line number Diff line change
@@ -1,28 +1,13 @@
from datetime import datetime, timedelta
import json
import os
import requests
import io

from mutagen.id3 import APIC, ID3
from mutagen.mp3 import MP3

from flask import flash, jsonify, make_response, request, send_file, url_for, redirect
from flask import current_app as app
from marshmallow import fields, post_load, Schema, ValidationError
from flask import jsonify, make_response, request, redirect
from flask_security import login_required, auth_token_required, roles_required
from marshmallow import fields, post_load, Schema
from sqlalchemy import func

from uuid import uuid4

from .utils import (
archive,
broadcast_audio,
dict_to_obj,
media_path,
normalise,
save_file,
item_duplications_number
)
from .utils import archive, broadcast_audio, normalise, save_file, item_duplications_number
from . import arcsi
from arcsi.handler.upload import DoArchive
from arcsi.model import db
Expand Down Expand Up @@ -80,6 +65,7 @@ def make_item(self, data, **kwargs):

@arcsi.route("/item", methods=["GET"])
@arcsi.route("/item/all", methods=["GET"])
@auth_token_required
def list_items():
do = DoArchive()
items = Item.query.all()
Expand All @@ -93,6 +79,7 @@ def list_items():


@arcsi.route("/item/latest", methods=["GET"])
@auth_token_required
def list_items_latest():
do = DoArchive()
page = request.args.get('page', 1, type=int)
Expand All @@ -111,6 +98,7 @@ def list_items_latest():


@arcsi.route("/item/<id>", methods=["GET"])
@auth_token_required
def view_item(id):
item_query = Item.query.filter_by(id=id)
item = item_query.first_or_404()
Expand All @@ -126,8 +114,89 @@ def view_item(id):
return make_response("Item not found", 404, headers)


@arcsi.route("/item", methods=["POST"])
@arcsi.route("/item/add", methods=["POST"])
@login_required
@roles_required("admin")
def add_item():
return _add_item()


@arcsi.route("/item/add_api", methods=["POST"])
@auth_token_required
@roles_required("admin")
def add_item_api():
return _add_item()


@arcsi.route("item/<id>/listen", methods=["GET"])
@auth_token_required
def listen_play_file(id):
do = DoArchive()
item_query = Item.query.filter_by(id=id)
item = item_query.first()
presigned = do.download(
item.shows[0].archive_lahmastore_base_url, item.archive_lahmastore_canonical_url
)
return presigned


@arcsi.route("/item/<id>/download", methods=["GET"])
@auth_token_required
def download_play_file(id):
do = DoArchive()
item_query = Item.query.filter_by(id=id)
item = item_query.first_or_404()
presigned = do.download(
item.shows[0].archive_lahmastore_base_url, item.archive_lahmastore_canonical_url
)
return redirect(presigned, code=302)


@arcsi.route("/item/<id>", methods=["DELETE"])
@auth_token_required
def delete_item(id):
item_query = Item.query.filter_by(id=id)
item = item_query.first_or_404()
item_query.delete()
db.session.commit()
return make_response("Deleted item successfully", 200, headers)


@arcsi.route("/item/<id>/edit", methods=["POST"])
@login_required
@roles_required("admin")
def edit_item(id):
return _edit_item(id)


@arcsi.route("/item/<id>/edit_api", methods=["POST"])
tuz666 marked this conversation as resolved.
Show resolved Hide resolved
@auth_token_required
@roles_required("admin")
def edit_item_api(id):
return _edit_item(id)


@arcsi.route("/item/search", methods=["GET"])
@auth_token_required
def search_item():
do = DoArchive()
page = request.args.get('page', 1, type=int)
size = request.args.get('size', 12, type=int)
param = request.args.get('param', "", type=str)
items = Item.query.filter(func.lower(Item.name).contains(func.lower(param)) |
func.lower(Item.description).contains(func.lower(param))
).filter(Item.play_date < datetime.today() - timedelta(days=1)
).order_by(Item.play_date.desc()).paginate(page, size, False)
for item in items.items:
if item.image_url:
item.image_url = do.download(
item.shows[0].archive_lahmastore_base_url, item.image_url
)
item.name_slug=normalise(item.name)
return items_schema.dumps(items.items)


def _add_item():
no_error = True
if request.is_json:
return make_response(
Expand Down Expand Up @@ -291,39 +360,7 @@ def add_item():
return "Some error happened, check server logs for details. Note that your media may have been uploaded (to DO and/or Azurcast)."


@arcsi.route("item/<id>/listen", methods=["GET"])
def listen_play_file(id):
do = DoArchive()
item_query = Item.query.filter_by(id=id)
item = item_query.first()
presigned = do.download(
item.shows[0].archive_lahmastore_base_url, item.archive_lahmastore_canonical_url
)
return presigned


@arcsi.route("/item/<id>/download", methods=["GET"])
def download_play_file(id):
do = DoArchive()
item_query = Item.query.filter_by(id=id)
item = item_query.first_or_404()
presigned = do.download(
item.shows[0].archive_lahmastore_base_url, item.archive_lahmastore_canonical_url
)
return redirect(presigned, code=302)


@arcsi.route("/item/<id>", methods=["DELETE"])
def delete_item(id):
item_query = Item.query.filter_by(id=id)
item = item_query.first_or_404()
item_query.delete()
db.session.commit()
return make_response("Deleted item successfully", 200, headers)


@arcsi.route("/item/<id>", methods=["POST"])
def edit_item(id):
def _edit_item(id):
no_error = True
image_file = None
image_file_name = None
Expand Down Expand Up @@ -465,22 +502,3 @@ def edit_item(id):
jsonify(item_partial_schema.dump(item)), 200, headers
)
return "Some error happened, check server logs for details. Note that your media may have been uploaded (to DO and/or Azurcast)."


@arcsi.route("/item/search", methods=["GET"])
def search_item():
do = DoArchive()
page = request.args.get('page', 1, type=int)
size = request.args.get('size', 12, type=int)
param = request.args.get('param', "", type=str)
items = Item.query.filter(func.lower(Item.name).contains(func.lower(param)) |
func.lower(Item.description).contains(func.lower(param))
).filter(Item.play_date < datetime.today() - timedelta(days=1)
).order_by(Item.play_date.desc()).paginate(page, size, False)
for item in items.items:
if item.image_url:
item.image_url = do.download(
item.shows[0].archive_lahmastore_base_url, item.image_url
)
item.name_slug=normalise(item.name)
return items_schema.dumps(items.items)
Loading