Django admin: reverse select foreign keys - django

I want to add pre-existing foreignkey items from the parent's admin. I have a "Bundle" model to hold "Product" items; many-to-one/foreignkey:
models.py
class Bundle(models.Model):
title = models.CharField(max_length=300)
class Product(models.Model):
title = models.CharField(max_length=300)
bundle = models.ForeignKey(
'Bundle',
on_delete=models.CASCADE,
null=True,
blank=True,
)
Below, I used StackedInline but this is for creating new products with a form:
admin.py
class ProductInline(admin.StackedInline):
model = Product
#admin.register(Bundle)
class BundleAdmin(admin.ModelAdmin):
inlines = [
ProductInline,
]
Instead, I want to repeatedly add existing products from a dropdown/search in the Bundle section of admin. So, I make a Bundle and then add a series of Products from a dropdown / with a search.
Thanks in advance.

For you requirement, you can use ManyToManyField in Bundle model instead of ForeignKey in Product model.
Check below code.
class Bundle(models.Model):
title = models.CharField(max_length=255)
product = models.ManyToManyField('Product')
class Product(models.Model):
title = models.CharField(max_length=255)
Then you can register admin interfaces:
admin.site.register(Bundle)
admin.site.register(Product)
Then you can add series of Product from a dropdown/search.

Related

What is the process that you follow to create model in Django?

What is the process that you follow to create model in Django? Thanks.
The most important part of a model – and the only required part of a model – is the list of database fields it defines. Fields are specified by class attributes. Be careful not to choose field names that conflict with the models API like clean, save, or delete.
Models.py
from django.db import models
class Musician(models.Model):
first_name = models.CharField(max_length=50)
last_name = models.CharField(max_length=50)
instrument = models.CharField(max_length=100)
class Album(models.Model):
artist = models.ForeignKey(Musician, on_delete=models.CASCADE)
name = models.CharField(max_length=100)
release_date = models.DateField()
num_stars = models.IntegerField()
You can start here Documentation
See also Django Girls Models

How to link two models, each with its own template using foreignKey in Django

I want to link two models using foreignKey, The problem is when i try to do that, one model does not get foreignKey value for the next model in the database table.
The aim is for user to fill information on the first page (have its own model and template) then click next (fill more info in the next page having its own model and template) then click next for the same logic. then when other users view this post it must show all content from different models in one page. here is my code.
1st model
class Map(models.Model):
user = models.ForeignKey(User, default=None, blank=True, null=True, on_delete=models.CASCADE)
name = models.CharField(max_length=100)
position = GeopositionField()
HAVING ITS OWN TEMPLATE
2nd Model
class Post(models.Model):
parent = models.ForeignKey("self", default=None, blank=True, null=True, on_delete=models.CASCADE)
user = models.ForeignKey(settings.AUTH_USER_MODEL, default=None, on_delete=models.CASCADE)
title = models.CharField(max_length=50)
content = models.TextField()
map = models.ForeignKey(Map, related_name='mapkey', default=None, blank=True, null=True, on_delete=models.CASCADE)
HAVING ITS OWN TEMPLATE BUT also has serializer method(API) below:
class PostModelSerializer(serializers.ModelSerializer):
user = UserDisplaySerializer(read_only=True)
parent = ParentPostModelSerializer()
map = serializers.SerializerMethodField()
class Meta:
start_date = forms.DateField(widget = forms.SelectDateWidget())
end_date = forms.DateField(widget = forms.SelectDateWidget())
model = Post
fields = [
'id',
'user',
'title',
'content'
'image',
'map',
]
Please focus only on the map field as its isolated in the above codes
everything works perfectly, but the foreignKey. also i didnt see the need to include all the code here but snippets.
i have been struggling with this for days now. do i need to write an api for 1st model also? for views i used class based views.
the database table for model 2, on the map field it shows null all the time.
I have i have provided enough information.Thanks

Edit django 'through' model inline in wagtail admin?

[Edited with better code sample]
As per the title I am trying to allow for inline editing for a very simple shop page in Wagtail (will probably make it into a simple package):
With the following models:
class Product(ClusterableModel):
page = ParentalKey(MiniShopPage, on_delete=models.CASCADE, related_name='shop_products')
name = models.CharField(max_length=255)
description = models.CharField(max_length=2500)
downloadable = models.BooleanField()
price = models.FloatField()
image = models.ForeignKey(
'wagtailimages.Image',
null=True,
blank=True,
on_delete=models.SET_NULL,
related_name='+'
)
# define the content_panels
panels = [
FieldPanel('name'),
FieldPanel('description'),
FieldPanel('downloadable'),
FieldPanel('price'),
ImageChooserPanel('image'),
]
class Order(TimeStampedModel, ClusterableModel):
'''
Example of use outside of the admin:
p = Product.objects.first()
order = Order.objects.create(client_email='someone#hotmail.com', gift_amount=0)
quantities = ProductInOrderCount(product=p, order=order, quantity=2)
quantities.save()
for itm in order.productinordercount_set.all():
print(itm.quantity)
'''
is_fulfilled = models.BooleanField(default=False)
is_paid_for = models.BooleanField(default=False)
client_email = models.EmailField(blank=False)
gift_amount = models.PositiveIntegerField()
# products = M2MTHROUGH
# the through model stores the quantity
products = models.ManyToManyField(Product, through='ProductInOrderCount')
content_panels = [
FieldPanel('is_fulfilled'),
FieldPanel('is_paid_for'),
FieldPanel('client_email'),
FieldPanel('gift_amount'),
InlinePanel('products'),
]
class OrderModelAdmin(ModelAdmin):
model = Order
menu_label = 'Orders'
...
modeladmin_register(OrderModelAdmin)
class ProductInOrderCount(Orderable):
product = models.ForeignKey(Product, on_delete=models.CASCADE)
order = models.ForeignKey(Order, on_delete=models.CASCADE)
quantity = models.PositiveIntegerField()
The tricky thing is that I get the error Cannot set values on a ManyToManyField which specifies an intermediary model. Or I simply don't get an inline panel, but rather a select.
I am assuming this is the case because the create and add methods do not work on through models, is that the case?
If so could you suggest a way I can rewrite the app so as to allow me to create orders with products in the admin and in my code?
InlinePanel only works with one-to-many ParentalKey relations, not a ManyToManyField. That shouldn't be a problem, because ParentalKey is a good fit for this case:
A ManyToManyField with a through model is really just two one-to-many relations back to back;
ParentalKey is designed for relations that are closely tied to the parent model, in the sense that they're always edited, validated and saved as a single unit. This is true for the relation between ProductInOrderCount and Order (a ProductInOrderCount record is conceptually part of an Order), but not the relation between ProductInOrderCount and Product (a ProductInOrderCount is not part of a Product).
This would give you a model definition like:
class ProductInOrderCount(Orderable):
order = ParentalKey(Order, on_delete=models.CASCADE, related_name='ordered_products')
product = models.ForeignKey(Product, on_delete=models.CASCADE)
quantity = models.PositiveIntegerField()
Your Order model can then have an InlinePanel('ordered_products'), and the products field can be omitted.

After saving object in django admin how to display it in foreign key inlining dropdown

When we save foreign key object from django admin. As following screenshot
click here to see the screenshot
Newly created object will get saved but not been able to display at same time in dropdown list.
We have measurement model which has material and product foreign key as showed in following snippet.
So I want when object is created it should display the newly created option in foreign key dropdown. Please suggest how do I do that.
Here is my code snippet
models.py
class MaterialName(models.Model):
material_name = models.CharField(max_length=150, default=None, null=True, unique=True)
class Product(models.Model):
product_name = models.CharField(max_length=100)
class Measurement(models.Model):
product = models.ForeignKey(Product,default=None, null=True, related_name='Measurement')
material_name = models.ForeignKey(MaterialName,default=None, blank=Blank, related_name='materialname')
admin.py
class MaterialTypeAdmin(admin.ModelAdmin):
model = MaterialType
list_display = ('material_type',)
class ProductAdmin(admin.ModelAdmin):
model = Product
inlines = [MaterialTypeAdminInline,]

django admin how to manipulate OneToMany related objects(not just inline)

I have 2 models.
One has a foreign key to another.
Say:
class Organization(models.Model):
title = models.CharField(max_length=300)
class User(models.Model):
name = models.CharField(max_length=300)
organization = models.ForeignKey(Organization)
I want to show all users who work in current organization in organizationAdmin, like a list of change links.
It should be possible
to add new user
to select existing user(no related to current organization) and set his organization to current
No need to edit them inline
Just like permissions in userAdmin + adding and changing them
Is there any ready solution? Not to make forms by hands
You can do that with exclude:
class UserInline(admin.TabularInline):
model = User
exclude = ['name', 'other_fields']
Or you can use ManyToMany relation:
class User(models.Model):
name = models.CharField(max_length=300)
class Organization(model.Model):
title = models.CharField(max_length=300)
users = models.ManyToManyField(User)