Private
Public Access
1
0

Merge branch 'feature/django4.2' into develop

This commit is contained in:
2024-05-31 14:43:09 +02:00
19 changed files with 317 additions and 58 deletions

1
.#requirementsdj4.2.txt Symbolic link
View File

@@ -0,0 +1 @@
sander@rowsandall-2.376838:1715854849

View File

@@ -1,5 +1,5 @@
from django.conf import settings from django.conf import settings
from django.conf.urls import url, include from django.conf.urls import include
from django.urls import path, re_path from django.urls import path, re_path
from django.views.generic.base import TemplateView from django.views.generic.base import TemplateView
@@ -7,21 +7,21 @@ from django.views.generic.base import TemplateView
import boatmovers.views as views import boatmovers.views as views
urlpatterns = [ urlpatterns = [
url(r'athlete/add/$',views.AthleteCreateView.as_view(),name='athlete_add'), re_path(r'athlete/add/$',views.AthleteCreateView.as_view(),name='athlete_add'),
url(r'athlete/(?P<id>\d+)/$',views.athlete_view,name='athlete_view'), re_path(r'athlete/(?P<id>\d+)/$',views.athlete_view,name='athlete_view'),
url(r'crew/add/$',views.CrewCreateView.as_view(),name='crew_add'), re_path(r'crew/add/$',views.CrewCreateView.as_view(),name='crew_add'),
url(r'race/add/$',views.RaceCreateView.as_view(),name='race_add'), re_path(r'race/add/$',views.RaceCreateView.as_view(),name='race_add'),
url(r'result/add/$',views.ResultCreateView.as_view(),name='result_add'), re_path(r'result/add/$',views.ResultCreateView.as_view(),name='result_add'),
url(r'race/(?P<id>\d+)/$',views.race_view,name='race_view'), re_path(r'race/(?P<id>\d+)/$',views.race_view,name='race_view'),
url(r'race/(?P<id>\d+)/csv/$',views.race_add_csv,name='race_add_csv'), re_path(r'race/(?P<id>\d+)/csv/$',views.race_add_csv,name='race_add_csv'),
url(r'race/(?P<id>\d+)/timeteam/$',views.race_handle_timeteam,name='race_handle_timeteam'), re_path(r'race/(?P<id>\d+)/timeteam/$',views.race_handle_timeteam,name='race_handle_timeteam'),
url(r'race/(?P<id>\d+)/verify/$',views.race_verify,name='race_verify'), re_path(r'race/(?P<id>\d+)/verify/$',views.race_verify,name='race_verify'),
url(r'race/(?P<id>\d+)/process/$',views.race_process,name='race_process'), re_path(r'race/(?P<id>\d+)/process/$',views.race_process,name='race_process'),
url(r'race/(?P<id>\d+)/deleteresults/$',views.race_delete_results, re_path(r'race/(?P<id>\d+)/deleteresults/$',views.race_delete_results,
name='race_delete_results'), name='race_delete_results'),
url(r'crew/(?P<id>\d+)/$',views.crew_view,name='crew_view'), re_path(r'crew/(?P<id>\d+)/$',views.crew_view,name='crew_view'),
url(r'^$',views.boatmovers_view,name='boatmovers'), re_path(r'^$',views.boatmovers_view,name='boatmovers'),
url(r'^compare/$',views.boatmovers_compareview,name='boatmovers_compare'), re_path(r'^compare/$',views.boatmovers_compareview,name='boatmovers_compare'),
path(r'faq/', TemplateView.as_view(template_name='faq.html'), name='faq'), path(r'faq/', TemplateView.as_view(template_name='faq.html'), name='faq'),
#url(r'(?P<filter>\b[0-9A-Fa-f]+\b)/$',views.boatmovers_view,name='boatmovers') #re_path(r'(?P<filter>\b[0-9A-Fa-f]+\b)/$',views.boatmovers_view,name='boatmovers')
] ]

18
diff.txt Normal file
View File

@@ -0,0 +1,18 @@
Install
common-fate-schema==0.7.0
types-python-dateutil==2.9.0.20240316
Upgrade
Django==4.2.13
django-tz-detect==0.5.0
geoip2
rowingdata
Uninstall
django-oauth2-provider==0.2.6.1
oauth2==1.9.0.post1
oauth2_provider==0.0

220
requirementsdj4.2.txt Normal file
View File

@@ -0,0 +1,220 @@
aiohttp==3.8.4
aiosignal==1.3.1
alabaster==0.7.13
amqp==5.1.1
arrow==1.2.3
asgiref==3.7.2
asttokens==2.2.1
async-timeout==4.0.2
attrs==23.1.0
Babel==2.12.1
backcall==0.2.0
beautifulsoup4==4.12.2
billiard==3.6.4.0
bleach==6.0.0
bokeh==3.1.1
boto3==1.26.159
botocore==1.29.159
braintree==4.21.0
celery==5.2.1
certifi==2023.5.7
cffi==1.15.1
charset-normalizer==3.1.0
click==8.1.3
click-didyoumean==0.3.0
click-plugins==1.1.1
click-repl==0.2.0
cloudpickle==2.2.1
colorcet==3.0.1
common-fate-schema==0.7.0
contourpy==1.0.7
coreapi==2.3.3
coreschema==0.0.4
coverage==7.2.7
cramjam==2.6.2
cryptography==41.0.1
cycler==0.11.0
Cython==0.29.35
dask==2023.5.1
decorator==5.1.1
Django==4.2.13
django-analytical==2.5.0
django-async-messages==0.3.1
django-classy-tags==4.0.0
django-cookie-law==2.0.1
django-cors-headers==3.10.1
django-countries==7.5.1
django-datetime-widget2==0.9.5
django-debug-toolbar==2.0
django-leaflet==0.28.2
django-oauth-toolkit==2.4.0
django-recaptcha==4.0.0
django-rest-framework==0.1.0
django-rest-swagger==2.2.0
django-rq==2.5.1
django-ses==2.0.0
django-shell-plus==1.1.7
django-social-share==1.3.2
django-taggit==4.0.0
django-tz-detect==0.5.0
djangorestframework==3.14.0
docopt==0.6.2
docutils==0.20.1
elementpath==4.3.0
exceptiongroup==1.1.1
execnet==2.1.1
executing==1.2.0
factory-boy==2.11.1
Faker==18.10.0
fastparquet==2023.4.0
fitparse==1.2.0
fonttools==4.39.4
frozenlist==1.3.3
fsspec==2023.5.0
future==0.18.3
geocoder==1.38.1
geoip2==4.7.0
greenlet==2.0.2
grpcio==1.26.0
gunicorn==21.2.0
h3==3.7.6
holoviews==1.16.0
httplib2==0.22.0
humanize==4.6.0
icalendar==5.0.7
idna==3.4
imagesize==1.4.1
importlib-metadata==6.6.0
importlib-resources==5.12.0
iniconfig==2.0.0
ipython==8.14.0
iso8601==1.1.0
isodate==0.6.1
itypes==1.2.0
jaraco.classes==3.2.3
jedi==0.18.2
jeepney==0.8.0
Jinja2==3.0.3
jmespath==1.0.1
jsmin==3.0.1
jwcrypto==1.5.6
keyring==23.13.1
kiwisolver==1.4.4
kombu==5.2.4
linkify-it-py==2.0.2
locket==1.0.0
lxml==4.9.2
Markdown==3.4.3
markdown-it-py==2.2.0
MarkupSafe==2.1.2
matplotlib==3.7.1
matplotlib-inline==0.1.6
maxminddb==2.3.0
mdit-py-plugins==0.3.5
mdurl==0.1.2
mock==5.0.2
more-itertools==9.1.0
mpld3==0.5.9
multidict==6.0.4
nose==1.3.7
nose-parameterized==0.6.0
numpy==1.24.3
oauthlib==3.2.2
openapi-codec==1.3.2
packaging==23.1
pandas==2.0.2
panel==1.0.4
param==1.13.0
parso==0.8.3
partd==1.4.0
pathspec==0.11.1
pendulum==2.1.2
pexpect==4.8.0
pickleshare==0.7.5
Pillow==9.5.0
Pint==0.22
pkginfo==1.9.6
pluggy==1.4.0
polars==0.20.18
prompt-toolkit==3.0.38
protobuf==4.25.3
ptyprocess==0.7.0
pure-eval==0.2.2
pyarrow==12.0.0
pycairo==1.23.0
pycparser==2.21
pyct==0.5.0
pydantic==1.10.8
Pygments==2.15.1
pyparsing==3.0.9
pytest==8.1.1
pytest-django==4.8.0
pytest-runner==6.0.0
pytest-xdist==3.5.0
python-dateutil==2.8.2
python-twitter==3.5
pytz==2024.1
pytzdata==2020.1
pyviz-comms==2.3.0
PyYAML==6.0
ratelim==0.1.6
readme-renderer==37.3
redis==4.5.5
requests==2.31.0
requests-oauthlib==1.2.0
requests-toolbelt==1.0.0
rfc3986==2.0.0
rich==13.4.1
rowingdata==3.6.10
rowingphysics==0.5.2
rq==1.15.0
rules==3.3
ruptures==1.1.7
s3transfer==0.6.1
scipy==1.10.1
SecretStorage==3.3.3
shortuuid==1.0.11
simplejson==3.19.1
six==1.16.0
snowballstemmer==2.2.0
soupsieve==2.4.1
Sphinx==7.0.1
sphinxcontrib-applehelp==1.0.4
sphinxcontrib-devhelp==1.0.2
sphinxcontrib-htmlhelp==2.0.1
sphinxcontrib-jsmath==1.0.1
sphinxcontrib-qthelp==1.0.3
sphinxcontrib-serializinghtml==1.1.5
SQLAlchemy==2.0.15
sqlparse==0.4.4
stack-data==0.6.2
stravalib==1.3.0
timezonefinder==6.2.0
tk==0.1.0
toml==0.10.2
tomli==2.0.1
toolz==0.12.0
tornado==6.3.2
tqdm==4.65.0
traitlets==5.9.0
trueskill==0.4.5
twine==4.0.2
types-python-dateutil==2.9.0.20240316
typing_extensions==4.6.3
tzdata==2023.3
uc-micro-py==1.0.2
uritemplate==4.1.1
urllib3==1.26.16
uWSGI==2.0.24
VerbalExpressions==0.0.2
vine==5.0.0
wcwidth==0.2.6
webencodings==0.5.1
Werkzeug==2.3.4
xmlschema==3.0.2
xmltodict==0.13.0
xyzservices==2023.5.0
yamjam==0.1.7
yamllint==1.32.0
yarl==1.9.2
zipp==3.15.0

View File

@@ -432,6 +432,7 @@ def resample(id, r, parent, overwrite='copy'):
def calculate_goldmedalstandard(rower, workout, recurrance=True): def calculate_goldmedalstandard(rower, workout, recurrance=True):
cpfile = 'media/cpdata_{id}.parquet.gz'.format(id=workout.id) cpfile = 'media/cpdata_{id}.parquet.gz'.format(id=workout.id)
try: try:
df = pl.read_parquet(cpfile) df = pl.read_parquet(cpfile)
except: except:
@@ -447,6 +448,7 @@ def calculate_goldmedalstandard(rower, workout, recurrance=True):
else: else:
return 0,0 return 0,0
if df.is_empty() and recurrance: # pragma: no cover if df.is_empty() and recurrance: # pragma: no cover
df, delta, cpvalues = setcp(workout, recurrance=False, background=True) df, delta, cpvalues = setcp(workout, recurrance=False, background=True)
if df.is_empty(): if df.is_empty():
@@ -562,7 +564,6 @@ def setcp(workout, background=False, recurrance=True):
return pl.DataFrame({'delta': [], 'cp': []}), pl.Series(dtype=pl.Float64), pl.Series(dtype=pl.Float64) return pl.DataFrame({'delta': [], 'cp': []}), pl.Series(dtype=pl.Float64), pl.Series(dtype=pl.Float64)
csvfile = os.path.abspath(csvfile) csvfile = os.path.abspath(csvfile)
with grpc.insecure_channel( with grpc.insecure_channel(
target='localhost:50052', target='localhost:50052',
options=[('grpc.lb_policy_name', 'pick_first'), options=[('grpc.lb_policy_name', 'pick_first'),

View File

@@ -117,7 +117,7 @@ def send_template_email(from_email, to_email, subject,
if createmessage: if createmessage:
for recipient in to_email: for recipient in to_email:
try: try:
soup = BeautifulSoup(html_content) soup = BeautifulSoup(html_content, 'lxml')
s2 = soup.body s2 = soup.body

View File

@@ -48,6 +48,7 @@ from sqlalchemy import create_engine
import sqlalchemy as sa import sqlalchemy as sa
from sqlite3 import OperationalError from sqlite3 import OperationalError
from django.utils import timezone from django.utils import timezone
from datetime import timezone as dt_timezone
import pandas as pd import pandas as pd
from dateutil import parser from dateutil import parser
import datetime import datetime
@@ -99,25 +100,25 @@ smoothingchoices = (
def half_year_from_now(ttz=None): def half_year_from_now(ttz=None):
if ttz is None: if ttz is None:
return (datetime.datetime.now(tz=timezone.utc)+timezone.timedelta(days=182)).date() return (datetime.datetime.now(tz=dt_timezone.utc)+timezone.timedelta(days=182)).date()
return (datetime.datetime.utcnow()+timezone.timedelta(days=182)).astimezone(pytz.timezone(ttz)).date() # pragma: no cover return (datetime.datetime.utcnow()+timezone.timedelta(days=182)).astimezone(pytz.timezone(ttz)).date() # pragma: no cover
def a_week_from_now(ttz=None): def a_week_from_now(ttz=None):
if ttz is None: if ttz is None:
return (datetime.datetime.now(tz=timezone.utc)+timezone.timedelta(days=7)).date() return (datetime.datetime.now(tz=dt_timezone.utc)+timezone.timedelta(days=7)).date()
return (datetime.datetime.utcnow()+timezone.timedelta(days=7)).astimezone(pytz.timezone(ttz)).date() # pragma: no cover return (datetime.datetime.utcnow()+timezone.timedelta(days=7)).astimezone(pytz.timezone(ttz)).date() # pragma: no cover
def current_day(ttz=None): def current_day(ttz=None):
if ttz is None: if ttz is None:
return (datetime.datetime.now(tz=timezone.utc)).date() return (datetime.datetime.now(tz=dt_timezone.utc)).date()
return datetime.datetime.utcnow().astimezone(pytz.timezone(ttz)).date() # pragma: no cover return datetime.datetime.utcnow().astimezone(pytz.timezone(ttz)).date() # pragma: no cover
def current_time(ttz=None): # pragma: no cover def current_time(ttz=None): # pragma: no cover
if ttz is None: if ttz is None:
return datetime.datetime.now(tz=timezone.utc) return datetime.datetime.now(tz=dt_timezone.utc)
return (datetime.datetime.utcnow()).astimezone(pytz.timezone(ttz)) # pragma: no cover return (datetime.datetime.utcnow()).astimezone(pytz.timezone(ttz)) # pragma: no cover

View File

@@ -1,7 +1,7 @@
# Interactions with Rowsandall.com API. Not fully complete. # Interactions with Rowsandall.com API. Not fully complete.
# Python # Python
import oauth2 as oauth #import oauth2 as oauth
import cgi import cgi
import requests import requests
import requests.auth import requests.auth

View File

@@ -62,7 +62,7 @@ from rowers.utils import NoTokenError
from rowers.plannedsessions import get_dates_timeperiod from rowers.plannedsessions import get_dates_timeperiod
from shutil import copyfile, copy from shutil import copyfile, copy
from nose.tools import assert_true from nose.tools import assert_true
from mock import Mock, patch from mock import Mock, patch, MagicMock
#from minimocktest import MockTestCase #from minimocktest import MockTestCase
import pandas as pd import pandas as pd
import polars as pl import polars as pl

View File

@@ -1103,7 +1103,8 @@ class WorkoutStatsTestNew(TestCase):
} }
request.COOKIES = SimpleCookie({'name': 'bla'}) request.COOKIES = SimpleCookie({'name': 'bla'})
# adding session # adding session
middleware = SessionMiddleware() get_response = MagicMock()
middleware = SessionMiddleware(get_response)
middleware.process_request(request) middleware.process_request(request)

View File

@@ -469,7 +469,8 @@ class SessionLinkTest(TestCase):
data=form_data) data=form_data)
# adding session # adding session
middleware = SessionMiddleware() get_response = MagicMock()
middleware = SessionMiddleware(get_response)
middleware.process_request(request) middleware.process_request(request)
request.session.save() request.session.save()
@@ -484,7 +485,7 @@ class SessionLinkTest(TestCase):
# and adding a get # and adding a get
request = self.factory.get(url) request = self.factory.get(url)
# adding session # adding session
middleware = SessionMiddleware() middleware = SessionMiddleware(get_response)
middleware.process_request(request) middleware.process_request(request)
request.session.save() request.session.save()

View File

@@ -856,7 +856,8 @@ class ChallengesTest(TestCase):
data=form_data) data=form_data)
# adding session # adding session
middleware = SessionMiddleware() get_response = MagicMock()
middleware = SessionMiddleware(get_response)
middleware.process_request(request) middleware.process_request(request)
request.session.save() request.session.save()

View File

@@ -41,7 +41,9 @@ class OtherUnitTests(TestCase):
# Test get_dates_timeperiod # Test get_dates_timeperiod
def test_get_dates_timeperiod(self): def test_get_dates_timeperiod(self):
rq = RequestFactory().get('/rowers/plannedsessions/') rq = RequestFactory().get('/rowers/plannedsessions/')
middleware = SessionMiddleware() get_response = MagicMock()
middleware = SessionMiddleware(get_response)
middleware.process_request(rq) middleware.process_request(rq)
# blanco should just run # blanco should just run

Binary file not shown.

View File

@@ -1,6 +1,6 @@
from oauth2_provider.views import base #from oauth2_provider.views import base
from django.conf import settings from django.conf import settings
from django.conf.urls import url, include, handler404, handler500 from django.conf.urls import include, handler404, handler500
from django.urls import path, re_path from django.urls import path, re_path
from django.contrib.auth.models import User from django.contrib.auth.models import User
from django.contrib.auth.decorators import login_required, permission_required from django.contrib.auth.decorators import login_required, permission_required
@@ -42,14 +42,14 @@ from rowers.forms import ForceCurveMultipleCompareForm
from rowers.models import ForceCurveAnalysis from rowers.models import ForceCurveAnalysis
from rowers.interactiveplots import forcecurve_multi_interactive_chart, instroke_multi_interactive_chart from rowers.interactiveplots import forcecurve_multi_interactive_chart, instroke_multi_interactive_chart
from oauth2_provider.views import ( #from oauth2_provider.views import (
AuthorizedTokensListView, # AuthorizedTokensListView,
AuthorizedTokenDeleteView, # AuthorizedTokenDeleteView,
) #)
from oauth2_provider.views.base import ( #from oauth2_provider.views.base import (
RevokeTokenView # RevokeTokenView
) #)
class PlannedSessionViewSet(viewsets.ModelViewSet): class PlannedSessionViewSet(viewsets.ModelViewSet):
@@ -237,8 +237,10 @@ handler500 = views.error500_view
urlpatterns = [ urlpatterns = [
re_path(r'^o/authorize/$', base.AuthorizationView.as_view(), name="authorize"), # re_path(r'^oauth2/', include('provider.oauth2.urls', namespace = 'oauth2')),
re_path(r'^o/token/$', base.TokenView.as_view(), name="token"), # re_path(r'^o/authorize/$', base.AuthorizationView.as_view(), name="authorize"),
# re_path(r'^o/token/$', base.TokenView.as_view(), name="token"),
re_path('^o/', include('oauth2_provider.urls', namespace='oauth2_provider')),
re_path(r'^', include(router.urls)), re_path(r'^', include(router.urls)),
re_path(r'^api-docs/$', views.schema_view, name='schema_view'), re_path(r'^api-docs/$', views.schema_view, name='schema_view'),
re_path(r'^api-auth/', include('rest_framework.urls', re_path(r'^api-auth/', include('rest_framework.urls',

View File

@@ -378,7 +378,7 @@ def get_crewnerd_liked(request):
# Stroke data views # Stroke data views
@csrf_exempt @csrf_exempt
@login_required() #@login_required()
@api_view(["POST"]) @api_view(["POST"])
@permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True) @permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True)
@permission_classes([IsAuthenticated]) @permission_classes([IsAuthenticated])
@@ -481,8 +481,8 @@ def strokedata_tcx(request):
@csrf_exempt @csrf_exempt
@login_required()
@api_view(["POST"]) @api_view(["POST"])
#@login_required()
@permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True) @permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True)
@permission_classes([IsAuthenticated]) @permission_classes([IsAuthenticated])
def strokedatajson_v3(request): def strokedatajson_v3(request):
@@ -517,6 +517,7 @@ def strokedatajson_v3(request):
} }
""" """
print("V3")
if request.method != 'POST': if request.method != 'POST':
return HttpResponseNotAllowed("Method not supported") # pragma: no cover return HttpResponseNotAllowed("Method not supported") # pragma: no cover
@@ -620,7 +621,7 @@ def strokedatajson_v3(request):
# Process the POSTed stroke data according to the API definition # Process the POSTed stroke data according to the API definition
# Return the GET stroke data according to the API definition # Return the GET stroke data according to the API definition
@csrf_exempt @csrf_exempt
@login_required() #@login_required()
@permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True) @permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True)
@api_view(["GET", "POST"]) @api_view(["GET", "POST"])
@permission_classes([IsAuthenticated]) @permission_classes([IsAuthenticated])
@@ -780,7 +781,7 @@ def strokedatajson_v2(request, id):
@csrf_exempt @csrf_exempt
@login_required() #@login_required()
@permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True) @permission_required('rower.is_not_freecoach', fn=get_user_by_userid, raise_exception=True)
@api_view(['GET', 'POST']) @api_view(['GET', 'POST'])
@permission_classes([IsAuthenticated]) @permission_classes([IsAuthenticated])

View File

@@ -1,4 +1,4 @@
from django.utils.encoding import force_bytes, force_text from django.utils.encoding import force_bytes, force_str
from rowers.tokens import account_activation_token from rowers.tokens import account_activation_token
from django.contrib.sites.shortcuts import get_current_site from django.contrib.sites.shortcuts import get_current_site
from django.utils.http import urlsafe_base64_encode, urlsafe_base64_decode from django.utils.http import urlsafe_base64_encode, urlsafe_base64_decode
@@ -782,7 +782,7 @@ def downgrade_completed_view(request):
def useractivate(request, uidb64, token): # pragma: no cover def useractivate(request, uidb64, token): # pragma: no cover
try: try:
uid = force_text(urlsafe_base64_decode(uidb64)) uid = force_str(urlsafe_base64_decode(uidb64))
user = User.objects.get(id=uid) user = User.objects.get(id=uid)
except(TypeError, ValueError, OverflowError, User.DoesNotExist): except(TypeError, ValueError, OverflowError, User.DoesNotExist):
user = None user = None

View File

@@ -3406,12 +3406,16 @@ def workout_data_view(request, id=0):
columns = datadf.columns.values columns = datadf.columns.values
to_be_dropped = [ to_be_dropped_all = [
'id', 'time', 'hr_an', 'hr_at', 'hr_bottom', 'hr_max', 'id', 'time', 'hr_an', 'hr_at', 'hr_bottom', 'hr_max',
'hr_tr', 'hr_ut1', 'hr_ut2', 'x_right', 'hr_tr', 'hr_ut1', 'hr_ut2', 'x_right',
] ]
to_be_dropped = [c for c in to_be_dropped if c in columns] to_be_dropped = []
for c in to_be_dropped_all:
if c in columns:
to_be_dropped.append(c)
datadf.drop(labels=to_be_dropped, inplace=True, axis=1) datadf.drop(labels=to_be_dropped, inplace=True, axis=1)
@@ -3686,7 +3690,6 @@ def workflow_default_view(request):
@login_required() @login_required()
def workout_workflow_config2_view(request, userid=0): def workout_workflow_config2_view(request, userid=0):
request.session['referer'] = absolute(request)['PATH'] request.session['referer'] = absolute(request)['PATH']
request.session[translation.LANGUAGE_SESSION_KEY] = USER_LANGUAGE
try: try:
workoutid = request.session['lastworkout'] workoutid = request.session['lastworkout']
except KeyError: except KeyError:
@@ -3735,7 +3738,6 @@ def workout_workflow_config2_view(request, userid=0):
def workout_workflow_view(request, id): def workout_workflow_view(request, id):
request.session['referer'] = absolute(request)['PATH'] request.session['referer'] = absolute(request)['PATH']
request.session['lastworkout'] = id request.session['lastworkout'] = id
request.session[translation.LANGUAGE_SESSION_KEY] = USER_LANGUAGE
row = get_workout_by_opaqueid(request, id) row = get_workout_by_opaqueid(request, id)
r = getrower(request.user) r = getrower(request.user)
@@ -3856,6 +3858,8 @@ def workout_flexchart3_view(request, *args, **kwargs):
favoritenr = 0 favoritenr = 0
except AssertionError: except AssertionError:
favoritenr = 0 favoritenr = 0
except ValueError:
favoritenr = 0
if 'xparam' in kwargs: if 'xparam' in kwargs:
xparam = kwargs['xparam'] xparam = kwargs['xparam']
@@ -4324,7 +4328,6 @@ def workout_comment_view(request, id=0):
@login_required() @login_required()
@permission_required('workout.change_workout', fn=get_workout_by_opaqueid, raise_exception=True) @permission_required('workout.change_workout', fn=get_workout_by_opaqueid, raise_exception=True)
def workout_edit_view(request, id=0, message="", successmessage=""): def workout_edit_view(request, id=0, message="", successmessage=""):
request.session[translation.LANGUAGE_SESSION_KEY] = USER_LANGUAGE
request.session['referer'] = absolute(request)['PATH'] request.session['referer'] = absolute(request)['PATH']
row = get_workoutuser(id, request) row = get_workoutuser(id, request)
@@ -4581,7 +4584,6 @@ def workout_edit_view(request, id=0, message="", successmessage=""):
@login_required() @login_required()
def workout_map_view(request, id=0): def workout_map_view(request, id=0):
request.session[translation.LANGUAGE_SESSION_KEY] = USER_LANGUAGE
request.session['referer'] = absolute(request)['PATH'] request.session['referer'] = absolute(request)['PATH']
w = get_workout(id) w = get_workout(id)
@@ -4811,11 +4813,12 @@ def workout_upload_api(request):
json_data = json.loads(request.body) json_data = json.loads(request.body)
secret = json_data['secret'] secret = json_data['secret']
post_data = json_data post_data = json_data
except (KeyError, JSONDecodeError): except:
q = request.POST q = request.POST
post_data = {k: q.getlist(k) if len( post_data = {k: q.getlist(k) if len(
q.getlist(k)) > 1 else v for k, v in q.items()} q.getlist(k)) > 1 else v for k, v in q.items()}
# only allow local host # only allow local host
hostt = request.get_host().split(':') hostt = request.get_host().split(':')
if hostt[0] not in ['localhost', '127.0.0.1', 'dev.rowsandall.com', 'rowsandall.com']: if hostt[0] not in ['localhost', '127.0.0.1', 'dev.rowsandall.com', 'rowsandall.com']:
@@ -4834,7 +4837,6 @@ def workout_upload_api(request):
message = {'status': 'false', 'message': 'invalid credentials'} message = {'status': 'false', 'message': 'invalid credentials'}
return JSONResponse(status=403, data=message) return JSONResponse(status=403, data=message)
form = DocumentsForm(post_data) form = DocumentsForm(post_data)
optionsform = TeamUploadOptionsForm(post_data) optionsform = TeamUploadOptionsForm(post_data)
rowerform = TeamInviteForm(post_data) rowerform = TeamInviteForm(post_data)

View File

@@ -72,6 +72,8 @@ INSTALLED_APPS = [
'datetimewidget', 'datetimewidget',
'rest_framework_swagger', 'rest_framework_swagger',
'oauth2_provider', 'oauth2_provider',
# 'provider',
# 'provider.oauth2',
'corsheaders', 'corsheaders',
'analytical', 'analytical',
'cookielaw', 'cookielaw',
@@ -86,10 +88,12 @@ INSTALLED_APPS = [
] ]
AUTHENTICATION_BACKENDS = ( AUTHENTICATION_BACKENDS = (
'oauth2_provider.backends.OAuth2Backend', #'oauth2_provider.backends.OAuth2Backend',
# Uncomment following if you want to access the admin # Uncomment following if you want to access the admin
'rules.permissions.ObjectPermissionBackend', 'rules.permissions.ObjectPermissionBackend',
'django.contrib.auth.backends.ModelBackend', 'django.contrib.auth.backends.ModelBackend',
'django.contrib.auth.backends.ModelBackend',
'django.contrib.auth.backends.RemoteUserBackend',
) )
MIDDLEWARE = [ MIDDLEWARE = [
@@ -105,7 +109,9 @@ MIDDLEWARE = [
'corsheaders.middleware.CorsMiddleware', 'corsheaders.middleware.CorsMiddleware',
'django.middleware.common.CommonMiddleware', 'django.middleware.common.CommonMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware', 'django.contrib.auth.middleware.AuthenticationMiddleware',
'oauth2_provider.middleware.OAuth2TokenMiddleware', # 'oauth2_provider.middleware.OAuth2TokenMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
#'provider.oauth2.middleware.Oauth2UserMiddleware',
'django.contrib.messages.middleware.MessageMiddleware', 'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware', 'django.middleware.clickjacking.XFrameOptionsMiddleware',
'tz_detect.middleware.TimezoneMiddleware', 'tz_detect.middleware.TimezoneMiddleware',
@@ -188,6 +194,8 @@ DATABASES = {
# Password validation # Password validation
# https://docs.djangoproject.com/en/1.9/ref/settings/#auth-password-validators # https://docs.djangoproject.com/en/1.9/ref/settings/#auth-password-validators
AUTH_USER_MLDEL = 'user.User'
AUTH_PASSWORD_VALIDATORS = [ AUTH_PASSWORD_VALIDATORS = [
{ {
'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator', 'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
@@ -450,7 +458,7 @@ OAUTH2_PROVIDER = {
'ACCESS_TOKEN_MODEL': 'oauth2_provider.AccessToken', 'ACCESS_TOKEN_MODEL': 'oauth2_provider.AccessToken',
'APPLICATION_MODEL': 'oauth2_provider.Application', 'APPLICATION_MODEL': 'oauth2_provider.Application',
'REFRESH_TOKEN_MODEL': 'oauth2_provider.RefreshToken', 'REFRESH_TOKEN_MODEL': 'oauth2_provider.RefreshToken',
'ACCESS_TOKEN_EXPIRE_SECONDS': 360000, 'ACCESS_TOKEN_EXPIRE_SECONDS': 3600000,
"PKCE_REQUIRED": False, "PKCE_REQUIRED": False,
# 'OAUTH2_BACKEND_CLASS': 'oauth2_provider.oauth2_backends.JSONOAuthLibCore' # 'OAUTH2_BACKEND_CLASS': 'oauth2_provider.oauth2_backends.JSONOAuthLibCore'
} }