java_identifier_listener.go 6.6 KB
Newer Older
P
Phodal HUANG 已提交
1
package identifier
P
Phodal HUANG 已提交
2 3

import (
P
Phodal Huang 已提交
4
	"github.com/antlr/antlr4/runtime/Go/antlr"
P
Phodal Huang 已提交
5 6
	"github.com/phodal/coca/pkg/domain"
	common_listener2 "github.com/phodal/coca/pkg/infrastructure/ast/common_listener"
P
Phodal Huang 已提交
7
	"github.com/phodal/coca/languages/java"
8
	"reflect"
9
	"strings"
P
Phodal HUANG 已提交
10 11
)

P
Phodal Huang 已提交
12 13
var currentNode *domain.JIdentifier
var nodes []domain.JIdentifier
P
Phodal HUANG 已提交
14

P
Phodal Huang 已提交
15
var currentMethod domain.JMethod
P
Phodal Huang 已提交
16
var hasEnterClass = false
17
var imports []string
P
Phodal Huang 已提交
18

P
Phodal Huang 已提交
19
func NewJavaIdentifierListener() *JavaIdentifierListener {
P
Phodal Huang 已提交
20
	nodes = nil
P
Phodal Huang 已提交
21 22
	currentNode = domain.NewJIdentifier()
	currentMethod = domain.NewJMethod()
P
Phodal Huang 已提交
23 24 25
	return &JavaIdentifierListener{}
}

P
Phodal HUANG 已提交
26
type JavaIdentifierListener struct {
P
Phodal Huang 已提交
27
	parser.BaseJavaParserListener
P
Phodal HUANG 已提交
28 29
}

30 31 32 33 34
func (s *JavaIdentifierListener) EnterImportDeclaration(ctx *parser.ImportDeclarationContext) {
	importText := ctx.QualifiedName().GetText()
	imports = append(imports, importText)
}

P
Phodal Huang 已提交
35
func (s *JavaIdentifierListener) EnterPackageDeclaration(ctx *parser.PackageDeclarationContext) {
P
Phodal Huang 已提交
36
	currentNode.Package = ctx.QualifiedName().GetText()
P
Phodal HUANG 已提交
37 38
}

P
Phodal Huang 已提交
39
func (s *JavaIdentifierListener) EnterClassDeclaration(ctx *parser.ClassDeclarationContext) {
P
Phodal Huang 已提交
40 41
	hasEnterClass = true

P
Phodal Huang 已提交
42
	currentNode.ClassType = "Class"
P
Phodal Huang 已提交
43
	if ctx.IDENTIFIER() != nil {
P
Phodal Huang 已提交
44
		currentNode.ClassName = ctx.IDENTIFIER().GetText()
P
Phodal Huang 已提交
45
	}
P
Phodal Huang 已提交
46 47

	if ctx.EXTENDS() != nil {
P
Phodal Huang 已提交
48
		currentNode.ExtendsName = ctx.TypeType().GetText()
P
Phodal Huang 已提交
49
	}
50 51 52 53 54 55 56

	if ctx.IMPLEMENTS() != nil {
		types := ctx.TypeList().(*parser.TypeListContext).AllTypeType()
		for _, typ := range types {
			typeText := typ.GetText()
			for _, imp := range imports {
				if strings.HasSuffix(imp, "."+typeText) {
P
Phodal Huang 已提交
57
					currentNode.Implements = append(currentNode.Implements, imp)
58 59 60 61
				}
			}
		}
	}
P
Phodal Huang 已提交
62

P
Phodal Huang 已提交
63
	currentMethod = domain.NewJMethod()
P
Phodal HUANG 已提交
64 65
}

P
Phodal Huang 已提交
66
func (s *JavaIdentifierListener) ExitClassBody(ctx *parser.ClassBodyContext) {
P
Phodal Huang 已提交
67
	hasEnterClass = false
P
Phodal Huang 已提交
68 69 70 71
	if currentNode.ClassName != "" {
		currentNode.Methods = currentNode.GetMethods()
		nodes = append(nodes, *currentNode)
	}
P
Phodal Huang 已提交
72
	currentNode = domain.NewJIdentifier()
P
Phodal Huang 已提交
73 74
}

P
Phodal Huang 已提交
75 76 77 78 79 80
func (s *JavaIdentifierListener) ExitInterfaceDeclaration(ctx *parser.InterfaceDeclarationContext) {
	hasEnterClass = false
	if currentNode.ClassName != "" {
		currentNode.Methods = currentNode.GetMethods()
		nodes = append(nodes, *currentNode)
	}
P
Phodal Huang 已提交
81
	currentNode = domain.NewJIdentifier()
P
Phodal Huang 已提交
82 83
}

84
func (s *JavaIdentifierListener) EnterConstructorDeclaration(ctx *parser.ConstructorDeclarationContext) {
P
Phodal Huang 已提交
85
	currentMethod = domain.JMethod{
P
Phodal Huang 已提交
86
		Name:              ctx.IDENTIFIER().GetText(),
87
		Type:              "",
P
Phodal Huang 已提交
88 89 90 91
		StartLine:         ctx.GetStart().GetLine(),
		StartLinePosition: ctx.GetStart().GetColumn(),
		StopLine:          ctx.GetStop().GetLine(),
		StopLinePosition:  ctx.GetStop().GetColumn(),
92
		Override:          isOverrideMethod,
P
Phodal Huang 已提交
93
		Annotations:       currentMethod.Annotations,
94 95 96 97 98 99 100 101
		IsConstructor:     true,
	}
}

func (s *JavaIdentifierListener) ExitConstructorDeclaration(ctx *parser.ConstructorDeclarationContext) {
	currentNode.AddMethod(currentMethod)
}

102
func (s *JavaIdentifierListener) EnterInterfaceBodyDeclaration(ctx *parser.InterfaceBodyDeclarationContext) {
P
Phodal Huang 已提交
103
	hasEnterClass = true
104 105
}

P
Phodal Huang 已提交
106
func (s *JavaIdentifierListener) EnterInterfaceMethodDeclaration(ctx *parser.InterfaceMethodDeclarationContext) {
P
Phodal HUANG 已提交
107
	startLine := ctx.GetStart().GetLine()
P
Phodal HUANG 已提交
108
	startLinePosition := ctx.GetStart().GetColumn()
P
Phodal HUANG 已提交
109
	stopLine := ctx.GetStop().GetLine()
P
Phodal HUANG 已提交
110
	stopLinePosition := ctx.GetStop().GetColumn()
P
Phodal HUANG 已提交
111 112
	name := ctx.IDENTIFIER().GetText()
	//XXX: find the start position of {, not public
P
Phodal HUANG 已提交
113 114
	typeType := ctx.TypeTypeOrVoid().GetText()

P
Phodal Huang 已提交
115
	if reflect.TypeOf(ctx.GetParent().GetParent().GetChild(0)).String() == "*parser.ModifierContext" {
P
Phodal Huang 已提交
116
		common_listener2.BuildAnnotationForMethod(ctx.GetParent().GetParent().GetChild(0).(*parser.ModifierContext), &currentMethod)
P
Phodal Huang 已提交
117 118
	}

P
Phodal Huang 已提交
119
	currentMethod = domain.JMethod{
P
Phodal Huang 已提交
120 121 122
		Name:              name,
		Type:              typeType,
		StartLine:         startLine,
P
Phodal Huang 已提交
123
		StartLinePosition: startLinePosition,
P
Phodal Huang 已提交
124 125 126
		StopLine:          stopLine,
		StopLinePosition:  stopLinePosition,
		Override:          isOverrideMethod,
P
Phodal Huang 已提交
127
		Annotations:       currentMethod.Annotations,
P
Phodal Huang 已提交
128
	}
P
Phodal Huang 已提交
129 130
}

131
func (s *JavaIdentifierListener) ExitInterfaceMethodDeclaration(ctx *parser.InterfaceMethodDeclarationContext) {
P
Phodal Huang 已提交
132
	currentNode.AddMethod(currentMethod)
P
Phodal Huang 已提交
133
	currentMethod = domain.NewJMethod()
P
Phodal HUANG 已提交
134 135
}

136 137
var isOverrideMethod = false

P
Phodal Huang 已提交
138
func (s *JavaIdentifierListener) EnterMethodDeclaration(ctx *parser.MethodDeclarationContext) {
P
Phodal Huang 已提交
139
	hasEnterClass = true
P
Phodal Huang 已提交
140

P
Phodal HUANG 已提交
141
	startLine := ctx.GetStart().GetLine()
P
Phodal HUANG 已提交
142
	startLinePosition := ctx.GetStart().GetColumn()
P
Phodal HUANG 已提交
143
	stopLine := ctx.GetStop().GetLine()
P
Phodal HUANG 已提交
144
	stopLinePosition := ctx.GetStop().GetColumn()
P
Phodal HUANG 已提交
145
	name := ctx.IDENTIFIER().GetText()
P
Phodal HUANG 已提交
146 147 148

	typeType := ctx.TypeTypeOrVoid().GetText()

P
Phodal Huang 已提交
149
	if reflect.TypeOf(ctx.GetParent().GetParent().GetChild(0)).String() == "*parser.ModifierContext" {
P
Phodal Huang 已提交
150
		common_listener2.BuildAnnotationForMethod(ctx.GetParent().GetParent().GetChild(0).(*parser.ModifierContext), &currentMethod)
P
Phodal Huang 已提交
151 152
	}

P
Phodal Huang 已提交
153
	currentMethod = domain.JMethod{
P
Phodal Huang 已提交
154 155 156
		Name:              name,
		Type:              typeType,
		StartLine:         startLine,
P
Phodal Huang 已提交
157
		StartLinePosition: startLinePosition,
P
Phodal Huang 已提交
158 159 160
		StopLine:          stopLine,
		StopLinePosition:  stopLinePosition,
		Override:          isOverrideMethod,
P
Phodal Huang 已提交
161
		Annotations:       currentMethod.Annotations,
P
Phodal Huang 已提交
162 163
	}

P
Phodal Huang 已提交
164 165 166
	if reflect.TypeOf(ctx.GetParent().GetParent()).String() == "*parser.ClassBodyDeclarationContext" {
		bodyCtx := ctx.GetParent().GetParent().(*parser.ClassBodyDeclarationContext)
		for _, modifier := range bodyCtx.AllModifier() {
P
Phodal Huang 已提交
167 168 169
			if !strings.Contains(modifier.GetText(), "@") {
				currentMethod.Modifiers = append(currentMethod.Modifiers, modifier.GetText())
			}
P
Phodal Huang 已提交
170 171 172
		}
	}

173 174 175
	isOverrideMethod = false
}

P
Phodal Huang 已提交
176
func (s *JavaIdentifierListener) ExitMethodDeclaration(ctx *parser.MethodDeclarationContext) {
P
Phodal Huang 已提交
177
	currentNode.AddMethod(currentMethod)
P
Phodal Huang 已提交
178
	currentMethod = domain.NewJMethod()
P
Phodal Huang 已提交
179 180
}

181 182 183 184 185
func (s *JavaIdentifierListener) EnterAnnotation(ctx *parser.AnnotationContext) {
	annotationName := ctx.QualifiedName().GetText()
	if annotationName == "Override" {
		isOverrideMethod = true
	}
186

P
Phodal Huang 已提交
187
	if !hasEnterClass {
P
Phodal Huang 已提交
188
		annotation := common_listener2.BuildAnnotation(ctx)
P
Phodal Huang 已提交
189
		currentNode.Annotations = append(currentNode.Annotations, annotation)
P
Phodal Huang 已提交
190 191 192
	}
}

P
Phodal Huang 已提交
193
func (s *JavaIdentifierListener) EnterInterfaceDeclaration(ctx *parser.InterfaceDeclarationContext) {
P
Phodal Huang 已提交
194
	hasEnterClass = true
P
Phodal Huang 已提交
195 196
	currentNode.ClassType = "Interface"
	currentNode.ClassName = ctx.IDENTIFIER().GetText()
P
Phodal HUANG 已提交
197 198
}

P
Phodal Huang 已提交
199 200 201 202 203
func (s *JavaIdentifierListener) EnterExpression(ctx *parser.ExpressionContext) {
	if reflect.TypeOf(ctx.GetParent()).String() == "*parser.StatementContext" {
		statementCtx := ctx.GetParent().(*parser.StatementContext)
		firstChild := statementCtx.GetChild(0).(antlr.ParseTree).GetText()
		if strings.ToLower(firstChild) == "return" {
P
Phodal Huang 已提交
204
			currentMethod.IsReturnNull = strings.Contains(ctx.GetText(), "null")
P
Phodal Huang 已提交
205 206 207 208
		}
	}
}

P
Phodal Huang 已提交
209
func (s *JavaIdentifierListener) GetNodes() []domain.JIdentifier {
P
Phodal Huang 已提交
210
	return nodes
P
Phodal HUANG 已提交
211
}