Stream: IG creation
Topic: slicing question for patterns on bindings
Eric Haas (Nov 25 2021 at 20:43):
based on this:
Each slice must use the element definition for the element(s) in the discriminator(s) to ensure that the slices are clearly differentiated by assigning an appropriate value domain, depending on the discriminator type. If the type is value, or pattern, then the element definition must use either:
ElementDefinition.fixed[x], or
ElementDefinition.pattern[x], or
if the element has a terminology binding, a required binding with a Value Set that enumerates the list of possible codes in the value set ("extensional definition") (my highlighting )
I did this ...
#....
- id: DiagnosticReport.category
path: DiagnosticReport.category
slicing:
discriminator:
- type: pattern #<<<<<<<<<<<<<<<<<<
path: $this #<<<<<<<<<<<<<<<<<<<
rules: open
min: 1
mustSupport: true
- id: 'DiagnosticReport.category:us-core'
path: DiagnosticReport.category
sliceName: us-core
min: 1
mustSupport: true
binding: #<<<<<<<<<<<<<<<<<<<<<
strength: extensible #<<<<<<<<<<<<<<<<<<<<<
valueSet: 'http://hl7.org/fhir/us/core/ValueSet/us-core-diagnosticreport-category' #<<<<<<<<<<<<<
which is causing this validation error:
1. ERROR: DiagnosticReport/bone-density-report: DiagnosticReport.category[0]: Slicing cannot be evaluated: Could not match discriminator ([$this]) for slice DiagnosticReport.category:us-core in profile http://hl7.org/fhir/us/core/StructureDefinition/us-core-diagnosticreport-note - the discriminator [$this] does not have fixed value, binding or existence assertions
Eric Haas (Nov 25 2021 at 20:45):
I want this slice to be an extensible binding and to replicate the same binding rules as an extensible binding on CodeableConcept behaves - i.e., at least one of the Categories contains a value from the extensible binding.
how do I fix it ?
- Does the binding need to be required? ()
What does "extensional definition" in the documentation above mean exactly ("a required binding with a Value Set that enumerates the list of possible codes in the value set ("extensional definition")?
Grahame Grieve (Nov 25 2021 at 21:16):
I think the definition is pretty clear: a required binding
Grahame Grieve (Nov 25 2021 at 21:16):
extensional: see https://www.hl7.org/fhir/valueset.html#int-ext
Eric Haas (Nov 25 2021 at 22:00):
Grahame Grieve said:
I think the definition is pretty clear: a required binding
My question really is the parenthetic "extensional definition" makes no sense in in the context of this documentation : "a required binding with a Value Set that enumerates the list of possible codes in the value set ("extensional definition")" Why is it there ?
Second, I want this slice to be an extensible binding and to replicate the same binding rules as an extensible binding on CodeableConcept behaves - i.e., at least one of the Categories contains a value from the extensible binding. how do I do that? In other words how does validation behave for extensible bindings on CodeableConcepts? it would be the same as that for slicing.
Eric Haas (Nov 25 2021 at 22:03):
for example, I have a value set A = 'foo', 'bar'. I would like a slice for element bound to value set A but also allow for 'baz' if that is a local extension of the valueset.
Grahame Grieve (Nov 25 2021 at 22:07):
I don't know how the documentation could be more clear: you can only slice by a required binding
Grahame Grieve (Nov 25 2021 at 22:08):
and the vocabulary committee don't think "extensional definition" makes no sense. it's just what we call 'a value set that enumerates the list of possible codes in the value set' is
Lloyd McKenzie (Nov 26 2021 at 05:46):
If the binding is extensible, there's no way for the engine to know when the slice doesn't apply - because any code you send could potentially fall into the 'extensible' space. (And it would take a human being to figure out whether it did or not.)
Eric Haas (Nov 26 2021 at 21:10):
IMO This is an academic argument that doesn't reflect the real world and is bad for actual implementation.
Grahame Grieve (Nov 26 2021 at 21:11):
no. using an extensible binding for a slice discriminator would be bad for actual implementation
Eric Haas (Nov 26 2021 at 21:11):
and what about CodeableConcept with extensiblible bindings - how does that work today?
Grahame Grieve (Nov 26 2021 at 21:14):
works moderately badly, but what's the relationship?
Eric Haas (Nov 26 2021 at 21:14):
We assumed incorrectly that an extensibly bound element would behave that way too. but alas it does not. So it turns out slicing does not get you that either. This is a gap
Eric Haas (Nov 26 2021 at 21:15):
moderately good or badly?
Grahame Grieve (Nov 26 2021 at 21:16):
I'm not sure what you're saying here. if your question is, 'can a slice have an extensible binding?' then the answer is yes, of course it can. Just like if it wasn't sliced. But if you question is 'can you discriminate a slice based on an extensible binding?' then the answer is no, you can't discriminate like that
Grahame Grieve (Nov 26 2021 at 21:18):
(and slices that can't be discriminated are bad for implementers)
Eric Haas (Nov 26 2021 at 21:22):
So one solution could be to describe the discriminator and let Inferno figure it out for certification ... @Yunwei Wang heads up
Lloyd McKenzie (Nov 26 2021 at 21:35):
How exactly would you expect the engine to discriminate on an extensible binding @Eric Haas? In what circumstances would an instance not always match the slice with that binding?
Grahame Grieve (Nov 26 2021 at 22:00):
So one solution could be to describe the discriminator and let Inferno figure it out for certification
well, FMG isn't going to approve of that, and inferno couldn't figure it out
Eric Haas (Nov 27 2021 at 02:24):
These value set are not designed to be required as there is not agreement within a context of use that a specified set of codes are the only ones that can be used. and a required bindings on category slice would imply this. Hopefully we can figure something out.
Grahame Grieve (Nov 27 2021 at 06:17):
well, you can have an extensible binding. you just can't slice by it
Grahame Grieve (Nov 27 2021 at 06:17):
what's the details?
Eric Haas (Nov 27 2021 at 23:11):
(deleted)
Eric Haas (Nov 28 2021 at 00:42):
Grahame Grieve said:
well, you can have an extensible binding. you just can't slice by it
We have several instances of extensible bindings on if the element category
which usually repeats for example DiagnosticReport.category
then If an extensible binding is applied to an element with maximum cardinality > 1, the binding applies to all the elements. (http://hl7.org/fhir/R4/terminologies.html#extensible) That was not our intent and has led to the current situation:
- Our intent is only single repeat be bound to the valueset. To illustrate this problem , look at SDOHCC Condition a derived profile from USCore Condition - there SDOH slice which is technically invalid since it does not contain the US Core valueset concepts.
- In addition we know our valuesets are incomplete so making it required prohibits other local valid category concepts.
I understand the technical difficulty with this but I can imagine defining multiple orthogonal categorization schemes that could be defined with orthogonal not-fully-realized valuesets at time of publishing.
Lloyd McKenzie (Nov 28 2021 at 15:22):
The rules with slicing are simple - the discriminators must discriminate. I.e. no two slices can allow overlapping values for the set of declared discriminators. Two extensible bindings will always overlap even if the base value sets don't because "extensible" means that codes not found within the value set are also allowed.
The best way to accomplish what you're trying to do is have 0..1 must support slices with required bindings. That says "you must be capable of sending and receiving content that looks like this, but it's ok if the category doesn't apply and you're free to send other categories too. Also, you can't have multiple categories from this value set." (Personally, I think that last statement is questionable - if you're going to say that you must ensure that there's never a circumstance where more than one of the codes could apply at the same time.)
Grahame Grieve (Nov 28 2021 at 22:03):
generally agree with Lloyd - but it sounds like you really want a pretty general binding and a 'must-support' value set tied to a functional context?
Lloyd McKenzie (Nov 29 2021 at 14:57):
Having a required or extensible binding across all category repetitions in US-Core is an error. That's saying that every repetition must satisfy the binding, which isn't what you want. If you make category 1..* overall and have a 0..1 required mustSupport slice with your current value set, you'll accomplish your desired outcome. I.e. "Must always have a category. Must send one of our category codes if one of them applies".
Eric Haas (Nov 29 2021 at 15:27):
Lloyd McKenzie said:
Having a required or extensible binding across all category repetitions in US-Core is an error. That's saying that every repetition must satisfy the binding, which isn't what you want. If you make category 1..* overall and have a 0..1 required mustSupport slice with your current value set, you'll accomplish your desired outcome. I.e. "Must always have a category. Must send one of our category codes if one of them applies".
I agree and that is what i stated earlier twice and why we are stuck using the more opaque slicing structure
Eric Haas (Nov 29 2021 at 15:39):
OK after stewing on this over the weekend.
element 1..* with 1..* slice on extensible binding ( which we can't do :rage:) ~= element 1..* with 0..* slice on required binding
The meaning of a required binding is compromised to allow for slicing in this case and folks reading us core are going to see required and have a cow. We are going to have to document how a required binding slice with a combination of cardinality is really an extensible binding in disguise.
Josh Mandel (Nov 29 2021 at 16:33):
I'm confused about the rules for discriminators -- I thought they were technically optional (i.e., without a discriminator, the semantics of slicing still work, just in a less computationally tractable way) per http://build.fhir.org/profiling.html#discriminator .
Grahame Grieve (Nov 29 2021 at 18:41):
yes that's right, so why confused?
Lloyd McKenzie (Nov 29 2021 at 21:59):
If you just express the rules with a description, you still need to express the rules in a way that can meet the requirements - i.e. every slice can be discriminated and every instance repetition matches against no more than one slice. If you've got multiple slices with extensible bindings, that's not possible.
Lloyd McKenzie (Nov 29 2021 at 22:00):
@Eric Haas Not sure what you mean by "the meaning of a required binding is compromised". I don't think there's any compromise here?
Josh Mandel (Nov 29 2021 at 22:04):
So there's (intentionally) no way to use slicing to say:
- Need at least one Coding from {"A", "B", "C"}
- Need at least one Coding from {"C", "D", "E"}
... and satisfy the slicing validator with a single Coding "C"?
Lloyd McKenzie (Nov 29 2021 at 22:06):
Right. Slices must be disjoint.
Josh Mandel (Nov 29 2021 at 22:07):
Can you help me with the intuition for why? Is it that use cases like the example above don't really exist? Or that supporting such things would introduce complexities elsewhere?
Grahame Grieve (Nov 29 2021 at 22:15):
hey no
Grahame Grieve (Nov 29 2021 at 22:15):
slices don't have to be disjoint, but discriminators have to be disjoint. But slices that are not disjoint are... not anticipated or desired
Grahame Grieve (Nov 29 2021 at 22:16):
the point of having slices is so that you can describe them differently.
Grahame Grieve (Nov 29 2021 at 22:21):
the specification does not rule out having over-lapping slices, because we never thought that would be a thing, really. The langauge is written for it not to be a thing, but it's not stated explicitly. E.g.
In this case, the "code" element in the target resource can be used to determine which slice that target refers to
It's always singular - an element fits into one slice. But it's only on discriminators that we say:
When a constraining structure designates one or more discriminators, it SHALL ensure that the possible values for each slice are different and non-overlapping, so that the slices can easily be distinguished
Note, though, that the reason is so that slices can easily be distinguished. Not so that they can be distinguished at all, since the language assumes that each element is in at most, one slice. Which is also how the validator is implemented - it allocates elements to slices, and then validates them against their slice (singular)
Grahame Grieve (Nov 29 2021 at 22:21):
I'm not in a hurry to change that either - slicing is the most difficult code I've ever written (both the snapshot generation, and the validation)
Josh Mandel (Nov 29 2021 at 22:23):
slices don't have to be disjoint, but discriminators have to be disjoint. But slices that are not disjoint are... not anticipated or desired
How can disjoint discriminators result in nondisjoint slices? At this point I'm just trying to follow the logic, not arguing for anything in particular.
Lloyd McKenzie (Nov 29 2021 at 22:29):
I don't understand how a slice can avoid being disjoint if the discriminators are disjoint? Can you give an example Grahame?
Grahame Grieve (Nov 29 2021 at 22:30):
if there is no discriminators
Grahame Grieve (Nov 29 2021 at 22:35):
the point of discriminators is to discriminate, so if there are any, then conformant slices will be disjoint - they must be.
but if there's no discriminators, then all bets are off. The spec anticipates that they are still disjoint, but it does not say so explicitly. And the validator implements that they are disjoint, but has no way to test that they are, other than trying to match. I guess I'll have to add a test case to find out what happens to my todo list
Lloyd McKenzie (Nov 29 2021 at 23:07):
If there are no discriminators, isn't the discrimination process defined in text - but still expected to actually discriminate?
Grahame Grieve (Nov 29 2021 at 23:15):
doesn't have to be defined in text. if it's not, then it's purely based on validation against the slices.
Grahame Grieve (Nov 29 2021 at 23:16):
as for
expected to actually discriminate
yes. it's expected to - at least, we expected it to when we wrote the spec, but we failed to be explicit about it
Lloyd McKenzie (Nov 29 2021 at 23:24):
Eric Haas (Nov 29 2021 at 23:49):
re "the meaning of a required binding is compromised"
required binding definition: "The other place where this is used is when profiling resources, and there is agreement within a context of use that a specified set of codes are the only ones that can be used. In these cases, the data type SHALL contain one of the values in the value set." ( http://hl7.org/fhir/terminologies.html#required )
required binding definition when slicing by valueset : "The other place where this is used is when slicing by valueset. Because it is necessary to define disjoint slices only a specified set of codes even if there is not agreement within a context of use that a specified set of codes are the only ones that can be used" ( my interpretation.)
Lloyd McKenzie (Nov 30 2021 at 02:12):
But the point is - within the slice, it is the only set of codes that can be used. You just have other slices that allow for other things too. The meaning of 'required' isn't any different. You're just using it (appropriately) in a more constrained space. Outside that space, the 'required' has no force.
Last updated: Apr 12 2022 at 19:14 UTC