Skip to content
This repository was archived by the owner on Dec 4, 2025. It is now read-only.

Commit 985db45

Browse files
committed
refactor: ♻️ enhance IJavadocDocTemplate with generics for method documentation
Refactored the `IJavadocDocTemplate` interface to support generics, improving flexibility in handling Java method documentation. This change includes the removal of deprecated templates and the addition of new methods to better support RPC documentation generation. BREAKING CHANGE: Existing implementations of `IJavadocDocTemplate` and `IDocBuildTemplate` need to be updated to accommodate the new method signatures and class structures.
1 parent fc7b8fb commit 985db45

File tree

5 files changed

+110
-102
lines changed

5 files changed

+110
-102
lines changed

src/main/java/com/ly/doc/template/GRpcDocBuildTemplate.java

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,23 @@
1+
/*
2+
* Copyright (C) 2018-2024 smart-doc
3+
*
4+
* Licensed to the Apache Software Foundation (ASF) under one
5+
* or more contributor license agreements. See the NOTICE file
6+
* distributed with this work for additional information
7+
* regarding copyright ownership. The ASF licenses this file
8+
* to you under the Apache License, Version 2.0 (the
9+
* "License"); you may not use this file except in compliance
10+
* with the License. You may obtain a copy of the License at
11+
*
12+
* http://www.apache.org/licenses/LICENSE-2.0
13+
*
14+
* Unless required by applicable law or agreed to in writing,
15+
* software distributed under the License is distributed on an
16+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17+
* KIND, either express or implied. See the License for the
18+
* specific language governing permissions and limitations
19+
* under the License.
20+
*/
121
package com.ly.doc.template;
222

323
import com.google.gson.Gson;
@@ -36,8 +56,9 @@
3656
* gRPC Doc build template.
3757
*
3858
* @author linwumingshi
59+
* @since 3.0.7
3960
*/
40-
public class GRpcDocBuildTemplate implements IDocBuildTemplate<GrpcApiDoc>, IRpcDocTemplate {
61+
public class GRpcDocBuildTemplate implements IDocBuildTemplate<GrpcApiDoc>, IJavadocDocTemplate<GrpcJavaMethod> {
4162

4263
/**
4364
* Logger for the class.
@@ -69,6 +90,11 @@ public boolean addMethodModifiers() {
6990
return false;
7091
}
7192

93+
@Override
94+
public GrpcJavaMethod createEmptyJavadocJavaMethod() {
95+
return new GrpcJavaMethod();
96+
}
97+
7298
@Override
7399
public boolean ignoreReturnObject(String typeName, List<String> ignoreParams) {
74100
return false;

src/main/java/com/ly/doc/template/IJavadocDocTemplate.java

Lines changed: 62 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -39,25 +39,37 @@
3939
import static com.ly.doc.constants.DocTags.DEPRECATED;
4040
import static com.ly.doc.constants.DocTags.IGNORE;
4141

42-
public interface IJavadocDocTemplate extends IBaseDocBuildTemplate {
42+
/**
43+
* java doc template
44+
*
45+
* @param <T> extends JavadocJavaMethod
46+
* @author shalousun
47+
* @since 3.0.5
48+
*/
49+
public interface IJavadocDocTemplate<T extends JavadocJavaMethod> extends IBaseDocBuildTemplate {
4350

4451
/**
4552
* Add method modifiers
4653
* @return boolean
4754
*/
4855
boolean addMethodModifiers();
4956

57+
/**
58+
* Create empty JavadocJavaMethod.
59+
* @return empty JavadocJavaMethod
60+
*/
61+
T createEmptyJavadocJavaMethod();
62+
5063
/**
5164
* Convert JavaMethod to JavadocJavaMethod
5265
* @param apiConfig ApiConfig
5366
* @param method JavaMethod
5467
* @param actualTypesMap Map
5568
* @return JavadocJavaMethod
5669
*/
57-
default JavadocJavaMethod convertToJavadocJavaMethod(ApiConfig apiConfig, JavaMethod method,
58-
Map<String, JavaType> actualTypesMap) {
70+
default T convertToJavadocJavaMethod(ApiConfig apiConfig, JavaMethod method, Map<String, JavaType> actualTypesMap) {
5971
JavaClass cls = method.getDeclaringClass();
60-
JavadocJavaMethod javadocJavaMethod = new JavadocJavaMethod();
72+
T javadocJavaMethod = this.createEmptyJavadocJavaMethod();
6173
javadocJavaMethod.setJavaMethod(method);
6274
javadocJavaMethod.setName(method.getName());
6375
javadocJavaMethod.setActualTypesMap(actualTypesMap);
@@ -108,7 +120,7 @@ default String methodDefinition(JavaMethod method, Map<String, JavaType> actualT
108120
// append method modifiers
109121
method.getModifiers().forEach(item -> methodBuilder.append(item).append(" "));
110122
}
111-
String returnType = getMethodReturnType(method, actualTypesMap);
123+
String returnType = this.getMethodReturnType(method, actualTypesMap);
112124
// append method return type
113125
methodBuilder.append(returnType).append(" ");
114126
List<String> params = new ArrayList<>();
@@ -122,47 +134,54 @@ default String methodDefinition(JavaMethod method, Map<String, JavaType> actualT
122134
}
123135

124136
/**
125-
* Get parent class methods
126-
* @param apiConfig ApiConfig
137+
* Processes methods of a given class and its parent or interfaces.
127138
* @param cls JavaClass
128-
* @return List
139+
* @param methodProcessor Function to process methods from a class
140+
* @return List of documented Java methods
129141
*/
130-
default List<? extends JavadocJavaMethod> getParentsClassMethods(ApiConfig apiConfig, JavaClass cls) {
131-
List<JavadocJavaMethod> docJavaMethods = new ArrayList<>();
132-
JavaClass parentClass = cls.getSuperJavaClass();
133-
// if parent class is not null and not Object
134-
if (Objects.nonNull(parentClass) && !JavaTypeConstants.OBJECT_SIMPLE_NAME.equals(parentClass.getSimpleName())) {
135-
Map<String, JavaType> actualTypesMap = JavaClassUtil.getActualTypesMap(parentClass);
136-
List<JavaMethod> parentMethodList = parentClass.getMethods();
137-
for (JavaMethod method : parentMethodList) {
138-
docJavaMethods.add(this.convertToJavadocJavaMethod(apiConfig, method, actualTypesMap));
142+
default List<T> processClassHierarchy(JavaClass cls, Function<JavaClass, List<T>> methodProcessor) {
143+
List<T> docJavaMethods = new ArrayList<>();
144+
Set<JavaClass> classesToProcess = new LinkedHashSet<>();
145+
classesToProcess.add(cls);
146+
147+
while (!classesToProcess.isEmpty()) {
148+
JavaClass currentClass = classesToProcess.iterator().next();
149+
classesToProcess.remove(currentClass);
150+
151+
// Process methods
152+
docJavaMethods.addAll(methodProcessor.apply(currentClass));
153+
154+
// Add parent class if not Object
155+
JavaClass parentClass = currentClass.getSuperJavaClass();
156+
if (Objects.nonNull(parentClass)
157+
&& !JavaTypeConstants.OBJECT_SIMPLE_NAME.equals(parentClass.getSimpleName())) {
158+
classesToProcess.add(parentClass);
139159
}
140-
// add interface methods
141-
docJavaMethods.addAll(this.getInterfaceMethods(apiConfig, parentClass));
142-
// add parent class methods
143-
docJavaMethods.addAll(this.getParentsClassMethods(apiConfig, parentClass));
160+
161+
// Add interfaces
162+
classesToProcess.addAll(currentClass.getInterfaces());
144163
}
164+
145165
return docJavaMethods;
146166
}
147167

148168
/**
149-
* Get interface methods
169+
* Get parent class and interface methods
150170
* @param apiConfig ApiConfig
151171
* @param cls JavaClass
152172
* @return List
153173
*/
154-
default List<? extends JavadocJavaMethod> getInterfaceMethods(ApiConfig apiConfig, JavaClass cls) {
155-
List<JavadocJavaMethod> docJavaMethods = new ArrayList<>();
156-
for (JavaClass javaInterface : cls.getInterfaces()) {
157-
Map<String, JavaType> actualTypesMap = JavaClassUtil.getActualTypesMap(javaInterface);
158-
List<JavaMethod> interfaceMethodList = javaInterface.getMethods();
159-
for (JavaMethod method : interfaceMethodList) {
174+
default List<T> getParentsClassAndInterfaceMethods(ApiConfig apiConfig, JavaClass cls) {
175+
return this.processClassHierarchy(cls, currentClass -> {
176+
List<T> docJavaMethods = new ArrayList<>();
177+
Map<String, JavaType> actualTypesMap = JavaClassUtil.getActualTypesMap(currentClass);
178+
List<JavaMethod> methodList = currentClass.getMethods();
179+
for (JavaMethod method : methodList) {
160180
docJavaMethods.add(this.convertToJavadocJavaMethod(apiConfig, method, actualTypesMap));
161181
}
162-
// add interface methods
163-
docJavaMethods.addAll(this.getInterfaceMethods(apiConfig, javaInterface));
164-
}
165-
return docJavaMethods;
182+
return docJavaMethods;
183+
});
184+
166185
}
167186

168187
/**
@@ -301,11 +320,11 @@ else if (javaClass.isEnum()) {
301320
* @return A list containing documented methods represented as JavadocJavaMethod
302321
* objects.
303322
*/
304-
default List<? extends JavadocJavaMethod> buildServiceMethod(final JavaClass cls, ApiConfig apiConfig,
323+
default List<T> buildServiceMethod(final JavaClass cls, ApiConfig apiConfig,
305324
ProjectDocConfigBuilder projectBuilder) {
306325
String clsCanonicalName = cls.getCanonicalName();
307326
List<JavaMethod> methods = cls.getMethods();
308-
List<JavadocJavaMethod> methodDocList = new ArrayList<>(methods.size());
327+
List<T> methodDocList = new ArrayList<>(methods.size());
309328

310329
Set<String> filterMethods = DocUtil.findFilterMethods(clsCanonicalName);
311330
boolean needAllMethods = filterMethods.contains(DocGlobalConstants.DEFAULT_FILTER_METHOD);
@@ -322,21 +341,19 @@ default List<? extends JavadocJavaMethod> buildServiceMethod(final JavaClass cls
322341
"Unable to find comment for method " + method.getName() + " in " + cls.getCanonicalName());
323342
}
324343
if (needAllMethods || filterMethods.contains(method.getName())) {
325-
JavadocJavaMethod apiMethodDoc = this.convertToJavadocJavaMethod(apiConfig, method, null);
344+
T apiMethodDoc = this.convertToJavadocJavaMethod(apiConfig, method, null);
326345
methodDocList.add(apiMethodDoc);
327346
}
328347

329348
}
330-
// Add parent class methods
331-
methodDocList.addAll(this.getParentsClassMethods(apiConfig, cls));
332-
// Add interface methods
333-
methodDocList.addAll(this.getInterfaceMethods(apiConfig, cls));
349+
// Add parent class And interface methods
350+
methodDocList.addAll(this.getParentsClassAndInterfaceMethods(apiConfig, cls));
334351

335-
Map<JavadocJavaMethod, List<ApiParam>> methodRequestParams = new HashMap<>(16);
336-
Map<JavadocJavaMethod, List<ApiParam>> methodResponseParams = new HashMap<>(16);
352+
Map<T, List<ApiParam>> methodRequestParams = new HashMap<>(16);
353+
Map<T, List<ApiParam>> methodResponseParams = new HashMap<>(16);
337354

338355
// Construct the method map
339-
Map<String, JavadocJavaMethod> methodMap = methodDocList.stream().collect(Collectors.toMap(method -> {
356+
Map<String, T> methodMap = methodDocList.stream().collect(Collectors.toMap(method -> {
340357
// Build request params
341358
List<ApiParam> requestParams = this.requestParams(method.getJavaMethod(), projectBuilder,
342359
new AtomicInteger(0), method.getActualTypesMap());
@@ -357,8 +374,8 @@ default List<? extends JavadocJavaMethod> buildServiceMethod(final JavaClass cls
357374
Function.identity(), this::mergeJavadocMethods, LinkedHashMap::new));
358375

359376
int methodOrder = 0;
360-
List<JavadocJavaMethod> javadocJavaMethods = new ArrayList<>(methodMap.values().size());
361-
for (JavadocJavaMethod method : methodMap.values()) {
377+
List<T> javadocJavaMethods = new ArrayList<>(methodMap.values().size());
378+
for (T method : methodMap.values()) {
362379
methodOrder++;
363380
method.setOrder(methodOrder);
364381
String methodUid = DocUtil.generateId(clsCanonicalName + method.getName() + methodOrder);
@@ -389,7 +406,7 @@ default List<? extends JavadocJavaMethod> buildServiceMethod(final JavaClass cls
389406
* @return The merged JavadocJavaMethod object, with details filled in from the
390407
* replacement method if necessary.
391408
*/
392-
default JavadocJavaMethod mergeJavadocMethods(JavadocJavaMethod existing, JavadocJavaMethod replacement) {
409+
default T mergeJavadocMethods(T existing, T replacement) {
393410
// if existing info is empty and replacement info has desc,replace the info
394411
if (StringUtil.isEmpty(existing.getDesc()) && StringUtil.isNotEmpty(replacement.getDesc())) {
395412
existing.setDesc(replacement.getDesc());

src/main/java/com/ly/doc/template/IRpcDocTemplate.java

Lines changed: 0 additions & 28 deletions
This file was deleted.

src/main/java/com/ly/doc/template/JavadocDocBuildTemplate.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,11 @@ public boolean addMethodModifiers() {
6565
return true;
6666
}
6767

68+
@Override
69+
public JavadocJavaMethod createEmptyJavadocJavaMethod() {
70+
return new JavadocJavaMethod();
71+
}
72+
6873
@Override
6974
@SuppressWarnings("unchecked")
7075
public ApiSchema<JavadocApiDoc> renderApi(ProjectDocConfigBuilder projectBuilder,

src/main/java/com/ly/doc/template/RpcDocBuildTemplate.java

Lines changed: 16 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -24,14 +24,20 @@
2424
import com.ly.doc.constants.DocTags;
2525
import com.ly.doc.constants.DubboAnnotationConstants;
2626
import com.ly.doc.constants.FrameworkEnum;
27-
import com.ly.doc.model.*;
27+
import com.ly.doc.model.ApiConfig;
28+
import com.ly.doc.model.ApiSchema;
29+
import com.ly.doc.model.RpcJavaMethod;
30+
import com.ly.doc.model.WebSocketDoc;
2831
import com.ly.doc.model.annotation.FrameworkAnnotations;
2932
import com.ly.doc.model.rpc.RpcApiDoc;
3033
import com.ly.doc.utils.DocUtil;
3134
import com.ly.doc.utils.JavaClassUtil;
3235
import com.power.common.util.StringUtil;
3336
import com.power.common.util.ValidateUtil;
34-
import com.thoughtworks.qdox.model.*;
37+
import com.thoughtworks.qdox.model.DocletTag;
38+
import com.thoughtworks.qdox.model.JavaAnnotation;
39+
import com.thoughtworks.qdox.model.JavaClass;
40+
import com.thoughtworks.qdox.model.JavaType;
3541
import com.thoughtworks.qdox.model.expression.AnnotationValue;
3642

3743
import java.util.*;
@@ -43,8 +49,8 @@
4349
*
4450
* @author yu 2020/1/29.
4551
*/
46-
public class RpcDocBuildTemplate
47-
implements IDocBuildTemplate<RpcApiDoc>, IWebSocketDocBuildTemplate<WebSocketDoc>, IRpcDocTemplate {
52+
public class RpcDocBuildTemplate implements IDocBuildTemplate<RpcApiDoc>, IWebSocketDocBuildTemplate<WebSocketDoc>,
53+
IJavadocDocTemplate<RpcJavaMethod> {
4854

4955
/**
5056
* api index
@@ -62,7 +68,11 @@ public boolean addMethodModifiers() {
6268
}
6369

6470
@Override
65-
@SuppressWarnings("unchecked")
71+
public RpcJavaMethod createEmptyJavadocJavaMethod() {
72+
return new RpcJavaMethod();
73+
}
74+
75+
@Override
6676
public ApiSchema<RpcApiDoc> renderApi(ProjectDocConfigBuilder projectBuilder,
6777
Collection<JavaClass> candidateClasses) {
6878
ApiConfig apiConfig = projectBuilder.getApiConfig();
@@ -81,8 +91,7 @@ public ApiSchema<RpcApiDoc> renderApi(ProjectDocConfigBuilder projectBuilder,
8191
setCustomOrder = true;
8292
maxOrder = Math.max(maxOrder, order);
8393
}
84-
List<RpcJavaMethod> apiMethodDocs = (List<RpcJavaMethod>) this.buildServiceMethod(cls, apiConfig,
85-
projectBuilder);
94+
List<RpcJavaMethod> apiMethodDocs = this.buildServiceMethod(cls, apiConfig, projectBuilder);
8695
this.handleJavaApiDoc(cls, apiDocList, apiMethodDocs, order, projectBuilder);
8796
}
8897
ApiSchema<RpcApiDoc> apiSchema = new ApiSchema<>();
@@ -222,25 +231,4 @@ private void handleJavaApiDoc(JavaClass cls, List<RpcApiDoc> apiDocList, List<Rp
222231
apiDocList.add(apiDoc);
223232
}
224233

225-
@Override
226-
public JavadocJavaMethod convertToJavadocJavaMethod(ApiConfig apiConfig, JavaMethod method,
227-
Map<String, JavaType> actualTypesMap) {
228-
JavadocJavaMethod javaMethod = IRpcDocTemplate.super.convertToJavadocJavaMethod(apiConfig, method,
229-
actualTypesMap);
230-
return new RpcJavaMethod().setDetail(javaMethod.getDetail())
231-
.setAuthor(javaMethod.getAuthor())
232-
.setMethodDefinition(javaMethod.getMethodDefinition())
233-
.setOrder(javaMethod.getOrder())
234-
.setRequestParams(javaMethod.getRequestParams())
235-
.setResponseParams(javaMethod.getResponseParams())
236-
.setDeprecated((javaMethod.isDeprecated()))
237-
.setVersion((javaMethod.getVersion()))
238-
.setActualTypesMap(javaMethod.getActualTypesMap())
239-
.setName(javaMethod.getName())
240-
.setEscapeMethodDefinition(javaMethod.getEscapeMethodDefinition())
241-
.setMethodId(javaMethod.getMethodId())
242-
.setJavaMethod(javaMethod.getJavaMethod())
243-
.setReturnClassInfo(javaMethod.getReturnClassInfo());
244-
}
245-
246234
}

0 commit comments

Comments
 (0)