1
我想我可以在scala-reflection或scala編譯器中找到它,但是我一直無法找到一個記錄的API。有沒有辦法在運行時執行此操作?如何判斷Scala中的標識符是否無效?
例如def isValidIdentifer(s:String)
(我沒有興趣在保留關鍵字,我可以寫我自己閱讀手冊的實際列表)
編輯:
基於@ sschaef的答案,更多的規格:它應該處理任何
import scala.tools.reflect.{ToolBox, ToolBoxError}
lazy val tb = scala.reflect.runtime.universe.runtimeMirror(getClass.getClassLoader).mkToolBox()
def isIdentifier(ident: String): Boolean = {
if (ident.startsWith(" ") || ident.endsWith(" ")) {
return false
}
try {
val tree = tb.parse(s"val $ident:Int = 0")
if (tree.toString().length != ident.length + 13) {
return false
}
tree.children match {
case c0 :: c1 :: Nil if
c0.children.isEmpty && c0.productArity == 1 && c0.productElement(0).toString == "Int"
&& c1.children.isEmpty && c1.productArity == 1 && c1.productElement(0).toString == "Constant(0)" => true
case _ => false
}
} catch {
case _: ToolBoxError => false
}
}
:如果
s
是一個有效的標識符
我想擴大這個答案類型的輸入並返回true
這成功以下惡性案件:b:Int
,b = 0; c
,b/*comment*/
該解決方案的空白正確不處理。 'isIdentifier(「x = 0; val b」)' – mauhiz
@mauhiz我用括號包圍了插入的代碼,希望這足夠安全。通過從網站輸入文本字段來評估此功能的用例不是問題中提到的要求...;) – sschaef
對,我並不十分清楚。仍然是'isIdentifier(「x)= 0; val(b」)';)只要我們盲目地允許輸入包含空格,try-to-parse解決方案對於注入將會很弱。 – mauhiz