diff --git a/Dockerfile b/Dockerfile
index 8c015f2b22350f1385ae55e40da81a185bf52a28..cf826e60f2f6eb93baa1a6cb95aca9e9abe2d799 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -1,16 +1,14 @@
-FROM python:3.7-alpine
+FROM python:3.8
 
 RUN mkdir /code
 WORKDIR /code
 COPY requirements.txt ./
 
-RUN apk add --no-cache nginx supervisor libpq \
-    && apk add --no-cache --virtual=.build-deps build-base postgresql-dev libffi-dev \
-    && pip install -r requirements.txt \
-    && pip install gunicorn \
-    && apk del .build-deps
-RUN rm /etc/nginx/conf.d/default.conf \
-    && echo "daemon off;" >> /etc/nginx/nginx.conf
+RUN apt-get update && apt-get install -y \
+    nginx supervisor
+RUN pip install -r requirements.txt \
+    && pip install gunicorn
+RUN echo "daemon off;" >> /etc/nginx/nginx.conf
 
 COPY . ./
 
diff --git a/openlobby/core/auth.py b/openlobby/core/auth.py
index 4508690585c4871ee48b8f5cf333f07dfe7968f3..40eb9d044d85568645be11f2cb7c1390c8f1f108 100644
--- a/openlobby/core/auth.py
+++ b/openlobby/core/auth.py
@@ -8,7 +8,7 @@ def create_access_token(username, expiration=None):
         expiration = int(time.time() + settings.SESSION_EXPIRATION)
     payload = {"sub": username, "exp": expiration}
     token = jwt.encode(payload, settings.SECRET_KEY, algorithm=settings.JWT_ALGORITHM)
-    return token.decode("utf-8")
+    return token
 
 
 def parse_access_token(token):
diff --git a/requirements.in b/requirements.in
index c240013d55ad6b3b5cb83a0bec02cf1269361c3f..5384b9f91bfcf903b9950787354b3a9c4161556b 100644
--- a/requirements.in
+++ b/requirements.in
@@ -1,9 +1,9 @@
-psycopg2-binary
-Django
+psycopg2-binary<2.9
+Django<3
 graphene
 graphene-django
 elasticsearch-dsl==6.1.0
-django-elasticsearch-dsl
+django-elasticsearch-dsl==0.5.0
 django-extensions
 oic
 pyjwt
diff --git a/requirements.txt b/requirements.txt
index f6eb71815d1a9d98c931a14e1d84719c3ab338a0..29014c478c55c8b616e4d0895349e03a96ea1ef9 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -1,48 +1,127 @@
 #
-# This file is autogenerated by pip-compile
+# This file is autogenerated by pip-compile with python 3.8
 # To update, run:
 #
-#    pip-compile --output-file requirements.txt requirements.in
+#    pip-compile requirements.in
 #
-alabaster==0.7.12         # via oic
-aniso8601==3.0.2          # via graphene
-arrow==0.12.1
-asn1crypto==0.24.0        # via cryptography
-beaker==1.10.0            # via oic
-bleach==3.0.2
-certifi==2018.10.15       # via requests
-cffi==1.11.5              # via cryptography
-chardet==3.0.4            # via requests
-cryptography==2.3.1       # via pyopenssl
+aniso8601==7.0.0
+    # via graphene
+arrow==1.2.0
+    # via -r requirements.in
+beaker==1.11.0
+    # via oic
+bleach==4.1.0
+    # via -r requirements.in
+certifi==2021.5.30
+    # via requests
+cffi==1.14.6
+    # via cryptography
+charset-normalizer==2.0.6
+    # via requests
+cryptography==35.0.0
+    # via oic
+defusedxml==0.7.1
+    # via oic
+django==2.2.24
+    # via
+    #   -r requirements.in
+    #   django-extensions
+    #   graphene-django
 django-elasticsearch-dsl==0.5.0
-django-extensions==2.1.3
-django==2.1.2
-dsnparse==0.1.12
+    # via -r requirements.in
+django-extensions==3.1.3
+    # via -r requirements.in
+dsnparse==0.1.15
+    # via -r requirements.in
+elasticsearch==6.8.2
+    # via elasticsearch-dsl
 elasticsearch-dsl==6.1.0
-elasticsearch==6.3.1      # via elasticsearch-dsl
-future==0.16.0            # via oic, pyjwkest
-graphene-django==2.2.0
-graphene==2.1.3
-graphql-core==2.1         # via graphene, graphene-django, graphql-relay
-graphql-relay==0.4.5      # via graphene
-idna==2.7                 # via cryptography, requests
-ipaddress==1.0.22         # via elasticsearch-dsl
-iso8601==0.1.12
-mako==1.0.7               # via oic
-markupsafe==1.0           # via mako
-oic==0.14.0
-promise==2.2.1            # via graphene, graphene-django, graphql-core, graphql-relay
-psycopg2-binary==2.7.5
-pycparser==2.19           # via cffi
-pycryptodomex==3.6.6      # via oic, pyjwkest
-pyjwkest==1.4.0           # via oic
-pyjwt==1.6.4
-pyopenssl==18.0.0         # via oic
-python-dateutil==2.7.3    # via arrow, elasticsearch-dsl
-pytz==2018.5              # via django
-requests==2.20.0          # via oic, pyjwkest
-rx==1.6.1                 # via graphql-core
-singledispatch==3.4.0.3   # via graphene-django
-six==1.11.0               # via bleach, cryptography, django-extensions, elasticsearch-dsl, graphene, graphene-django, graphql-core, graphql-relay, oic, promise, pyjwkest, pyopenssl, python-dateutil, singledispatch
-urllib3==1.24             # via elasticsearch, requests
-webencodings==0.5.1       # via bleach
+    # via
+    #   -r requirements.in
+    #   django-elasticsearch-dsl
+future==0.18.2
+    # via pyjwkest
+graphene==2.1.9
+    # via
+    #   -r requirements.in
+    #   graphene-django
+graphene-django==2.15.0
+    # via -r requirements.in
+graphql-core==2.3.2
+    # via
+    #   graphene
+    #   graphene-django
+    #   graphql-relay
+graphql-relay==2.0.1
+    # via graphene
+idna==3.2
+    # via requests
+ipaddress==1.0.23
+    # via elasticsearch-dsl
+iso8601==0.1.16
+    # via -r requirements.in
+mako==1.1.5
+    # via oic
+markupsafe==2.0.1
+    # via mako
+oic==1.3.0
+    # via -r requirements.in
+packaging==21.0
+    # via bleach
+promise==2.3
+    # via
+    #   graphene-django
+    #   graphql-core
+    #   graphql-relay
+psycopg2-binary==2.8.6
+    # via -r requirements.in
+pycparser==2.20
+    # via cffi
+pycryptodomex==3.10.4
+    # via
+    #   oic
+    #   pyjwkest
+pyjwkest==1.4.2
+    # via oic
+pyjwt==2.1.0
+    # via -r requirements.in
+pyparsing==2.4.7
+    # via packaging
+python-dateutil==2.8.2
+    # via
+    #   arrow
+    #   elasticsearch-dsl
+pytz==2021.1
+    # via django
+requests==2.26.0
+    # via
+    #   oic
+    #   pyjwkest
+rx==1.6.1
+    # via graphql-core
+singledispatch==3.7.0
+    # via graphene-django
+six==1.16.0
+    # via
+    #   bleach
+    #   elasticsearch-dsl
+    #   graphene
+    #   graphene-django
+    #   graphql-core
+    #   graphql-relay
+    #   promise
+    #   pyjwkest
+    #   python-dateutil
+    #   singledispatch
+sqlparse==0.4.2
+    # via django
+text-unidecode==1.3
+    # via graphene-django
+typing-extensions==3.10.0.2
+    # via oic
+urllib3==1.26.7
+    # via
+    #   elasticsearch
+    #   requests
+webencodings==0.5.1
+    # via bleach
diff --git a/test-requirements.txt b/test-requirements.txt
index 2cdcddcd067b279b9b3f67b150101aadfe03d542..f622e8a6374299b0a1257fb24337316a200d0120 100644
--- a/test-requirements.txt
+++ b/test-requirements.txt
@@ -1,25 +1,63 @@
 #
-# This file is autogenerated by pip-compile
+# This file is autogenerated by pip-compile with python 3.8
 # To update, run:
 #
-#    pip-compile --output-file test-requirements.txt test-requirements.in
+#    pip-compile test-requirements.in
 #
-atomicwrites==1.2.1       # via pytest
-attrs==18.2.0             # via pytest
-factory-boy==2.11.1       # via pytest-factoryboy
-faker==0.9.2              # via factory-boy
-freezegun==0.3.11         # via pytest-freezegun
-inflection==0.3.1         # via pytest-factoryboy
-more-itertools==4.3.0     # via pytest
-pluggy==0.8.0             # via pytest
-py==1.7.0                 # via pytest
-pytest-django==3.4.3
+attrs==21.2.0
+    # via pytest
+factory-boy==3.2.0
+    # via pytest-factoryboy
+faker==8.14.1
+    # via factory-boy
+fastdiff==0.3.0
+    # via snapshottest
+freezegun==1.1.0
+    # via pytest-freezegun
+inflection==0.5.1
+    # via pytest-factoryboy
+iniconfig==1.1.1
+    # via pytest
+packaging==21.0
+    # via pytest
+pluggy==1.0.0
+    # via pytest
+py==1.10.0
+    # via pytest
+pyparsing==2.4.7
+    # via packaging
+pytest==6.2.5
+    # via
+    #   -r test-requirements.in
+    #   pytest-django
+    #   pytest-env
+    #   pytest-factoryboy
+    #   pytest-freezegun
+pytest-django==4.4.0
+    # via -r test-requirements.in
 pytest-env==0.6.2
-pytest-factoryboy==2.0.1
-pytest-freezegun==0.2.0
-pytest==3.9.1
-python-dateutil==2.7.3    # via faker, freezegun
-six==1.11.0               # via faker, freezegun, more-itertools, pytest, python-dateutil, snapshottest
-snapshottest==0.5.0
-termcolor==1.1.0          # via snapshottest
-text-unidecode==1.2       # via faker
+    # via -r test-requirements.in
+pytest-factoryboy==2.1.0
+    # via -r test-requirements.in
+pytest-freezegun==0.4.2
+    # via -r test-requirements.in
+python-dateutil==2.8.2
+    # via
+    #   faker
+    #   freezegun
+six==1.16.0
+    # via
+    #   python-dateutil
+    #   snapshottest
+snapshottest==0.6.0
+    # via -r test-requirements.in
+termcolor==1.1.0
+    # via snapshottest
+text-unidecode==1.3
+    # via faker
+toml==0.10.2
+    # via pytest
+wasmer==1.0.0
+    # via fastdiff
+wasmer-compiler-cranelift==1.0.0
+    # via fastdiff
diff --git a/tests/factories.py b/tests/factories.py
index c6075eddfb99b2328cf871436a2127834a81ca68..fda5e1152a3e6ac7fe8e466a322d43653a6889f1 100644
--- a/tests/factories.py
+++ b/tests/factories.py
@@ -1,4 +1,5 @@
-from factory import DjangoModelFactory, Faker, SubFactory
+from factory import Faker, SubFactory
+from factory.django import DjangoModelFactory
 from django.conf import settings
 
 from openlobby.core.models import Report