私が書いているサービスはコードスニペットを受け取って処理しますが、スニペットは補完プログラムまたはフラグメントのいずれかになります。フラグメントの場合は、それを囲むmain
関数。例えば、スニペット:フラグメントを解析してトップレベルの定義をすべて見つけよう
var v int
v = 3
fmt.Println(v)
フラグメントとして分類され、それにmain
を追加しなければならない。
func main() {
var v int
v = 3
fmt.Println(v)
}
スニペットの場合:
package main
import "fmt"
func main() {
fmt.Println("hello")
}
次いで全く変更があってはなりません完了しました。
は私が今やっている方法は、スニペットに反するパーサーを実行している:
var fset *token.FileSet
file, err := parser.ParseFile(fset, "stdin", code, 0)
if err != nil {
// add function
code = fmt.Sprintf("func main() {\n%s\n}", code)
// ...
}
これは、上記第一のスニペットのために働くのフラグメントは、いくつかの他の宣言の後にmain
機能を持っている場合しかし、それは失敗し、例えば
type S struct {
a int
}
func main() {
fmt.Println("foo")
}
私はまた、ParseFile
によって返さfile
に見てみてくださいDecls
をチェックし、それはそれは第一にエラーの後で解析を停止します見えますので、Decls
はこのケースでnil
です。だから私の質問は、これを処理する堅牢な方法ですか?
PS。とにかく処理されたコードをgolang.org/x/tools/imports
に送っているので、package句と必要なインポートのインクルードは関係ありません。
grepのソースは本当に最後の手段ですが、私はより洗練されたソリューションを探しています。 – fluter