mirror of
https://github.com/daniviga/django-ram.git
synced 2025-08-04 05:07:50 +02:00
Use slugs to filter
This commit is contained in:
93
ram/metadata/migrations/0011_company_slug_and_more.py
Normal file
93
ram/metadata/migrations/0011_company_slug_and_more.py
Normal file
@@ -0,0 +1,93 @@
|
||||
# Generated by Django 4.1.5 on 2023-01-09 11:22
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
from ram.utils import slugify
|
||||
|
||||
|
||||
def create_slug(apps, schema_editor):
|
||||
fields = ["Company", "Manufacturer", "RollingStockType", "Scale"]
|
||||
|
||||
for m in fields:
|
||||
model = apps.get_model("metadata", m)
|
||||
|
||||
for row in model.objects.all():
|
||||
if hasattr(row, "type"):
|
||||
row.slug = slugify("{} {}".format(row.type, row.category))
|
||||
elif hasattr(row, "scale"):
|
||||
row.slug = slugify(row.scale)
|
||||
else:
|
||||
row.slug = slugify(row.name)
|
||||
|
||||
row.save(update_fields=["slug"])
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
("metadata", "0010_alter_manufacturer_category"),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AddField(
|
||||
model_name="company",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=64, blank=True
|
||||
),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name="manufacturer",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=128, blank=True
|
||||
),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name="rollingstocktype",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=128, blank=True
|
||||
),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name="scale",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=32, blank=True
|
||||
),
|
||||
),
|
||||
migrations.RunPython(
|
||||
create_slug,
|
||||
reverse_code=migrations.RunPython.noop
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name="company",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=64, unique=True
|
||||
),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name="manufacturer",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=128, unique=True
|
||||
),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name="rollingstocktype",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=128, unique=True
|
||||
),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name="scale",
|
||||
name="slug",
|
||||
field=models.CharField(
|
||||
editable=False, max_length=32, unique=True
|
||||
),
|
||||
),
|
||||
]
|
@@ -1,6 +1,7 @@
|
||||
from urllib.parse import quote
|
||||
|
||||
from django.db import models
|
||||
from django.urls import reverse
|
||||
from django.conf import settings
|
||||
from django.dispatch.dispatcher import receiver
|
||||
from django_countries.fields import CountryField
|
||||
@@ -22,6 +23,7 @@ class Property(models.Model):
|
||||
|
||||
class Manufacturer(models.Model):
|
||||
name = models.CharField(max_length=128, unique=True)
|
||||
slug = models.CharField(max_length=128, unique=True, editable=False)
|
||||
category = models.CharField(
|
||||
max_length=64, choices=settings.MANUFACTURER_TYPES
|
||||
)
|
||||
@@ -36,8 +38,13 @@ class Manufacturer(models.Model):
|
||||
def __str__(self):
|
||||
return self.name
|
||||
|
||||
def safe_name(self):
|
||||
return quote(self.__str__().lower(), safe="& ")
|
||||
def get_absolute_url(self):
|
||||
return reverse(
|
||||
"filtered", kwargs={
|
||||
"_filter": "manufacturer",
|
||||
"search": self.slug,
|
||||
}
|
||||
)
|
||||
|
||||
def logo_thumbnail(self):
|
||||
return get_image_preview(self.logo.url)
|
||||
@@ -47,6 +54,7 @@ class Manufacturer(models.Model):
|
||||
|
||||
class Company(models.Model):
|
||||
name = models.CharField(max_length=64, unique=True)
|
||||
slug = models.CharField(max_length=64, unique=True, editable=False)
|
||||
extended_name = models.CharField(max_length=128, blank=True)
|
||||
country = CountryField()
|
||||
freelance = models.BooleanField(default=False)
|
||||
@@ -61,8 +69,13 @@ class Company(models.Model):
|
||||
def __str__(self):
|
||||
return self.name
|
||||
|
||||
def safe_name(self):
|
||||
return quote(self.__str__().lower(), safe="& ")
|
||||
def get_absolute_url(self):
|
||||
return reverse(
|
||||
"filtered", kwargs={
|
||||
"_filter": "company",
|
||||
"search": self.slug,
|
||||
}
|
||||
)
|
||||
|
||||
def logo_thumbnail(self):
|
||||
return get_image_preview(self.logo.url)
|
||||
@@ -94,6 +107,7 @@ class Decoder(models.Model):
|
||||
|
||||
class Scale(models.Model):
|
||||
scale = models.CharField(max_length=32, unique=True)
|
||||
slug = models.CharField(max_length=32, unique=True, editable=False)
|
||||
ratio = models.CharField(max_length=16, blank=True)
|
||||
gauge = models.CharField(max_length=16, blank=True)
|
||||
tracks = models.CharField(max_length=16, blank=True)
|
||||
@@ -101,11 +115,40 @@ class Scale(models.Model):
|
||||
class Meta:
|
||||
ordering = ["scale"]
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse(
|
||||
"filtered", kwargs={
|
||||
"_filter": "scale",
|
||||
"search": self.slug,
|
||||
}
|
||||
)
|
||||
|
||||
def __str__(self):
|
||||
return str(self.scale)
|
||||
|
||||
def safe_name(self):
|
||||
return quote(self.__str__(), safe="& ")
|
||||
|
||||
class RollingStockType(models.Model):
|
||||
type = models.CharField(max_length=64)
|
||||
order = models.PositiveSmallIntegerField()
|
||||
category = models.CharField(
|
||||
max_length=64, choices=settings.ROLLING_STOCK_TYPES
|
||||
)
|
||||
slug = models.CharField(max_length=128, unique=True, editable=False)
|
||||
|
||||
class Meta(object):
|
||||
unique_together = ("category", "type")
|
||||
ordering = ["order"]
|
||||
|
||||
def get_absolute_url(self):
|
||||
return reverse(
|
||||
"filtered", kwargs={
|
||||
"_filter": "type",
|
||||
"search": self.slug,
|
||||
}
|
||||
)
|
||||
|
||||
def __str__(self):
|
||||
return "{0} {1}".format(self.type, self.category)
|
||||
|
||||
|
||||
class Tag(models.Model):
|
||||
@@ -115,28 +158,20 @@ class Tag(models.Model):
|
||||
def __str__(self):
|
||||
return self.name
|
||||
|
||||
def safe_name(self):
|
||||
return self.slug
|
||||
def get_absolute_url(self):
|
||||
return reverse(
|
||||
"filtered", kwargs={
|
||||
"_filter": "tag",
|
||||
"search": self.slug,
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
|
||||
@receiver(models.signals.pre_save, sender=Manufacturer)
|
||||
@receiver(models.signals.pre_save, sender=Company)
|
||||
@receiver(models.signals.pre_save, sender=Scale)
|
||||
@receiver(models.signals.pre_save, sender=RollingStockType)
|
||||
@receiver(models.signals.pre_save, sender=Tag)
|
||||
def slug_pre_save(sender, instance, **kwargs):
|
||||
instance.slug = slugify(instance.name)
|
||||
|
||||
|
||||
class RollingStockType(models.Model):
|
||||
type = models.CharField(max_length=64)
|
||||
order = models.PositiveSmallIntegerField()
|
||||
category = models.CharField(
|
||||
max_length=64, choices=settings.ROLLING_STOCK_TYPES
|
||||
)
|
||||
|
||||
class Meta(object):
|
||||
unique_together = ("category", "type")
|
||||
ordering = ["order"]
|
||||
|
||||
def __str__(self):
|
||||
return "{0} {1}".format(self.type, self.category)
|
||||
|
||||
def safe_name(self):
|
||||
return quote(self.__str__().lower(), safe="& ")
|
||||
instance.slug = slugify(instance.__str__())
|
||||
|
@@ -38,7 +38,7 @@
|
||||
<tr>
|
||||
<th scope="row">Company</th>
|
||||
<td>
|
||||
<a href="{% url 'filtered' _filter="company" search=d.rolling_class.company.safe_name %}"><abbr title="{{ d.rolling_class.company.extended_name }}">{{ d.rolling_class.company }}</abbr></a>
|
||||
<a href="{% url 'filtered' _filter="company" search=d.rolling_class.company.slug %}"><abbr title="{{ d.rolling_class.company.extended_name }}">{{ d.rolling_class.company }}</abbr></a>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
@@ -56,12 +56,12 @@
|
||||
<tr>
|
||||
<th width="35%" scope="row">Manufacturer</th>
|
||||
<td>{%if d.manufacturer %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=d.manufacturer.safe_name %}">{{ d.manufacturer }}{% if d.manufacturer.website %}</a> <a href="{{ d.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=d.manufacturer.slug %}">{{ d.manufacturer }}{% if d.manufacturer.website %}</a> <a href="{{ d.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
{% endif %}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th scope="row">Scale</th>
|
||||
<td><a href="{% url 'filtered' _filter="scale" search=d.scale.safe_name %}"><abbr title="{{ d.scale.ratio }} - {{ d.scale.tracks }}">{{ d.scale }}</abbr></a></td>
|
||||
<td><a href="{% url 'filtered' _filter="scale" search=d.scale.slug %}"><abbr title="{{ d.scale.ratio }} - {{ d.scale.tracks }}">{{ d.scale }}</abbr></a></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th scope="row">SKU</th>
|
||||
|
@@ -42,7 +42,7 @@
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="d-grid gap-2 mb-1 d-md-block">
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="company" search=d.safe_name %}">Show all rolling stock</a>
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="company" search=d.slug %}">Show all rolling stock</a>
|
||||
{% if request.user.is_staff %}<a class="btn btn-sm btn-outline-danger" href="{% url 'admin:metadata_company_change' d.pk %}">Edit</a>{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -34,7 +34,7 @@
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="d-grid gap-2 mb-1 d-md-block">
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="manufacturer" search=d.safe_name %}">Show all rolling stock</a>
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="manufacturer" search=d.slug %}">Show all rolling stock</a>
|
||||
{% if request.user.is_staff %}<a class="btn btn-sm btn-outline-danger" href="{% url 'admin:metadata_manufacturer_change' d.pk %}">Edit</a>{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -70,7 +70,7 @@
|
||||
<tr>
|
||||
<th scope="row">Company</th>
|
||||
<td>
|
||||
<a href="{% url 'filtered' _filter="company" search=rolling_stock.rolling_class.company.safe_name %}"><abbr title="{{ rolling_stock.rolling_class.company.extended_name }}">{{ rolling_stock.rolling_class.company }}</abbr></a>
|
||||
<a href="{% url 'filtered' _filter="company" search=rolling_stock.rolling_class.company.slug %}"><abbr title="{{ rolling_stock.rolling_class.company.extended_name }}">{{ rolling_stock.rolling_class.company }}</abbr></a>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
@@ -97,7 +97,7 @@
|
||||
<tr>
|
||||
<th width="35%" scope="row">Manufacturer</th>
|
||||
<td>{%if rolling_stock.manufacturer %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=rolling_stock.manufacturer.safe_name %}">{{ rolling_stock.manufacturer }}{% if rolling_stock.manufacturer.website %}</a> <a href="{{ rolling_stock.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=rolling_stock.manufacturer.slug %}">{{ rolling_stock.manufacturer }}{% if rolling_stock.manufacturer.website %}</a> <a href="{{ rolling_stock.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
{% endif %}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
@@ -147,7 +147,7 @@
|
||||
<tr>
|
||||
<th width="35%" scope="row">Manufacturer</th>
|
||||
<td>{%if rolling_stock.manufacturer %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=rolling_stock.manufacturer.safe_name %}">{{ rolling_stock.manufacturer }}{% if rolling_stock.manufacturer.website %}</a> <a href="{{ rolling_stock.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=rolling_stock.manufacturer.slug %}">{{ rolling_stock.manufacturer }}{% if rolling_stock.manufacturer.website %}</a> <a href="{{ rolling_stock.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
{% endif %}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
@@ -209,7 +209,7 @@
|
||||
<tr>
|
||||
<th scope="row">Company</th>
|
||||
<td>
|
||||
<a href="{% url 'filtered' _filter="company" search=rolling_stock.rolling_class.company.safe_name %}">{{ rolling_stock.rolling_class.company }}</a> ({{ rolling_stock.rolling_class.company.extended_name }})
|
||||
<a href="{% url 'filtered' _filter="company" search=rolling_stock.rolling_class.company.slug %}">{{ rolling_stock.rolling_class.company }}</a> ({{ rolling_stock.rolling_class.company.extended_name }})
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
@@ -219,7 +219,7 @@
|
||||
<tr>
|
||||
<th scope="row">Manufacturer</th>
|
||||
<td>{%if rolling_stock.rolling_class.manufacturer %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=rolling_stock.rolling_class.manufacturer.safe_name %}">{{ rolling_stock.rolling_class.manufacturer }}{% if rolling_stock.rolling_class.manufacturer.website %}</a> <a href="{{ rolling_stock.rolling_class.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
<a href="{% url 'filtered' _filter="manufacturer" search=rolling_stock.rolling_class.manufacturer.slug %}">{{ rolling_stock.rolling_class.manufacturer }}{% if rolling_stock.rolling_class.manufacturer.website %}</a> <a href="{{ rolling_stock.rolling_class.manufacturer.website }}" target="_blank"><i class="bi bi-box-arrow-up-right"></i></a>{% endif %}
|
||||
{% endif %}</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
|
@@ -32,7 +32,7 @@
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="d-grid gap-2 mb-1 d-md-block">
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="scale" search=d.safe_name %}">Show all rolling stock</a>
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="scale" search=d.slug %}">Show all rolling stock</a>
|
||||
{% if request.user.is_staff %}<a class="btn btn-sm btn-outline-danger" href="{% url 'admin:metadata_scale_change' d.pk %}">Edit</a>{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -24,7 +24,7 @@
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="d-grid gap-2 mb-1 d-md-block">
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="type" search=d.safe_name %}">Show all rolling stock</a>
|
||||
<a class="btn btn-sm btn-outline-primary" href="{% url 'filtered' _filter="type" search=d.slug %}">Show all rolling stock</a>
|
||||
{% if request.user.is_staff %}<a class="btn btn-sm btn-outline-danger" href="{% url 'admin:metadata_scale_change' d.pk %}">Edit</a>{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
|
@@ -174,33 +174,22 @@ class GetRosterFiltered(View):
|
||||
def run_filter(self, request, search, _filter, page=1):
|
||||
site_conf = get_site_conf()
|
||||
if _filter == "type":
|
||||
type_ = " ".join(search.split()[:-1])
|
||||
category = search.split()[-1]
|
||||
try:
|
||||
title = (
|
||||
RollingStockType.objects.filter(type__iexact=type_)
|
||||
.get(category__iexact=category)
|
||||
)
|
||||
except ObjectDoesNotExist:
|
||||
raise Http404
|
||||
query = Q(
|
||||
Q(rolling_class__type__type__iexact=type_)
|
||||
& Q(rolling_class__type__category__iexact=category)
|
||||
)
|
||||
title = RollingStockType.objects.get(slug__iexact=search)
|
||||
query = Q(rolling_class__type__slug__iexact=search)
|
||||
elif _filter == "company":
|
||||
title = get_object_or_404(Company, name__iexact=search)
|
||||
query = Q(rolling_class__company__name__iexact=search)
|
||||
title = get_object_or_404(Company, slug__iexact=search)
|
||||
query = Q(rolling_class__company__slug__iexact=search)
|
||||
elif _filter == "manufacturer":
|
||||
title = get_object_or_404(Manufacturer, name__iexact=search)
|
||||
title = get_object_or_404(Manufacturer, slug__iexact=search)
|
||||
query = Q(
|
||||
Q(rolling_class__manufacturer__name__iexact=search)
|
||||
| Q(manufacturer__name__iexact=search)
|
||||
Q(rolling_class__manufacturer__slug__iexact=search)
|
||||
| Q(manufacturer__slug__iexact=search)
|
||||
)
|
||||
elif _filter == "scale":
|
||||
title = get_object_or_404(Scale, scale__iexact=search)
|
||||
query = Q(scale__scale__iexact=search)
|
||||
title = get_object_or_404(Scale, slug__iexact=search)
|
||||
query = Q(scale__slug__iexact=search)
|
||||
elif _filter == "tag":
|
||||
title = get_object_or_404(Tag, slug=search)
|
||||
title = get_object_or_404(Tag, slug__iexact=search)
|
||||
query = Q(tags__slug__iexact=search)
|
||||
else:
|
||||
raise Http404
|
||||
|
@@ -1,4 +1,4 @@
|
||||
from ram.utils import git_suffix
|
||||
|
||||
__version__ = "0.1.2"
|
||||
__version__ = "0.2.0"
|
||||
__version__ += git_suffix(__file__)
|
||||
|
Reference in New Issue
Block a user