【问题标题】:Django Full example of dropdown menu populated from postgresql databaseDjango 从 postgresql 数据库填充的下拉菜单的完整示例
【发布时间】:2019-02-16 06:14:37
【问题描述】:

我对 django 很陌生(使用 django 2.1.5 和 python 3.7),我似乎不知道如何添加下拉菜单,显示我的 postgresql 数据库中表中一个字段的元素。我希望最终允许用户从下拉菜单中选择一个元素,然后我将使用该选项构建一个查询并返回该查询的结果。但我已经被下拉菜单卡住了。 这是我在 models.py 文件中的模型

class Locations(models.Model):
    gid = models.AutoField(primary_key=True)
    field_gid = models.BigIntegerField(db_column='__gid', blank=True, null=True)  # Field renamed because it contained more than one '_' in a row. Field renamed because it started with '_'.
    name_location= models.CharField(unique=True, max_length=254, blank=True, null=True)
    x = models.DecimalField(max_digits=10, decimal_places=2, blank=True, null=True)
    y = models.DecimalField(max_digits=10, decimal_places=2, blank=True, null=True)
    z = models.DecimalField(max_digits=10, decimal_places=2, blank=True, null=True)
    geom = geomodels.PointField(srid=3912)

    def __str__(self):
        return self.name_location

    class Meta:
        managed = False
        db_table = 'locations'
        verbose_name_plural = "Locations"

这是我在 forms.py 文件中的表单:

from .models import Locations
class LocationsForm(forms.ModelForm):
    class Meta:
        model = Locations
        fields = ('name_location',)
        #Down here is what I actually thought I need, but maybe I am not using it right 
        locations_list = forms.ModelChoiceField(queryset=Locations.objects.all().only('name_location').order_by('name_location'))

然后,在我的 views.py 文件中:

from .forms import LocationsForm
def LocationsView(request):
    form = LocationsForm
    return render(request, 'geoportal/mforest.html', {'form': form})

我的urls.py如下:

from django.urls import path
from . import views
urlpatterns = [
path('', views.home, name='geoportal-home'),
path('mforest/', views.LocationsView, name='geoportal-mforest')
]

最后在我的模板 mforest.html 文件中(我只放了一个提取,因为 base.html 有一个我在 mforest.html 中扩展的块内容):

{% extends "geoportal/base.html" %}
{% block content %}
<div class="col-md-3" style="height: 100vh; border: 2px red; background-color: lightgray">
    <h3>Meteo Stations of the SFI</h3>
    <form method="GET">
        {% csrf_token %}
        {{ form }}
    </form>
    </div>
<div class="col-md-9">
    <h3>Output of the query</h3>
    <table width="100%" class="blueTable"> </table>
</div>
{% endblock content %}

对于模板文件,我还尝试了一些迭代查询集结果的建议。但是,我尝试过的解决方案都没有显示我的下拉菜单。我确定我做错了什么,因为我没有得到预期的结果,但我不知道要纠正什么。 PS。我没有收到错误。它根本没有显示任何东西。 提前感谢您的帮助!

编辑:更多关于我想要实现的目标,please click here 看看我的页面上有什么(尽管几乎什么都没有)。 (不要注意我在这个问题中用“name_location”替换的标签“kraj_odvze”)。现在;而不是有一个文本框,我真正想要的是一个下拉菜单,其中包含我数据库中“name_location”字段中的元素。我将进一步包括一个日期时间范围选择器和一个按钮来执行查询以在我的页面右侧 div 上呈现为表格和图形。

【问题讨论】:

  • 你的 urls.py 文件是什么样子的?顺便说一句,modelForm 应该具有在 Meta 类中指定的 model 属性。 编辑:请描述您实际想要实现的目标。
  • @art06 请看我的编辑。谢谢。

标签: python django django-forms django-templates django-views


【解决方案1】:

感谢@art06 的评论,我明白了这个问题。 因为我要查询另一个表(“Meteo”),它有一个代表foreign_key的列,它指向“Locations”表的“name_location”列,我应该使用“Meteo”表而不是“Locations” .

因此,models.py 文件如下:

class Locations(models.Model):
    gid = models.AutoField(primary_key=True)
    field_gid = models.BigIntegerField(db_column='__gid', blank=True, null=True)  # Field renamed because it contained more than one '_' in a row. Field renamed because it started with '_'.
    name_location = models.CharField(unique=True, max_length=254, blank=True, null=True)
    x = models.DecimalField(max_digits=10, decimal_places=2, blank=True, null=True)
    y = models.DecimalField(max_digits=10, decimal_places=2, blank=True, null=True)
    z = models.DecimalField(max_digits=10, decimal_places=2, blank=True, null=True)
    geom = geomodels.PointField(srid=3912)

    def __str__(self):  # __unicode__ for py2
        return self.name_location

    class Meta:
        managed = False
        db_table = 'locations'
        verbose_name_plural = "Locations"


class Meteo(models.Model):
    time = models.DateTimeField()
    air_temp = models.FloatField(blank=True, null=True)
    soil_temp = models.FloatField(blank=True, null=True)
    precipitation = models.FloatField(blank=True, null=True)
    global_rad = models.FloatField(blank=True, null=True)
    relative_hum = models.FloatField(blank=True, null=True)
    wind_speed = models.FloatField(blank=True, null=True)
    swc = models.FloatField(blank=True, null=True)
    pressure = models.FloatField(blank=True, null=True)
    location = models.ForeignKey(Locations, models.DO_NOTHING, db_column='location', to_field='name_location')  # to_field is required because the Foreignkey field is a text
    id = models.BigAutoField(primary_key=True)

    class Meta:
        managed = False
        db_table = 'meteo'
        unique_together = (('time', 'id'),)
        verbose_name_plural = "Meteo"

forms.py 如下:

from django import forms
from .models import Meteo
class LocationsForm(forms.ModelForm):
    class Meta:
        model = Meteo
        fields = ('location',)

通过在我的帖子中更改之前的内容,django 将该字段格式化为下拉菜单,并且显示良好。

因此,我在这里没有得到正确的关键点是: 即使不写 ModelChoiceField,当 ModelForm 与外键一起使用时,它也会自动创建一个下拉菜单。

【讨论】:

    猜你喜欢
    • 2015-07-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-03-12
    • 2013-02-15
    • 1970-01-01
    • 2020-06-23
    相关资源
    最近更新 更多