Skip to content

Commit 07b8a46

Browse files
Add "Find Usages" support
1 parent 6645bda commit 07b8a46

File tree

19 files changed

+333
-131
lines changed

19 files changed

+333
-131
lines changed

build.gradle

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -45,12 +45,12 @@ intellij {
4545
// plugins 'properties'
4646
downloadSources = false
4747
publish {
48-
username = project.hasProperty('jetbrainsUser') \
49-
? project.property('jetbrainsUser') \
50-
: System.getenv('JETBRAINS_USER')
51-
password = project.hasProperty('jetbrainsPassword') \
52-
? project.property('jetbrainsPassword') \
53-
: System.getenv('JETBRAINS_PASSWORD')
48+
username = project.hasProperty('jetbrainsUser') \
49+
? project.property('jetbrainsUser') \
50+
: System.getenv('JETBRAINS_USER')
51+
password = project.hasProperty('jetbrainsPassword') \
52+
? project.property('jetbrainsPassword') \
53+
: System.getenv('JETBRAINS_PASSWORD')
5454
pluginId = '8277'
5555
}
5656
}
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
package io.protostuff.jetbrains.plugin;
2+
3+
import com.intellij.lang.cacheBuilder.DefaultWordsScanner;
4+
import com.intellij.lang.cacheBuilder.WordsScanner;
5+
import com.intellij.lang.findUsages.FindUsagesProvider;
6+
import com.intellij.psi.PsiElement;
7+
import com.intellij.psi.PsiNamedElement;
8+
import com.intellij.psi.tree.TokenSet;
9+
import io.protostuff.compiler.parser.ProtoLexer;
10+
import io.protostuff.jetbrains.plugin.psi.EnumNode;
11+
import io.protostuff.jetbrains.plugin.psi.MessageNode;
12+
import io.protostuff.jetbrains.plugin.psi.UserType;
13+
import org.antlr.jetbrains.adapter.lexer.PSIElementTypeFactory;
14+
import org.jetbrains.annotations.NotNull;
15+
import org.jetbrains.annotations.Nullable;
16+
17+
/**
18+
* @author Kostiantyn Shchepanovskyi
19+
*/
20+
public class ProtoFindUsagesProvider implements FindUsagesProvider {
21+
22+
@Nullable
23+
@Override
24+
public WordsScanner getWordsScanner() {
25+
26+
return new DefaultWordsScanner(new ProtoLexerAdapter(),
27+
ProtoParserDefinition.IDENTIFIER_TOKEN_SET,
28+
ProtoParserDefinition.COMMENT_TOKEN_SET,
29+
ProtoParserDefinition.LITERAL_TOKEN_SET);
30+
}
31+
32+
@Override
33+
public boolean canFindUsagesFor(@NotNull PsiElement psiElement) {
34+
return psiElement instanceof UserType;
35+
}
36+
37+
@Nullable
38+
@Override
39+
public String getHelpId(@NotNull PsiElement psiElement) {
40+
return null;
41+
}
42+
43+
@NotNull
44+
@Override
45+
public String getType(@NotNull PsiElement element) {
46+
if (element instanceof MessageNode) {
47+
return "message";
48+
}
49+
if (element instanceof EnumNode) {
50+
return "enum";
51+
}
52+
return "";
53+
}
54+
55+
@NotNull
56+
@Override
57+
public String getDescriptiveName(@NotNull PsiElement element) {
58+
if (element instanceof UserType) {
59+
UserType type = (UserType) element;
60+
return type.getFullName();
61+
}
62+
return "";
63+
}
64+
65+
@NotNull
66+
@Override
67+
public String getNodeText(@NotNull PsiElement element, boolean useFullName) {
68+
if (element instanceof UserType) {
69+
UserType type = (UserType) element;
70+
if (useFullName) {
71+
return type.getFullName();
72+
}
73+
//noinspection ConstantConditions
74+
return type.getName();
75+
}
76+
return "";
77+
}
78+
}
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
package io.protostuff.jetbrains.plugin;
2+
3+
import com.intellij.lang.Language;
4+
import io.protostuff.compiler.parser.ProtoLexer;
5+
import org.antlr.jetbrains.adapter.lexer.ANTLRLexerAdaptor;
6+
import org.antlr.v4.runtime.Lexer;
7+
8+
/**
9+
* @author Kostiantyn Shchepanovskyi
10+
*/
11+
public class ProtoLexerAdapter extends ANTLRLexerAdaptor {
12+
13+
public ProtoLexerAdapter() {
14+
super(ProtoLanguage.INSTANCE, new ProtoLexer(null));
15+
}
16+
}

src/main/java/io/protostuff/jetbrains/plugin/ProtoParserDefinition.java

Lines changed: 157 additions & 88 deletions
Original file line numberDiff line numberDiff line change
@@ -33,109 +33,178 @@
3333
*/
3434
public class ProtoParserDefinition implements ParserDefinition {
3535

36-
public static final TokenIElementType ID;
37-
public static final TokenSet KEYWORDS;
36+
static {
37+
PSIElementTypeFactory.defineLanguageIElementTypes(ProtoLanguage.INSTANCE,
38+
ProtoParser.tokenNames, ProtoParser.ruleNames);
39+
}
3840

39-
// tokens
41+
private static final List<TokenIElementType> TOKEN_TYPES = PSIElementTypeFactory.getTokenIElementTypes(ProtoLanguage.INSTANCE);
42+
private static final List<RuleIElementType> RULE_TYPES = PSIElementTypeFactory.getRuleIElementTypes(ProtoLanguage.INSTANCE);
4043

41-
public static final TokenIElementType LCURLY;
42-
public static final TokenIElementType RCURLY;
43-
public static final TokenIElementType LPAREN;
44-
public static final TokenIElementType RPAREN;
45-
public static final TokenIElementType LSQUARE;
46-
public static final TokenIElementType RSQUARE;
47-
public static final TokenIElementType LT;
48-
public static final TokenIElementType GT;
49-
public static final TokenIElementType ASSIGN;
44+
public static final TokenIElementType ID = TOKEN_TYPES.get(ProtoLexer.IDENT);
5045

51-
// Rules
52-
public static final IElementType R_TYPE_REFERENCE;
53-
public static final IElementType R_NAME;
54-
public static final IElementType R_FIELD_MODIFIER;
55-
private static final IFileElementType FILE;
56-
private static final TokenSet COMMENTS;
57-
public static final TokenSet WHITESPACE;
46+
public static final TokenSet KEYWORDS = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE,
47+
ProtoLexer.PACKAGE,
48+
ProtoLexer.SYNTAX,
49+
ProtoLexer.IMPORT,
50+
ProtoLexer.PUBLIC,
51+
ProtoLexer.OPTION,
52+
ProtoLexer.MESSAGE,
53+
ProtoLexer.GROUP,
54+
ProtoLexer.OPTIONAL,
55+
ProtoLexer.REQUIRED,
56+
ProtoLexer.REPEATED,
57+
ProtoLexer.ONEOF,
58+
ProtoLexer.EXTEND,
59+
ProtoLexer.EXTENSIONS,
60+
ProtoLexer.RESERVED,
61+
ProtoLexer.TO,
62+
ProtoLexer.MAX,
63+
ProtoLexer.ENUM,
64+
ProtoLexer.SERVICE,
65+
ProtoLexer.RPC,
66+
ProtoLexer.STREAM,
67+
ProtoLexer.RETURNS,
68+
ProtoLexer.MAP,
69+
ProtoLexer.BOOLEAN_VALUE,
70+
ProtoLexer.DOUBLE,
71+
ProtoLexer.FLOAT,
72+
ProtoLexer.INT32,
73+
ProtoLexer.INT64,
74+
ProtoLexer.UINT32,
75+
ProtoLexer.UINT64,
76+
ProtoLexer.SINT32,
77+
ProtoLexer.SINT64,
78+
ProtoLexer.FIXED32,
79+
ProtoLexer.FIXED64,
80+
ProtoLexer.SFIXED32,
81+
ProtoLexer.SFIXED64,
82+
ProtoLexer.BOOL,
83+
ProtoLexer.STRING,
84+
ProtoLexer.BYTES
85+
);
5886

59-
private static final TokenSet STRING;
87+
// keywords also can be identifiers
88+
public static final TokenSet IDENTIFIER_TOKEN_SET = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE,
89+
ProtoLexer.IDENT,
90+
ProtoLexer.PACKAGE,
91+
ProtoLexer.SYNTAX,
92+
ProtoLexer.IMPORT,
93+
ProtoLexer.PUBLIC,
94+
ProtoLexer.OPTION,
95+
ProtoLexer.MESSAGE,
96+
ProtoLexer.GROUP,
97+
ProtoLexer.OPTIONAL,
98+
ProtoLexer.REQUIRED,
99+
ProtoLexer.REPEATED,
100+
ProtoLexer.ONEOF,
101+
ProtoLexer.EXTEND,
102+
ProtoLexer.EXTENSIONS,
103+
ProtoLexer.RESERVED,
104+
ProtoLexer.TO,
105+
ProtoLexer.MAX,
106+
ProtoLexer.ENUM,
107+
ProtoLexer.SERVICE,
108+
ProtoLexer.RPC,
109+
ProtoLexer.STREAM,
110+
ProtoLexer.RETURNS,
111+
ProtoLexer.MAP,
112+
ProtoLexer.BOOLEAN_VALUE,
113+
ProtoLexer.DOUBLE,
114+
ProtoLexer.FLOAT,
115+
ProtoLexer.INT32,
116+
ProtoLexer.INT64,
117+
ProtoLexer.UINT32,
118+
ProtoLexer.UINT64,
119+
ProtoLexer.SINT32,
120+
ProtoLexer.SINT64,
121+
ProtoLexer.FIXED32,
122+
ProtoLexer.FIXED64,
123+
ProtoLexer.SFIXED32,
124+
ProtoLexer.SFIXED64,
125+
ProtoLexer.BOOL,
126+
ProtoLexer.STRING,
127+
ProtoLexer.BYTES
128+
);
60129

61-
private static List<TokenIElementType> tokenTypes;
62-
private static List<RuleIElementType> ruleTypes;
63-
64-
static {
65-
PSIElementTypeFactory.defineLanguageIElementTypes(ProtoLanguage.INSTANCE,
66-
ProtoParser.tokenNames, ProtoParser.ruleNames);
67-
tokenTypes = PSIElementTypeFactory.getTokenIElementTypes(ProtoLanguage.INSTANCE);
68-
ID = tokenTypes.get(ProtoLexer.IDENT);
69-
FILE = new IFileElementType(ProtoLanguage.INSTANCE);
70-
COMMENTS = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE, COMMENT, LINE_COMMENT);
71-
WHITESPACE = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE, WS, NL);
72-
STRING = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE, STRING_VALUE);
130+
public static final TokenSet COMMENT_TOKEN_SET = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE,
131+
ProtoLexer.COMMENT,
132+
ProtoLexer.LINE_COMMENT
133+
);
73134

135+
public static final TokenSet LITERAL_TOKEN_SET = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE,
136+
ProtoLexer.STRING_VALUE,
137+
ProtoLexer.FLOAT_VALUE,
138+
ProtoLexer.INTEGER_VALUE,
139+
ProtoLexer.IDENT,
140+
ProtoLexer.PACKAGE,
141+
ProtoLexer.SYNTAX,
142+
ProtoLexer.IMPORT,
143+
ProtoLexer.PUBLIC,
144+
ProtoLexer.OPTION,
145+
ProtoLexer.MESSAGE,
146+
ProtoLexer.GROUP,
147+
ProtoLexer.OPTIONAL,
148+
ProtoLexer.REQUIRED,
149+
ProtoLexer.REPEATED,
150+
ProtoLexer.ONEOF,
151+
ProtoLexer.EXTEND,
152+
ProtoLexer.EXTENSIONS,
153+
ProtoLexer.RESERVED,
154+
ProtoLexer.TO,
155+
ProtoLexer.MAX,
156+
ProtoLexer.ENUM,
157+
ProtoLexer.SERVICE,
158+
ProtoLexer.RPC,
159+
ProtoLexer.STREAM,
160+
ProtoLexer.RETURNS,
161+
ProtoLexer.MAP,
162+
ProtoLexer.BOOLEAN_VALUE,
163+
ProtoLexer.DOUBLE,
164+
ProtoLexer.FLOAT,
165+
ProtoLexer.INT32,
166+
ProtoLexer.INT64,
167+
ProtoLexer.UINT32,
168+
ProtoLexer.UINT64,
169+
ProtoLexer.SINT32,
170+
ProtoLexer.SINT64,
171+
ProtoLexer.FIXED32,
172+
ProtoLexer.FIXED64,
173+
ProtoLexer.SFIXED32,
174+
ProtoLexer.SFIXED64,
175+
ProtoLexer.BOOL,
176+
ProtoLexer.STRING,
177+
ProtoLexer.BYTES
178+
);
74179

75-
KEYWORDS = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE,
76-
ProtoLexer.PACKAGE,
77-
ProtoLexer.SYNTAX,
78-
ProtoLexer.IMPORT,
79-
ProtoLexer.PUBLIC,
80-
ProtoLexer.OPTION,
81-
ProtoLexer.MESSAGE,
82-
ProtoLexer.GROUP,
83-
ProtoLexer.OPTIONAL,
84-
ProtoLexer.REQUIRED,
85-
ProtoLexer.REPEATED,
86-
ProtoLexer.ONEOF,
87-
ProtoLexer.EXTEND,
88-
ProtoLexer.EXTENSIONS,
89-
ProtoLexer.RESERVED,
90-
ProtoLexer.TO,
91-
ProtoLexer.MAX,
92-
ProtoLexer.ENUM,
93-
ProtoLexer.SERVICE,
94-
ProtoLexer.RPC,
95-
ProtoLexer.STREAM,
96-
ProtoLexer.RETURNS,
97-
ProtoLexer.MAP,
98-
ProtoLexer.BOOLEAN_VALUE,
99-
ProtoLexer.DOUBLE,
100-
ProtoLexer.FLOAT,
101-
ProtoLexer.INT32,
102-
ProtoLexer.INT64,
103-
ProtoLexer.UINT32,
104-
ProtoLexer.UINT64,
105-
ProtoLexer.SINT32,
106-
ProtoLexer.SINT64,
107-
ProtoLexer.FIXED32,
108-
ProtoLexer.FIXED64,
109-
ProtoLexer.SFIXED32,
110-
ProtoLexer.SFIXED64,
111-
ProtoLexer.BOOL,
112-
ProtoLexer.STRING,
113-
ProtoLexer.BYTES
114-
);
180+
// tokens
115181

116-
ruleTypes = PSIElementTypeFactory.getRuleIElementTypes(ProtoLanguage.INSTANCE);
182+
public static final TokenIElementType LCURLY = TOKEN_TYPES.get(ProtoLexer.LCURLY);
183+
public static final TokenIElementType RCURLY = TOKEN_TYPES.get(ProtoLexer.RCURLY);
184+
public static final TokenIElementType LPAREN = TOKEN_TYPES.get(ProtoLexer.LPAREN);
185+
public static final TokenIElementType RPAREN = TOKEN_TYPES.get(ProtoLexer.RPAREN);
186+
public static final TokenIElementType LSQUARE = TOKEN_TYPES.get(ProtoLexer.LSQUARE);
187+
public static final TokenIElementType RSQUARE = TOKEN_TYPES.get(ProtoLexer.RSQUARE);
188+
public static final TokenIElementType LT = TOKEN_TYPES.get(ProtoLexer.LT);
189+
public static final TokenIElementType GT = TOKEN_TYPES.get(ProtoLexer.GT);
190+
public static final TokenIElementType ASSIGN = TOKEN_TYPES.get(ProtoLexer.ASSIGN);
117191

118-
R_TYPE_REFERENCE = ruleTypes.get(ProtoParser.RULE_typeReference);
119-
R_NAME = ruleTypes.get(ProtoParser.RULE_ident);
120-
R_FIELD_MODIFIER = ruleTypes.get(ProtoParser.RULE_fieldModifier);
192+
// Rules
193+
public static final IElementType R_TYPE_REFERENCE = RULE_TYPES.get(ProtoParser.RULE_typeReference);
194+
public static final IElementType R_NAME = RULE_TYPES.get(ProtoParser.RULE_ident);
195+
public static final IElementType R_FIELD_MODIFIER = RULE_TYPES.get(ProtoParser.RULE_fieldModifier);
196+
private static final IFileElementType FILE = new IFileElementType(ProtoLanguage.INSTANCE);
197+
private static final TokenSet COMMENTS = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE, COMMENT, LINE_COMMENT);
198+
public static final TokenSet WHITESPACE = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE, WS, NL);
121199

122-
LCURLY = tokenTypes.get(ProtoLexer.LCURLY);
123-
RCURLY = tokenTypes.get(ProtoLexer.RCURLY);
124-
LPAREN = tokenTypes.get(ProtoLexer.LPAREN);
125-
RPAREN = tokenTypes.get(ProtoLexer.RPAREN);
126-
LSQUARE = tokenTypes.get(ProtoLexer.LSQUARE);
127-
RSQUARE = tokenTypes.get(ProtoLexer.RSQUARE);
128-
ASSIGN = tokenTypes.get(ProtoLexer.ASSIGN);
129-
LT = tokenTypes.get(ProtoLexer.LT);
130-
GT = tokenTypes.get(ProtoLexer.GT);
131-
}
200+
private static final TokenSet STRING = PSIElementTypeFactory.createTokenSet(ProtoLanguage.INSTANCE, STRING_VALUE);
132201

133202
public static TokenIElementType token(int token) {
134-
return tokenTypes.get(token);
203+
return TOKEN_TYPES.get(token);
135204
}
136205

137206
public static RuleIElementType rule(int rule) {
138-
return ruleTypes.get(rule);
207+
return RULE_TYPES.get(rule);
139208
}
140209

141210
@NotNull

0 commit comments

Comments
 (0)