We have a type defined for our application's settings, but a nested data structure (like the one we use today) inherently adds complexity when modifying slices of state. We can't simply Object.assign our state changes overtop of the existing settings values, because if only one field is modified, the unmodified fields in a nested object are overwritten.
This leads to us doing weird things like using _.merge, which carries its own quirkiness because merge isn't pure and modifies its parameter vars directly. When comparing to things like the returned values from React.useState, which should be immutable, it creates weird side effects that are painstaking to debug.
We're solving it now by explicitly referencing the fields on the settings type to updated them, like below:
setFormFields({
heartbeatIndices: changedField.heartbeatIndices ?? formFields.heartbeatIndices,
certThresholds: Object.assign(
{},
formFields.certThresholds,
changedField?.certThresholds ?? null
),
});
This is a pure method of handling state change and it works fine, but obviously it isn't scalable. The more fields we add to settings down the line, the more complex any snippet of code doing this will become.
The obvious solution is to flatten our settings fields. There will likely not be that many fields, and it would be best to nail this down before we release 7.8, because we haven't released any code yet that uses nested fields. Then we will be ok to simply Object.assign({...oldState, ...newState}) anytime we modify settings.
We have a type defined for our application's settings, but a nested data structure (like the one we use today) inherently adds complexity when modifying slices of state. We can't simply
Object.assignour state changes overtop of the existing settings values, because if only one field is modified, the unmodified fields in a nested object are overwritten.This leads to us doing weird things like using
_.merge, which carries its own quirkiness becausemergeisn't pure and modifies its parameter vars directly. When comparing to things like the returned values fromReact.useState, which should be immutable, it creates weird side effects that are painstaking to debug.We're solving it now by explicitly referencing the fields on the settings type to updated them, like below:
This is a pure method of handling state change and it works fine, but obviously it isn't scalable. The more fields we add to settings down the line, the more complex any snippet of code doing this will become.
The obvious solution is to flatten our settings fields. There will likely not be that many fields, and it would be best to nail this down before we release 7.8, because we haven't released any code yet that uses nested fields. Then we will be ok to simply
Object.assign({...oldState, ...newState})anytime we modify settings.