Skip to content

Utility function get_field_value returns last value when used on a multi-value field #17794

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
DanSheps opened this issue Oct 17, 2024 · 6 comments
Assignees
Labels

Comments

@DanSheps
Copy link
Member

Deployment Type

Self-hosted

Triage priority

I volunteer to perform this work (if approved)

NetBox Version

v4.1.4

Python Version

3.10

Steps to Reproduce

  1. Utilize get_field_value on a form field that may produce a single value or multiple values (Ex: tagged_vlans)

Expected Behavior

get_field_value to return multiple values

Observed Behavior

get_field_valueu returns a single value

@DanSheps DanSheps added type: bug A confirmed report of unexpected behavior in the application status: accepted This issue has been accepted for implementation severity: low Does not significantly disrupt application functionality, or a workaround is available labels Oct 17, 2024
@DanSheps DanSheps self-assigned this Oct 17, 2024
@DanSheps
Copy link
Member Author

This is expected (but annoying) behaviour as per: https://code.djangoproject.com/ticket/1130

Two options are possible:

  1. Rewrite get_field_value to dynamically determine if the field is capable of returning multiple values
  2. Create a new get_field_values to call getlist() instead of get()

@DanSheps
Copy link
Member Author

Proposed rewrite:

def get_field_value(form, field_name):
    """
    Return the current bound or initial value associated with a form field, prior to calling
    clean() for the form.
    """
    field = form.fields[field_name]
    
    if form.is_bound:
        # Get list or get single value
        if isinstance(field, MultipleChoiceField):
            data = form.data.getlist(field_name)
        else:
            data = form.data.get(field_name)
        
        if hasattr(field, 'valid_value') and field.valid_value(data):
            return data

    return form.get_initial_for_field(field, field_name)

@DanSheps DanSheps added status: under review Further discussion is needed to determine this issue's scope and/or implementation and removed status: accepted This issue has been accepted for implementation labels Oct 17, 2024
@jeremystretch jeremystretch added the netbox label Nov 1, 2024 — with Linear
@jeremystretch
Copy link
Member

@DanSheps to submit a PR per maintainers meeting

@jeremystretch
Copy link
Member

jeremystretch commented Apr 28, 2025

@DanSheps could you please rewrite the original issue to include reproduction steps? I'm not able to reproduce this:

>>> from django.http import QueryDict
>>> from utilities.forms import get_field_value
>>> from dcim.forms import InterfaceForm
>>> 
>>> qd = QueryDict("mode=tagged&tagged_vlans=2&tagged_vlans=27")
>>> f = InterfaceForm(initial=qd)
>>> get_field_value(f, 'tagged_vlans')
['2', '27']

@DanSheps
Copy link
Member Author

DanSheps commented May 15, 2025

After re-reviewing the code, I realised I made an error before trying to fix this:

On March 31st, when fixing another issue, the code around this function changed from:

    if form.is_bound and (data := form.data.get(field_name)):
        if hasattr(field, 'valid_value') and field.valid_value(data):
            return data

to

    if form.is_bound and field_name in form.data:
        if (value := form.data[field_name]) is None:
            return
        if hasattr(field, 'valid_value') and field.valid_value(value):
            return value

This slight change in code seems to have resolved the issue fully as we are no longer using .get() to retrieve the field value.

@DanSheps
Copy link
Member Author

Fixed by: #19023

@DanSheps DanSheps closed this as not planned Won't fix, can't repro, duplicate, stale May 15, 2025
@DanSheps DanSheps removed type: bug A confirmed report of unexpected behavior in the application status: under review Further discussion is needed to determine this issue's scope and/or implementation severity: low Does not significantly disrupt application functionality, or a workaround is available labels May 15, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
2 participants