Odd scoping issue

Hi,

today I experimented with scopes. I have a concept A which holds a reference to an instance of concept B and one of concept C. A itself is a ScopeProvider but only provides a scope for instances of concept B. For concept C it returns null in the getScope(...) method implementation. According to the documentation the engine then searches for more distant ancestors that are ScopeProviders, too. In the ancestor hierarchy there is another ScopeProvider which is able to provide a scope for references to instances of concept C. But there the child parameter in getScope(child,kind) is not, as expected, of concept A but concept X. Instances of X are far ancestors of instances of A, but this should not have any influence, imho. However, I need the exact container of the reference, which means A. Is this a bug or have I misinterpreted anything?

It would be great if anybody has an idea.

Thank you very much in advance,
LaAck
4 comments
Hi!
It's not a bug. The docs, as I see, don't mention it explicitly, but the name of the 'child' parameter in ScopeProvider.getScope() is 'child' after all, and it's indeed always a child node of the given scope provider.

Note, node of X should be a child of that another ScopeProvider in your example. Is it true?

Thus, the scope provider doesn't get all the path in the tree from the reference up to itself, rather only which of its own children is asking, no matter if the child is asking itself or it's acting on behalf of somebody deeply down the tree.

For the sake of discussion, it wouldn't be modular for the ScopeProvider to accept the node enclosing the reference, because the scope provider would have to be aware of various kinds of references to the concept (to treat the enclosing node in a sensible way) , which is impossible given that any language could introduce new kinds of refs.

Of course, hypothetically it could handle some of the cases which it knows about and resort to default in other cases. But that's not the way it is now.

Could you describe your example in more detail? How exactly would you use the node of A in that high-in-the-tree ScopeProvider? Maybe you could use parent scope construct in A, and then post-process/wrap that scope using the knowledge that you're in A. Still, it feels like a lack for expressiveness in the scoping language, yes.
0
Hi Daniil,

thank you very much for your informative reply. Ok, so I misinterpreted the meaning of the child node in terms of what I have to expect if someone deep in the tree asks for nodes that can be referenced.

And yes, you are right, the node of X is a direct child of the second ScopeProvider. I absolutely get the point that the modularity is somehow contaminated if the ScopeProvider directly accepts the node enclosing the reference. But then you also have to use the "kind" parameter in a similar generic way, i.e. you mustn't do things like kind.isSubConceptOf(...). Am I right?

My concrete example is as follows. I have an Interface Concept named FormalContentValueReference which is the interface of something like a Dot expression, e.g. class.member. In order to understand the problem I have to say that I have a concept ParameterDefinition and a second one called RuleDefinition that implement an Interface Concept FormalContentDefinition. During runtime the application I generate code for can assign a value to the respective parameter. The overall set of possible values is defined as a discrete value range in ParameterDefinition. Secondly a RuleDefinition checks if a certain parameter value constellation is present and returns a certain value for an available constellation. It is also possible to reference rule results in the check for parameter constellations, which is used for producing more readable rule lists. That's why both, the ParameterDefinition and the RuleDefinition can be referenced. Therefore I created another Interface Concept - the already mentioned FormalContentValueReference. It consists of a reference "B" to either a ParameterDefinition or a RuleDefinition (B in my previous post) as well as a set of references to values (C in my previous post).
Ok, now the problem. One implementation of FormalContentValueReference called ParameterValueReference (A in my previous post) may only refer to nodes of ParameterDefinition. But the second ScopeProvider just gets FormalContentDefinition as "kind". So it is not possible to distinguish between ParameterDefinitions and RuleDefinitions.
The reason for two scope provider is that the FormalContentValueReference nows all possible values for e.g. a parameter because it knows the respective ParameterDefinition. But it does not know all ParameterDefinitions because they may be distributed over several higher order structures called "Sections". This is where the parent of X comes into play.

According to your explanations, I now would change the ParameterValueReference introducing a scoping constraint like:
link {B} 
  referent set handler:<none> 
  scope: 
    inherited for ParameterDefinition 
  presentation : 
    <no presentation> 
;
prettyPrint();

Currently I have a more general constraint in FormalContentValueReference which inherits for "FormalContentDefinition". As far as I know I cannot use the "can be parent" constraint section because it is a reference and not a node. Is this true?

Thank you very much for your help!

Kind regards,
LaAck
0
According to your explanations, I now would change the ParameterValueReference introducing a scoping constraint like:
 
link {B} 
  referent set handler:<none> 
  scope: 
    inherited for ParameterDefinition 
  presentation : 
    <no presentation> 
;
prettyPrint();


To me this looks like the correct solution. Does it have any drawbacks? I can't see any.

Currently I have a more general constraint in FormalContentValueReference which inherits for "FormalContentDefinition". As far as I know I cannot use the "can be parent" constraint section because it is a reference and not a node. Is this true?


It's true.
Since you're asking about 'can be parent', you seem to be seeking for some means to state the constraint that one ref can reference only one sub-concept and the other ref only the other one. And it is very understandable because you _must_ somehow state it.

So, to me, in your code snippet above you do exactly that.

If you want to stick to the more general constraint in FormalContValRef but somehow implement the correct scoping in the ScopeProvider, then that just seems wrong to me.
0
Ok, thank you, Daniil! I tried it and it worked for me!
0

Please sign in to leave a comment.