Skip to content
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

Preventing data mutation in format_fields #75

Open
mamico opened this issue Jan 16, 2025 · 3 comments
Open

Preventing data mutation in format_fields #75

mamico opened this issue Jan 16, 2025 · 3 comments

Comments

@mamico
Copy link
Contributor

mamico commented Jan 16, 2025

def format_fields(self, fields):

The fields object passed as an argument is modified within the function, which can lead to issues if the function is called multiple times, as it may result in broken or unintended data.

For example, in the following snippet:

                if self.block["subblocks"][field_index].get("field_type") == "date":
                    field["value"] = api.portal.get_localized_time(field["value"])

It seems get_localized_time expects a datetime object or an ISO-formatted string, not a localized string.

A quick fix to avoid mutating the original fields object is to add a deepcopy at the start of the function:

def format_fields(self, fields):
    fields = deepcopy(fields)

@JeffersonBledsoe thoughts ?

see #34

@JeffersonBledsoe
Copy link
Member

@mamico I noticed a similar problem when getting #37 up-to-date . In this PR which reworks the API with fields to be a dedicated field object, I avoid the problem by re-getting the fields every time format_fields is called. This didn't seem to have any noticeable impact on performance (we have some 30 question forms), but I haven't done any actual time measurements.

Originally I wanted to compute all the fields once at the start after validation so as to only have to do this work once, however it looks like the PostEvent is currently allowed to make whatever changes it wants to the form data and so you can't really guarantee the state of the field data until after this has happened.

@mamico
Copy link
Contributor Author

mamico commented Jan 22, 2025

@JeffersonBledsoe Do you see any contraindications to using deepcopy as suggested above?
The issue is that it seems counterintuitive to me, for developers, that the 'format' method modifies the data passed as a parameter.

@JeffersonBledsoe
Copy link
Member

JeffersonBledsoe commented Jan 23, 2025

@mamico I agree that it's counter-intuitive. I mentioned my other PR because it should already solve this problem by assigning all of the values in the passed in fields value to a dedicated field class which has functions for getting the modified versions of each field so as not to mutate the data. Until that PR is merged though, I'd agree that the deepcopy is a good quick solution for this. Unless the forms on a site are high traffic + the forms are really long, I don't imagine the memory impact being too significant

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants