如何使用 AJAX、Django REST API 和 jQuery 在模态表单中更新记录时显示外键字段名称而不是 ID



我有两个模型

class Properties(models.Model):
property_name = models.CharField(max_length=100)
property_type = models.CharField(choices=TYPE, max_length=50)
property_location = models.CharField(max_length=100)
county = models.CharField(choices=COUNTY, max_length=50)
number_of_units = models.IntegerField()
date_created = models.DateField(auto_now_add=True)
last_modified = models.DateField(auto_now=True)

def __str__(self):
return self.property_name

class Meta:
verbose_name_plural = "Properties"
class RentalUnits(models.Model):
unit_number = models.CharField(max_length=10)
property = models.ForeignKey(Properties, on_delete=models.CASCADE)
no_of_bedrooms = models.IntegerField(default=0)
no_of_bathrooms = models.IntegerField(default=0)
rent_per_month = models.IntegerField(default=0)
status = models.CharField(max_length=20, choices=STATUS)
date_created = models.DateField(auto_now_add=True)
last_modified = models.DateField(auto_now=True)
def __str__(self):
return self.unit_number
class Meta:
verbose_name_plural = 'Units'

和它们对应的序列化器

class PropertiesSerializers(serializers.ModelSerializer):
class Meta:
model = Properties
fields = '__all__'
class RentalUnitsSerializers(serializers.ModelSerializer):
property = serializers.SerializerMethodField()
class Meta:
model = RentalUnits
fields = ('id', 'unit_number', 'property', 'no_of_bedrooms', 'no_of_bathrooms', 'rent_per_month', 'status',)

我想在数据表中显示它们的外键名而不是id,我在这里找到了一个很好的解决方案,所以我最终使用

def to_representation(self, instance):
rep = super(RentalUnitsSerializers, self).to_representation(instance)
rep['property'] = instance.property.property_name
return rep

它给了我这个

{
"id": 12,
"unit_number": "1A",
"property": 1,
"no_of_bedrooms": 3,
"no_of_bathrooms": 2,
"rent_per_month": 60000,
"status": "Occupied"
},
{
"id": 12,
"unit_number": "1A",
"property": "New Apartments",
"no_of_bedrooms": 3,
"no_of_bathrooms": 2,
"rent_per_month": 60000,
"status": "Occupied"
},

添加单位&删除单元仍然可以正常工作。当我想编辑出租单位的详细信息时,我的问题出现了。我使用jQuery和AJAX填充我的数据表& &;表单通过API。将def to_representation(self, instance):添加到Rental Unit序列化器后,数据表将使用外键名称填充,但是当编辑表单加载时,属性字段将保持空白,并且外键字段名称不出现在该输入字段中。然而,当我删除这个def to_representation(self, instance):属性输入字段&使用属性Foreign Key填充数据表,并继续成功编辑。这是我的jQuery代码编辑:

//Edit Units API
$('#RentalUnits-Records').on('click', '.update', function(e){
e.preventDefault();

let id = $(this).attr('id');
$('input[id=unitID]').val(id);
console.log(id)
let myurl = "http://127.0.0.1:8000/api/units/"+id+"/";
$.ajax({
async: true,
url:myurl,
method:'GET',
success: function(result){
$('input[name="unit_number"]').val(result.unit_number);
$('input[name="property"]').val(result.property);
$('input[name="no_of_bedrooms"]').val(result.no_of_bedrooms);
$('input[name="no_of_bathrooms"]').val(result.no_of_bathrooms);
$('input[name="rent_per_month"]').val(result.rent_per_month);
$('select[name="status"]').val(result.status);
}
});
$( "#u-number" ).change(function() {
$('input[name=unit_number]').val($(this).val());
});
$( "#u-property" ).change(function() {
$('input[name=property]').val($(this).val());
});
$( "#u-bedrooms" ).change(function() {
$('input[name=no_of_bedrooms]').val($(this).val());
});
$( "#u-bathrooms" ).change(function() {
$('input[name=no_of_bathrooms]').val($(this).val());
});
$( "#u-rent" ).change(function() {
$('input[name=rent_per_month]').val($(this).val());
});
$( "#u-status" ).change(function() {
$('select[name=status]').val($(this).val());
});
});
//Save Edited Rental Unit Button
$(function() { 
$('#editUnit').on('submit', function(e) { 
e.preventDefault();  
let id = $("#unitID").attr("value");
console.log(id);
let myurl = "http://127.0.0.1:8000/api/units/edit/"+id+"/";
$.ajax({
type : 'PUT',
url : myurl,
data : $("#editUnit :input").serializeArray(),
dataType: "json",
success: function(data){
alert("Unit Details Updated!");
location.reload();
},
error:function(data){
alert("Unit Details Not Updated!");
location.reload();
}
});
});
});
});

和编辑表单:

<form id="editUnit" action="">
{% csrf_token %}
<div class="mb-3">
<input type="hidden" id="unitID" value="">
</div>
<div class="mb-3">
<label>Unit Number</label>
<input type="text" class="form-control" name="unit_number" id="u-number" placeholder="Unit Number">
</div>
<div class="mb-3">
<label>Associated Property</label>
<input type="number" class="form-control" name="property" id="u-property" placeholder="Property" readonly>
</div>
<div class="mb-3">
<label>No. of Bedrooms</label>
<input type="number" class="form-control" name="no_of_bedrooms" id="u-bedrooms" placeholder="No. of Bedrooms">
</div>
<div class="mb-3">
<label>No. of Bathrooms</label>
<input type="number" class="form-control" name="no_of_bathrooms" id="u-bathrooms" placeholder="No. of Bathrooms">
</div>
<div class="mb-3">
<label>Rent</label>
<input type="number" class="form-control" name="rent_per_month" id="u-rent" placeholder="Rent Per Month">
</div>
<div class="mb-3">
<label>Status</label>
<select class="form-select" name="status" id="u-status" aria-label="Default select example" placeholder="Associated Property">
<option selected disabled>Status</option>
<option value="Occupied">Occupied</option>
<option value="Under Maintenance">Under Maintenance</option>
<option value="Vacant">Vacant</option>
</select>
</div>
<div class="mb-3">
<button class="btn btn-soft-success btn-sm" id="u-edit" type="submit">Save Changes</button>
<button class="btn btn-soft-secondary btn-sm" type="button" data-bs-dismiss="modal">Cancel</button>
</div>
</form>

:我如何在数据表和模态编辑表单中显示Foreign Key field name而不是ID,但仍然在DB中维护property_id。我在某处读到使用字符串而不是id的外部字段是不好的做法?

在弄清楚如何显示属性在dropdown list的情况下,有一个以上的属性将有助于允许用户改变,以及一些帮助。目前是readonly。对此的任何帮助都将不胜感激。谢谢你。

如果你想显示外键的任何字段而不是id,那么你可以使用StringRelatedField

例如: -

class RentalUnitsSerializers(serializers.ModelSerializer):
property = serializers.StringRelatedField()
class Meta:
model = RentalUnits
fields = ('id', 'unit_number', 'property', 'no_of_bedrooms', 
'no_of_bathrooms', 'rent_per_month', 'status',)

这将显示从str返回的值该模型的方法。你可以从文档

查看更多信息

最新更新