我正在使用Django Rest Framework。我有一个现有的数据库(无法对其进行任何更改)。我的桌子TestSuite上有复合pk。当我在test_suites上执行get()时,将引发错误-'str' object has no attribute 'pk'
。我没有在模型中定义pk,就像使用django一样,我无法定义复合主键。因此,django使用“ id”作为模型的自动生成的pk。我无法在数据库中添加ID(因为无法修改数据库)。
post()可以正常工作,但是get()通过postman()和可浏览的API引发错误。
我是DRF的新手。任何帮助表示赞赏。
数据库创建语句:
CREATE TABLE `test_suite` (
`team_name` varchar(30) NOT NULL,
`suite_name` varchar(100) NOT NULL,
`description` varchar(200) DEFAULT NULL,
`schedule` varchar(100) DEFAULT NULL,
`email_list_ok` varchar(200) DEFAULT NULL,
`email_list_fail` varchar(200) DEFAULT NULL,
`template_name` varchar(100) NOT NULL,
PRIMARY KEY (`team_name`,`suite_name`),
KEY `fk_test_suite__email_templates` (`template_name`),
CONSTRAINT `fk_test_suite__email_templates` FOREIGN KEY (`template_name`) REFERENCES `email_templates` (`template_name`),
CONSTRAINT `fk_test_suite__team` FOREIGN KEY (`team_name`) REFERENCES `team` (`team_name`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
我需要对此表进行get()和post()操作。下面是我的模型,序列化器和视图集。
models.py
class Team(models.Model):
team_name = models.CharField(primary_key=True, max_length=30)
description = models.CharField(max_length=100, blank=True, null=True)
class Meta:
managed = False
db_table = 'team'
class TestSuite(models.Model):
team_name = models.ForeignKey(Team, on_delete=models.DO_NOTHING, db_column='team_name')
suite_name = models.CharField(max_length=100)
description = models.CharField(max_length=200, blank=True, null=True)
schedule = models.CharField(max_length=100, blank=True, null=True)
email_list_ok = models.CharField(max_length=200, blank=True, null=True)
email_list_fail = models.CharField(max_length=200, blank=True, null=True)
template_name = models.ForeignKey(EmailTemplates, on_delete=models.DO_NOTHING, db_column='template_name')
class Meta:
managed = False
db_table = 'test_suite'
unique_together = (('team_name', 'suite_name'),)
views.py
class TestSuiteViewSet(viewsets.ModelViewSet):
queryset = models.TestSuite.objects.values('team_name','suite_name', 'description','schedule','email_list_ok','email_list_fail','template_name')
serializer_class = serializers.TestSuiteSerializer
class TeamViewSet(viewsets.ModelViewSet):
queryset = models.Team.objects.all()
serializer_class = serializers.TeamSerializer
serializers.py
class TestSuiteSerializer(serializers.ModelSerializer):
class Meta:
model = models.TestSuite
fields = ['team_name','suite_name', 'description','schedule','email_list_ok','email_list_fail','template_name']
错误回溯:
File "/usr/local/lib/python3.6/dist-packages/django/core/handlers/exception.py" in inner
35. response = get_response(request)
File "/usr/local/lib/python3.6/dist-packages/django/core/handlers/base.py" in _get_response
128. response = self.process_exception_by_middleware(e, request)
File "/usr/local/lib/python3.6/dist-packages/django/core/handlers/base.py" in _get_response
126. response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "/usr/lib/python3.6/contextlib.py" in inner
52. return func(*args, **kwds)
File "/usr/local/lib/python3.6/dist-packages/django/views/decorators/csrf.py" in wrapped_view
54. return view_func(*args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/viewsets.py" in view
116. return self.dispatch(request, *args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/views.py" in dispatch
495. response = self.handle_exception(exc)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/views.py" in handle_exception
455. self.raise_uncaught_exception(exc)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/views.py" in dispatch
492. response = handler(request, *args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/mixins.py" in list
48. return Response(serializer.data)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in data
768. ret = super(ListSerializer, self).data
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in data
262. self._data = self.to_representation(self.instance)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in to_representation
686. self.child.to_representation(item) for item in iterable
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in <listcomp>
686. self.child.to_representation(item) for item in iterable
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in to_representation
530. ret[field.field_name] = field.to_representation(attribute)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/relations.py" in to_representation
272. return value.pk
Exception Type: AttributeError at /dqf_api/test_suites/
Exception Value: 'str' object has no attribute 'pk'
urls.py
router = routers.DefaultRouter()
router.register(r'teams', views.TeamViewSet)
router.register(r'test_suites', views.TestSuiteViewSet)
urlpatterns = [ url(r'^dqf_api/', include(router.urls))]
编辑:
我可以通过将以下代码添加到serializers.py中来解析get()。但是,现在我的post()无法正常工作-ValueError at /dqf_api/test_suites/
Cannot assign "'ede'": "TestSuiteModel.team_name" must be a "Team" instance.
def to_representation(self, obj):
return {
'team_name': obj.get('team_name'),
'suite_name': obj.get('suite_name'),
'description': obj.get('description'),
'schedule': obj.get('schedule'),
'email_list_ok': obj.get('email_list_ok'),
'email_list_fail': obj.get('email_list_fail'),
'template_name': obj.get('template_name'),
}
def to_internal_value(self, data):
return {
'team_name': data.get('team_name'),
'suite_name': data.get('suite_name'),
'description': data.get('description'),
'schedule': data.get('schedule'),
'email_list_ok': data.get('email_list_ok'),
'email_list_fail': data.get('email_list_fail'),
'template_name': data.get('template_name'),
}
错误回溯:
File "/usr/local/lib/python3.6/dist-packages/django/core/handlers/exception.py" in inner
35. response = get_response(request)
File "/usr/local/lib/python3.6/dist-packages/django/core/handlers/base.py" in _get_response
128. response = self.process_exception_by_middleware(e, request)
File "/usr/local/lib/python3.6/dist-packages/django/core/handlers/base.py" in _get_response
126. response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "/usr/lib/python3.6/contextlib.py" in inner
52. return func(*args, **kwds)
File "/usr/local/lib/python3.6/dist-packages/django/views/decorators/csrf.py" in wrapped_view
54. return view_func(*args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/viewsets.py" in view
116. return self.dispatch(request, *args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/views.py" in dispatch
495. response = self.handle_exception(exc)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/views.py" in handle_exception
455. self.raise_uncaught_exception(exc)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/views.py" in dispatch
492. response = handler(request, *args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/mixins.py" in create
21. self.perform_create(serializer)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/mixins.py" in perform_create
26. serializer.save()
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in save
214. self.instance = self.create(validated_data)
File "/usr/local/lib/python3.6/dist-packages/rest_framework/serializers.py" in create
943. instance = ModelClass._default_manager.create(**validated_data)
File "/usr/local/lib/python3.6/dist-packages/django/db/models/manager.py" in manager_method
82. return getattr(self.get_queryset(), name)(*args, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/django/db/models/query.py" in create
415. obj = self.model(**kwargs)
File "/usr/local/lib/python3.6/dist-packages/django/db/models/base.py" in __init__
477. _setattr(self, field.name, rel_obj)
File "/usr/local/lib/python3.6/dist-packages/django/db/models/fields/related_descriptors.py" in __set__
197. self.field.remote_field.model._meta.object_name,
Exception Type: ValueError at /dqf_api/test_suites/
Exception Value: Cannot assign "'ede'": "TestSuiteModel.team_name" must be a "Team" instance.
答案 0 :(得分:1)
如下更改您的 ref = Database.database().reference()
ref.child("locations").observeSingleEvent(of: .value) { (snapshot) in
if snapshot.exists() {
if let location = snapshot.value as? [String:Any] {
for eachLocation in location {
print("Location: \(eachLocation)")
if let locationCoordinate = eachLocation.value as? [String: Any] {
if let lavLatitude = locationCoordinate["latitude"] as? Double {
if let lavLongitude = locationCoordinate["longitude"] as? Double {
print(lavLatitude)
print(lavLongitude)
let marker = GMSMarker()
marker.position = CLLocationCoordinate2DMake(lavLatitude, lavLongitude)
marker.map = mapView
}
}
}
}
}
}
}
类,
TestSuiteViewSet
来自Django Doc,
class TestSuiteViewSet(viewsets.ModelViewSet): queryset = models.TestSuite.objects.all() serializer_class = serializers.TestSuiteSerializer
返回一个values()
,该字典在用作迭代时会返回字典,而不是模型实例,是
答案 1 :(得分:0)
存在与外键关系进行序列化和反序列化的问题。我通过将以下代码添加到serializers.py
来修复它class TestSuiteSerializer(serializers.ModelSerializer):
class Meta:
model = models.TestSuiteModel
fields = ['team_name','suite_name', 'description','schedule','email_list_ok','email_list_fail','template_name']
def to_representation(self, obj):
if isinstance(obj, dict): # get methods
return obj
else:
self.fields['team_name'] = TeamSerializer()
self.fields['template_name'] = EmailTemplatesSerializer()
return super(TestSuiteSerializer, self).to_representation(obj)