diff --git a/core/build.gradle.kts b/core/build.gradle.kts index df0f3f364..8c9d549a5 100644 --- a/core/build.gradle.kts +++ b/core/build.gradle.kts @@ -273,3 +273,67 @@ protobuf { generateProtoTasks { all().configureEach { dependsOn(submodulesUpdate) } } protoc { artifact = "com.google.protobuf:protoc:" + libs.protoc.get().getVersion() } } + +val protoJavaDir = layout.buildDirectory.dir("generated/sources/proto/main/java") + +// First pass: Javadoc for generated protobufs — ignore warnings. +tasks.register("javadocProto") { + group = JavaBasePlugin.DOCUMENTATION_GROUP + description = "Generate Javadoc for protobuf-generated sources (warnings suppressed)." + + // Only the generated proto sources + setSource(fileTree(protoJavaDir) { include("**/*.java") }) + + // Use the main source set classpath to resolve types referenced by the generated code + classpath = sourceSets["main"].compileClasspath + + // Destination separate from main Javadoc + destinationDir = rootProject.layout.buildDirectory.dir("docs/${version}/core-proto").get().asFile + + // Make sure protobufs are generated before Javadoc runs + dependsOn("generateProto") + + // Suppress warnings/doclint for protobuf pass + (options as StandardJavadocDocletOptions).apply { + // Disable doclint entirely + addBooleanOption("Xdoclint:none", true) + // Be quiet + addBooleanOption("quiet", true) + // Encoding is good practice + encoding = "UTF-8" + } + + // Do not fail the build if javadoc finds issues in generated sources + isFailOnError = false +} + +// Second pass: Javadoc for main code, excluding the generated protobuf sources. +tasks.named("javadoc") { + mustRunAfter("javadocProto") + description = "Generate Javadoc for main sources (excludes protobuf-generated sources)." + + // Exclude the protobuf-generated directory from the main pass + val protoDirFile = protoJavaDir.get().asFile + exclude { spec -> spec.file.toPath().startsWith(protoDirFile.toPath()) } + + // Keep normal behavior for main javadoc (warnings allowed to show/fail if you want) + (options as StandardJavadocDocletOptions).apply { + encoding = "UTF-8" + destinationDir = rootProject.layout.buildDirectory.dir("docs/${version}/core").get().asFile + + addStringOption("overview", "${rootProject.projectDir}/core/src/main/javadoc/overview.html") + addStringOption("link", "../core-proto") + } +} + +// Bundle both passes into the Javadoc JAR used for publishing. +tasks.named("javadocJar") { + val shared = rootProject.layout.buildDirectory.dir("docs/${version}").get().asFile + if (!shared.exists()) { + println("Creating a dir for javadoc ${rootProject.buildDir}/docs/${version}") + shared.mkdirs() + } + + // Ensure both javadoc tasks have produced outputs + dependsOn(tasks.named("javadocProto"), tasks.named("javadoc")) +} diff --git a/core/src/main/java/io/substrait/package-info.java b/core/src/main/java/io/substrait/package-info.java index a62caaf60..e90c4c332 100644 --- a/core/src/main/java/io/substrait/package-info.java +++ b/core/src/main/java/io/substrait/package-info.java @@ -1,2 +1,6 @@ +/** + * The {@code io.substrait} package provides core classes and interfaces for working with the + * Substrait specification, which defines a portable representation of query plans and expressions. + */ @org.immutables.value.Value.Style(allowedClasspathAnnotations = {java.lang.Override.class}) package io.substrait; diff --git a/core/src/main/javadoc/overview.html b/core/src/main/javadoc/overview.html new file mode 100644 index 000000000..c75444241 --- /dev/null +++ b/core/src/main/javadoc/overview.html @@ -0,0 +1,22 @@ + +
+

Core Substrait Java API

+

+ The {@code io.substrait} package provides core classes and interfaces for + working with the Substrait specification, which defines a portable + representation of query plans and expressions. +

+ +

Components

+
    +
  • core - Core classes and interfaces
  • +
  • + core-protobuf - The Proto Buffers wrapper + classes +
  • +
  • + Isthmus API - Utility module that uses + Calcite to convert SQL to/from Substrait +
  • +
+ diff --git a/examples/substrait-spark/src/main/java/io/substrait/examples/util/SubstraitStringify.java b/examples/substrait-spark/src/main/java/io/substrait/examples/util/SubstraitStringify.java index a94d47fd4..fa7207e9c 100644 --- a/examples/substrait-spark/src/main/java/io/substrait/examples/util/SubstraitStringify.java +++ b/examples/substrait-spark/src/main/java/io/substrait/examples/util/SubstraitStringify.java @@ -72,9 +72,9 @@ public SubstraitStringify() { } /** - * Explains the Sustrait plan + * Explains the Substrait plan * - * @param plan Subsrait plan + * @param plan Substrait Plan * @return List of strings; typically these would then be logged or sent to stdout */ public static List explain(io.substrait.plan.Plan plan) { @@ -94,9 +94,9 @@ public static List explain(io.substrait.plan.Plan plan) { } /** - * Explains the Sustrait relation + * Explains the Substrait relation * - * @param plan Subsrait relation + * @param rel Substrait relation * @return List of strings; typically these would then be logged or sent to stdout */ public static List explain(io.substrait.relation.Rel rel) { diff --git a/isthmus/build.gradle.kts b/isthmus/build.gradle.kts index ad6ce6230..ca36c2c6a 100644 --- a/isthmus/build.gradle.kts +++ b/isthmus/build.gradle.kts @@ -147,3 +147,29 @@ tasks { sourceSets { test { proto.srcDirs("src/test/resources/extensions") } } protobuf { protoc { artifact = "com.google.protobuf:protoc:" + libs.protoc.get().getVersion() } } + +tasks.named("javadoc") { + description = "Generate Javadoc for main sources (excludes protobuf-generated sources)." + + // Keep normal behavior for main javadoc (warnings allowed to show/fail if you want) + (options as StandardJavadocDocletOptions).apply { + encoding = "UTF-8" + destinationDir = rootProject.layout.buildDirectory.dir("docs/${version}/isthmus").get().asFile + + addStringOption("link", "../core-proto") + addStringOption("link", "../core") + addStringOption("link", "https://calcite.apache.org/javadocAggregate/") + } +} + +// Bundle both passes into the Javadoc JAR used for publishing. +tasks.named("javadocJar") { + val shared = rootProject.layout.buildDirectory.dir("docs/${version}").get().asFile + if (!shared.exists()) { + println("Creating a dir for javadoc ${rootProject.buildDir}/${version}") + shared.mkdirs() + } + + // Ensure javadoc tasks have produced output + dependsOn(tasks.named("javadoc")) +}