[FIX] survey_record_generation: link to already created record at creation
A NOT required "other_record" field was always set after the loop with a write(), even when the linked record was already created. This late write triggers the recomputation of stored computed fields depending on the relation, overriding the values answered by the user. E.g. with subscription_oca, sale.subscription.line price_unit depends on sale_subscription_id.partner_id/pricelist_id: a free amount typed in a numerical_box question (33) was replaced by the product price (20) when the line was linked to its subscription. Now the relation is given to create() when the linked record already exists, so that the user's values are protected from recomputation. The deferred write is kept for records created later. Assisted-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -160,8 +160,9 @@ class SurveyUserInput(models.Model):
|
||||
elif field_value.value_origin == "question":
|
||||
value = self.get_value_from_user_answer(field_value, user_input)
|
||||
elif field_value.value_origin == "other_record":
|
||||
# if the other_record value is a required field, get it or raise
|
||||
value = self.get_required_value_from_other_record(
|
||||
# if the other record is already created, get it
|
||||
# (or raise if it is not created yet and the field is required)
|
||||
value = self.get_value_from_other_record(
|
||||
model, created_records, field_value
|
||||
)
|
||||
# otherwise, we update the record later (out of this for loop)
|
||||
@@ -198,35 +199,30 @@ class SurveyUserInput(models.Model):
|
||||
duplicate = self.env[model].search(uniq_domain, limit=1)
|
||||
return duplicate
|
||||
|
||||
def get_required_value_from_other_record(
|
||||
def get_value_from_other_record(
|
||||
self,
|
||||
model: str,
|
||||
created_records: dict[Any, Any],
|
||||
field_value: "SurveyRecordCreationFieldValues",
|
||||
) -> Any:
|
||||
model_class = self.env[model]
|
||||
if model_class._fields[field_value.field_id.name].required:
|
||||
# check if the other record is already created,
|
||||
# if yes add it to vals, else raise
|
||||
if (
|
||||
len(created_records) > 0
|
||||
and created_records[field_value.other_created_record_id.id]
|
||||
):
|
||||
linked_record = created_records[field_value.other_created_record_id.id]
|
||||
return self.get_value_for_relational_field(field_value, linked_record)
|
||||
else:
|
||||
raise UserError(
|
||||
_(
|
||||
"The field %(field)s is mandatory for model %(model)s. "
|
||||
"In Record Creation tab, drag %(record)s "
|
||||
"on top of the model %(model)s."
|
||||
)
|
||||
% {
|
||||
"field": field_value.field_id.display_name,
|
||||
"model": model,
|
||||
"record": field_value.other_created_record_id.name,
|
||||
}
|
||||
linked_record = created_records.get(field_value.other_created_record_id.id)
|
||||
if linked_record:
|
||||
# The other record is already created: link it right away.
|
||||
return self.get_value_for_relational_field(field_value, linked_record)
|
||||
if self.env[model]._fields[field_value.field_id.name].required:
|
||||
raise UserError(
|
||||
_(
|
||||
"The field %(field)s is mandatory for model %(model)s. "
|
||||
"In Record Creation tab, drag %(record)s "
|
||||
"on top of the model %(model)s."
|
||||
)
|
||||
% {
|
||||
"field": field_value.field_id.display_name,
|
||||
"model": model,
|
||||
"record": field_value.other_created_record_id.name,
|
||||
}
|
||||
)
|
||||
return None
|
||||
|
||||
def get_value_from_user_answer(
|
||||
self,
|
||||
|
||||
Reference in New Issue
Block a user