Skip to content

Conversation

@lindsay-stevens
Copy link
Contributor

Closes #791

Why is this the best possible solution? Were any other approaches considered?

See commit messages for details.

Considered keeping lowest_common_ancestor behaviour of identifying other node relationship types but the name of the function is about common ancestors and it's only used for that purpose.

What are the regression risks?

Fixes a regression.

Does this change require updates to documentation? If so, please file an issue here and include the link below.

No

Before submitting this PR, please make sure you have:

  • included test cases for core behavior and edge cases in tests
  • run python -m unittest and verified all tests pass
  • run ruff format pyxform tests and ruff check pyxform tests to lint code
  • verified that any code or assets from external sources are properly credited in comments

- unlikely to be a problem but if iter_ancestors yields nothing then
  the default for `next()` should be an iterable so it can be unpacked
  like the expected values are.
- makes debugging quite a bit more convenient
- previous test cases focussed on the references targeting questions
  but as noted in test_references__source_under_target it's useful for
  a source to be able to refer to its parent repeat
- the test build_survey_from_path_spec syntax is modified to recognise
  "at" as the target which is also an ancestor repeat of the source.
- SurveyElement.lowest_common_ancestor is changed to only deal with
  finding common ancestors, rather than identifying any other node
  relationship types (e.g. parent / child / ancestor).
@lindsay-stevens
Copy link
Contributor Author

The CI test failure here is due to the issue described in this comment.

Copy link
Contributor

@lognaturel lognaturel left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you! Looks good to me but some of the tests would benefit from referencing real nodes, I think. Their assertions are technically correct but feel more confusing than necessary.

I also want to note that there is ambiguity in the targeted expressions. Someone could conceivably use a ${} from within a repeat and want a relative reference. But I think the behavior from this PR is more likely to match their expectations. I assume that if someone knows how to formulate this kind of more complex expression they can also write relative references themselves comfortably. Most importantly, we didn't intend to change the behavior from what it was before.

- the tests passed before since they are about resolving `t` relative
  to `s` but for completeness/accuracy the `default` path now matches
  the actual relative position of `s`.
@lindsay-stevens
Copy link
Contributor Author

Thanks I updated the test case paths to match the form structure in 5b0289a. Not sure if it's what you meant but the tests added in this PR under TestGetPathRelativeToLCAR show that if the target repeat (parent of source) is itself inside a repeat then the path will be relative (e.g. /y/r1o/at/s -> ../../at); while the tests under TestReferencesToAncestorRepeat show that if the target repeat (parent of source) is not inside a repeat then the path will be absolute (e.g. /y/at/s -> /y/at). Then within those sets of tests are combinations of one or two groups or repeats either above or below the target. The confusing case might be when the source is in a nested repeat but the target (which is also a repeat) is not in a repeat so the path is absolute (e.g. /y/at/r1s/s -> /y/at).

Copy link
Contributor

@lognaturel lognaturel left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! It feels easier to understand when the paths exist. Of course the expressions with repeats still wouldn’t really make sense because they return nodesets but at least the shape of the paths look right.

There are a couple things in the other PR I’m not yet understanding. I’ll finish that review after some rest! I think it will be fine to merge first.

@lognaturel lognaturel merged commit 8288ba5 into XLSForm:master Dec 15, 2025
13 of 14 checks passed
@lindsay-stevens lindsay-stevens deleted the pyxform-791 branch December 16, 2025 06:30
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

Successfully merging this pull request may close these issues.

Incorrect parenting when accessing a repeat from a child group

2 participants