Skip to content

Commit

Permalink
add tests for tag slugging (codebuddies#121)
Browse files Browse the repository at this point in the history
* add tests for tag slugging

* validate slugs on model save
    - prevent generation of tag with non-unique slug
    - prevent generation of tag with name containing
      only invalid characters

* skip assertions about brahmic/abugida slugs

Co-authored-by: BethanyG <BethanyG@users.noreply.github.com>
  • Loading branch information
chris48s and BethanyG authored Apr 7, 2020
1 parent 1ad65a9 commit 412d7dd
Show file tree
Hide file tree
Showing 4 changed files with 105 additions and 10 deletions.
2 changes: 1 addition & 1 deletion project/resources/migrations/0006_auto_20200303_1257.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ class Migration(migrations.Migration):

dependencies = [
('resources', '0005_auto_20200118_1036'),
('tagging', '__latest__')
('tagging', '0001_initial')
]

operations = [
Expand Down
18 changes: 18 additions & 0 deletions project/tagging/migrations/0002_auto_20200405_0312.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
# Generated by Django 2.2.4 on 2020-04-05 10:12

from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('tagging', '0001_initial'),
]

operations = [
migrations.AlterField(
model_name='customtag',
name='slug',
field=models.SlugField(allow_unicode=True, max_length=100, unique=True, verbose_name='Slug'),
),
]
19 changes: 11 additions & 8 deletions project/tagging/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,12 @@

class CustomTag(TagBase):
guid = models.UUIDField(default=uuid.uuid1, editable=False)
slug = models.SlugField(verbose_name=_("Slug"), unique=True, max_length=100)
slug = models.SlugField(
verbose_name=_("Slug"),
unique=True,
max_length=100,
allow_unicode=True
)
name = models.CharField(verbose_name=_("Name"), unique=True, max_length=100)

class Meta:
Expand All @@ -17,15 +22,13 @@ class Meta:
verbose_name_plural = _("Tags")
app_label = 'tagging'

def save(self, *args, **kwargs):
self.slug = self.slugify(self.name)
self.full_clean()
return super().save(*args, **kwargs)

def slugify(self, tag, i=None):
slug = slugify(tag, allow_unicode=True)

if i is not None:
slug += "_%d" % i

return slug

return slugify(tag, allow_unicode=True)

class TaggedItems(GenericTaggedItemBase, TaggedItemBase):
tag = models.ForeignKey(CustomTag,
Expand Down
76 changes: 75 additions & 1 deletion project/tagging/tests.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,77 @@
import unittest
from django.core.exceptions import ValidationError
from django.test import TestCase
from .models import CustomTag

# Create your tests here.

class CustomTagTests(TestCase):
def test_valid_slugs(self):
test_tags = [
{"name": "programming", "expected_slug": "programming"},
{"name": "PyCon", "expected_slug": "pycon"},
{"name": "local storage", "expected_slug": "local-storage"},
{"name": "PEN testing", "expected_slug": "pen-testing"},
{"name": "תִּיכְנוּת", "expected_slug": "תיכנות"},
{"name": " 프로그램 작성", "expected_slug": "프로그램-작성"},
{"name": "程式设计", "expected_slug": "程式设计"},
{"name": "برمجة", "expected_slug": "برمجة"},
{"name": "आनंद", "expected_slug": "आनद"},
{"name": "лягушачий", "expected_slug": "лягушачий"},
{"name": "教程", "expected_slug": "教程"},
{"name": "Inicio r\u00e1pido", "expected_slug": "inicio-r\u00e1pido"},
{"name": "最后", "expected_slug": "最后"},
{"name": " 欲求不満", "expected_slug": "欲求不満"},
{"name": "စမ်းသပ်ခြင်း", "expected_slug": "စမသပခင"},
{"name": "ฐานข้อมูล", "expected_slug": "ฐานขอมล"},
{"name": "основы", "expected_slug": "основы"},
{"name": "אַלגערידאַם", "expected_slug": "אלגערידאם"},
{"name": "自動化する", "expected_slug": "自動化する"},
{"name": "sjálfvirkan", "expected_slug": "sjálfvirkan"},
{"name": "پژوهش ", "expected_slug": "پژوهش"},
{"name": " గ్రాఫ్", "expected_slug": "గరఫ"},
{"name": "데이터 베이스", "expected_slug": "데이터-베이스"},
{"name": "stòran-dàta", "expected_slug": "stòran-dàta"},
]

for entry in test_tags:
tag = CustomTag(name=entry["name"])
tag.save()
self.assertEqual(tag.slug, entry["expected_slug"])

@unittest.skip('https://github.com/codebuddies/backend/issues/123')
def test_brahmic_abugida_slugs(self):
test_tags = [
{"name": "हिंदी में जानकारी", "expected_slug": "TODO"},
{"name": "प्रयास है", "expected_slug": "TODO"},
{"name": "స్వయంచాలక", "expected_slug": "TODO"},
]

for entry in test_tags:
tag = CustomTag(name=entry["name"])
tag.save()
self.assertEqual(tag.slug, entry["expected_slug"])

def test_invalid_slugs(self):
invalid_tag_names = [
"❤🐸",
"🐸",
" %",
"//",
]
for name in invalid_tag_names:
with self.assertRaises(ValidationError):
tag = CustomTag(name=name)
tag.save()

def test_duplicates(self):
tag1 = CustomTag(name='javascript')
tag1.save()

# fail if we try to generate more tags with the same slug
with self.assertRaises(ValidationError):
tag2 = CustomTag(name='Javascript')
tag2.save()

with self.assertRaises(ValidationError):
tag3 = CustomTag(name='JaVascripT%/')
tag3.save()

0 comments on commit 412d7dd

Please sign in to comment.