From 22c867f3f20fd4ccf4c5e5a6afb9507927c4b26f Mon Sep 17 00:00:00 2001 From: gbrodman Date: Mon, 6 Jul 2026 15:26:42 -0400 Subject: [PATCH] Add TLD verification to GenerateZoneFilesAction (#3132) 1. this is a good idea in general 2. it can prevent GCS path traversal if someone somehow bypasses auth to add a weird path --- .../tools/server/GenerateZoneFilesAction.java | 2 ++ .../tools/server/GenerateZoneFilesActionTest.java | 15 +++++++++++++++ 2 files changed, 17 insertions(+) diff --git a/core/src/main/java/google/registry/tools/server/GenerateZoneFilesAction.java b/core/src/main/java/google/registry/tools/server/GenerateZoneFilesAction.java index 5827b09c1..147488361 100644 --- a/core/src/main/java/google/registry/tools/server/GenerateZoneFilesAction.java +++ b/core/src/main/java/google/registry/tools/server/GenerateZoneFilesAction.java @@ -33,6 +33,7 @@ import google.registry.model.domain.Domain; import google.registry.model.domain.secdns.DomainDsData; import google.registry.model.host.Host; import google.registry.model.tld.Tld; +import google.registry.model.tld.Tlds; import google.registry.request.Action; import google.registry.request.HttpException.BadRequestException; import google.registry.request.JsonActionRunner; @@ -119,6 +120,7 @@ public class GenerateZoneFilesAction implements Runnable, JsonActionRunner.JsonA public Map handleJsonRequest(Map json) { @SuppressWarnings("unchecked") ImmutableSet tlds = ImmutableSet.copyOf((List) json.get("tlds")); + Tlds.assertTldsExist(tlds); Instant exportTime = Instant.parse(json.get("exportTime").toString()); // We disallow exporting within the past 2 minutes because there might be outstanding writes. // We can only reliably call loadAtPointInTime at times that are UTC midnight and > diff --git a/core/src/test/java/google/registry/tools/server/GenerateZoneFilesActionTest.java b/core/src/test/java/google/registry/tools/server/GenerateZoneFilesActionTest.java index 8f0dbe4c0..047c35d04 100644 --- a/core/src/test/java/google/registry/tools/server/GenerateZoneFilesActionTest.java +++ b/core/src/test/java/google/registry/tools/server/GenerateZoneFilesActionTest.java @@ -23,6 +23,7 @@ import static google.registry.testing.DatabaseHelper.persistResource; import static google.registry.testing.TestDataHelper.loadFile; import static google.registry.util.DateTimeUtils.plusMinutes; import static java.nio.charset.StandardCharsets.UTF_8; +import static org.junit.jupiter.api.Assertions.assertThrows; import com.google.cloud.storage.BlobId; import com.google.cloud.storage.contrib.nio.testing.LocalStorageHelper; @@ -56,6 +57,20 @@ class GenerateZoneFilesActionTest { private final GcsUtils gcsUtils = new GcsUtils(LocalStorageHelper.getOptions()); + @Test + void testGenerate_nonexistentTld_throwsException() { + GenerateZoneFilesAction action = new GenerateZoneFilesAction(); + IllegalArgumentException thrown = + assertThrows( + IllegalArgumentException.class, + () -> + action.handleJsonRequest( + ImmutableMap.of( + "tlds", ImmutableList.of("nonexistent-tld"), + "exportTime", Instant.parse("2024-03-27T00:00:00Z")))); + assertThat(thrown).hasMessageThat().contains("TLDs do not exist: nonexistent-tld"); + } + @Test void testGenerate_defaultTtls() throws Exception { createTlds("tld", "com");