diff --git a/build.gradle b/build.gradle index 7c8b51fb26e..316228248b3 100644 --- a/build.gradle +++ b/build.gradle @@ -610,14 +610,22 @@ gradle.taskGraph.whenReady { graph -> } } -task buildAll { +task fastBuild { group = 'build' - description = 'Runs the standard build plus all heavy staging/Docker dependencies and fragile tests that were stripped out of the default build for performance.' + description = 'A lightweight build for local dev. Compiles Java, runs standard tests, and checks formatting, but skips Docker images, fragile tests, and the massive Angular console builds. (Do not use this target to verify console changes.)' + dependsOn build - dependsOn ':core:fragileTest' - dependsOn ':core:sqlIntegrationTest' - dependsOn ':core:buildToolImage' - dependsOn ':stage' - dependsOn ':jetty:buildNomulusImage' - dependsOn ':console-webapp:buildConsoleForAll' + // Remove the heavy default dependencies specifically for fastBuild + gradle.taskGraph.whenReady { graph -> + if (graph.hasTask(fastBuild)) { + project(':console-webapp').tasks.named('buildConsoleForAll').get().enabled = false + project(':jetty').tasks.named('buildNomulusImage').get().enabled = false + project(':core').tasks.named('buildToolImage').get().enabled = false + project(':core').tasks.named('fragileTest').get().enabled = false + project(':jetty').tasks.named('stage').get().enabled = false + if (project.tasks.findByName('stage') != null) { + project.tasks.named('stage').get().enabled = false + } + } + } } diff --git a/console-webapp/build.gradle b/console-webapp/build.gradle index 2a47ed70866..7d71f194c8b 100644 --- a/console-webapp/build.gradle +++ b/console-webapp/build.gradle @@ -100,3 +100,4 @@ tasks.applyFormatting.dependsOn(tasks.npmInstallDeps) tasks.checkFormatting.dependsOn(tasks.npmInstallDeps) tasks.build.dependsOn(tasks.checkFormatting) tasks.build.dependsOn(tasks.runConsoleWebappUnitTests) +tasks.build.dependsOn(tasks.buildConsoleForAll) diff --git a/core/build.gradle b/core/build.gradle index 86935b15a61..71cb8c79a6b 100644 --- a/core/build.gradle +++ b/core/build.gradle @@ -442,7 +442,7 @@ project.tasks.create('generateSqlSchema', JavaExec) { mainClass = 'google.registry.tools.DevTool' jvmArgs "--sun-misc-unsafe-memory-access=allow" args = [ - '-e', 'alpha', + '-e', 'unittest', 'generate_sql_schema', '--start_postgresql', '-o', "${rootProject.projectRootDir}/db/src/main/resources/sql/schema/" + "db-schema.sql.generated" @@ -741,9 +741,9 @@ test { // Don't run any tests from this task, all testing gets done in the // FilteringTest tasks. exclude "**" -}.dependsOn(standardTest, registryToolIntegrationTest, sqlIntegrationTest) +}.dependsOn(standardTest, registryToolIntegrationTest, sqlIntegrationTest, fragileTest) // When we override tests, we also break the cleanTest command. -cleanTest.dependsOn(cleanStandardTest, cleanRegistryToolIntegrationTest, cleanSqlIntegrationTest) +cleanTest.dependsOn(cleanStandardTest, cleanRegistryToolIntegrationTest, cleanSqlIntegrationTest, cleanFragileTest) -project.build.dependsOn devtool +project.build.dependsOn devtool, buildToolImage diff --git a/db/src/main/resources/sql/schema/db-schema.sql.generated b/db/src/main/resources/sql/schema/db-schema.sql.generated index 3e1c7e5eb0e..f6521283abb 100644 --- a/db/src/main/resources/sql/schema/db-schema.sql.generated +++ b/db/src/main/resources/sql/schema/db-schema.sql.generated @@ -333,7 +333,7 @@ ); create table "FeatureFlag" ( - feature_name text not null check ((feature_name in ('TEST_FEATURE','FEE_EXTENSION_1_DOT_0_IN_PROD','MINIMUM_DATASET_CONTACTS_OPTIONAL','MINIMUM_DATASET_CONTACTS_PROHIBITED','INCLUDE_PENDING_DELETE_DATE_FOR_DOMAINS','PROHIBIT_CONTACT_OBJECTS_ON_LOGIN'))), + feature_name text not null check ((feature_name in ('TEST_FEATURE','FEE_EXTENSION_1_DOT_0_IN_PROD','MINIMUM_DATASET_CONTACTS_OPTIONAL','MINIMUM_DATASET_CONTACTS_PROHIBITED','INCLUDE_PENDING_DELETE_DATE_FOR_DOMAINS','PROHIBIT_CONTACT_OBJECTS_ON_LOGIN','FORBID_INSECURE_ALGORITHMS_RFC_9904'))), status hstore not null, primary key (feature_name) ); diff --git a/integration/build.gradle b/integration/build.gradle index fb44b92c000..08850c58ab1 100644 --- a/integration/build.gradle +++ b/integration/build.gradle @@ -77,35 +77,54 @@ task extractSqlIntegrationTestSuite (type: Copy) { } } -// TODO(weiminyu): inherit from FilteringTest (defined in :core). -task sqlIntegrationTest(type: Test) { - // Use JUnit 5 Platform for local tests since the suite has been migrated to @Suite. - // However, Kokoro runs cross-version compatibility tests against older, deployed nomulus - // artifacts that were compiled using the legacy JUnit 4 @RunWith(JUnitPlatform.class) runner. - // We must fall back to the classic JUnit 4 runner for those remote environments to prevent - // NoClassDefFoundError and test discovery failures. - // TODO: Remove this fallback and use useJUnitPlatform() unconditionally once all deployed - // environments (sandbox and production) are running a Nomulus release built after the - // JUnit 5 @Suite migration. - if (nomulus_env == USE_LOCAL) { - useJUnitPlatform() - } else { - useJUnit() +task removeUnpackedTests { + doLast { + delete file(unpackedTestDir) } +} + +task sqlIntegrationTestLegacy(type: Test) { + useJUnit() testClassesDirs = files(unpackedTestDir) classpath = configurations.testRuntimeClasspath include 'google/registry/schema/integration/SqlIntegrationTestSuite.*' - dependsOn extractSqlIntegrationTestSuite + // Prevent build failures when evaluating newer JUnit 5 artifacts that have no JUnit 4 tests. + failOnNoDiscoveredTests = false + outputs.upToDateWhen { false } +} - finalizedBy tasks.create('removeUnpackedTests') { - doLast { - delete file(unpackedTestDir) - } - } - - // Disable incremental build/test since Gradle cannot detect changes - // in dependencies on its own. Will not fix since this test is typically - // run once (in presubmit or ci tests). +task sqlIntegrationTestModern(type: Test) { + useJUnitPlatform() + testClassesDirs = files(unpackedTestDir) + classpath = configurations.testRuntimeClasspath + include 'google/registry/schema/integration/SqlIntegrationTestSuite.*' + dependsOn extractSqlIntegrationTestSuite + // Prevent build failures when evaluating older JUnit 4 artifacts that have no JUnit 5 tests. + failOnNoDiscoveredTests = false outputs.upToDateWhen { false } } + +// TODO(weiminyu): inherit from FilteringTest (defined in :core). +task sqlIntegrationTest { + // Kokoro runs cross-version compatibility tests against both older deployed artifacts + // (which use the legacy JUnit 4 @RunWith wrapper) and newer deployed artifacts (which use + // the JUnit 5 @Suite annotation). We cannot statically configure the test runner because + // we do not know which runner the downloaded artifact expects, nor can we inject the + // modern junit-platform-suite engine dependency without causing a classpath collision + // with older embedded engine APIs. + // To solve this, we execute both test runners sequentially and ignore "no tests discovered" + // errors. The runner compatible with the artifact will discover and execute the tests, + // while the incompatible runner will safely no-op. + // + // TODO: Remove this split fallback once all deployed environments (sandbox, qa, production) + // are running a Nomulus release built after the JUnit 5 @Suite migration. + // When that happens: + // 1. Delete the 'sqlIntegrationTestLegacy' and 'sqlIntegrationTestModern' tasks entirely. + // 2. Change this task back to: task sqlIntegrationTest(type: Test) { ... } + // 3. Add 'useJUnitPlatform()' unconditionally inside it. + // 4. Move the 'testClassesDirs', 'classpath', 'include', and 'outputs.upToDateWhen' + // configurations back into it. + dependsOn sqlIntegrationTestLegacy, sqlIntegrationTestModern + finalizedBy removeUnpackedTests +} diff --git a/jetty/build.gradle b/jetty/build.gradle index 6be34c34a8e..191e4754144 100644 --- a/jetty/build.gradle +++ b/jetty/build.gradle @@ -148,4 +148,5 @@ tasks.register('getEndpoints', Exec) { commandLine './get-endpoints.py', "${rootProject.gcpProject}" } +project.build.dependsOn(tasks.named('buildNomulusImage')) rootProject.deploy.dependsOn(tasks.named('deployNomulus'))