我是Xtext / Xtend的新手,如果答案显而易见,请提前道歉。
我想允许我的DSL的最终用户定义一个'过滤器',当应用和'返回'时,它意味着他们想要“过滤掉”给定的数据实体。
我想让他们有两种方法来定义过滤器
A)通过内省给定数据对象的属性并应用基本规则,如
if (obj.field1<CURRENT_DATE && obj.field2=="EXPIRED)
{ return true;} else {return false;}
B)使用我的主语语言“eval”执行受控片段
换句话说,用户需要输入一个有效的字符串/代码块
托管语言的代码段
我已经决定支持案例A)的最简单方法是利用XBase规则(包括表达式/ etc)
因此,我定义了过滤器(主要是复制Lorenzo的书中的想法)
Filter:
(FilterDSL | FilterCode);
FilterDSL:
'filterDSL' (type=JvmTypeReference)? name=ID
'(' (params+=FullJvmFormalParameter (',' params+=FullJvmFormalParameter)*)? ')'
body=XBlockExpression ;
FilterCode:
'filterCode' (type=JvmTypeReference)? name=ID
'(' (params+=FullJvmFormalParameter (',' params+=FullJvmFormalParameter)*)? ')'
'{'
body=STRING
'}';
现在,当我尝试通过Xtend中的推理存根实现我的DSL的Java映射时,我遇到了多个问题。
所有这些都可能表明我缺少一些基本的理解
问题1) fl.body未定义。 fl是Filter类型,而不是FilterDSL或FilterCode
我不明白如何检查给定实例的类型,以便我可以访问“正文”功能的内容。
问题2)我不明白推理方法中'body'属性的定义及原因。这是ECore的一部分吗? (我找不到了)
问题3)允许用户指定代码块的正确方法是什么?字符串似乎不正确,因为它不允许多行
问题4)如何正确地将代码块转换为“正文”接受的内容,使其最终生成代码。
问题5)如何设置多个推子(因为我需要通过xBase代码生成器生成的代码(主要是),不止一件事)
事先欣赏任何建议,或指向解决类似问题的代码示例的指针。
作为一个侧面观察,Inferrer及其与XBase的相互作用已经成为最难以理解的问题。
答案 0 :(得分:1)
一般情况下:查看xtend-lang.org上的xtend文档
您可以使用Type guards执行if(x instanceof Type)或switch语句(请参阅域模型示例)
我不明白这个问题。您的FilterDSL和FilterCode EClasses都应该有一个名为body的字段+ getter / setter,类型为String的FilterCode,类型为XBlockExpression的FilterDSL。 JvmTypesBuilder将扩展方法添加到JvmOperation,称为setBody(String)和setBody(XExpression),语法糖允许你调用body = ....而不是setBody(...) (顺便说一句,你可以做crtl +点击查找确定事物的位置)
字符串实际上是多行
由(2)
你不需要多个推子,你可以推断多个东西,例如通过多次调用toClass或toField获取相同的输入