Skip to content

Commit bb395e5

Browse files
committed
Support inner modifier for java non-static classes
1 parent 9ce37af commit bb395e5

File tree

2 files changed

+202
-0
lines changed
  • dokka-subprojects

2 files changed

+202
-0
lines changed

dokka-subprojects/analysis-java-psi/src/main/kotlin/org/jetbrains/dokka/analysis/java/parsers/DokkaPsiParser.kt

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -236,6 +236,18 @@ internal class DokkaPsiParser(
236236
val implementedInterfacesExtra =
237237
ImplementedInterfaces(ancestry.allImplementedInterfaces().toSourceSetDependent())
238238

239+
// used only for class and enum
240+
val innerModifierExtra = when {
241+
// top level java classes - no `inner`
242+
psi.containingClass == null -> null
243+
// java `static class` = kotlin `class`
244+
psi.hasModifier(JvmModifier.STATIC) -> null
245+
// java `class` = kotlin `inner class`
246+
else -> setOf(
247+
ExtraModifiers.KotlinOnlyModifiers.Inner
248+
).toSourceSetDependent().toAdditionalModifiers()
249+
}
250+
239251
when {
240252
isAnnotationType ->
241253
DAnnotation(
@@ -295,6 +307,7 @@ internal class DokkaPsiParser(
295307
isExpectActual = false,
296308
extra = PropertyContainer.withAll(
297309
implementedInterfacesExtra,
310+
innerModifierExtra,
298311
annotations.toList().toListOfAnnotations().toSourceSetDependent()
299312
.toAnnotations()
300313
)
@@ -341,6 +354,7 @@ internal class DokkaPsiParser(
341354
isExpectActual = false,
342355
extra = PropertyContainer.withAll(
343356
implementedInterfacesExtra,
357+
innerModifierExtra,
344358
annotations.toList().toListOfAnnotations().toSourceSetDependent()
345359
.toAnnotations(),
346360
ancestry.exceptionInSupertypesOrNull()

dokka-subprojects/plugin-base/src/test/kotlin/model/JavaTest.kt

Lines changed: 188 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ package model
66

77
import org.jetbrains.dokka.DokkaConfiguration
88
import org.jetbrains.dokka.Platform
9+
import org.jetbrains.dokka.base.signatures.KotlinSignatureUtils.modifiers
910
import org.jetbrains.dokka.base.transformers.documentables.InheritorsInfo
1011
import org.jetbrains.dokka.links.*
1112
import org.jetbrains.dokka.model.*
@@ -232,6 +233,193 @@ class JavaTest : AbstractModelTest("/src/main/kotlin/java/Test.java", "java") {
232233
}
233234
}
234235

236+
@Test
237+
fun innerClassModifiers() = inlineModelTest(
238+
"""
239+
|public class JavaClass {
240+
| public class InnerClass { }
241+
| public static class NestedClass { }
242+
| public enum InnerEnum {S}
243+
| public static enum NestedEnum {S}
244+
| public interface InnerInterface { }
245+
| public static interface NestedInterface { }
246+
| public @interface InnerAnnotation { }
247+
| public static @interface NestedAnnotation { }
248+
|}
249+
""",
250+
configuration = configuration
251+
) {
252+
with((this / "java" / "JavaClass").cast<DClass>()) {
253+
assertTrue(modifiers().isEmpty())
254+
255+
with((this / "InnerClass").cast<DClass>()) {
256+
assertContains(modifiers().values.single(), ExtraModifiers.KotlinOnlyModifiers.Inner)
257+
}
258+
with((this / "NestedClass").cast<DClass>()) {
259+
assertTrue(modifiers().isEmpty())
260+
}
261+
with((this / "InnerEnum").cast<DEnum>()) {
262+
assertTrue(modifiers().isEmpty())
263+
}
264+
with((this / "NestedEnum").cast<DEnum>()) {
265+
assertTrue(modifiers().isEmpty())
266+
}
267+
with((this / "InnerInterface").cast<DInterface>()) {
268+
assertTrue(modifiers().isEmpty())
269+
}
270+
with((this / "NestedInterface").cast<DInterface>()) {
271+
assertTrue(modifiers().isEmpty())
272+
}
273+
with((this / "InnerAnnotation").cast<DAnnotation>()) {
274+
assertTrue(modifiers().isEmpty())
275+
}
276+
with((this / "NestedAnnotation").cast<DAnnotation>()) {
277+
assertTrue(modifiers().isEmpty())
278+
}
279+
}
280+
}
281+
282+
@Test
283+
fun innerEnumModifiers() = inlineModelTest(
284+
"""
285+
|public enum JavaEnum { S;
286+
| public class InnerClass { }
287+
| public static class NestedClass { }
288+
| public enum InnerEnum {S}
289+
| public static enum NestedEnum {S}
290+
| public interface InnerInterface { }
291+
| public static interface NestedInterface { }
292+
| public @interface InnerAnnotation { }
293+
| public static @interface NestedAnnotation { }
294+
|}
295+
""",
296+
configuration = configuration
297+
) {
298+
// `enum` behaves the same as `class` regarding `inner`
299+
with((this / "java" / "JavaEnum").cast<DEnum>()) {
300+
assertTrue(modifiers().isEmpty())
301+
302+
with((this / "InnerClass").cast<DClass>()) {
303+
assertContains(modifiers().values.single(), ExtraModifiers.KotlinOnlyModifiers.Inner)
304+
}
305+
with((this / "NestedClass").cast<DClass>()) {
306+
assertTrue(modifiers().isEmpty())
307+
}
308+
with((this / "InnerEnum").cast<DEnum>()) {
309+
assertTrue(modifiers().isEmpty())
310+
}
311+
with((this / "NestedEnum").cast<DEnum>()) {
312+
assertTrue(modifiers().isEmpty())
313+
}
314+
with((this / "InnerInterface").cast<DInterface>()) {
315+
assertTrue(modifiers().isEmpty())
316+
}
317+
with((this / "NestedInterface").cast<DInterface>()) {
318+
assertTrue(modifiers().isEmpty())
319+
}
320+
with((this / "InnerAnnotation").cast<DAnnotation>()) {
321+
assertTrue(modifiers().isEmpty())
322+
}
323+
with((this / "NestedAnnotation").cast<DAnnotation>()) {
324+
assertTrue(modifiers().isEmpty())
325+
}
326+
}
327+
}
328+
329+
@Test
330+
fun innerInterfaceModifiers() = inlineModelTest(
331+
"""
332+
|public interface JavaInterface {
333+
| public class InnerClass { }
334+
| public static class NestedClass { }
335+
| public enum InnerEnum {S}
336+
| public static enum NestedEnum {S}
337+
| public interface InnerInterface { }
338+
| public static interface NestedInterface { }
339+
| public @interface InnerAnnotation { }
340+
| public static @interface NestedAnnotation { }
341+
|}
342+
""",
343+
configuration = configuration
344+
) {
345+
// new types nested in `interface` are `static` by default (no `inner` modifier)
346+
with((this / "java" / "JavaInterface").cast<DInterface>()) {
347+
assertTrue(modifiers().isEmpty())
348+
349+
with((this / "InnerClass").cast<DClass>()) {
350+
assertTrue(modifiers().isEmpty())
351+
}
352+
with((this / "NestedClass").cast<DClass>()) {
353+
assertTrue(modifiers().isEmpty())
354+
}
355+
with((this / "InnerEnum").cast<DEnum>()) {
356+
assertTrue(modifiers().isEmpty())
357+
}
358+
with((this / "NestedEnum").cast<DEnum>()) {
359+
assertTrue(modifiers().isEmpty())
360+
}
361+
with((this / "InnerInterface").cast<DInterface>()) {
362+
assertTrue(modifiers().isEmpty())
363+
}
364+
with((this / "NestedInterface").cast<DInterface>()) {
365+
assertTrue(modifiers().isEmpty())
366+
}
367+
with((this / "InnerAnnotation").cast<DAnnotation>()) {
368+
assertTrue(modifiers().isEmpty())
369+
}
370+
with((this / "NestedAnnotation").cast<DAnnotation>()) {
371+
assertTrue(modifiers().isEmpty())
372+
}
373+
}
374+
}
375+
376+
@Test
377+
fun innerAnnotationModifiers() = inlineModelTest(
378+
"""
379+
|public @interface JavaInterface {
380+
| public class InnerClass { }
381+
| public static class NestedClass { }
382+
| public enum InnerEnum {S}
383+
| public static enum NestedEnum {S}
384+
| public interface InnerInterface { }
385+
| public static interface NestedInterface { }
386+
| public @interface InnerAnnotation { }
387+
| public static @interface NestedAnnotation { }
388+
|}
389+
""",
390+
configuration = configuration
391+
) {
392+
// `@interface` behaves the same as `interface` regarding `inner`
393+
with((this / "java" / "JavaInterface").cast<DAnnotation>()) {
394+
assertTrue(modifiers().isEmpty())
395+
396+
with((this / "InnerClass").cast<DClass>()) {
397+
assertTrue(modifiers().isEmpty())
398+
}
399+
with((this / "NestedClass").cast<DClass>()) {
400+
assertTrue(modifiers().isEmpty())
401+
}
402+
with((this / "InnerEnum").cast<DEnum>()) {
403+
assertTrue(modifiers().isEmpty())
404+
}
405+
with((this / "NestedEnum").cast<DEnum>()) {
406+
assertTrue(modifiers().isEmpty())
407+
}
408+
with((this / "InnerInterface").cast<DInterface>()) {
409+
assertTrue(modifiers().isEmpty())
410+
}
411+
with((this / "NestedInterface").cast<DInterface>()) {
412+
assertTrue(modifiers().isEmpty())
413+
}
414+
with((this / "InnerAnnotation").cast<DAnnotation>()) {
415+
assertTrue(modifiers().isEmpty())
416+
}
417+
with((this / "NestedAnnotation").cast<DAnnotation>()) {
418+
assertTrue(modifiers().isEmpty())
419+
}
420+
}
421+
}
422+
235423
@Test
236424
fun varargs() {
237425
inlineModelTest(

0 commit comments

Comments
 (0)