func (vis *sourceVisitor) Visit(node ast.Node) ast.Visitor { switch t := node.(type) { case *ast.SelectorExpr: ast.Walk(vis, t.X) return nil case *ast.Ident: sym := vis.IdentMap.GetSymbol(t) if ps, ok := sym.(*st.PackageSymbol); ok { p := ps.Package imp := vis.Package.GetImport(vis.destFile, p) if imp != nil { if imp.Name() != ps.Name() { vis.Chan <- &ast.Ident{t.NamePos, imp.Name(), nil} } else { vis.Chan <- nil } return nil } vis.importsToAdd[ps] = true vis.Chan <- &ast.Ident{t.NamePos, ps.Name(), nil} return nil } if nn, ok := vis.newNames[sym]; ok { vis.Chan <- utils.CopyAstNode(nn).(ast.Expr) } else { vis.Chan <- nil } return nil } return vis }
func AddDecl(fset *token.FileSet, filename string, file *ast.File, withFileSet *token.FileSet, withFileName string, withFile *ast.File, withPosStart, withPosEnd token.Position, identMap st.IdentifierMap) (bool, *token.FileSet, *ast.File, *errors.GoRefactorError) { withNode := FindNode(withFileSet, withFile, withPosStart, withPosEnd) if withNode == nil { return false, nil, nil, errors.PrinterError("couldn't find node with given positions") } if _, ok := withNode.(ast.Decl); !ok { return false, nil, nil, errors.PrinterError("node is not a declaration") } withTokFile := GetFileFromFileSet(withFileSet, withFileName) withOldSize := withTokFile.Size() l := int(withNode.End() - withNode.Pos()) fset, file = ReparseFile(file, filename, l, identMap) if filename == withFileName { withFileSet, withFile = fset, file withNode = FindNode(withFileSet, withFile, withPosStart, withPosEnd) } withNode = utils.CopyAstNode(withNode) tokFile := GetFileFromFileSet(fset, filename) withTokFile = GetFileFromFileSet(withFileSet, withFileName) if tokFile == nil || withTokFile == nil { return false, nil, nil, errors.PrinterError("couldn't find file " + filename + " in fileset") } lines := GetLines(tokFile) fmt.Printf("linesCount = %d\n", len(lines)) tokFile.SetLines(lines[:len(lines)-(l)]) lines = GetLines(tokFile) for i, offset := range lines { fmt.Printf("%d -> %s(%d)\n", i+1, fset.Position(tokFile.Pos(offset)), offset) } withNodeLines, _ := GetRangeLines(withTokFile, withNode.Pos(), withNode.End(), withOldSize) withMod := int(tokFile.Offset(file.Decls[len(file.Decls)-1].End()) + 1 - withTokFile.Offset(withNode.Pos())) fmt.Printf("withMod: %v\n", withMod) for i, _ := range withNodeLines { withNodeLines[i] += withMod } tokFile.SetLines(addLinesOfRange(withTokFile.Offset(withNode.Pos()), withTokFile.Offset(withNode.End()), lines, withNodeLines, -1)) //to the end file.Decls = append(file.Decls, withNode.(ast.Decl)) return true, fset, file, nil }
func ReplaceNode(fset *token.FileSet, filename string, file *ast.File, posStart, posEnd token.Position, withFileSet *token.FileSet, withFileName string, withFile *ast.File, withPosStart, withPosEnd token.Position, identMap st.IdentifierMap) (bool, *token.FileSet, *ast.File, *errors.GoRefactorError) { tokFile := GetFileFromFileSet(fset, filename) withTokFile := GetFileFromFileSet(withFileSet, withFileName) if tokFile == nil { return false, nil, nil, errors.PrinterError("couldn't find file " + filename + " in fileset") } if withTokFile == nil { return false, nil, nil, errors.PrinterError("couldn't find file " + withFileName + " in fileset") } node := FindNode(fset, file, posStart, posEnd) withNode := FindNode(withFileSet, withFile, withPosStart, withPosEnd) if node == nil || withNode == nil { return false, nil, nil, errors.PrinterError("couldn't find node with given positions") } printDecls(tokFile, file) oldSize := tokFile.Size() withOldSize := withTokFile.Size() l, wl := int(node.End()-node.Pos()), int(withNode.End()-withNode.Pos()) if wl > l { fmt.Printf("length to add = %d\n", wl-l) inc := 1 - tokFile.Base() fmt.Printf("inc = %d\n", inc) fset, file = ReparseFile(file, filename, wl-l, identMap) node = FindNode(fset, file, posStart, posEnd) tokFile = GetFileFromFileSet(fset, filename) if filename == withFileName { withFileSet, withFile, withTokFile = fset, file, tokFile withNode = FindNode(withFileSet, withFile, withPosStart, withPosEnd) } lines := GetLines(tokFile) fmt.Printf("linesCount = %d\n", len(lines)) tokFile.SetLines(lines[:len(lines)-(wl-l)]) } withNode = utils.CopyAstNode(withNode) lines := GetLines(tokFile) for i, offset := range lines { fmt.Printf("%d -> %s(%d)\n", i+1, fset.Position(tokFile.Pos(offset)), offset) } nodeLines, firstLine := GetRangeLines(tokFile, node.Pos(), node.End(), oldSize) withNodeLines, _ := GetRangeLines(withTokFile, withNode.Pos(), withNode.End(), withOldSize) fmt.Printf("withnodeLines: %v\n", withNodeLines) mod := wl - l withMod := int(tokFile.Offset(node.Pos()) - withTokFile.Offset(withNode.Pos())) fmt.Printf("withMod: %v\n", withMod) for i, _ := range withNodeLines { withNodeLines[i] += withMod } newLines := removeLinesOfRange(tokFile.Offset(node.Pos()), tokFile.Offset(node.End()), lines, nodeLines, firstLine) tokFile.SetLines(addLinesOfRange(withTokFile.Offset(withNode.Pos()), withTokFile.Offset(withNode.End()), newLines, withNodeLines, firstLine)) printDecls(tokFile, file) fmt.Printf("node -------- %d %d --------- %d %d\n", node.Pos(), node.End(), tokFile.Offset(node.Pos()), tokFile.Offset(node.End())) fmt.Printf("with -------- %d %d --------- %d %d\n", withNode.Pos(), withNode.End(), withTokFile.Offset(withNode.Pos()), withTokFile.Offset(withNode.End())) FixPositions(0, withMod, withNode, true) fmt.Printf("node -------- %d %d --------- %d %d\n", node.Pos(), node.End(), tokFile.Offset(node.Pos()), tokFile.Offset(node.End())) fmt.Printf("with -------- %d %d --------- %d %d\n", withNode.Pos(), withNode.End(), withTokFile.Offset(withNode.Pos()), withTokFile.Offset(withNode.End())) printDecls(tokFile, file) if _, ok := replaceNode(fset, posStart, posEnd, file, withNode); !ok { return false, nil, nil, errors.PrinterError("didn't find node to replace") } except := map[ast.Node]bool{withNode: true} FixPositionsExcept(withNode.Pos(), mod, file, true, except) printDecls(tokFile, file) return true, fset, file, nil }