Xtext中如何集成QualifiedName与DotExpression实现嵌套对象作用域提供器
问题:引入Context与QualifiedName后DotExpression的Scope解析异常
背景
我正在为实体映射模型开发Scope Provider,模型中实体属性可引用其他实体,DSL的映射部分需要支持嵌套实体属性的引用。此前实现的方案运行正常,但引入Context元素并修改QualifiedName相关DSL定义后,Eclipse智能提示无法识别Entity.p.x这类嵌套表达式。
初始DSL定义
Model: elements+=BaseElement*; BaseElement: Context | Entity | Mapping; QualifiedName: ID ('.' ID)*; QualifiedNameWithWildcard: QualifiedName '.*'?; Context: 'context' name=QualifiedName '{' entities+=Entity* '}'; Entity: 'entity' name=ID fields+=Field*; Field: Attribute | Reference ; Attribute: name=ID type=TYPE_ENUM ; Reference: name=ID type=[Entity] ; enum TYPE_ENUM: INT | LONG | STRING | BOOLEAN | UUID ; Mapping: 'mapping' name=ID mappings+=FieldMapping* ; FieldMapping: name=ID '=>' ref=DotExpression ; DotExpression returns Ref: EntityRef ({DotExpression.ref=current} "." tail=[Field])* ; EntityRef returns Ref: {EntityRef} entity=[Entity] ;
初始正常运行的模型示例
entity entityA { x STRING y STRING z INT } entity EntityB { a INT b STRING } entity EntityC { m STRING n INT p EntityA } mapping Absender Sender_PostCode => Entity.p.x
修改后的问题场景
修改后的模型示例
context org.test.example { entity entityA { x STRING y STRING z INT } entity EntityB { a INT b STRING } entity EntityC { m STRING n INT p EntityA } } mapping Absender Sender_PostCode => Entity.p.x
DSL修改部分
仅修改了Reference和EntityRef的类型引用,加入QualifiedName限定:
Reference: name=ID type=[Entity|QualifiedName] ; EntityRef returns Ref: {EntityRef} entity=[Entity|QualifiedName] ;
修改后智能提示无法识别嵌套表达式,推测是QualifiedName干扰了DotExpression的解析逻辑。
当前ScopeProvider代码
@Override public IScope getScope(EObject context, EReference reference) { if(context instanceof DotExpression) { DotExpression dotExpression = (DotExpression) context; Ref head = dotExpression.getRef(); return recursive(head); } return super.getScope(context, reference); } private IScope recursive(Ref head) { if(head instanceof EntityRef) { EntityRef entity = (EntityRef) head; return Scopes.scopeFor(entity.getEntity().getFields()); } else if(head instanceof DotExpression) { DotExpression nextDE = (DotExpression) head; if(nextDE.getTail() instanceof Attribute) { return IScope.NULLSCOPE; } else if(nextDE.getTail() instanceof Reference) { Reference ref = (Reference) nextDE.getTail(); return Scopes.scopeFor(ref.getType().getFields()); } else if(nextDE.getTail() instanceof DotExpression){ DotExpression tail = (DotExpression) nextDE.getTail(); return recursive((tail.getRef())); } else { return IScope.NULLSCOPE; } } else { return IScope.NULLSCOPE; } }
问题
如何将QualifiedName与DotExpression集成,解决当前智能提示无法识别嵌套表达式的问题?
内容的提问来源于stack exchange,提问作者posthumecaver
相关产品推荐
相关产品推荐

