Verified Commit 06b38add authored by Oliver Falk's avatar Oliver Falk

Merge branch 'devel' of git.linux-kernel.at:oliver/ivatar into devel

parents e9fe81a8 0cb30a82
# Generated by Django 3.0.3 on 2020-02-25 09:34
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('ivataraccount', '0014_auto_20190218_1602'),
]
operations = [
migrations.AddField(
model_name='confirmedopenid',
name='alt_digest1',
field=models.CharField(blank=True, default=None, max_length=64, null=True),
),
migrations.AddField(
model_name='confirmedopenid',
name='alt_digest2',
field=models.CharField(blank=True, default=None, max_length=64, null=True),
),
migrations.AddField(
model_name='confirmedopenid',
name='alt_digest3',
field=models.CharField(blank=True, default=None, max_length=64, null=True),
),
]
......@@ -32,6 +32,7 @@ from ivatar.settings import MAX_LENGTH_EMAIL, logger
from ivatar.settings import MAX_PIXELS, AVATAR_MAX_SIZE, JPEG_QUALITY
from ivatar.settings import MAX_LENGTH_URL
from ivatar.settings import SECURE_BASE_URL, SITE_NAME, DEFAULT_FROM_EMAIL
from ivatar.utils import openid_variations
from .gravatar import get_photo as get_gravatar_photo
......@@ -422,7 +423,15 @@ class ConfirmedOpenId(BaseAccountModel):
null=True,
on_delete=models.deletion.SET_NULL,
)
# http://<id>/ base version - http w/ trailing slash
digest = models.CharField(max_length=64)
# http://<id> - http w/o trailing slash
alt_digest1 = models.CharField(max_length=64, null=True, blank=True, default=None)
# https://<id>/ - https w/ trailing slash
alt_digest2 = models.CharField(max_length=64, null=True, blank=True, default=None)
# https://<id> - https w/o trailing slash
alt_digest3 = models.CharField(max_length=64, null=True, blank=True, default=None)
access_count = models.BigIntegerField(default=0, editable=False)
class Meta: # pylint: disable=too-few-public-methods
......@@ -450,10 +459,13 @@ class ConfirmedOpenId(BaseAccountModel):
lowercase_url = urlunsplit(
(url.scheme.lower(), netloc, url.path, url.query, url.fragment)
)
#if lowercase_url[-1] != '/':
# lowercase_url += '/'
self.openid = lowercase_url
self.digest = hashlib.sha256(lowercase_url.encode('utf-8')).hexdigest()
self.digest = hashlib.sha256(openid_variations(lowercase_url)[0].encode('utf-8')).hexdigest()
self.alt_digest1 = hashlib.sha256(openid_variations(lowercase_url)[1].encode('utf-8')).hexdigest()
self.alt_digest2 = hashlib.sha256(openid_variations(lowercase_url)[2].encode('utf-8')).hexdigest()
self.alt_digest3 = hashlib.sha256(openid_variations(lowercase_url)[3].encode('utf-8')).hexdigest()
return super().save(force_insert, force_update, using, update_fields)
def __str__(self):
......
'''
Test our utils from ivatar.utils
'''
from django.test import TestCase
from ivatar.utils import openid_variations
class Tester(TestCase):
'''
Main test class
'''
def test_openid_variations(self):
'''
Test if the OpenID variation "generator" does the correct thing
'''
openid0 = 'http://user.url/'
openid1 = 'http://user.url'
openid2 = 'https://user.url/'
openid3 = 'https://user.url'
# First variation
self.assertEqual(openid_variations(openid0)[0], openid0)
self.assertEqual(openid_variations(openid0)[1], openid1)
self.assertEqual(openid_variations(openid0)[2], openid2)
self.assertEqual(openid_variations(openid0)[3], openid3)
# Second varitations
self.assertEqual(openid_variations(openid1)[0], openid0)
self.assertEqual(openid_variations(openid1)[1], openid1)
self.assertEqual(openid_variations(openid1)[2], openid2)
self.assertEqual(openid_variations(openid1)[3], openid3)
# Third varitations
self.assertEqual(openid_variations(openid2)[0], openid0)
self.assertEqual(openid_variations(openid2)[1], openid1)
self.assertEqual(openid_variations(openid2)[2], openid2)
self.assertEqual(openid_variations(openid2)[3], openid3)
# Forth varitations
self.assertEqual(openid_variations(openid3)[0], openid0)
self.assertEqual(openid_variations(openid3)[1], openid1)
self.assertEqual(openid_variations(openid3)[2], openid2)
self.assertEqual(openid_variations(openid3)[3], openid3)
......@@ -11,3 +11,25 @@ def random_string(length=10):
'''
return ''.join(random.SystemRandom().choice(
string.ascii_lowercase + string.digits) for _ in range(length))
def openid_variations(openid):
'''
Return the various OpenID variations, ALWAYS in the same order:
- http w/ trailing slash
- http w/o trailing slash
- https w/ trailing slash
- https w/o trailing slash
'''
# Make the 'base' version: http w/ trailing slash
if openid.startswith('https://'):
openid = openid.replace('https://', 'http://')
if openid[-1] != '/':
openid = openid + '/'
# http w/o trailing slash
var1 = openid[0:-1]
var2 = openid.replace('http://', 'https://')
var3 = var2[0:-1]
return (openid, var1, var2, var3)
......@@ -12,6 +12,7 @@ from django.http import HttpResponse, HttpResponseRedirect, HttpResponseNotFound
from django.core.exceptions import ObjectDoesNotExist
from django.utils.translation import ugettext_lazy as _
from django.urls import reverse_lazy
from django.db.models import Q
from PIL import Image
......@@ -109,7 +110,15 @@ class AvatarImageView(TemplateView):
except ObjectDoesNotExist:
model = ConfirmedOpenId
try:
obj = model.objects.get(digest=kwargs['digest'])
d = kwargs['digest']
# OpenID is tricky. http vs. https, versus trailing slash or not
# However, some users eventually have added their variations already
# and therfore we need to use filter() and first()
obj = model.objects.filter(
Q(digest=d) |
Q(alt_digest1=d) |
Q(alt_digest2=d) |
Q(alt_digest3=d)).first()
except:
pass
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment