• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 package com.github.javaparser.generator.metamodel;
2 
3 import com.github.javaparser.ast.*;
4 import com.github.javaparser.ast.body.*;
5 import com.github.javaparser.ast.comments.BlockComment;
6 import com.github.javaparser.ast.comments.Comment;
7 import com.github.javaparser.ast.comments.JavadocComment;
8 import com.github.javaparser.ast.comments.LineComment;
9 import com.github.javaparser.ast.expr.*;
10 import com.github.javaparser.ast.modules.*;
11 import com.github.javaparser.ast.stmt.*;
12 import com.github.javaparser.ast.type.*;
13 import com.github.javaparser.printer.PrettyPrinter;
14 import com.github.javaparser.printer.PrettyPrinterConfiguration;
15 import com.github.javaparser.utils.SourceRoot;
16 
17 import java.io.IOException;
18 import java.lang.reflect.Field;
19 import java.nio.file.Path;
20 import java.nio.file.Paths;
21 import java.util.ArrayList;
22 import java.util.Comparator;
23 import java.util.List;
24 
25 import static com.github.javaparser.utils.Utils.decapitalize;
26 
27 public class MetaModelGenerator {
28     static final String BASE_NODE_META_MODEL = "BaseNodeMetaModel";
29     private static List<Class<? extends Node>> ALL_NODE_CLASSES = new ArrayList<Class<? extends Node>>() {{
30         /* Base classes go first, so we don't have to do any sorting to make sure
31          generated classes can refer to their base generated classes without
32          being afraid those are not initialized yet. */
33         add(Node.class);
34 
35         add(BodyDeclaration.class);
36         add(CallableDeclaration.class);
37         add(Statement.class);
38         add(Expression.class);
39         add(Type.class);
40 
41         add(AnnotationExpr.class);
42         add(TypeDeclaration.class);
43         add(ReferenceType.class);
44 
45         add(LiteralExpr.class);
46         add(LiteralStringValueExpr.class);
47         add(StringLiteralExpr.class);
48 
49         add(ModuleDeclaration.class);
50         add(ModuleStmt.class);
51 
52         //
53         add(ArrayCreationLevel.class);
54         add(CompilationUnit.class);
55         add(PackageDeclaration.class);
56 
57         add(AnnotationDeclaration.class);
58         add(AnnotationMemberDeclaration.class);
59         add(ClassOrInterfaceDeclaration.class);
60         add(ConstructorDeclaration.class);
61         add(EnumConstantDeclaration.class);
62         add(EnumDeclaration.class);
63         add(FieldDeclaration.class);
64         add(InitializerDeclaration.class);
65         add(MethodDeclaration.class);
66         add(Parameter.class);
67         add(ReceiverParameter.class);
68         add(VariableDeclarator.class);
69 
70         add(Comment.class);
71         add(BlockComment.class);
72         add(JavadocComment.class);
73         add(LineComment.class);
74 
75         add(ArrayAccessExpr.class);
76         add(ArrayCreationExpr.class);
77         add(ArrayInitializerExpr.class);
78         add(AssignExpr.class);
79         add(BinaryExpr.class);
80         add(BooleanLiteralExpr.class);
81         add(CastExpr.class);
82         add(CharLiteralExpr.class);
83         add(ClassExpr.class);
84         add(ConditionalExpr.class);
85         add(DoubleLiteralExpr.class);
86         add(EnclosedExpr.class);
87         add(FieldAccessExpr.class);
88         add(InstanceOfExpr.class);
89         add(IntegerLiteralExpr.class);
90         add(LambdaExpr.class);
91         add(LongLiteralExpr.class);
92         add(MarkerAnnotationExpr.class);
93         add(MemberValuePair.class);
94         add(MethodCallExpr.class);
95         add(MethodReferenceExpr.class);
96         add(NameExpr.class);
97         add(Name.class);
98         add(NormalAnnotationExpr.class);
99         add(NullLiteralExpr.class);
100         add(ObjectCreationExpr.class);
101         add(SimpleName.class);
102         add(SingleMemberAnnotationExpr.class);
103         add(SuperExpr.class);
104         add(ThisExpr.class);
105         add(TypeExpr.class);
106         add(UnaryExpr.class);
107         add(VariableDeclarationExpr.class);
108 
109         add(ImportDeclaration.class);
110 
111         add(AssertStmt.class);
112         add(BlockStmt.class);
113         add(BreakStmt.class);
114         add(CatchClause.class);
115         add(ContinueStmt.class);
116         add(DoStmt.class);
117         add(EmptyStmt.class);
118         add(ExplicitConstructorInvocationStmt.class);
119         add(ExpressionStmt.class);
120         add(ForeachStmt.class);
121         add(ForStmt.class);
122         add(IfStmt.class);
123         add(LabeledStmt.class);
124         add(ReturnStmt.class);
125         add(SwitchEntryStmt.class);
126         add(SwitchStmt.class);
127         add(SynchronizedStmt.class);
128         add(ThrowStmt.class);
129         add(TryStmt.class);
130         add(LocalClassDeclarationStmt.class);
131         add(WhileStmt.class);
132         add(UnparsableStmt.class);
133 
134         add(ArrayType.class);
135         add(ClassOrInterfaceType.class);
136         add(IntersectionType.class);
137         add(PrimitiveType.class);
138         add(TypeParameter.class);
139         add(UnionType.class);
140         add(UnknownType.class);
141         add(VoidType.class);
142         add(WildcardType.class);
143         add(VarType.class);
144 
145         add(ModuleRequiresStmt.class);
146         add(ModuleExportsStmt.class);
147         add(ModuleProvidesStmt.class);
148         add(ModuleUsesStmt.class);
149         add(ModuleOpensStmt.class);
150     }};
151 
152     static String METAMODEL_PACKAGE = "com.github.javaparser.metamodel";
153 
main(String[] args)154     public static void main(String[] args) throws IOException, NoSuchMethodException {
155         if (args.length != 1) {
156             throw new RuntimeException("Need 1 parameter: the JavaParser source checkout root directory.");
157         }
158         final Path root = Paths.get(args[0], "..", "javaparser-core", "src", "main", "java");
159         final SourceRoot sourceRoot = new SourceRoot(root);
160         sourceRoot.setPrinter(new PrettyPrinter(new PrettyPrinterConfiguration().setEndOfLineCharacter("\n"))::print);
161 
162         new MetaModelGenerator().run(sourceRoot);
163 
164         sourceRoot.saveAll();
165     }
166 
run(SourceRoot sourceRoot)167     private void run(SourceRoot sourceRoot) throws IOException, NoSuchMethodException {
168         final CompilationUnit javaParserMetaModel = sourceRoot.parse(METAMODEL_PACKAGE, "JavaParserMetaModel.java");
169 
170         generateNodeMetaModels(javaParserMetaModel, sourceRoot);
171     }
172 
generateNodeMetaModels(CompilationUnit javaParserMetaModelCu, SourceRoot sourceRoot)173     private void generateNodeMetaModels(CompilationUnit javaParserMetaModelCu, SourceRoot sourceRoot) throws NoSuchMethodException {
174         final ClassOrInterfaceDeclaration metaModelCoid = javaParserMetaModelCu.getClassByName("JavaParserMetaModel").get();
175         final NodeList<Statement> initializeNodeMetaModelsStatements = metaModelCoid.getMethodsByName("initializeNodeMetaModels").get(0).getBody().get().getStatements();
176         final NodeList<Statement> initializePropertyMetaModelsStatements = metaModelCoid.getMethodsByName("initializePropertyMetaModels").get(0).getBody().get().getStatements();
177         final NodeList<Statement> initializeConstructorParametersStatements = metaModelCoid.getMethodsByName("initializeConstructorParameters").get(0).getBody().get().getStatements();
178         initializeNodeMetaModelsStatements.clear();
179         initializePropertyMetaModelsStatements.clear();
180         initializeConstructorParametersStatements.clear();
181 
182         metaModelCoid.getFields().stream().filter(f -> f.getVariable(0).getNameAsString().endsWith("MetaModel")).forEach(Node::remove);
183         final NodeMetaModelGenerator nodeMetaModelGenerator = new NodeMetaModelGenerator();
184         for (Class<? extends Node> nodeClass : ALL_NODE_CLASSES) {
185             nodeMetaModelGenerator.generate(nodeClass, metaModelCoid, initializeNodeMetaModelsStatements, initializePropertyMetaModelsStatements, initializeConstructorParametersStatements, sourceRoot);
186         }
187 
188         initializeNodeMetaModelsStatements.sort(Comparator.comparing(Node::toString));
189     }
190 
isNode(Class<?> c)191     static boolean isNode(Class<?> c) {
192         return Node.class.isAssignableFrom(c);
193     }
194 
nodeMetaModelName(Class<?> c)195     static String nodeMetaModelName(Class<?> c) {
196         return c.getSimpleName() + "MetaModel";
197     }
198 
propertyMetaModelFieldName(Field field)199     static String propertyMetaModelFieldName(Field field) {
200         return field.getName() + "PropertyMetaModel";
201     }
202 
nodeMetaModelFieldName(Class<?> nodeClass)203     static String nodeMetaModelFieldName(Class<?> nodeClass) {
204         return decapitalize(nodeMetaModelName(nodeClass));
205     }
206 
207 }
208