Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

How to show more object information on forms in django

This is a follow up question to this question:
How to pass user object to forms in Django

Here is my form:

class SellForm(forms.Form):
    symbol = forms.ModelChoiceField(queryset=None, widget=forms.Select(attrs={
        'class': 'form-control',
        'placeholder': 'Symbol',
        'autofocus': 'autofocus',
        }))
    
    def __init__(self, *args, **kwargs):
        self.request = kwargs.pop('request')
        super(SellForm, self).__init__(*args, **kwargs)
        self.fields['symbol'].queryset = Holdings.objects.filter(student=self.request.user.student)

This form is providing me with this dropdown:
the example of the dropdown that this form creates

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

I have extra information in the model which is the purchase price of each share, is there a way to get this onto the form also? It would have to be non editable though as its the price that the share was purchased at.

Here is the model that the form is getting the data from:

class Holdings(models.Model):
    student = models.ForeignKey(Student, on_delete=models.CASCADE)
    symbol = models.CharField(max_length=10)
    purchase_price = models.DecimalField(max_digits=10, decimal_places=2)
    
    class Meta:
        verbose_name_plural = "Holdings"
        ordering = ['symbol']
    
    def __str__(self):
        return self.symbol

I would very much appreciate any help if possible! Thank you!

>Solution :

The simplest way is just overriding the __str__ method and include the purchase price:

class Holdings(models.Model):
    student = models.ForeignKey(Student, on_delete=models.CASCADE)
    symbol = models.CharField(max_length=10)
    purchase_price = models.DecimalField(max_digits=10, decimal_places=2)

    class Meta:
        verbose_name_plural = "Holdings"
        ordering = ['symbol']

    def __str__(self):
        return f'{self.symbol} ({self.purchase_price})'

Filtering can be done more efficiently though with:

class SellForm(forms.Form):
    symbol = forms.ModelChoiceField(
        queryset=None,
        widget=forms.Select(
            attrs={
                'class': 'form-control',
                'placeholder': 'Symbol',
                'autofocus': 'autofocus',
            }
        ),
    )

    def __init__(self, *args, request, **kwargs):
        super(SellForm, self).__init__(*args, **kwargs)
        self.fields['symbol'].queryset = Holdings.objects.filter(
            student__user=self.request.user
        )

since this will prevent a query to get the Student object for the user, or we can work with:

class SellForm(forms.Form):
    symbol = forms.ModelChoiceField(
        queryset=None,
        widget=forms.Select(
            attrs={
                'class': 'form-control',
                'placeholder': 'Symbol',
                'autofocus': 'autofocus',
            }
        ),
    )

    def __init__(self, *args, request, **kwargs):
        super(SellForm, self).__init__(*args, **kwargs)
        self.fields['symbol'].queryset = Holdings.objects.filter(
            student_id=self.request.user.student_id
        )
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading