I have a model that is sublcassed
class Foo(models.Model):
name = models.CharField(max_length=255)
child_model = models.CharField(max_length=255)
class Bar(Foo):
woots = models.ManyToManyField(Woot)
class Woot(models.Model):
color = models.CharField(max_length=255)
And some tastypie resources:
class FooResource(ModelResource):
class Meta:
queryset = Foo.objects.all()
class BarResource(ModelResource):
class Meta:
queryset = Foo.objects.all()
class WootResource(ModelResource):
class Meta:
queryset = Woot.objects.all()
When accessing the FooResource, I'd ideally like it to 'reroute' and return a BarResource instead if the child_model attribute == bar.
If I can't do that, then any way that I can get an array of woots serialized and into the bundle (when child_model attribute == bar) would be fine by me.
Try this:
class FooResource(ModelResource):
class Meta:
queryset = Foo.objects.all()
def dehydrate(self, bundle):
if bundle.data['child_model']=="bar":
return json.loads(BarResource().dispatch_list(bundle.request).content)
return bundle
Related
Django inheritance error: (models.E005)
Do you have a solution to get around this problem, is there a way to add a prefix or idk because I must have several User with the same heritage?
Django dont like this:
class Dispositif(Infos, ChefGO, ADJChefGO):
bcs ChefGO and ADJChefGO depend on the same class Member, but i realy need two member
class Members(models.Model):
phone_regex = RegexValidator(regex=r'^[0-9]{10}$', message="Error: Format 0611223344")
indicative = models.CharField(max_length=16, default="Default indicative")
phone = models.CharField(max_length=10, validators=[phone_regex])
class Meta:
abstract = True
class ChefGO(Members):
pass
class ADJChefGO(Members):
pass
class Dispositif(Infos, ChefGO, ADJChefGO):
name = models.CharField(max_length=32, default="Name")
place = models.CharField(max_length=64)
start_date = models.DateTimeField(default=datetime.datetime.now)
end_date = models.DateTimeField(default=datetime.datetime.now)
Thanks
Are foreign keys a workaround there ?
# model
class Dispositif(Infos):
myChefGO = models.ForeignKey(ChefGO, on_delete=models.CASCADE)
myADJChefGO = models.ForeignKey(ADJChefGO, on_delete=models.CASCADE)
# instanciation
dispositif = Dispositif(Infos)
dispositif.myChefGO = A
dispositif.myADJChefGO = B
I have found solution with this method:
1- Create "Device" class with 'Fields' and 'Forms'
class Device:
#staticmethod
class Fields:
#staticmethod
class Member:
#staticmethod
def indicative():
return models.CharField(max_length=16, default="Default indicative")
#staticmethod
def phone():
phone_regex = RegexValidator(regex=r'^[0-9]{10}$', message="Error: Format 0611223344")
return models.CharField(max_length=10, validators=[phone_regex])
#staticmethod
def function():
return models.CharField(max_length=10)
#staticmethod
class Forms:
#staticmethod
class Member:
#staticmethod
def indicative():
return django.forms.TextInput(attrs={'placeholder': 'indivatif'})
#staticmethod
def phone(placeholder="06 12 34 56 78"):
return django.forms.TextInput(attrs={'placeholder': placeholder})
#staticmethod
def function():
return django.forms.TextInput(attrs={'placeholder': 'fonction'})
2- Use 'Device' Fields like this
class ChefGO(models.Model):
cgo_indicative = Device.Fields.Member.indicative()
cgo_phone = Device.Fields.Member.phone()
cgo_function = Device.Fields.Member.function()
class Meta:
abstract = True
class ADJChefGO(models.Model):
adjcgo_indicative = Device.Fields.Member.indicative()
adjcgo_phone = Device.Fields.Member.phone()
adjcgo_function = Device.Fields.Member.function()
class Meta:
abstract = True
3- Inheritance
class Dispositif(ChefGO, ADJChefGO):
pass
4- "Bonus"
You can use'it in ModelForm like that:
class DispositifForm(ModelForm):
class Meta:
model = Dispositif
fields = [
'cgo_phone', 'cgo_indicative', 'cgo_function',
'adjcgo_phone', 'adjcgo_indicative', 'adjcgo_function',
'dso_phone', 'dso_indicative', 'dso_function'
]
widgets = {
'cgo_phone': Device.Forms.Member.phone(),
'cgo_indicative': Device.Forms.Member.indicative(),
'cgo_function': Device.Forms.Member.function(),
'adjcgo_phone': Device.Forms.Member.phone(),
'adjcgo_indicative': Device.Forms.Member.indicative(),
'adjcgo_function': Device.Forms.Member.function(),
'dso_phone': Device.Forms.Member.phone(),
'dso_indicative': Device.Forms.Member.indicative(),
'dso_function': Device.Forms.Member.function()
}
I have a problem with creating new ratings for cars.
When i try to send a post request from Postman in order to create/add a new rating for a specific car i get the error:
The `.create()` method does not support writable nested fields by default.
These are my models:
class Car(models.Model):
name = models.CharField(max_length=50)
symbol = models.CharField(max_length = 5)
def __str__(self):
return self.name
class Type(models.Model):
name = models.CharField(max_length = 50)
fuel = models.CharField(max_length = 1)##1 or 2 for fuel type
car = models.ManyToManyField(Car)
def __str__(self):
return self.name
class Rating(models.Model):
rating = models.IntegerField(validators=[
MaxValueValidator(10),
MinValueValidator(0)
])
car = models.ForeignKey(Car, on_delete=models.CASCADE)
type = models.ForeignKey(Type, on_delete=models.CASCADE)
def __int__(self):
return self.rating
My serializers:
class CarSerializer(serializers.ModelSerializer):
class Meta:
model = Car
fields = ('id','name')
class TypeSerializer(serializers.ModelSerializer):
car = CarSerializer(many=True)
class Meta:
model = Type
fields = ('id','name', 'fuel', 'car')
#depth=2
class RatingSerializer(serializers.ModelSerializer):
type = TypeSerializer()
class Meta:
model = Rating
fields = ('id','rating', 'car', 'type')
def create(self, validated_data):
type_data = validated_data.pop('type')
rating = Rating.objects.create(**validated_data)
for t_data in type_data:
Type.objects.create(rating=rating, **t_data)
return rating
When i try to do a post request to rating such as :
{"rating":5, "car": 2,"type":{"id":1,"name":"OffRoad","fuel":"1","car":[{"id":2,"name":"Ford"}] } }
I get:
The `.create()` method does not support writable nested fields by default.
Please help if you can, ive been trying to fix this all day. Thank you!
Let's say I have three models:
class ThingOne:
field1 = ...
field2 = ...
class ThingTwo:
thingone = models.ForeignKey("ThingOne")
field3 = ...
field4 = ...
class ThingTree:
thingtwo = models.ForeignKey("ThingTwo")
field5 = ...
field6 = ...
Let's also say I've made top level ViewSets and Serializers for the above. Easy peasy.
Now I'd like to create a custom endpoint (detail_route) that is based on a subset of ThingTwo and includes corresponding fields from ThingOne and ThingThree. I'll use a custom serializer to pack my data:
class MyComboThingSerializer(ModelSerializer):
field1 = serializers.SerializerMethodField()
field5 = serializers.SerializerMethodField()
def get_field1(self, obj):
return ?
def get_field5(self, obj):
return ?
class Meta:
model = ThingTwo
fields = "__all__"
What would I put into either return statement to achieve the values I'm looking for?
Something like
class ThingTwoSerializer(ModelSerializer):
thing1 = ThingOneSerializer()
thingthree_set = ThingThreeSerializer(many=True)
class Meta:
model = ThingTwo
fields = ['id', 'thing1', 'thingthree_set', 'field3', 'field4']
I would like to serialize all the nodes in my PolymorphicMPTTModel with their corresponding fields. Following the documentation django-polymorphic and django-mptt i get this:
{
"count":1,
"next":null,
"previous":null,
"results":[
{
"title":"Submenu",
"subcategories":[
{
"title":"Plato1",
"subcategories":[
]
},enter code here
{
"title":"Plato2",
"subcategories":[
]
}
]
}
]
}
The structure is fine, but the fields of the children are missing.
Models:
class Menu(PolymorphicMPTTModel):
parent = PolymorphicTreeForeignKey('self', blank=True, null=True, related_name='children', verbose_name='parent')
title = models.CharField("Title", max_length=200)
class SubMenu(Menu):
titulo = models.CharField("Titulo", max_length=200,default="not defined")
class Plato(Menu):
titulo = models.CharField("Titulo",max_length=200,default="not defined")
descripcion = models.TextField()
ingredientes = JSONField()
precio = models.PositiveSmallIntegerField(default=0)
# Extra settings:
can_have_children = False
Serializers:
class PlatoSerializer(serializers.ModelSerializer):
class Meta:
model = Plato
fields = ('titulo', 'descripcion', 'ingredientes', 'precio')
class SubMenuSerializer(serializers.ModelSerializer):
class Meta:
model = SubMenu
fields = ('titulo',)
class MenuItemModuleSerializer(serializers.ModelSerializer):
subcategories = serializers.ListSerializer(source="children",child=RecursiveField())
class Meta:
model = Menu
fields = ('title','subcategories')
View:
class MenuView(viewsets.ModelViewSet):
queryset = Menu.objects.all()
queryset = queryset.toplevel()
serializer_class = MenuItemModuleSerializer
I know I'm kinda late to the party but I had the same issue and finally found a solution that is working for me.
As django-rest-polymorphic states, you need a mapping between models and serializers:
class ProjectPolymorphicSerializer(PolymorphicSerializer):
model_serializer_mapping = {
Menu: MenuItemModuleSerializer,
SubMenu: SubMenuSerializer,
Plato: PlatoSerializer
}
Your RecursiveField() creates a serializer instance from its parent class. That makes all your child objects using the MenuItemModuleSerializer and thus missing child fields.
Every child needs to get mapped to its serializer using ProjectPolymorphicSerializer
RecursiveField(to='ProjectPolymorphicSerializer')
Change your MenuItemModuleSerializer to this:
class MenuItemModuleSerializer(serializers.ModelSerializer):
subcategories = serializers.ListSerializer(source="children", child=RecursiveField(to='ProjectPolymorphicSerializer'))
class Meta:
model = Menu
fields = ('title','subcategories')
I'm using eav-django for a project and I need to serialize it's models with DjangoRestFramework, but I got some issues.
My models (models.py) are the standard models needed by eav-django:
class ServiceSchema(BaseSchema):
pass
class ServiceChoice(BaseSchema):
schema = models.ForeignKey(ServiceSchema, related_name='choices')
class ServiceAttr(BaseAttribute):
schema = models.ForeignKey(ServiceSchema, related_name='attrs')
choice = models.ForeignKey(ServiceChoice, related_name='attrs', null=True)
class ServiceEntity(BaseEntity):
title = models.CharField(max_length=100)
attrs = generic.GenericRelation(ServiceAttr, object_id_field='entity_id', content_type_field='entity_type')
#classmethod
def get_schemata_for_model(cls):
return ServiceSchema.objects.all()
def __unicode__(self):
return self.title
class ServiceFacetSet(BaseFacetSet):
def get_queryset(self, **kwargs):
return ServiceEntity.objects.filter(**kwargs)
class HostSchema(BaseSchema):
pass
class HostChoice(BaseChoice):
schema = models.ForeignKey(HostSchema, related_name='choices')
class HostAttr(BaseAttribute):
schema = models.ForeignKey(HostSchema, related_name='attrs')
choice = models.ForeignKey(HostChoice, related_name='attrs', null=True)
class HostEntity(BaseEntity):
title = models.CharField(max_length=100)
attrs = generic.GenericRelation(HostAttr, object_id_field='entity_id', content_type_field='entity_type')
services = models.ManyToManyField(ServiceEntity, null=True, blank=True, default=None, related_name='hosts')
#classmethod
def get_schemata_for_model(cls):
return HostSchema.objects.all()
def __unicode__(self):
return self.title
class HostFacetSet(BaseFacetSet):
def get_queryset(self, **kwargs):
return HostEntity.objects.filter(**kwargs)
And I'm trying to serialize them with this piece of code in serializers.py:
class ServiceSchemaSerializer(serializers.HyperlinkedModelSerializer):
class Meta:
model = ServiceSchema
class ServiceChoiceSerializer(serializers.HyperlinkedModelSerializer):
schema = ServiceSchemaSerializer(many=False)
class Meta:
model = ServiceChoice
fields = ('schema', )
class ServiceAttrSerializer(serializers.HyperlinkedModelSerializer):
schema = ServiceSchemaSerializer(many=False)
choice = ServiceChoiceSerializer(many=False)
class Meta:
model = ServiceAttr
fields = ('schema', 'choice')
class ServiceEntitySerializer(serializers.HyperlinkedModelSerializer):
class Meta:
model = HostEntity
fields = ('title', 'attrs')
class HostSchemaSerializer(serializers.HyperlinkedModelSerializer):
class Meta:
model = HostSchema
class HostChoiceSerializer(serializers.HyperlinkedModelSerializer):
schema = HostSchemaSerializer(many=False)
class Meta:
model = HostChoice
fields = ('schema', )
class HostAttrSerializer(serializers.HyperlinkedModelSerializer):
schema = HostSchemaSerializer(many=False)
choice = HostChoiceSerializer(many=False)
class Meta:
model = HostAttr
fields = ('schema', 'choice')
class HostEntitySerializer(serializers.HyperlinkedModelSerializer):
services = ServiceEntitySerializer(many=True)
class Meta:
model = HostEntity
fields = ('title', 'attrs', 'services')
Django rest framework error is [...] GenericRelatedObjectManager is not JSON serializable. Ok, got it. But there is some way to accomplish the serialization?