Skip to content

Commit

Permalink
Implement method parameter comments
Browse files Browse the repository at this point in the history
Resolves: #72
  • Loading branch information
matshou committed Mar 14, 2021
2 parents e43f561 + d5d81bd commit 4e469e9
Show file tree
Hide file tree
Showing 10 changed files with 230 additions and 47 deletions.
2 changes: 1 addition & 1 deletion src/main/java/io/cocolabs/pz/zdoc/compile/LuaCompiler.java
Original file line number Diff line number Diff line change
Expand Up @@ -225,7 +225,7 @@ public Set<ZomboidLuaDoc> compile() throws CompilerException {
for (IParameter param : method.getParams())
{
LuaType paramClass = resolveLuaType(param.getType());
parameters.add(new LuaParameter(paramClass, param.getName()));
parameters.add(new LuaParameter(paramClass, param.getName(), param.getComment()));
}
JavaMethod.ReturnType returnType = method.getReturnType();
luaMethods.add(LuaMethod.Builder.create(method.getName())
Expand Down
108 changes: 78 additions & 30 deletions src/main/java/io/cocolabs/pz/zdoc/doc/detail/MethodDetail.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,13 +17,11 @@
*/
package io.cocolabs.pz.zdoc.doc.detail;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Set;
import java.util.*;
import java.util.stream.Collectors;

import org.apache.commons.collections4.list.SetUniqueList;
import org.apache.logging.log4j.util.Strings;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;

Expand Down Expand Up @@ -77,44 +75,81 @@ protected List<JavaMethod> parse() throws DetailParsingException {
}
}
String returnTypeComment = "";
Elements listElements = blockList.getAllElements();
for (int i = 0; i < listElements.size(); i++)
Map<String, String> paramComments = new HashMap<>();
Map<Element, Elements> descriptionList = new HashMap<>();

Elements ddElements = new Elements();
for (Element element : blockList.getAllElements())
{
Element listElement = listElements.get(i);
String className = listElement.className();
// description list title
if (element.tagName().equals("dt"))
{
ddElements = new Elements();
descriptionList.put(element, ddElements);
}
// description list elements
else if (element.tagName().equals("dd")) {
ddElements.add(element);
}
}
for (Map.Entry<Element, Elements> entry : descriptionList.entrySet())
{
Element listTitle = entry.getKey();
Elements listEntries = entry.getValue();
if (listEntries.isEmpty())
{
Logger.debug(String.format("Missing list elements for title '%s'", listTitle.text()));
continue;
}
Element titleContainer = listTitle.getElementsByTag("span").first();
// we're expecting to find list title in span container
if (titleContainer == null)
{
Logger.error(String.format("Unexpected description list title '%s'", listTitle));
continue;
}
String className = titleContainer.className();

// include override method documentation
//noinspection IfCanBeSwitch
if (className.equals("overrideSpecifyLabel"))
{
if (commentBuilder.length() > 0) {
commentBuilder.append('\n');
}
commentBuilder.append(listElement.text());
// avoid accessing index out of bounds
if (i + 1 < listElements.size())
{
Element overrideLabelElement = listElements.get(i += 1);
if (!overrideLabelElement.tagName().equals("dd"))
{
String format = "Unexpected description list element '%s'";
Logger.error(String.format(format, overrideLabelElement));
}
else commentBuilder.append('\n').append(overrideLabelElement.text());
}
commentBuilder.append(listTitle.text());
Element overrideLabelElement = listEntries.get(0);
commentBuilder.append('\n').append(overrideLabelElement.text());
}
// include method return value documentation
else if (className.equals("returnLabel"))
{
// avoid accessing index out of bounds
if (i + 1 < listElements.size())
Element returnLabelElement = listEntries.get(0);
returnTypeComment = returnLabelElement.text();
}
// include method parameter documentation
else if (className.equals("paramLabel"))
{
for (Element listEntry : listEntries)
{
Element returnLabelElement = listElements.get(i += 1);
if (returnLabelElement.tagName().equals("dd")) {
returnTypeComment = returnLabelElement.text();
Element eParamName = listEntry.getElementsByTag("code").first();
if (eParamName == null)
{
Logger.error(String.format("No paramLabel name found '%s'", listEntry));
continue;
}
else {
String format = "Unexpected description list element '%s'";
Logger.error(String.format(format, returnLabelElement));
String sParamName = eParamName.text();
int stringIndex = sParamName.length() + 3;
String sListEntry = listEntry.text();

// make sure parameter comment exists before trimming
if (stringIndex <= sListEntry.length())
{
// trim element text to get only parameter comment
String paramText = sListEntry.substring(stringIndex);
if (!Strings.isBlank(paramText)) {
paramComments.put(sParamName, paramText);
}
}
}
}
Expand All @@ -131,13 +166,14 @@ else if (className.equals("returnLabel"))
Logger.detail(String.format(msg, signature.toString(), signature.returnType));
continue;
}
List<JavaParameter> params = new ArrayList<>();
// rawParams is a list of parameter without comments
List<JavaParameter> rawParams = new ArrayList<>();
boolean isVarArgs = false;
if (!signature.params.isEmpty())
{
try {
MethodSignatureParser parser = new MethodSignatureParser(signature.params);
params = parser.parse();
rawParams = parser.parse();
isVarArgs = parser.isVarArg();
}
catch (SignatureParsingException e)
Expand All @@ -147,6 +183,18 @@ else if (className.equals("returnLabel"))
continue;
}
}
// match parameters with their respected comments
List<JavaParameter> params = new ArrayList<>();
for (int i = 0; i < rawParams.size(); i++)
{
JavaParameter param = rawParams.get(i);
String comment = paramComments.get(param.getName());
if (comment != null) {
params.add(i, new JavaParameter(param.getType(), param.getName(), comment));
}
// when no comment was found use raw parameter
else params.add(i, param);
}
result.add(JavaMethod.Builder.create(signature.name)
.withReturnType(type, returnTypeComment).withModifier(signature.modifier)
.withParams(params).withVarArgs(isVarArgs).withComment(signature.comment).build());
Expand Down
2 changes: 2 additions & 0 deletions src/main/java/io/cocolabs/pz/zdoc/element/IParameter.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,4 +24,6 @@ public interface IParameter {
String getName();

String getAsVarArg();

String getComment();
}
22 changes: 18 additions & 4 deletions src/main/java/io/cocolabs/pz/zdoc/element/java/JavaParameter.java
Original file line number Diff line number Diff line change
Expand Up @@ -25,19 +25,28 @@
public class JavaParameter implements IParameter, SignatureToken {

private final JavaClass type;
private final String name;
private final String name, comment;

public JavaParameter(JavaClass type, String name) {
public JavaParameter(JavaClass type, String name, String comment) {
this.type = type;
this.name = name;
this.comment = comment;
}

public JavaParameter(JavaClass type, String name) {
this(type, name, "");
}

public JavaParameter(Class<?> type, String name, String comment) {
this(new JavaClass(type), name, comment);
}

public JavaParameter(Class<?> type, String name) {
this(new JavaClass(type), name);
this(type, name, "");
}

public JavaParameter(Parameter parameter) {
this(new JavaClass(parameter.getType()), parameter.getName());
this(new JavaClass(parameter.getType()), parameter.getName(), "");
}

@Override
Expand All @@ -55,6 +64,11 @@ public String getAsVarArg() {
return (sType + "... " + getName()).trim();
}

@Override
public String getComment() {
return comment;
}

@Override
public JavaClass getType() {
return type;
Expand Down
13 changes: 8 additions & 5 deletions src/main/java/io/cocolabs/pz/zdoc/element/lua/LuaMethod.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,7 @@
*/
package io.cocolabs.pz.zdoc.element.lua;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Objects;
import java.util.*;

import org.jetbrains.annotations.Nullable;
import org.jetbrains.annotations.Unmodifiable;
Expand Down Expand Up @@ -71,7 +68,8 @@ private LuaMethod(Builder builder) {
for (int i = 0, size = params.size() - 1; i < size; i++) {
annotations.addAll(params.get(i).getAnnotations());
}
annotations.add(new EmmyLuaVarArg(params.get(params.size() - 1).getType()));
LuaParameter param = params.get(params.size() - 1);
annotations.add(new EmmyLuaVarArg(param.getType(), param.getComment()));
}
else {
builder.hasVarArg = false;
Expand Down Expand Up @@ -249,6 +247,11 @@ public Builder withParams(List<LuaParameter> params) {
return this;
}

public Builder withParams(LuaParameter...params) {
this.params = new ArrayList<>(Arrays.asList(params));
return this;
}

public LuaMethod build() {
return new LuaMethod(this);
}
Expand Down
16 changes: 13 additions & 3 deletions src/main/java/io/cocolabs/pz/zdoc/element/lua/LuaParameter.java
Original file line number Diff line number Diff line change
Expand Up @@ -29,14 +29,19 @@
public class LuaParameter implements IParameter, Annotated {

private final LuaType type;
private final String name;
private final String name, comment;
private final List<EmmyLua> annotations;

public LuaParameter(LuaType type, String name) {
public LuaParameter(LuaType type, String name, String comment) {

this.type = type;
this.name = EmmyLua.getSafeLuaName(name);
this.annotations = Collections.singletonList(new EmmyLuaParam(this.name, type));
this.comment = comment;
this.annotations = Collections.singletonList(new EmmyLuaParam(this.name, type, comment));
}

public LuaParameter(LuaType type, String name) {
this(type, name, "");
}

@Override
Expand All @@ -49,6 +54,11 @@ public String getAsVarArg() {
return "...";
}

@Override
public String getComment() {
return comment;
}

@Override
public LuaType getType() {
return type;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,11 @@
*/
public class EmmyLuaVarArg extends EmmyLua {

public EmmyLuaVarArg(LuaType type, String comment) {
super("vararg", type.getName(), comment);
}

public EmmyLuaVarArg(LuaType type) {
super("vararg", type.getName(), "");
this(type, "");
}
}
49 changes: 49 additions & 0 deletions src/test/java/io/cocolabs/pz/zdoc/doc/ZomboidLuaDocTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -493,6 +493,55 @@ void shouldWriteZomboidLuaDocMethodsWithValidReturnTypeComments() throws IOExcep
Assertions.assertEquals(expectedResult, writeToFileAndRead(zDoc));
}

@Test
void shouldWriteZomboidLuaDocMethodsWithValidParameterComments() throws IOException {

Set<LuaMethod> luaMethods = new LinkedHashSet<>();
luaMethods.add(LuaMethod.Builder.create("getObject").withOwner(TEST_LUA_CLASS)
.withReturnType(new LuaType("Object"))
.withParams(new LuaParameter(new LuaType("Object"), "arg0", "object to get"))
.build()
);
luaMethods.add(LuaMethod.Builder.create("getNumber").withOwner(TEST_LUA_CLASS)
.withReturnType(new LuaType("Number"), "returns a simple number")
.withParams(ImmutableList.of(
new LuaParameter(new LuaType("String"), "arg0", "some string param"),
new LuaParameter(new LuaType("Number"), "arg1", "some number param")
)).build()
);
luaMethods.add(LuaMethod.Builder.create("getString").withOwner(TEST_LUA_CLASS).withVarArg(true)
.withReturnType(new LuaType("String"), "returns a simple string")
.withParams(ImmutableList.of(
new LuaParameter(new LuaType("String"), "arg0", "some string param"),
new LuaParameter(new LuaType("Number"), "arg1", "some number param"),
new LuaParameter(new LuaType("Object"), "arg2", "variadic argument")
)).build()
);
ZomboidLuaDoc zDoc = new ZomboidLuaDoc(
TEST_LUA_CLASS, new ArrayList<>(), luaMethods
);
List<String> expectedResult = ImmutableList.of(
"---@class ZomboidLuaDocTest : io.cocolabs.pz.zdoc.doc.ZomboidLuaDocTest",
"ZomboidLuaDocTest = {}",
"",
"---@param arg0 Object @object to get",
"---@return Object",
"function ZomboidLuaDocTest:getObject(arg0) end",
"",
"---@param arg0 String @some string param",
"---@param arg1 Number @some number param",
"---@return Number @returns a simple number",
"function ZomboidLuaDocTest:getNumber(arg0, arg1) end",
"",
"---@param arg0 String @some string param",
"---@param arg1 Number @some number param",
"---@vararg Object @variadic argument",
"---@return String @returns a simple string",
"function ZomboidLuaDocTest:getString(arg0, arg1, ...) end"
);
Assertions.assertEquals(expectedResult, writeToFileAndRead(zDoc));
}

@TestOnly
private List<String> writeToFileAndRead(ZomboidLuaDoc zDoc) throws IOException {

Expand Down
Loading

0 comments on commit 4e469e9

Please sign in to comment.