From ae00cccf1462b3a00befdb05d3aeb10eb68fb434 Mon Sep 17 00:00:00 2001
From: Eliot Berriot <contact@eliotberriot.com>
Date: Mon, 21 May 2018 19:04:28 +0200
Subject: [PATCH] Fix #207: Consistent constraints/checks for URL size

---
 .../migrations/0006_auto_20180521_1702.py     | 28 ++++++++
 api/funkwhale_api/federation/models.py        |  6 +-
 api/funkwhale_api/federation/serializers.py   | 70 +++++++++----------
 changes/changelog.d/207.bugfix                |  1 +
 4 files changed, 67 insertions(+), 38 deletions(-)
 create mode 100644 api/funkwhale_api/federation/migrations/0006_auto_20180521_1702.py
 create mode 100644 changes/changelog.d/207.bugfix

diff --git a/api/funkwhale_api/federation/migrations/0006_auto_20180521_1702.py b/api/funkwhale_api/federation/migrations/0006_auto_20180521_1702.py
new file mode 100644
index 00000000..7dcf8567
--- /dev/null
+++ b/api/funkwhale_api/federation/migrations/0006_auto_20180521_1702.py
@@ -0,0 +1,28 @@
+# Generated by Django 2.0.4 on 2018-05-21 17:02
+
+from django.db import migrations, models
+
+
+class Migration(migrations.Migration):
+
+    dependencies = [
+        ('federation', '0005_auto_20180413_1723'),
+    ]
+
+    operations = [
+        migrations.AlterField(
+            model_name='library',
+            name='url',
+            field=models.URLField(max_length=500),
+        ),
+        migrations.AlterField(
+            model_name='librarytrack',
+            name='audio_url',
+            field=models.URLField(max_length=500),
+        ),
+        migrations.AlterField(
+            model_name='librarytrack',
+            name='url',
+            field=models.URLField(max_length=500, unique=True),
+        ),
+    ]
diff --git a/api/funkwhale_api/federation/models.py b/api/funkwhale_api/federation/models.py
index 69d0ea92..8b4f2847 100644
--- a/api/funkwhale_api/federation/models.py
+++ b/api/funkwhale_api/federation/models.py
@@ -139,7 +139,7 @@ class Library(models.Model):
         on_delete=models.CASCADE,
         related_name='library')
     uuid = models.UUIDField(default=uuid.uuid4)
-    url = models.URLField()
+    url = models.URLField(max_length=500)
 
     # use this flag to disable federation with a library
     federation_enabled = models.BooleanField()
@@ -166,8 +166,8 @@ def get_file_path(instance, filename):
 
 
 class LibraryTrack(models.Model):
-    url = models.URLField(unique=True)
-    audio_url = models.URLField()
+    url = models.URLField(unique=True, max_length=500)
+    audio_url = models.URLField(max_length=500)
     audio_mimetype = models.CharField(max_length=200)
     audio_file = models.FileField(
         upload_to=get_file_path,
diff --git a/api/funkwhale_api/federation/serializers.py b/api/funkwhale_api/federation/serializers.py
index 8d3dd637..51561e22 100644
--- a/api/funkwhale_api/federation/serializers.py
+++ b/api/funkwhale_api/federation/serializers.py
@@ -26,16 +26,16 @@ logger = logging.getLogger(__name__)
 
 
 class ActorSerializer(serializers.Serializer):
-    id = serializers.URLField()
-    outbox = serializers.URLField()
-    inbox = serializers.URLField()
+    id = serializers.URLField(max_length=500)
+    outbox = serializers.URLField(max_length=500)
+    inbox = serializers.URLField(max_length=500)
     type = serializers.ChoiceField(choices=models.TYPE_CHOICES)
     preferredUsername = serializers.CharField()
     manuallyApprovesFollowers = serializers.NullBooleanField(required=False)
     name = serializers.CharField(required=False, max_length=200)
     summary = serializers.CharField(max_length=None, required=False)
-    followers = serializers.URLField(required=False, allow_null=True)
-    following = serializers.URLField(required=False, allow_null=True)
+    followers = serializers.URLField(max_length=500, required=False, allow_null=True)
+    following = serializers.URLField(max_length=500, required=False, allow_null=True)
     publicKey = serializers.JSONField(required=False)
 
     def to_representation(self, instance):
@@ -224,7 +224,7 @@ class APILibraryFollowUpdateSerializer(serializers.Serializer):
 
 
 class APILibraryCreateSerializer(serializers.ModelSerializer):
-    actor = serializers.URLField()
+    actor = serializers.URLField(max_length=500)
     federation_enabled = serializers.BooleanField()
     uuid = serializers.UUIDField(read_only=True)
 
@@ -315,9 +315,9 @@ class APILibraryTrackSerializer(serializers.ModelSerializer):
 
 
 class FollowSerializer(serializers.Serializer):
-    id = serializers.URLField()
-    object = serializers.URLField()
-    actor = serializers.URLField()
+    id = serializers.URLField(max_length=500)
+    object = serializers.URLField(max_length=500)
+    actor = serializers.URLField(max_length=500)
     type = serializers.ChoiceField(choices=['Follow'])
 
     def validate_object(self, v):
@@ -374,8 +374,8 @@ class APIFollowSerializer(serializers.ModelSerializer):
 
 
 class AcceptFollowSerializer(serializers.Serializer):
-    id = serializers.URLField()
-    actor = serializers.URLField()
+    id = serializers.URLField(max_length=500)
+    actor = serializers.URLField(max_length=500)
     object = FollowSerializer()
     type = serializers.ChoiceField(choices=['Accept'])
 
@@ -417,8 +417,8 @@ class AcceptFollowSerializer(serializers.Serializer):
 
 
 class UndoFollowSerializer(serializers.Serializer):
-    id = serializers.URLField()
-    actor = serializers.URLField()
+    id = serializers.URLField(max_length=500)
+    actor = serializers.URLField(max_length=500)
     object = FollowSerializer()
     type = serializers.ChoiceField(choices=['Undo'])
 
@@ -459,9 +459,9 @@ class UndoFollowSerializer(serializers.Serializer):
 
 class ActorWebfingerSerializer(serializers.Serializer):
     subject = serializers.CharField()
-    aliases = serializers.ListField(child=serializers.URLField())
+    aliases = serializers.ListField(child=serializers.URLField(max_length=500))
     links = serializers.ListField()
-    actor_url = serializers.URLField(required=False)
+    actor_url = serializers.URLField(max_length=500, required=False)
 
     def validate(self, validated_data):
         validated_data['actor_url'] = None
@@ -496,8 +496,8 @@ class ActorWebfingerSerializer(serializers.Serializer):
 
 
 class ActivitySerializer(serializers.Serializer):
-    actor = serializers.URLField()
-    id = serializers.URLField(required=False)
+    actor = serializers.URLField(max_length=500)
+    id = serializers.URLField(max_length=500, required=False)
     type = serializers.ChoiceField(
         choices=[(c, c) for c in activity.ACTIVITY_TYPES])
     object = serializers.JSONField()
@@ -539,8 +539,8 @@ class ActivitySerializer(serializers.Serializer):
 
 
 class ObjectSerializer(serializers.Serializer):
-    id = serializers.URLField()
-    url = serializers.URLField(required=False, allow_null=True)
+    id = serializers.URLField(max_length=500)
+    url = serializers.URLField(max_length=500, required=False, allow_null=True)
     type = serializers.ChoiceField(
         choices=[(c, c) for c in activity.OBJECT_TYPES])
     content = serializers.CharField(
@@ -554,16 +554,16 @@ class ObjectSerializer(serializers.Serializer):
     updated = serializers.DateTimeField(
         required=False, allow_null=True)
     to = serializers.ListField(
-        child=serializers.URLField(),
+        child=serializers.URLField(max_length=500),
         required=False, allow_null=True)
     cc = serializers.ListField(
-        child=serializers.URLField(),
+        child=serializers.URLField(max_length=500),
         required=False, allow_null=True)
     bto = serializers.ListField(
-        child=serializers.URLField(),
+        child=serializers.URLField(max_length=500),
         required=False, allow_null=True)
     bcc = serializers.ListField(
-        child=serializers.URLField(),
+        child=serializers.URLField(max_length=500),
         required=False, allow_null=True)
 
 OBJECT_SERIALIZERS = {
@@ -575,10 +575,10 @@ OBJECT_SERIALIZERS = {
 class PaginatedCollectionSerializer(serializers.Serializer):
     type = serializers.ChoiceField(choices=['Collection'])
     totalItems = serializers.IntegerField(min_value=0)
-    actor = serializers.URLField()
-    id = serializers.URLField()
-    first = serializers.URLField()
-    last = serializers.URLField()
+    actor = serializers.URLField(max_length=500)
+    id = serializers.URLField(max_length=500)
+    first = serializers.URLField(max_length=500)
+    last = serializers.URLField(max_length=500)
 
     def to_representation(self, conf):
         paginator = Paginator(
@@ -607,13 +607,13 @@ class CollectionPageSerializer(serializers.Serializer):
     type = serializers.ChoiceField(choices=['CollectionPage'])
     totalItems = serializers.IntegerField(min_value=0)
     items = serializers.ListField()
-    actor = serializers.URLField()
-    id = serializers.URLField()
-    first = serializers.URLField()
-    last = serializers.URLField()
-    next = serializers.URLField(required=False)
-    prev = serializers.URLField(required=False)
-    partOf = serializers.URLField()
+    actor = serializers.URLField(max_length=500)
+    id = serializers.URLField(max_length=500)
+    first = serializers.URLField(max_length=500)
+    last = serializers.URLField(max_length=500)
+    next = serializers.URLField(max_length=500, required=False)
+    prev = serializers.URLField(max_length=500, required=False)
+    partOf = serializers.URLField(max_length=500)
 
     def validate_items(self, v):
         item_serializer = self.context.get('item_serializer')
@@ -698,7 +698,7 @@ class AudioMetadataSerializer(serializers.Serializer):
 
 class AudioSerializer(serializers.Serializer):
     type = serializers.CharField()
-    id = serializers.URLField()
+    id = serializers.URLField(max_length=500)
     url = serializers.JSONField()
     published = serializers.DateTimeField()
     updated = serializers.DateTimeField(required=False)
diff --git a/changes/changelog.d/207.bugfix b/changes/changelog.d/207.bugfix
new file mode 100644
index 00000000..edab45cd
--- /dev/null
+++ b/changes/changelog.d/207.bugfix
@@ -0,0 +1 @@
+Consistent constraints/checks for URL size (#207)
-- 
GitLab