0

I would need some help to understand a problem in order to try to fix it.

Currently, my form ignores readonly=True or readonly="readonly" for a multiple select field linking to a ManytoManyfield.

However, within the same form, readonly=True works on a CharField, as intended (view but not save)

If I use ignore=True, it works on both fields, but then an empty list is saved replacing the original value.

Therefore I assume the problem has to do with the multiple select field in combination with read-only and perhaps the fact I am using Crispy forms

Q: What component determines the behaviour of a read-only field why it seems to accept one type of field but not another? Thanks and regards

class Product(models.Model):
    product_type = models.CharField(max_length=22, blank=True)

class Package(models.Model):
    product_code = models.CharField(max_length=3)
    products = models.ManyToManyField('product.Product', blank=True)


class ProductModelForm(ModelForm):
    class Meta:
        model = Package
        fields = '__all__'


class ProductFieldsForm(ProductModelForm):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.helper = FormHelper()
        self.helper.form_class = 'form-horizontal'
        self.helper.label_class = 'col-sm-4'
        self.helper.field_class = 'col-sm-7'
        self.helper.form_tag = False

        prd_code = 'product_code'
        prds = 'products'

        self.helper.layout = Layout (
            Field(prd_code, readonly=True), # WORKS FINE, as intended
            Field(prds, readonly=True), # **CAN CHANGE and SAVE (gray area)**
        )

The resulting html (i have also tried with readonly="readonly", but with same result. Using Firefox 69)

<div class="col-sm-7"><select name="product" readonly="True" class="selectmultiple form-control" id="id_product"
                              multiple>
    <option value="4">Product 4</option>
    <option value="5">Product 5</option>
    <option value="6">Product 6</option>
    <option value="3" selected>Product 3</option>

</select></div>
Jaco
  • 1,564
  • 2
  • 9
  • 33

1 Answers1

0

After some research, it seems this is a common problem.

It seems the problem is that it is easy to read-only one value but hard to read-only a list of values.

Solutions I found are workarounds, such as scripts.

Below worked well which means you add a disabled = "true" but before submitting the form, you remove this through a script, I referred to this script as: onsubmit="form" within the form tag on the template.

    $('form').submit(function () {
      $('[disabled]').removeAttr('disabled');
      })

('disable' gives a truncated and locked list, but this list does not save, instead a empty list is saved).

I found the answer here: Link

Jaco
  • 1,564
  • 2
  • 9
  • 33