mirror of
https://github.com/google/nomulus
synced 2026-01-16 10:43:06 +00:00
Compare commits
132 Commits
proxy-2025
...
master
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
c187c92ae4 | ||
|
|
22ca4e3f2b | ||
|
|
f27136458a | ||
|
|
d8e647316e | ||
|
|
d6e0a7b979 | ||
|
|
5725eb95e0 | ||
|
|
aa12998276 | ||
|
|
d415416bc5 | ||
|
|
3a1068f313 | ||
|
|
69e5d40f04 | ||
|
|
64f6cd9af4 | ||
|
|
40184689ca | ||
|
|
826ad85d20 | ||
|
|
2b47bc9b0a | ||
|
|
9555dca8c6 | ||
|
|
49484c06d3 | ||
|
|
81d222e7d6 | ||
|
|
7e9d4c27d1 | ||
|
|
f9c22ff1c5 | ||
|
|
2562d582f3 | ||
|
|
6f0bc1ded9 | ||
|
|
db9fc3271d | ||
|
|
84491fde70 | ||
|
|
0519e2ffcf | ||
|
|
85f75494ab | ||
|
|
cbba91558a | ||
|
|
c24f09febc | ||
|
|
fd51035f23 | ||
|
|
90eb078e3f | ||
|
|
2a94bdc257 | ||
|
|
50fa49e0c0 | ||
|
|
a581259edb | ||
|
|
fcdac3e86e | ||
|
|
b652f81193 | ||
|
|
d98d65eee5 | ||
|
|
28e72bd0d0 | ||
|
|
0777be3d6c | ||
|
|
f9cd167ae4 | ||
|
|
eed1886121 | ||
|
|
7149fd3307 | ||
|
|
0dc7ab99d7 | ||
|
|
76d4dfbb04 | ||
|
|
8547ad7941 | ||
|
|
b1266c95e8 | ||
|
|
bc9aab6790 | ||
|
|
6cb669a5a7 | ||
|
|
0f92e98028 | ||
|
|
5f0526c07a | ||
|
|
759aaddb5f | ||
|
|
816180f3b3 | ||
|
|
bf66b374c6 | ||
|
|
666cee1d9f | ||
|
|
d4a70c29a8 | ||
|
|
7b8d07954b | ||
|
|
34bea69a48 | ||
|
|
363800bd86 | ||
|
|
dee132d04b | ||
|
|
847ef12a4f | ||
|
|
d9349be18e | ||
|
|
0c74883428 | ||
|
|
b357fc79f7 | ||
|
|
754e7fbddc | ||
|
|
ad07b32638 | ||
|
|
8f69b48e87 | ||
|
|
c33f0dc07f | ||
|
|
969353d4e2 | ||
|
|
6cd351ec7c | ||
|
|
19e03dbd2e | ||
|
|
fc1eb162f2 | ||
|
|
ed25854fbc | ||
|
|
0aa6bc6aaa | ||
|
|
ff4c326ebe | ||
|
|
51b579871a | ||
|
|
b144aafb22 | ||
|
|
ddd955e156 | ||
|
|
6863f678f1 | ||
|
|
6bd90e967b | ||
|
|
5faf3d283c | ||
|
|
149fb66ac5 | ||
|
|
8c96940a27 | ||
|
|
9c5510f05d | ||
|
|
84884de77b | ||
|
|
d6c35df9bc | ||
|
|
7caa0ec9d6 | ||
|
|
ee3866ec4a | ||
|
|
97d0b7680f | ||
|
|
5700a008d6 | ||
|
|
dc9f5b99bc | ||
|
|
d3c6de7a38 | ||
|
|
3c3303c16a | ||
|
|
2a86a1bbe9 | ||
|
|
ea148ac13e | ||
|
|
06299ccb86 | ||
|
|
732c30b359 | ||
|
|
ee5a2d3916 | ||
|
|
2b5643df4c | ||
|
|
6bbd7a2290 | ||
|
|
77ab80f3dc | ||
|
|
5e1cd0120f | ||
|
|
0167dad85f | ||
|
|
1eaf3d4aa8 | ||
|
|
d9c46170dd | ||
|
|
e8a475f48b | ||
|
|
bdaab9daa5 | ||
|
|
7e07fabf7e | ||
|
|
16859bb36a | ||
|
|
7c92928f2c | ||
|
|
de8d205657 | ||
|
|
4738b979e4 | ||
|
|
a61a667992 | ||
|
|
1164070576 | ||
|
|
d23640a54f | ||
|
|
cc347264f1 | ||
|
|
e5d4cbb9fc | ||
|
|
8c1e0ff4de | ||
|
|
5cef2dd8b5 | ||
|
|
62b2585220 | ||
|
|
8692fe35db | ||
|
|
18614ba11e | ||
|
|
427f6db820 | ||
|
|
5aa40b2208 | ||
|
|
95c89bc856 | ||
|
|
c21b66f0fb | ||
|
|
b070c46231 | ||
|
|
a20eb8d1e9 | ||
|
|
338b8edb97 | ||
|
|
9f191e9392 | ||
|
|
39c2a79898 | ||
|
|
e2e9d4cfc7 | ||
|
|
2948dcc1be | ||
|
|
c5644d5c8b | ||
|
|
514d24ed67 |
11
.gitignore
vendored
11
.gitignore
vendored
@@ -18,6 +18,13 @@ gjf.out
|
||||
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
|
||||
hs_err_pid*
|
||||
|
||||
# Environment-specific configuration files
|
||||
core/src/main/java/google/registry/config/files/nomulus-config-alpha.yaml
|
||||
core/src/main/java/google/registry/config/files/nomulus-config-crash.yaml
|
||||
core/src/main/java/google/registry/config/files/nomulus-config-production.yaml
|
||||
core/src/main/java/google/registry/config/files/nomulus-config-qa.yaml
|
||||
core/src/main/java/google/registry/config/files/nomulus-config-sandbox.yaml
|
||||
|
||||
######################################################################
|
||||
# Eclipse Ignores
|
||||
|
||||
@@ -114,9 +121,5 @@ core/**/registrar_dbg*.js
|
||||
core/**/registrar_bin*.css
|
||||
core/**/registrar_dbg*.css
|
||||
|
||||
# Appengine generated files
|
||||
core/WEB-INF/appengine-generated/*.bin
|
||||
core/WEB-INF/appengine-generated/*.xml
|
||||
|
||||
# jEnv
|
||||
.java-version
|
||||
|
||||
@@ -1,108 +0,0 @@
|
||||
// Copyright 2019 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
apply plugin: 'war'
|
||||
|
||||
def environment = rootProject.environment
|
||||
def gcpProject = rootProject.gcpProject
|
||||
|
||||
// Set this directory before applying the appengine plugin so that the
|
||||
// plugin will recognize this as an app-engine standard app (and also
|
||||
// obtains the appengine-web.xml from the correct location)
|
||||
project.convention.plugins['war'].webAppDirName =
|
||||
"../../core/src/main/java/google/registry/env/${environment}/${project.name}"
|
||||
|
||||
apply plugin: 'com.google.cloud.tools.appengine'
|
||||
|
||||
def coreResourcesDir = "${rootDir}/core/build/resources/main"
|
||||
def coreLibsDir = "${rootDir}/core/build/libs"
|
||||
|
||||
// Get the web.xml file for the service.
|
||||
war {
|
||||
webInf {
|
||||
from "../../core/src/main/java/google/registry/env/common/${project.name}/WEB-INF"
|
||||
}
|
||||
}
|
||||
|
||||
war {
|
||||
from("${coreResourcesDir}/google/registry/ui/html") {
|
||||
include "*.html"
|
||||
}
|
||||
from("${coreLibsDir}") {
|
||||
include "core.jar"
|
||||
into("WEB-INF/lib")
|
||||
}
|
||||
}
|
||||
|
||||
if (project.path == ":services:default") {
|
||||
war {
|
||||
from("${coreResourcesDir}/google/registry/ui/html") {
|
||||
include "*.html"
|
||||
into("registrar")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
appengine {
|
||||
deploy {
|
||||
// appengineDeployAll task requires the version to be set. So,
|
||||
// this config lets gcloud select a version name when deploying
|
||||
// to alpha or sandbox from our workstation.
|
||||
if (!rootProject.prodOrSandboxEnv) {
|
||||
version = 'GCLOUD_CONFIG'
|
||||
}
|
||||
|
||||
// Don't set gcpProject directly, it gets overriden in ./build.gradle.
|
||||
// Do -P environment={crash,alpha} instead. For sandbox/production,
|
||||
// use Spinnaker.
|
||||
projectId = gcpProject
|
||||
}
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation project(path: ':core', configuration: 'deploy_jar')
|
||||
}
|
||||
|
||||
// The tools.jar file gets pulled in from the java environment and for some
|
||||
// reason gets exploded "readonly", causing subsequent builds to fail when
|
||||
// they can't overwrite it. The hack below makes the file writable after
|
||||
// we're done exploding it.
|
||||
//
|
||||
// Fun fact: We only use this jar for documentation generation and as such we
|
||||
// don't need it in our warfile, as it is not used by the application at
|
||||
// runtime. But it's not clear how to exclude it, as we seem to be
|
||||
// constructing the jar from the entire WEB-INF directory and per-file
|
||||
// exclude rules don't seem to work on it. Better solutions are welcome :-)
|
||||
explodeWar.doLast {
|
||||
file("${it.explodedAppDirectory}/WEB-INF/lib/tools.jar").setWritable(true)
|
||||
}
|
||||
|
||||
appengineDeployAll.mustRunAfter ':console-webapp:deploy'
|
||||
appengineDeployAll.finalizedBy ':deployCloudSchedulerAndQueue'
|
||||
|
||||
rootProject.stage.dependsOn appengineStage
|
||||
tasks['war'].dependsOn ':core:processResources'
|
||||
tasks['war'].dependsOn ':core:jar'
|
||||
|
||||
// Impose verification for all of the deployment tasks. We haven't found a
|
||||
// better way to do this other than to apply to each of them independently.
|
||||
// If a new task gets added, it will still fail if "environment" is not defined
|
||||
// because gcpProject is null. We just won't get as friendly an error message.
|
||||
appengineDeployAll.configure rootProject.verifyDeploymentConfig
|
||||
appengineDeploy.configure rootProject.verifyDeploymentConfig
|
||||
appengineDeployCron.configure rootProject.verifyDeploymentConfig
|
||||
appengineDeployDispatch.configure rootProject.verifyDeploymentConfig
|
||||
appengineDeployDos.configure rootProject.verifyDeploymentConfig
|
||||
appengineDeployIndex.configure rootProject.verifyDeploymentConfig
|
||||
appengineDeployQueue.configure rootProject.verifyDeploymentConfig
|
||||
18
build.gradle
18
build.gradle
@@ -84,10 +84,10 @@ tasks.build.dependsOn(tasks.checkLicense)
|
||||
// Paths to main and test sources.
|
||||
ext.projectRootDir = "${rootDir}"
|
||||
|
||||
// Tasks to deploy/stage all App Engine services
|
||||
// Tasks to deploy/stage all services
|
||||
task deploy {
|
||||
group = 'deployment'
|
||||
description = 'Deploys all services to App Engine.'
|
||||
description = 'Deploys all services.'
|
||||
}
|
||||
|
||||
task stage {
|
||||
@@ -331,9 +331,6 @@ subprojects {
|
||||
|
||||
// Set up all of the deployment projects.
|
||||
if (services.contains(project.path)) {
|
||||
|
||||
apply from: "${rootDir.path}/appengine_war.gradle"
|
||||
|
||||
// Return early, do not apply the settings below.
|
||||
return
|
||||
}
|
||||
@@ -380,17 +377,6 @@ subprojects {
|
||||
}
|
||||
}
|
||||
|
||||
// Force SDK download and deployment to be sequential, otherwise parallel tasks
|
||||
// will fail. For SDK download, they will try to write to the same location to
|
||||
// upgrade gcloud. For deployment, they will try to deploy different services to
|
||||
// the same project at the same time.
|
||||
for (int i = 1; i < services.size(); i++) {
|
||||
project("${services[i]}").downloadCloudSdk
|
||||
.dependsOn(project("${services[i - 1]}").downloadCloudSdk)
|
||||
project("${services[i]}").appengineDeployAll
|
||||
.dependsOn(project("${services[i - 1]}").appengineDeployAll)
|
||||
}
|
||||
|
||||
// If "-P verboseTestOutput=true" is passed in, configure all subprojects to dump all of their
|
||||
// output and final test status (pass/fail, errors) for each test class.
|
||||
//
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
# This file is expected to be part of source control.
|
||||
aopalliance:aopalliance:1.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.github.ben-manes.caffeine:caffeine:3.0.5=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.github.ben-manes.caffeine:caffeine:3.2.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.github.ben-manes.caffeine:caffeine:3.2.2=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.github.kevinstern:software-and-algorithms:1.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.auto.service:auto-service-annotations:1.0.1=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.auto.value:auto-value-annotations:1.11.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
@@ -12,13 +12,13 @@ com.google.auto:auto-common:1.2.1=annotationProcessor,errorprone,testAnnotationP
|
||||
com.google.code.findbugs:jsr305:3.0.2=annotationProcessor,checkstyle,compileClasspath,deploy_jar,errorprone,runtimeClasspath,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath,testing,testingAnnotationProcessor,testingCompileClasspath
|
||||
com.google.errorprone:error_prone_annotation:2.23.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.errorprone:error_prone_annotations:2.23.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.errorprone:error_prone_annotations:2.36.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.google.errorprone:error_prone_annotations:2.40.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.google.errorprone:error_prone_annotations:2.7.1=checkstyle
|
||||
com.google.errorprone:error_prone_check_api:2.23.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.errorprone:error_prone_core:2.23.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.errorprone:error_prone_type_annotations:2.23.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.errorprone:javac:9+181-r4173-1=errorproneJavac
|
||||
com.google.flogger:flogger:0.8=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.google.flogger:flogger:0.9=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.google.guava:failureaccess:1.0.1=annotationProcessor,checkstyle,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
com.google.guava:failureaccess:1.0.2=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
com.google.guava:guava-parent:32.1.1-jre=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
@@ -37,15 +37,14 @@ commons-collections:commons-collections:3.2.2=checkstyle
|
||||
info.picocli:picocli:4.6.2=checkstyle
|
||||
io.github.eisop:dataflow-errorprone:3.34.0-eisop1=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
io.github.java-diff-utils:java-diff-utils:4.12=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
io.github.java-diff-utils:java-diff-utils:4.15=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
io.github.java-diff-utils:java-diff-utils:4.16=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
jakarta.inject:jakarta.inject-api:2.0.1=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
javax.inject:javax.inject:1=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
joda-time:joda-time:2.13.1=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
joda-time:joda-time:2.14.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
junit:junit:4.13.2=testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
net.sf.saxon:Saxon-HE:10.6=checkstyle
|
||||
org.antlr:antlr4-runtime:4.9.3=checkstyle
|
||||
org.apiguardian:apiguardian-api:1.1.2=testCompileClasspath
|
||||
org.checkerframework:checker-compat-qual:2.5.3=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
org.checkerframework:checker-qual:3.12.0=checkstyle
|
||||
org.checkerframework:checker-qual:3.33.0=annotationProcessor,errorprone,testAnnotationProcessor,testingAnnotationProcessor
|
||||
org.checkerframework:checker-qual:3.42.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
@@ -56,12 +55,12 @@ org.jacoco:org.jacoco.core:0.8.12=jacocoAnt
|
||||
org.jacoco:org.jacoco.report:0.8.12=jacocoAnt
|
||||
org.javassist:javassist:3.28.0-GA=checkstyle
|
||||
org.jspecify:jspecify:1.0.0=compileClasspath,deploy_jar,runtimeClasspath,testCompileClasspath,testRuntimeClasspath,testing,testingCompileClasspath
|
||||
org.junit.jupiter:junit-jupiter-api:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-engine:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-commons:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-engine:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-launcher:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit:junit-bom:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-api:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-engine:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-commons:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-engine:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-launcher:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit:junit-bom:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.opentest4j:opentest4j:1.3.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.ow2.asm:asm-commons:9.7=jacocoAnt
|
||||
org.ow2.asm:asm-tree:9.7=jacocoAnt
|
||||
|
||||
@@ -33,8 +33,8 @@ public abstract class DateTimeUtils {
|
||||
/**
|
||||
* A date in the far future that we can treat as infinity.
|
||||
*
|
||||
* <p>This value is (2^63-1)/1000 rounded down. AppEngine stores dates as 64 bit microseconds, but
|
||||
* Java uses milliseconds, so this is the largest representable date that will survive a
|
||||
* <p>This value is (2^63-1)/1000 rounded down. Postgres can store dates as 64 bit microseconds,
|
||||
* but Java uses milliseconds, so this is the largest representable date that will survive a
|
||||
* round-trip through the database.
|
||||
*/
|
||||
public static final DateTime END_OF_TIME = new DateTime(Long.MAX_VALUE / 1000, DateTimeZone.UTC);
|
||||
|
||||
@@ -92,17 +92,19 @@ public class TextDiffSubject extends Subject {
|
||||
|
||||
private ImmutableList<String> filterComments(List<String> lines) {
|
||||
return lines.stream()
|
||||
.filter(line -> !line.isBlank())
|
||||
.filter(line -> comments.stream().noneMatch(line::startsWith))
|
||||
.collect(ImmutableList.toImmutableList());
|
||||
}
|
||||
|
||||
public void hasSameContentAs(List<String> expectedContent) {
|
||||
checkNotNull(expectedContent, "expectedContent");
|
||||
ImmutableList<String> expected = filterComments(expectedContent);
|
||||
if (filterComments(expected).equals(filterComments(actual))) {
|
||||
ImmutableList<String> filteredExpected = filterComments(expectedContent);
|
||||
ImmutableList<String> filteredActual = filterComments(actual);
|
||||
if (filteredExpected.equals(filteredActual)) {
|
||||
return;
|
||||
}
|
||||
String diffString = diffFormat.generateDiff(expected, actual);
|
||||
String diffString = diffFormat.generateDiff(filteredExpected, filteredActual);
|
||||
failWithoutActual(
|
||||
Fact.simpleFact(
|
||||
Joiner.on('\n')
|
||||
|
||||
@@ -56,7 +56,7 @@ PROPERTIES_HEADER = """\
|
||||
# nom_build), run ./nom_build --help.
|
||||
#
|
||||
# DO NOT EDIT THIS FILE BY HAND
|
||||
org.gradle.jvmargs=-Xmx1024m
|
||||
org.gradle.jvmargs=-Xmx4096m
|
||||
org.gradle.caching=true
|
||||
org.gradle.parallel=true
|
||||
"""
|
||||
@@ -104,7 +104,7 @@ PROPERTIES = [
|
||||
Property('testFilter',
|
||||
'Comma separated list of test patterns, if specified run only '
|
||||
'these.'),
|
||||
Property('environment', 'GAE Environment for deployment and staging.'),
|
||||
Property('environment', 'Environment for deployment and staging.'),
|
||||
|
||||
# Cloud SQL properties
|
||||
Property('dbServer',
|
||||
@@ -117,28 +117,19 @@ PROPERTIES = [
|
||||
Property('dbUser', 'Database user name for use in connection'),
|
||||
Property('dbPassword', 'Database password for use in connection'),
|
||||
|
||||
Property('publish_repo',
|
||||
'Maven repository that hosts the Cloud SQL schema jar and the '
|
||||
'registry server test jars. Such jars are needed for '
|
||||
'server/schema integration tests. Please refer to <a '
|
||||
'href="./integration/README.md">integration project</a> for more '
|
||||
'information.'),
|
||||
Property('baseSchemaTag',
|
||||
'The nomulus version tag of the schema for use in the schema'
|
||||
'deployment integration test (:db:schemaIncrementalDeployTest)'),
|
||||
Property('schema_version',
|
||||
'The nomulus version tag of the schema for use in a database'
|
||||
'integration test.'),
|
||||
Property('nomulus_version',
|
||||
'The version of nomulus to test against in a database '
|
||||
'integration test.'),
|
||||
Property('dot_path',
|
||||
'The path to "dot", part of the graphviz package that converts '
|
||||
'a BEAM pipeline to image. Setting this property to empty string '
|
||||
'will disable image generation.',
|
||||
'/usr/bin/dot'),
|
||||
Property('pipeline',
|
||||
'The name of the Beam pipeline being staged.')
|
||||
'The name of the Beam pipeline being staged.'),
|
||||
Property('nomulus_env',
|
||||
'For use by scripts. Normally not set manually.'),
|
||||
Property('schema_env',
|
||||
'For use by scripts. Normally not set manually.'),
|
||||
Property('schemaTestArtifactsDir',
|
||||
'For use by scripts. Normally not set manually.')
|
||||
]
|
||||
|
||||
GRADLE_FLAGS = [
|
||||
|
||||
@@ -98,16 +98,15 @@ PRESUBMITS = {
|
||||
"File did not include the license header.",
|
||||
|
||||
# Files must end in a newline
|
||||
PresubmitCheck(r".*\n$", ("java", "js", "soy", "sql", "py", "sh", "gradle", "ts"),
|
||||
{"node_modules/"}, REQUIRED):
|
||||
PresubmitCheck(r".*\n$", ("java", "js", "soy", "sql", "py", "sh", "gradle", "ts", "xml"),
|
||||
{"node_modules/", ".idea"}, REQUIRED):
|
||||
"Source files must end in a newline.",
|
||||
|
||||
# System.(out|err).println should only appear in tools/ or load-testing/
|
||||
PresubmitCheck(
|
||||
r".*\bSystem\.(out|err)\.print", "java", {
|
||||
"StackdriverDashboardBuilder.java", "/tools/", "/example/",
|
||||
"/load-testing/", "RegistryTestServerMain.java",
|
||||
"TestServerExtension.java", "FlowDocumentationTool.java"
|
||||
"/tools/", "/example/", "/load-testing/",
|
||||
"RegistryTestServerMain.java", "TestServerExtension.java"
|
||||
}):
|
||||
"System.(out|err).println is only allowed in tools/ packages. Please "
|
||||
"use a logger instead.",
|
||||
@@ -120,7 +119,7 @@ PRESUBMITS = {
|
||||
):
|
||||
"In SOY please use the ({@param name: string} /** User name. */) style"
|
||||
" parameter passing instead of the ( * @param name User name.) style "
|
||||
"parameter pasing.",
|
||||
"parameter passing.",
|
||||
PresubmitCheck(
|
||||
r'.*\{[^}]+\w+:\s+"',
|
||||
"soy",
|
||||
@@ -139,41 +138,6 @@ PRESUBMITS = {
|
||||
{},
|
||||
):
|
||||
"All soy templates must use strict autoescaping",
|
||||
|
||||
# various JS linting checks
|
||||
PresubmitCheck(
|
||||
r".*goog\.base\(",
|
||||
"js",
|
||||
{"/node_modules/"},
|
||||
):
|
||||
"Use of goog.base is not allowed.",
|
||||
PresubmitCheck(
|
||||
r".*goog\.dom\.classes",
|
||||
"js",
|
||||
{"/node_modules/"},
|
||||
):
|
||||
"Instead of goog.dom.classes, use goog.dom.classlist which is smaller "
|
||||
"and faster.",
|
||||
PresubmitCheck(
|
||||
r".*goog\.getMsg",
|
||||
"js",
|
||||
{"/node_modules/"},
|
||||
):
|
||||
"Put messages in Soy, instead of using goog.getMsg().",
|
||||
PresubmitCheck(
|
||||
r".*(innerHTML|outerHTML)\s*(=|[+]=)([^=]|$)",
|
||||
"js",
|
||||
{"/node_modules/", "registrar_bin."},
|
||||
):
|
||||
"Do not assign directly to the dom. Use goog.dom.setTextContent to set"
|
||||
" to plain text, goog.dom.removeChildren to clear, or "
|
||||
"soy.renderElement to render anything else",
|
||||
PresubmitCheck(
|
||||
r".*console\.(log|info|warn|error)",
|
||||
"js",
|
||||
{"/node_modules/", "google/registry/ui/js/util.js", "registrar_bin."},
|
||||
):
|
||||
"JavaScript files should not include console logging.",
|
||||
PresubmitCheck(
|
||||
r".*\nimport (static )?.*\.shaded\..*",
|
||||
"java",
|
||||
@@ -303,26 +267,6 @@ def verify_flyway_index():
|
||||
return not success
|
||||
|
||||
|
||||
def verify_javascript_deps():
|
||||
"""Verifies that we haven't introduced any new javascript dependencies."""
|
||||
with open('package.json') as f:
|
||||
package = json.load(f)
|
||||
|
||||
deps = list(package['dependencies'].keys())
|
||||
if deps != EXPECTED_JS_PACKAGES:
|
||||
print('Unexpected javascript dependencies. Was expecting '
|
||||
'%s, got %s.' % (EXPECTED_JS_PACKAGES, deps))
|
||||
print(textwrap.dedent("""
|
||||
* If the new dependencies are intentional, please verify that the
|
||||
* license is one of the allowed licenses (see
|
||||
* config/dependency-license/allowed_licenses.json) and add an entry
|
||||
* for the package (with the license in a comment) to the
|
||||
* EXPECTED_JS_PACKAGES variable in config/presubmits.py.
|
||||
"""))
|
||||
return True
|
||||
return False
|
||||
|
||||
|
||||
def get_files():
|
||||
for root, dirnames, filenames in os.walk("."):
|
||||
for filename in filenames:
|
||||
@@ -347,8 +291,5 @@ if __name__ == "__main__":
|
||||
# when we put it here it fails fast before all of the tests are run.
|
||||
failed |= verify_flyway_index()
|
||||
|
||||
# Make sure we haven't introduced any javascript dependencies.
|
||||
failed |= verify_javascript_deps()
|
||||
|
||||
if failed:
|
||||
sys.exit(1)
|
||||
|
||||
@@ -9,7 +9,7 @@ expected to change.
|
||||
|
||||
## Deployment
|
||||
|
||||
Webapp is deployed with the nomulus default service war to Google App Engine.
|
||||
The webapp is deployed with the nomulus default service war to GKE.
|
||||
During nomulus default service war build task, gradle script triggers the
|
||||
following:
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"/console-api":
|
||||
{
|
||||
"target": "http://localhost:8080",
|
||||
"target": "http://[::1]:8080",
|
||||
"secure": false,
|
||||
"logLevel": "debug",
|
||||
"changeOrigin": true
|
||||
|
||||
@@ -26,6 +26,8 @@ import SecurityComponent from './settings/security/security.component';
|
||||
import { SettingsComponent } from './settings/settings.component';
|
||||
import { SupportComponent } from './support/support.component';
|
||||
import RdapComponent from './settings/rdap/rdap.component';
|
||||
import { HistoryComponent } from './history/history.component';
|
||||
import { PasswordResetVerifyComponent } from './shared/components/passwordReset/passwordResetVerify.component';
|
||||
|
||||
export interface RouteWithIcon extends Route {
|
||||
iconName?: string;
|
||||
@@ -38,6 +40,10 @@ export const PATHS = {
|
||||
};
|
||||
export const routes: RouteWithIcon[] = [
|
||||
{ path: '', redirectTo: '/home', pathMatch: 'full' },
|
||||
{
|
||||
path: PasswordResetVerifyComponent.PATH,
|
||||
component: PasswordResetVerifyComponent,
|
||||
},
|
||||
{
|
||||
path: RegistryLockVerifyComponent.PATH,
|
||||
component: RegistryLockVerifyComponent,
|
||||
@@ -59,13 +65,18 @@ export const routes: RouteWithIcon[] = [
|
||||
title: 'Dashboard',
|
||||
iconName: 'view_comfy_alt',
|
||||
},
|
||||
// { path: 'tlds', component: TldsComponent, title: "TLDs", iconName: "event_list" },
|
||||
{
|
||||
path: DomainListComponent.PATH,
|
||||
component: DomainListComponent,
|
||||
title: 'Domains',
|
||||
iconName: 'view_list',
|
||||
},
|
||||
{
|
||||
path: HistoryComponent.PATH,
|
||||
component: HistoryComponent,
|
||||
// title: 'History',
|
||||
// iconName: 'history',
|
||||
},
|
||||
{
|
||||
path: SettingsComponent.PATH,
|
||||
component: SettingsComponent,
|
||||
|
||||
@@ -56,11 +56,14 @@ import { GlobalLoaderService } from './shared/services/globalLoader.service';
|
||||
import { UserDataService } from './shared/services/userData.service';
|
||||
import { SnackBarModule } from './snackbar.module';
|
||||
import { SupportComponent } from './support/support.component';
|
||||
import { TldsComponent } from './tlds/tlds.component';
|
||||
import { ForceFocusDirective } from './shared/directives/forceFocus.directive';
|
||||
import RdapComponent from './settings/rdap/rdap.component';
|
||||
import RdapEditComponent from './settings/rdap/rdapEdit.component';
|
||||
import { PocReminderComponent } from './shared/components/pocReminder/pocReminder.component';
|
||||
import { PasswordResetVerifyComponent } from './shared/components/passwordReset/passwordResetVerify.component';
|
||||
import { PasswordInputForm } from './shared/components/passwordReset/passwordInputForm.component';
|
||||
import { HistoryComponent } from './history/history.component';
|
||||
import { HistoryListComponent } from './history/historyList.component';
|
||||
|
||||
@NgModule({
|
||||
declarations: [SelectedRegistrarWrapper],
|
||||
@@ -79,15 +82,19 @@ export class SelectedRegistrarModule {}
|
||||
EppPasswordEditComponent,
|
||||
ForceFocusDirective,
|
||||
HeaderComponent,
|
||||
HistoryComponent,
|
||||
HistoryListComponent,
|
||||
HomeComponent,
|
||||
LocationBackDirective,
|
||||
NavigationComponent,
|
||||
NewRegistrarComponent,
|
||||
NotificationsComponent,
|
||||
PasswordInputForm,
|
||||
PasswordResetVerifyComponent,
|
||||
PocReminderComponent,
|
||||
RdapComponent,
|
||||
RdapEditComponent,
|
||||
ReasonDialogComponent,
|
||||
PocReminderComponent,
|
||||
RegistrarComponent,
|
||||
RegistrarDetailsComponent,
|
||||
RegistrarSelectorComponent,
|
||||
@@ -100,7 +107,6 @@ export class SelectedRegistrarModule {}
|
||||
SettingsComponent,
|
||||
SettingsContactComponent,
|
||||
SupportComponent,
|
||||
TldsComponent,
|
||||
UserLevelVisibility,
|
||||
],
|
||||
bootstrap: [AppComponent],
|
||||
|
||||
62
console-webapp/src/app/history/history.component.html
Normal file
62
console-webapp/src/app/history/history.component.html
Normal file
@@ -0,0 +1,62 @@
|
||||
<app-selected-registrar-wrapper>
|
||||
<div class="history-log">
|
||||
<h1 class="mat-headline-4" forceFocus>
|
||||
Registrar Console Activity History
|
||||
</h1>
|
||||
<mat-tab-group
|
||||
[elementId]="getElementIdForUserLog()"
|
||||
class="history-log__tabs"
|
||||
>
|
||||
<mat-tab label="Registrar Activity">
|
||||
<div class="spacer"></div>
|
||||
|
||||
<app-history-list
|
||||
[historyRecords]="historyService.historyRecordsRegistrar()"
|
||||
[isLoading]="isLoading"
|
||||
/>
|
||||
</mat-tab>
|
||||
<mat-tab label="User Activity">
|
||||
<div class="spacer"></div>
|
||||
<form (ngSubmit)="loadHistory()" #form="ngForm">
|
||||
<section>
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>Console User Email: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
id="email"
|
||||
type="email"
|
||||
name="consoleUserEmail"
|
||||
required
|
||||
email
|
||||
[(ngModel)]="consoleUserEmail"
|
||||
#emailControl="ngModel"
|
||||
/>
|
||||
</mat-form-field>
|
||||
</section>
|
||||
<div class="spacer"></div>
|
||||
<button
|
||||
mat-flat-button
|
||||
color="primary"
|
||||
type="submit"
|
||||
aria-label="Search user history"
|
||||
[disabled]="!form.valid"
|
||||
>
|
||||
Search
|
||||
</button>
|
||||
</form>
|
||||
<div class="spacer"></div>
|
||||
<app-history-list
|
||||
[historyRecords]="historyService.historyRecordsUser()"
|
||||
[isLoading]="isLoading"
|
||||
/>
|
||||
</mat-tab>
|
||||
</mat-tab-group>
|
||||
</div>
|
||||
|
||||
<app-history-list
|
||||
[elementId]="getElementIdForUserLog()"
|
||||
[isReverse]="true"
|
||||
[historyRecords]="historyService.historyRecordsUser()"
|
||||
[isLoading]="isLoading"
|
||||
/>
|
||||
</app-selected-registrar-wrapper>
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2017 The Nomulus Authors. All Rights Reserved.
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
@@ -12,5 +12,11 @@
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
@javax.annotation.ParametersAreNonnullByDefault
|
||||
package google.registry.module.frontend;
|
||||
.history-log {
|
||||
font-family: "Roboto", sans-serif;
|
||||
max-width: 760px;
|
||||
|
||||
.spacer {
|
||||
margin: 20px 0;
|
||||
}
|
||||
}
|
||||
80
console-webapp/src/app/history/history.component.ts
Normal file
80
console-webapp/src/app/history/history.component.ts
Normal file
@@ -0,0 +1,80 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Component, effect } from '@angular/core';
|
||||
import { UserDataService } from '../shared/services/userData.service';
|
||||
import { BackendService } from '../shared/services/backend.service';
|
||||
import { RegistrarService } from '../registrar/registrar.service';
|
||||
import { HistoryService } from './history.service';
|
||||
import { MatSnackBar } from '@angular/material/snack-bar';
|
||||
import {
|
||||
GlobalLoader,
|
||||
GlobalLoaderService,
|
||||
} from '../shared/services/globalLoader.service';
|
||||
import { HttpErrorResponse } from '@angular/common/http';
|
||||
import { RESTRICTED_ELEMENTS } from '../shared/directives/userLevelVisiblity.directive';
|
||||
|
||||
@Component({
|
||||
selector: 'app-history',
|
||||
templateUrl: './history.component.html',
|
||||
styleUrls: ['./history.component.scss'],
|
||||
providers: [HistoryService],
|
||||
standalone: false,
|
||||
})
|
||||
export class HistoryComponent implements GlobalLoader {
|
||||
public static PATH = 'history';
|
||||
|
||||
consoleUserEmail: string = '';
|
||||
isLoading: boolean = false;
|
||||
|
||||
constructor(
|
||||
private backendService: BackendService,
|
||||
private registrarService: RegistrarService,
|
||||
protected historyService: HistoryService,
|
||||
protected globalLoader: GlobalLoaderService,
|
||||
protected userDataService: UserDataService,
|
||||
private _snackBar: MatSnackBar
|
||||
) {
|
||||
effect(() => {
|
||||
if (registrarService.registrarId()) {
|
||||
this.loadHistory();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
getElementIdForUserLog() {
|
||||
return RESTRICTED_ELEMENTS.ACTIVITY_PER_USER;
|
||||
}
|
||||
|
||||
loadingTimeout() {
|
||||
this._snackBar.open('Timeout loading records history');
|
||||
}
|
||||
|
||||
loadHistory() {
|
||||
this.globalLoader.startGlobalLoader(this);
|
||||
this.isLoading = true;
|
||||
this.historyService
|
||||
.getHistoryLog(this.registrarService.registrarId(), this.consoleUserEmail)
|
||||
.subscribe({
|
||||
error: (err: HttpErrorResponse) => {
|
||||
this._snackBar.open(err.error || err.message);
|
||||
this.isLoading = false;
|
||||
},
|
||||
next: () => {
|
||||
this.globalLoader.stopGlobalLoader(this);
|
||||
this.isLoading = false;
|
||||
},
|
||||
});
|
||||
}
|
||||
}
|
||||
46
console-webapp/src/app/history/history.service.ts
Normal file
46
console-webapp/src/app/history/history.service.ts
Normal file
@@ -0,0 +1,46 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Injectable, signal } from '@angular/core';
|
||||
import { BackendService } from '../shared/services/backend.service';
|
||||
import { tap } from 'rxjs';
|
||||
|
||||
export interface HistoryRecord {
|
||||
modificationTime: string;
|
||||
type: string;
|
||||
description: string;
|
||||
actingUser: {
|
||||
emailAddress: string;
|
||||
};
|
||||
}
|
||||
|
||||
@Injectable()
|
||||
export class HistoryService {
|
||||
historyRecordsRegistrar = signal<HistoryRecord[]>([]);
|
||||
historyRecordsUser = signal<HistoryRecord[]>([]);
|
||||
|
||||
constructor(private backendService: BackendService) {}
|
||||
|
||||
getHistoryLog(registrarId: string, userEmail?: string) {
|
||||
return this.backendService.getHistoryLog(registrarId, userEmail).pipe(
|
||||
tap((historyRecords: HistoryRecord[]) => {
|
||||
if (userEmail) {
|
||||
this.historyRecordsUser.set(historyRecords);
|
||||
} else {
|
||||
this.historyRecordsRegistrar.set(historyRecords);
|
||||
}
|
||||
})
|
||||
);
|
||||
}
|
||||
}
|
||||
50
console-webapp/src/app/history/historyList.component.html
Normal file
50
console-webapp/src/app/history/historyList.component.html
Normal file
@@ -0,0 +1,50 @@
|
||||
@if (!isLoading && historyRecords.length == 0) {
|
||||
<div class="history-list__no-records">
|
||||
<mat-icon class="history-list__no-records-icon secondary-text"
|
||||
>apps_outage</mat-icon
|
||||
>
|
||||
<h1>No records found</h1>
|
||||
</div>
|
||||
} @else {
|
||||
<mat-card>
|
||||
<mat-card-content>
|
||||
<mat-list role="list">
|
||||
<ng-container *ngFor="let item of historyRecords; let last = last">
|
||||
<mat-list-item class="history-list__item">
|
||||
<mat-icon
|
||||
[ngClass]="getIconClass(item.type)"
|
||||
class="history-list__icon"
|
||||
>
|
||||
{{ getIconForType(item.type) }}
|
||||
</mat-icon>
|
||||
|
||||
<div class="history-list__content">
|
||||
<div class="history-list__description">
|
||||
<span class="history-list__description--main">{{
|
||||
item.type
|
||||
}}</span>
|
||||
<div>
|
||||
<mat-chip
|
||||
*ngIf="parseDescription(item.description).detail"
|
||||
class="history-list__chip"
|
||||
>
|
||||
{{ parseDescription(item.description).detail }}
|
||||
</mat-chip>
|
||||
</div>
|
||||
</div>
|
||||
<div class="history-list__user">
|
||||
<b>User - {{ item.actingUser.emailAddress }}</b>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<span class="history-list__timestamp">
|
||||
{{ item.modificationTime | date : "MMM d, y, h:mm a" }}
|
||||
</span>
|
||||
</mat-list-item>
|
||||
|
||||
<mat-divider *ngIf="!last"></mat-divider>
|
||||
</ng-container>
|
||||
</mat-list>
|
||||
</mat-card-content>
|
||||
</mat-card>
|
||||
}
|
||||
81
console-webapp/src/app/history/historyList.component.scss
Normal file
81
console-webapp/src/app/history/historyList.component.scss
Normal file
@@ -0,0 +1,81 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
.history-list {
|
||||
font-family: "Roboto", sans-serif;
|
||||
&__item {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
// Override default mat-list-item height to fit content
|
||||
height: auto !important;
|
||||
padding: 16px 0;
|
||||
}
|
||||
|
||||
&__no-records {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
flex-direction: column;
|
||||
}
|
||||
&__no-records-icon {
|
||||
width: 4rem;
|
||||
height: 4rem;
|
||||
font-size: 4rem;
|
||||
margin-top: 1.5rem;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
margin-right: 16px;
|
||||
|
||||
&--update {
|
||||
color: #1976d2;
|
||||
}
|
||||
|
||||
&--security {
|
||||
color: #d32f2f;
|
||||
}
|
||||
}
|
||||
|
||||
&__description {
|
||||
&--main {
|
||||
font-size: 1rem;
|
||||
font-weight: 500;
|
||||
color: rgba(0, 0, 0, 0.87);
|
||||
margin-bottom: 1em;
|
||||
}
|
||||
}
|
||||
|
||||
&__content {
|
||||
flex-grow: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 4px;
|
||||
margin-right: 16px;
|
||||
}
|
||||
|
||||
&__chip {
|
||||
margin: 0.5rem 0;
|
||||
}
|
||||
|
||||
&__user {
|
||||
font-size: 0.9rem;
|
||||
color: rgba(0, 0, 0, 0.6);
|
||||
}
|
||||
|
||||
&__timestamp {
|
||||
color: rgba(0, 0, 0, 0.6);
|
||||
white-space: nowrap;
|
||||
text-align: right;
|
||||
}
|
||||
}
|
||||
66
console-webapp/src/app/history/historyList.component.ts
Normal file
66
console-webapp/src/app/history/historyList.component.ts
Normal file
@@ -0,0 +1,66 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { ChangeDetectionStrategy, Component, Input } from '@angular/core';
|
||||
import { HistoryRecord } from './history.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-history-list',
|
||||
templateUrl: './historyList.component.html',
|
||||
styleUrls: ['./historyList.component.scss'],
|
||||
changeDetection: ChangeDetectionStrategy.OnPush,
|
||||
standalone: false,
|
||||
})
|
||||
export class HistoryListComponent {
|
||||
@Input() historyRecords: HistoryRecord[] = [];
|
||||
@Input() isLoading: boolean = false;
|
||||
|
||||
getIconForType(type: string): string {
|
||||
switch (type) {
|
||||
case 'REGISTRAR_UPDATE':
|
||||
return 'edit';
|
||||
case 'REGISTRAR_SECURITY_UPDATE':
|
||||
return 'security';
|
||||
default:
|
||||
return 'history'; // A fallback icon
|
||||
}
|
||||
}
|
||||
|
||||
getIconClass(type: string): string {
|
||||
switch (type) {
|
||||
case 'REGISTRAR_UPDATE':
|
||||
return 'history-log__icon--update';
|
||||
case 'REGISTRAR_SECURITY_UPDATE':
|
||||
return 'history-log__icon--security';
|
||||
default:
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
parseDescription(description: string): {
|
||||
main: string;
|
||||
detail: string | null;
|
||||
} {
|
||||
if (!description) {
|
||||
return { main: 'N/A', detail: null };
|
||||
}
|
||||
const parts = description.split('|');
|
||||
const detail = parts.length > 1 ? parts[1].replace(/_/g, ' ') : parts[0];
|
||||
|
||||
return {
|
||||
main: parts[0],
|
||||
detail: detail,
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -25,7 +25,10 @@ export class RegistrarSelectorComponent {
|
||||
registrarInput = signal<string>(this.registrarService.registrarId());
|
||||
filteredOptions?: string[];
|
||||
allRegistrarIds = computed(() =>
|
||||
this.registrarService.registrars().map((r) => r.registrarId)
|
||||
this.registrarService
|
||||
.registrars()
|
||||
.map((r) => r.registrarId)
|
||||
.sort()
|
||||
);
|
||||
|
||||
constructor(protected registrarService: RegistrarService) {
|
||||
|
||||
@@ -47,9 +47,9 @@ export interface Contact {
|
||||
registrarId?: string;
|
||||
faxNumber?: string;
|
||||
types: Array<contactType>;
|
||||
visibleInWhoisAsAdmin?: boolean;
|
||||
visibleInWhoisAsTech?: boolean;
|
||||
visibleInDomainWhoisAsAbuse?: boolean;
|
||||
visibleInRdapAsAdmin?: boolean;
|
||||
visibleInRdapAsTech?: boolean;
|
||||
visibleInDomainRdapAsAbuse?: boolean;
|
||||
}
|
||||
|
||||
export interface ViewReadyContact extends Contact {
|
||||
|
||||
@@ -57,6 +57,11 @@
|
||||
[(ngModel)]="contactService.contactInEdit.emailAddress"
|
||||
[ngModelOptions]="{ standalone: true }"
|
||||
[disabled]="emailAddressIsDisabled()"
|
||||
[matTooltip]="
|
||||
emailAddressIsDisabled()
|
||||
? 'Reach out to registry customer support to update email address'
|
||||
: ''
|
||||
"
|
||||
/>
|
||||
</mat-form-field>
|
||||
|
||||
@@ -84,6 +89,7 @@
|
||||
<h1>Contact Type</h1>
|
||||
<p class="console-app__contact-required">
|
||||
<mat-icon color="accent">error</mat-icon>Required to select at least one
|
||||
(primary contact can't be updated)
|
||||
</p>
|
||||
<div class="">
|
||||
<ng-container
|
||||
@@ -105,7 +111,7 @@
|
||||
<h1>RDAP Preferences</h1>
|
||||
<div>
|
||||
<mat-checkbox
|
||||
[(ngModel)]="contactService.contactInEdit.visibleInWhoisAsAdmin"
|
||||
[(ngModel)]="contactService.contactInEdit.visibleInRdapAsAdmin"
|
||||
[ngModelOptions]="{ standalone: true }"
|
||||
>Show in Registrar RDAP record as admin contact</mat-checkbox
|
||||
>
|
||||
@@ -113,7 +119,7 @@
|
||||
|
||||
<div>
|
||||
<mat-checkbox
|
||||
[(ngModel)]="contactService.contactInEdit.visibleInWhoisAsTech"
|
||||
[(ngModel)]="contactService.contactInEdit.visibleInRdapAsTech"
|
||||
[ngModelOptions]="{ standalone: true }"
|
||||
>Show in Registrar RDAP record as technical contact</mat-checkbox
|
||||
>
|
||||
@@ -121,7 +127,7 @@
|
||||
|
||||
<div>
|
||||
<mat-checkbox
|
||||
[(ngModel)]="contactService.contactInEdit.visibleInDomainWhoisAsAbuse"
|
||||
[(ngModel)]="contactService.contactInEdit.visibleInDomainRdapAsAbuse"
|
||||
[ngModelOptions]="{ standalone: true }"
|
||||
>Show Phone and Email in Domain RDAP Record as registrar abuse contact
|
||||
(per CL&D requirements)</mat-checkbox
|
||||
@@ -183,24 +189,24 @@
|
||||
<mat-list-item role="listitem">
|
||||
<h2>RDAP Preferences</h2>
|
||||
</mat-list-item>
|
||||
@if(contactService.contactInEdit.visibleInWhoisAsAdmin) {
|
||||
@if(contactService.contactInEdit.visibleInRdapAsAdmin) {
|
||||
<mat-divider></mat-divider>
|
||||
<mat-list-item role="listitem">
|
||||
<span class="console-app__list-value"
|
||||
>Show in Registrar RDAP record as admin contact</span
|
||||
>
|
||||
</mat-list-item>
|
||||
} @if(contactService.contactInEdit.visibleInWhoisAsTech) {
|
||||
} @if(contactService.contactInEdit.visibleInRdapAsTech) {
|
||||
<mat-divider></mat-divider>
|
||||
<mat-list-item
|
||||
role="listitem"
|
||||
*ngIf="contactService.contactInEdit.visibleInWhoisAsTech"
|
||||
*ngIf="contactService.contactInEdit.visibleInRdapAsTech"
|
||||
>
|
||||
<span class="console-app__list-value"
|
||||
>Show in Registrar RDAP record as technical contact</span
|
||||
>
|
||||
</mat-list-item>
|
||||
} @if(contactService.contactInEdit.visibleInDomainWhoisAsAbuse) {
|
||||
} @if(contactService.contactInEdit.visibleInDomainRdapAsAbuse) {
|
||||
<mat-divider></mat-divider>
|
||||
<mat-list-item role="listitem">
|
||||
<span class="console-app__list-value"
|
||||
|
||||
@@ -16,65 +16,22 @@
|
||||
<p class="secondary-text">
|
||||
Passwords must be between 6 and 16 alphanumeric characters
|
||||
</p>
|
||||
<form
|
||||
(ngSubmit)="save()"
|
||||
<password-input-form-component
|
||||
[displayOldPasswordField]="true"
|
||||
[formGroup]="passwordUpdateForm"
|
||||
class="settings-security__edit-password-form"
|
||||
>
|
||||
<div class="settings-security__edit-password-field">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>Old password: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
type="text"
|
||||
formControlName="oldPassword"
|
||||
required
|
||||
autocomplete="current-password"
|
||||
/>
|
||||
<mat-error *ngIf="hasError('oldPassword') as errorText">{{
|
||||
errorText
|
||||
}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
<div class="settings-security__edit-password-field">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>New password: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
type="text"
|
||||
formControlName="newPassword"
|
||||
required
|
||||
autocomplete="new-password"
|
||||
/>
|
||||
<mat-error *ngIf="hasError('newPassword') as errorText">{{
|
||||
errorText
|
||||
}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
<div class="settings-security__edit-password-field">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>Confirm new password: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
type="text"
|
||||
formControlName="newPasswordRepeat"
|
||||
required
|
||||
autocomplete="new-password"
|
||||
/>
|
||||
<mat-error *ngIf="hasError('newPasswordRepeat') as errorText">{{
|
||||
errorText
|
||||
}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
(submitResults)="save($event)"
|
||||
/>
|
||||
@if(userDataService.userData()?.isAdmin) {
|
||||
<div class="settings-security__reset-password-field">
|
||||
<h2>Need to reset your EPP password?</h2>
|
||||
<button
|
||||
mat-flat-button
|
||||
color="primary"
|
||||
[disabled]="!passwordUpdateForm.valid"
|
||||
aria-label="Save epp password update"
|
||||
type="submit"
|
||||
class="settings-security__edit-password-save"
|
||||
aria-label="Reset EPP password via email"
|
||||
(click)="requestEppPasswordReset()"
|
||||
>
|
||||
Save
|
||||
Reset EPP password via email
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
|
||||
@@ -1,16 +1,19 @@
|
||||
.settings-security__edit-password {
|
||||
max-width: 616px;
|
||||
&-field {
|
||||
width: 100%;
|
||||
mat-form-field {
|
||||
margin-bottom: 20px;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
&-form {
|
||||
margin-top: 30px;
|
||||
}
|
||||
&-save {
|
||||
margin-top: 30px;
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
.settings-security {
|
||||
&__reset-password-field {
|
||||
margin-top: 60px;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -14,20 +14,46 @@
|
||||
|
||||
import { HttpErrorResponse } from '@angular/common/http';
|
||||
import { Component } from '@angular/core';
|
||||
import {
|
||||
AbstractControl,
|
||||
FormControl,
|
||||
FormGroup,
|
||||
ValidatorFn,
|
||||
Validators,
|
||||
} from '@angular/forms';
|
||||
import { FormControl, FormGroup, Validators } from '@angular/forms';
|
||||
import { MatSnackBar } from '@angular/material/snack-bar';
|
||||
import { RegistrarService } from 'src/app/registrar/registrar.service';
|
||||
import { SecurityService } from './security.service';
|
||||
import { UserDataService } from 'src/app/shared/services/userData.service';
|
||||
import { MatDialog, MatDialogRef } from '@angular/material/dialog';
|
||||
import { CommonModule } from '@angular/common';
|
||||
import { MaterialModule } from 'src/app/material.module';
|
||||
import { filter, switchMap, take } from 'rxjs';
|
||||
import { BackendService } from 'src/app/shared/services/backend.service';
|
||||
import {
|
||||
PasswordInputForm,
|
||||
PasswordResults,
|
||||
} from 'src/app/shared/components/passwordReset/passwordInputForm.component';
|
||||
|
||||
type errorCode = 'required' | 'maxlength' | 'minlength' | 'passwordsDontMatch';
|
||||
@Component({
|
||||
selector: 'app-reset-epp-password-dialog',
|
||||
template: `
|
||||
<h2 mat-dialog-title>Please confirm the password reset:</h2>
|
||||
<mat-dialog-content>
|
||||
This will send an EPP password reset email to the admin POC.
|
||||
</mat-dialog-content>
|
||||
<mat-dialog-actions>
|
||||
<button mat-button (click)="onCancel()">Cancel</button>
|
||||
<button mat-button color="warn" (click)="onSave()">Confirm</button>
|
||||
</mat-dialog-actions>
|
||||
`,
|
||||
imports: [CommonModule, MaterialModule],
|
||||
})
|
||||
export class ResetEppPasswordComponent {
|
||||
constructor(public dialogRef: MatDialogRef<ResetEppPasswordComponent>) {}
|
||||
|
||||
type errorFriendlyText = { [type in errorCode]: String };
|
||||
onSave(): void {
|
||||
this.dialogRef.close(true);
|
||||
}
|
||||
|
||||
onCancel(): void {
|
||||
this.dialogRef.close(false);
|
||||
}
|
||||
}
|
||||
|
||||
@Component({
|
||||
selector: 'app-epp-password-edit',
|
||||
@@ -36,76 +62,38 @@ type errorFriendlyText = { [type in errorCode]: String };
|
||||
standalone: false,
|
||||
})
|
||||
export default class EppPasswordEditComponent {
|
||||
MIN_MAX_LENGHT = new String(
|
||||
'Passwords must be between 6 and 16 alphanumeric characters'
|
||||
);
|
||||
|
||||
errorTextMap: errorFriendlyText = {
|
||||
required: "This field can't be empty",
|
||||
maxlength: this.MIN_MAX_LENGHT,
|
||||
minlength: this.MIN_MAX_LENGHT,
|
||||
passwordsDontMatch: "Passwords don't match",
|
||||
};
|
||||
|
||||
constructor(
|
||||
public securityService: SecurityService,
|
||||
private _snackBar: MatSnackBar,
|
||||
public registrarService: RegistrarService
|
||||
) {}
|
||||
|
||||
hasError(controlName: string) {
|
||||
const maybeErrors = this.passwordUpdateForm.get(controlName)?.errors;
|
||||
const maybeError =
|
||||
maybeErrors && (Object.keys(maybeErrors)[0] as errorCode);
|
||||
if (maybeError) {
|
||||
return this.errorTextMap[maybeError];
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
newPasswordsMatch: ValidatorFn = (control: AbstractControl) => {
|
||||
if (
|
||||
this.passwordUpdateForm?.get('newPassword')?.value ===
|
||||
this.passwordUpdateForm?.get('newPasswordRepeat')?.value
|
||||
) {
|
||||
this.passwordUpdateForm?.get('newPasswordRepeat')?.setErrors(null);
|
||||
} else {
|
||||
// latest angular just won't detect the error without setTimeout
|
||||
setTimeout(() => {
|
||||
this.passwordUpdateForm
|
||||
?.get('newPasswordRepeat')
|
||||
?.setErrors({ passwordsDontMatch: control.value });
|
||||
});
|
||||
}
|
||||
return null;
|
||||
};
|
||||
static EPP_VALIDATORS = [
|
||||
Validators.required,
|
||||
Validators.minLength(6),
|
||||
Validators.maxLength(16),
|
||||
PasswordInputForm.newPasswordsMatch,
|
||||
];
|
||||
|
||||
passwordUpdateForm = new FormGroup({
|
||||
oldPassword: new FormControl('', [Validators.required]),
|
||||
newPassword: new FormControl('', [
|
||||
Validators.required,
|
||||
Validators.minLength(6),
|
||||
Validators.maxLength(16),
|
||||
this.newPasswordsMatch,
|
||||
]),
|
||||
newPasswordRepeat: new FormControl('', [
|
||||
Validators.required,
|
||||
Validators.minLength(6),
|
||||
Validators.maxLength(16),
|
||||
this.newPasswordsMatch,
|
||||
]),
|
||||
newPassword: new FormControl('', EppPasswordEditComponent.EPP_VALIDATORS),
|
||||
newPasswordRepeat: new FormControl(
|
||||
'',
|
||||
EppPasswordEditComponent.EPP_VALIDATORS
|
||||
),
|
||||
});
|
||||
|
||||
save() {
|
||||
const { oldPassword, newPassword, newPasswordRepeat } =
|
||||
this.passwordUpdateForm.value;
|
||||
if (!oldPassword || !newPassword || !newPasswordRepeat) return;
|
||||
constructor(
|
||||
public registrarService: RegistrarService,
|
||||
public securityService: SecurityService,
|
||||
protected userDataService: UserDataService,
|
||||
private backendService: BackendService,
|
||||
private resetPasswordDialog: MatDialog,
|
||||
private _snackBar: MatSnackBar
|
||||
) {}
|
||||
|
||||
save(passwordResults: PasswordResults) {
|
||||
this.securityService
|
||||
.saveEppPassword({
|
||||
registrarId: this.registrarService.registrarId(),
|
||||
oldPassword,
|
||||
newPassword,
|
||||
newPasswordRepeat,
|
||||
oldPassword: passwordResults.oldPassword!,
|
||||
newPassword: passwordResults.newPassword,
|
||||
newPasswordRepeat: passwordResults.newPasswordRepeat,
|
||||
})
|
||||
.subscribe({
|
||||
complete: () => {
|
||||
@@ -120,4 +108,26 @@ export default class EppPasswordEditComponent {
|
||||
goBack() {
|
||||
this.securityService.isEditingPassword = false;
|
||||
}
|
||||
|
||||
sendEppPasswordResetRequest() {
|
||||
return this.backendService.requestEppPasswordReset(
|
||||
this.registrarService.registrarId()
|
||||
);
|
||||
}
|
||||
|
||||
requestEppPasswordReset() {
|
||||
const dialogRef = this.resetPasswordDialog.open(ResetEppPasswordComponent);
|
||||
dialogRef
|
||||
.afterClosed()
|
||||
.pipe(
|
||||
take(1),
|
||||
filter((result) => !!result)
|
||||
)
|
||||
.pipe(switchMap((_) => this.sendEppPasswordResetRequest()))
|
||||
.subscribe({
|
||||
next: (_) => this.goBack(),
|
||||
error: (err: HttpErrorResponse) =>
|
||||
this._snackBar.open(err.error || err.message),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,63 @@
|
||||
<form
|
||||
(ngSubmit)="save()"
|
||||
[formGroup]="formGroup()!"
|
||||
class="console-app__password-input-form"
|
||||
>
|
||||
@if (displayOldPasswordField()) {
|
||||
<div class="console-app__password-input-form-field">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>Old password: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
type="text"
|
||||
formControlName="oldPassword"
|
||||
required
|
||||
autocomplete="current-password"
|
||||
/>
|
||||
<mat-error *ngIf="hasError('oldPassword') as errorText">{{
|
||||
errorText
|
||||
}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
}
|
||||
<div class="console-app__password-input-form-field">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>New password: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
type="text"
|
||||
formControlName="newPassword"
|
||||
required
|
||||
autocomplete="new-password"
|
||||
/>
|
||||
<mat-error *ngIf="hasError('newPassword') as errorText">{{
|
||||
errorText
|
||||
}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
<div class="console-app__password-input-form-field">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label>Confirm new password: </mat-label>
|
||||
<input
|
||||
matInput
|
||||
type="text"
|
||||
formControlName="newPasswordRepeat"
|
||||
required
|
||||
autocomplete="new-password"
|
||||
/>
|
||||
<mat-error *ngIf="hasError('newPasswordRepeat') as errorText">{{
|
||||
errorText
|
||||
}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
<button
|
||||
mat-flat-button
|
||||
color="primary"
|
||||
[disabled]="!formGroup()?.valid"
|
||||
aria-label="Save new password"
|
||||
type="submit"
|
||||
class="console-app__password-input-form-save"
|
||||
>
|
||||
Save
|
||||
</button>
|
||||
</form>
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 The Nomulus Authors. All Rights Reserved.
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
@@ -12,17 +12,19 @@
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
.console-tlds {
|
||||
&__cards {
|
||||
display: flex;
|
||||
border-top: 1px solid #ddd;
|
||||
padding: 1rem;
|
||||
.console-app__password-input-form {
|
||||
max-width: 450px;
|
||||
&-field {
|
||||
width: 100%;
|
||||
mat-form-field {
|
||||
margin-bottom: 20px;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
&__card {
|
||||
max-width: 300px;
|
||||
&-form {
|
||||
margin-top: 30px;
|
||||
}
|
||||
&__card-links {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
&-save {
|
||||
margin-top: 30px;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,82 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Component, EventEmitter, input, Output } from '@angular/core';
|
||||
import { AbstractControl, FormGroup, ValidatorFn } from '@angular/forms';
|
||||
|
||||
type errorCode = 'required' | 'maxlength' | 'minlength' | 'passwordsDontMatch';
|
||||
|
||||
type errorFriendlyText = { [type in errorCode]: String };
|
||||
|
||||
export interface PasswordResults {
|
||||
oldPassword: string | null;
|
||||
newPassword: string;
|
||||
newPasswordRepeat: string;
|
||||
}
|
||||
|
||||
@Component({
|
||||
selector: 'password-input-form-component',
|
||||
templateUrl: './passwordInputForm.component.html',
|
||||
styleUrls: ['./passwordInputForm.component.scss'],
|
||||
standalone: false,
|
||||
})
|
||||
export class PasswordInputForm {
|
||||
static newPasswordsMatch: ValidatorFn = (control: AbstractControl) => {
|
||||
const parent = control.parent;
|
||||
if (
|
||||
parent?.get('newPassword')?.value ===
|
||||
parent?.get('newPasswordRepeat')?.value
|
||||
) {
|
||||
parent?.get('newPasswordRepeat')?.setErrors(null);
|
||||
} else {
|
||||
// latest angular just won't detect the error without setTimeout
|
||||
setTimeout(() => {
|
||||
parent
|
||||
?.get('newPasswordRepeat')
|
||||
?.setErrors({ passwordsDontMatch: control.value });
|
||||
});
|
||||
}
|
||||
return null;
|
||||
};
|
||||
|
||||
MIN_MAX_LENGTH = 'Passwords must be between 6 and 16 alphanumeric characters';
|
||||
|
||||
errorTextMap: errorFriendlyText = {
|
||||
required: "This field can't be empty",
|
||||
maxlength: this.MIN_MAX_LENGTH,
|
||||
minlength: this.MIN_MAX_LENGTH,
|
||||
passwordsDontMatch: "Passwords don't match",
|
||||
};
|
||||
|
||||
displayOldPasswordField = input<boolean>(false);
|
||||
formGroup = input<FormGroup>();
|
||||
@Output() submitResults = new EventEmitter<PasswordResults>();
|
||||
|
||||
hasError(controlName: string) {
|
||||
const maybeErrors = this.formGroup()!.get(controlName)?.errors;
|
||||
const maybeError =
|
||||
maybeErrors && (Object.keys(maybeErrors)[0] as errorCode);
|
||||
if (maybeError) {
|
||||
return this.errorTextMap[maybeError];
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
save() {
|
||||
const results: PasswordResults = this.formGroup()!.value;
|
||||
if (this.displayOldPasswordField() && !results.oldPassword) return;
|
||||
if (!results.newPassword || !results.newPasswordRepeat) return;
|
||||
this.submitResults.emit(results);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
<p>
|
||||
<button mat-icon-button aria-label="Go home" [routerLink]="['']">
|
||||
<mat-icon>arrow_back</mat-icon>
|
||||
</button>
|
||||
</p>
|
||||
@if (isLoading) {
|
||||
<div class="console-app__password-reset-verify-spinner">
|
||||
<mat-spinner />
|
||||
</div>
|
||||
} @else if (errorMessage) {
|
||||
<h1 class="mat-headline-4">Failure</h1>
|
||||
<div class="console-app__password-reset-content">
|
||||
<div class="console-app__password-reset-subhead">
|
||||
An error occurred: {{ errorMessage }}.<br /><br />Please double-check the
|
||||
verification code and try again.
|
||||
</div>
|
||||
</div>
|
||||
} @else {
|
||||
<div class="console-app__password-reset-verify">
|
||||
<h1 class="mat-headline-4">{{ type }} password reset</h1>
|
||||
<password-input-form-component
|
||||
[displayOldPasswordField]="false"
|
||||
[formGroup]="passwordUpdateForm!"
|
||||
(submitResults)="save($event)"
|
||||
/>
|
||||
</div>
|
||||
}
|
||||
@@ -0,0 +1,110 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { Component } from '@angular/core';
|
||||
import { ActivatedRoute, ParamMap, Router } from '@angular/router';
|
||||
import { HttpErrorResponse } from '@angular/common/http';
|
||||
import { take } from 'rxjs';
|
||||
import { RegistrarService } from 'src/app/registrar/registrar.service';
|
||||
import { BackendService } from '../../services/backend.service';
|
||||
import { FormControl, FormGroup, Validators } from '@angular/forms';
|
||||
import {
|
||||
PasswordInputForm,
|
||||
PasswordResults,
|
||||
} from './passwordInputForm.component';
|
||||
import EppPasswordEditComponent from 'src/app/settings/security/eppPasswordEdit.component';
|
||||
import { MatSnackBar } from '@angular/material/snack-bar';
|
||||
|
||||
export interface PasswordResetVerifyResponse {
|
||||
registrarId: string;
|
||||
type: string;
|
||||
}
|
||||
|
||||
@Component({
|
||||
selector: 'app-password-reset-verify',
|
||||
templateUrl: './passwordResetVerify.component.html',
|
||||
standalone: false,
|
||||
})
|
||||
export class PasswordResetVerifyComponent {
|
||||
public static PATH = 'password-reset-verify';
|
||||
|
||||
REGISTRY_LOCK_PASSWORD_VALIDATORS = [
|
||||
Validators.required,
|
||||
PasswordInputForm.newPasswordsMatch,
|
||||
];
|
||||
|
||||
isLoading = true;
|
||||
type?: string;
|
||||
errorMessage?: string;
|
||||
requestVerificationCode = '';
|
||||
|
||||
passwordUpdateForm: FormGroup<any> | null = null;
|
||||
|
||||
constructor(
|
||||
protected backendService: BackendService,
|
||||
protected registrarService: RegistrarService,
|
||||
private route: ActivatedRoute,
|
||||
private router: Router,
|
||||
private _snackBar: MatSnackBar
|
||||
) {}
|
||||
|
||||
ngOnInit() {
|
||||
this.route.queryParamMap.pipe(take(1)).subscribe((params: ParamMap) => {
|
||||
this.requestVerificationCode =
|
||||
params.get('resetRequestVerificationCode') || '';
|
||||
this.backendService
|
||||
.getPasswordResetInformation(this.requestVerificationCode)
|
||||
.subscribe({
|
||||
error: (err: HttpErrorResponse) => {
|
||||
this.isLoading = false;
|
||||
this.errorMessage = err.error;
|
||||
},
|
||||
next: this.presentData.bind(this),
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
presentData(verificationResponse: PasswordResetVerifyResponse) {
|
||||
this.type = verificationResponse.type === 'EPP' ? 'EPP' : 'Registry lock';
|
||||
this.registrarService.registrarId.set(verificationResponse.registrarId);
|
||||
const validators =
|
||||
verificationResponse.type === 'EPP'
|
||||
? EppPasswordEditComponent.EPP_VALIDATORS
|
||||
: this.REGISTRY_LOCK_PASSWORD_VALIDATORS;
|
||||
|
||||
this.passwordUpdateForm = new FormGroup({
|
||||
newPassword: new FormControl('', validators),
|
||||
newPasswordRepeat: new FormControl('', validators),
|
||||
});
|
||||
this.isLoading = false;
|
||||
}
|
||||
|
||||
save(passwordResults: PasswordResults) {
|
||||
this.backendService
|
||||
.finalizePasswordReset(
|
||||
this.requestVerificationCode,
|
||||
passwordResults.newPassword
|
||||
)
|
||||
.subscribe({
|
||||
error: (err: HttpErrorResponse) => {
|
||||
this.isLoading = false;
|
||||
this.errorMessage = err.error;
|
||||
},
|
||||
next: (_) => {
|
||||
this.router.navigate(['']);
|
||||
this._snackBar.open('Password reset completed successfully');
|
||||
},
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -16,6 +16,7 @@ import { Directive, ElementRef, Input, effect } from '@angular/core';
|
||||
import { UserDataService } from '../services/userData.service';
|
||||
|
||||
export enum RESTRICTED_ELEMENTS {
|
||||
ACTIVITY_PER_USER,
|
||||
REGISTRAR_ELEMENT,
|
||||
OTE,
|
||||
USERS,
|
||||
@@ -28,9 +29,10 @@ export const DISABLED_ELEMENTS_PER_ROLE = {
|
||||
RESTRICTED_ELEMENTS.REGISTRAR_ELEMENT,
|
||||
RESTRICTED_ELEMENTS.OTE,
|
||||
RESTRICTED_ELEMENTS.SUSPEND,
|
||||
RESTRICTED_ELEMENTS.ACTIVITY_PER_USER,
|
||||
],
|
||||
SUPPORT_LEAD: [],
|
||||
SUPPORT_AGENT: [],
|
||||
SUPPORT_AGENT: [RESTRICTED_ELEMENTS.ACTIVITY_PER_USER],
|
||||
};
|
||||
|
||||
@Directive({
|
||||
@@ -40,6 +42,8 @@ export const DISABLED_ELEMENTS_PER_ROLE = {
|
||||
export class UserLevelVisibility {
|
||||
@Input() elementId!: RESTRICTED_ELEMENTS | null;
|
||||
|
||||
@Input() isReverse: boolean = false;
|
||||
|
||||
constructor(
|
||||
private userDataService: UserDataService,
|
||||
private el: ElementRef
|
||||
@@ -56,9 +60,9 @@ export class UserLevelVisibility {
|
||||
// @ts-ignore
|
||||
(DISABLED_ELEMENTS_PER_ROLE[globalRole] || []).includes(this.elementId)
|
||||
) {
|
||||
this.el.nativeElement.style.display = 'none';
|
||||
this.el.nativeElement.style.display = this.isReverse ? '' : 'none';
|
||||
} else {
|
||||
this.el.nativeElement.style.display = '';
|
||||
this.el.nativeElement.style.display = this.isReverse ? 'none' : '';
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -30,6 +30,8 @@ import {
|
||||
import { Contact } from '../../settings/contact/contact.service';
|
||||
import { EppPasswordBackendModel } from '../../settings/security/security.service';
|
||||
import { UserData } from './userData.service';
|
||||
import { PasswordResetVerifyResponse } from '../components/passwordReset/passwordResetVerify.component';
|
||||
import { HistoryRecord } from '../../history/history.service';
|
||||
|
||||
@Injectable()
|
||||
export class BackendService {
|
||||
@@ -122,6 +124,16 @@ export class BackendService {
|
||||
.pipe(catchError((err) => this.errorCatcher<DomainListResult>(err)));
|
||||
}
|
||||
|
||||
getHistoryLog(registrarId: string, userEmail?: string) {
|
||||
return this.http
|
||||
.get<HistoryRecord[]>(
|
||||
userEmail
|
||||
? `/console-api/history?registrarId=${registrarId}&consoleUserEmail=${userEmail}`
|
||||
: `/console-api/history?registrarId=${registrarId}`
|
||||
)
|
||||
.pipe(catchError((err) => this.errorCatcher<HistoryRecord[]>(err)));
|
||||
}
|
||||
|
||||
getRegistrars(): Observable<Registrar[]> {
|
||||
return this.http
|
||||
.get<Registrar[]>('/console-api/registrars')
|
||||
@@ -280,4 +292,37 @@ export class BackendService {
|
||||
`/console-api/registry-lock-verify?lockVerificationCode=${lockVerificationCode}`
|
||||
);
|
||||
}
|
||||
|
||||
requestRegistryLockPasswordReset(
|
||||
registrarId: string,
|
||||
registryLockEmail: string
|
||||
) {
|
||||
return this.http.post('/console-api/password-reset-request', {
|
||||
type: 'REGISTRY_LOCK',
|
||||
registrarId,
|
||||
registryLockEmail,
|
||||
});
|
||||
}
|
||||
|
||||
requestEppPasswordReset(registrarId: string) {
|
||||
return this.http.post('/console-api/password-reset-request', {
|
||||
type: 'EPP',
|
||||
registrarId,
|
||||
});
|
||||
}
|
||||
|
||||
getPasswordResetInformation(
|
||||
verificationCode: string
|
||||
): Observable<PasswordResetVerifyResponse> {
|
||||
return this.http.get<PasswordResetVerifyResponse>(
|
||||
`/console-api/password-reset-verify?resetRequestVerificationCode=${verificationCode}`
|
||||
);
|
||||
}
|
||||
|
||||
finalizePasswordReset(verificationCode: string, newPassword: string) {
|
||||
return this.http.post(
|
||||
`/console-api/password-reset-verify?resetRequestVerificationCode=${verificationCode}`,
|
||||
newPassword
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1 +0,0 @@
|
||||
<div class="console-tlds__cards"></div>
|
||||
@@ -1,38 +0,0 @@
|
||||
// Copyright 2024 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { TldsComponent } from './tlds.component';
|
||||
import { MaterialModule } from '../material.module';
|
||||
|
||||
describe('TldsComponent', () => {
|
||||
let component: TldsComponent;
|
||||
let fixture: ComponentFixture<TldsComponent>;
|
||||
|
||||
beforeEach(async () => {
|
||||
await TestBed.configureTestingModule({
|
||||
imports: [MaterialModule],
|
||||
declarations: [TldsComponent],
|
||||
}).compileComponents();
|
||||
|
||||
fixture = TestBed.createComponent(TldsComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@@ -80,7 +80,15 @@
|
||||
roleToDescription(userDetails().role)
|
||||
}}</span>
|
||||
</mat-list-item>
|
||||
@if (userDetails().password) {
|
||||
@if (userDetails().registryLockEmailAddress) {
|
||||
<mat-divider></mat-divider>
|
||||
<mat-list-item role="listitem">
|
||||
<span class="console-app__list-key">Registry Lock email</span>
|
||||
<span class="console-app__list-value">{{
|
||||
userDetails().registryLockEmailAddress
|
||||
}}</span>
|
||||
</mat-list-item>
|
||||
} @if (userDetails().password) {
|
||||
<mat-divider></mat-divider>
|
||||
<mat-list-item role="listitem">
|
||||
<span class="console-app__list-key">Password</span>
|
||||
|
||||
@@ -35,5 +35,8 @@
|
||||
border: 1px solid #ddd;
|
||||
border-radius: 10px;
|
||||
}
|
||||
.console-app__list-key {
|
||||
width: 160px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,45 +1,57 @@
|
||||
<form (ngSubmit)="saveEdit($event)" #form>
|
||||
<p *ngIf="isNew()">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label
|
||||
>User name prefix:
|
||||
<mat-icon
|
||||
matTooltip="Prefix will be combined with registrar ID to create a unique user name - {prefix}.{registrarId}@registry.google"
|
||||
>help_outline</mat-icon
|
||||
></mat-label
|
||||
>
|
||||
<input
|
||||
matInput
|
||||
minlength="3"
|
||||
maxlength="3"
|
||||
[required]="true"
|
||||
[(ngModel)]="user().emailAddress"
|
||||
[ngModelOptions]="{ standalone: true }"
|
||||
/>
|
||||
</mat-form-field>
|
||||
</p>
|
||||
<p>
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label
|
||||
>User Role:
|
||||
<mat-icon
|
||||
matTooltip="Viewer role doesn't allow making updates; Editor role allows updates, like Contacts delete or SSL certificate change"
|
||||
>help_outline</mat-icon
|
||||
></mat-label
|
||||
>
|
||||
<mat-select [(ngModel)]="user().role" name="userRole">
|
||||
<mat-option value="PRIMARY_CONTACT">Editor</mat-option>
|
||||
<mat-option value="ACCOUNT_MANAGER">Viewer</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
</p>
|
||||
<div class="console-app__user-edit">
|
||||
<form (ngSubmit)="saveEdit($event)" #form>
|
||||
<p *ngIf="isNew()">
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label
|
||||
>User name prefix:
|
||||
<mat-icon
|
||||
matTooltip="Prefix will be combined with registrar ID to create a unique user name - {prefix}.{registrarId}@registry.google"
|
||||
>help_outline</mat-icon
|
||||
></mat-label
|
||||
>
|
||||
<input
|
||||
matInput
|
||||
minlength="3"
|
||||
maxlength="3"
|
||||
[required]="true"
|
||||
[(ngModel)]="user().emailAddress"
|
||||
[ngModelOptions]="{ standalone: true }"
|
||||
/>
|
||||
</mat-form-field>
|
||||
</p>
|
||||
<p>
|
||||
<mat-form-field appearance="outline">
|
||||
<mat-label
|
||||
>User Role:
|
||||
<mat-icon
|
||||
matTooltip="Viewer role doesn't allow making updates; Editor role allows updates, like Contacts delete or SSL certificate change"
|
||||
>help_outline</mat-icon
|
||||
></mat-label
|
||||
>
|
||||
<mat-select [(ngModel)]="user().role" name="userRole">
|
||||
<mat-option value="TECH_CONTACT">Editor</mat-option>
|
||||
<mat-option value="ACCOUNT_MANAGER">Viewer</mat-option>
|
||||
</mat-select>
|
||||
</mat-form-field>
|
||||
</p>
|
||||
<button
|
||||
mat-flat-button
|
||||
color="primary"
|
||||
aria-label="Save user"
|
||||
type="submit"
|
||||
aria-label="Save changes to the user"
|
||||
>
|
||||
Save
|
||||
</button>
|
||||
</form>
|
||||
@if(userDataService.userData()?.isAdmin) {
|
||||
<button
|
||||
mat-flat-button
|
||||
color="primary"
|
||||
aria-label="Save user"
|
||||
type="submit"
|
||||
aria-label="Save changes to the user"
|
||||
aria-label="Reset registry lock password"
|
||||
(click)="requestRegistryLockPasswordReset()"
|
||||
>
|
||||
Save
|
||||
Reset registry lock password
|
||||
</button>
|
||||
</form>
|
||||
}
|
||||
</div>
|
||||
|
||||
@@ -0,0 +1,20 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
.console-app__user-edit {
|
||||
button {
|
||||
display: block;
|
||||
margin-bottom: 5px;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -17,13 +17,56 @@ import {
|
||||
Component,
|
||||
ElementRef,
|
||||
EventEmitter,
|
||||
Inject,
|
||||
input,
|
||||
Output,
|
||||
ViewChild,
|
||||
} from '@angular/core';
|
||||
import { MaterialModule } from '../material.module';
|
||||
import { FormsModule } from '@angular/forms';
|
||||
import { User } from './users.service';
|
||||
import { User, UsersService } from './users.service';
|
||||
import { UserDataService } from '../shared/services/userData.service';
|
||||
import { BackendService } from '../shared/services/backend.service';
|
||||
import { RegistrarService } from '../registrar/registrar.service';
|
||||
import {
|
||||
MAT_DIALOG_DATA,
|
||||
MatDialog,
|
||||
MatDialogRef,
|
||||
} from '@angular/material/dialog';
|
||||
import { filter, switchMap, take } from 'rxjs';
|
||||
import { MatSnackBar } from '@angular/material/snack-bar';
|
||||
import { HttpErrorResponse } from '@angular/common/http';
|
||||
|
||||
@Component({
|
||||
selector: 'app-reset-lock-password-dialog',
|
||||
template: `
|
||||
<h2 mat-dialog-title>Please confirm the password reset:</h2>
|
||||
<mat-dialog-content>
|
||||
This will send a registry lock password reset email to
|
||||
{{ data.registryLockEmailAddress }}.
|
||||
</mat-dialog-content>
|
||||
<mat-dialog-actions>
|
||||
<button mat-button (click)="onCancel()">Cancel</button>
|
||||
<button mat-button color="warn" (click)="onSave()">Confirm</button>
|
||||
</mat-dialog-actions>
|
||||
`,
|
||||
imports: [CommonModule, MaterialModule],
|
||||
})
|
||||
export class ResetRegistryLockPasswordComponent {
|
||||
constructor(
|
||||
public dialogRef: MatDialogRef<ResetRegistryLockPasswordComponent>,
|
||||
@Inject(MAT_DIALOG_DATA)
|
||||
public data: { registryLockEmailAddress: string }
|
||||
) {}
|
||||
|
||||
onSave(): void {
|
||||
this.dialogRef.close(true);
|
||||
}
|
||||
|
||||
onCancel(): void {
|
||||
this.dialogRef.close(false);
|
||||
}
|
||||
}
|
||||
|
||||
@Component({
|
||||
selector: 'app-user-edit-form',
|
||||
@@ -39,12 +82,22 @@ export class UserEditFormComponent {
|
||||
{
|
||||
emailAddress: '',
|
||||
role: 'ACCOUNT_MANAGER',
|
||||
registryLockEmailAddress: '',
|
||||
},
|
||||
{ transform: (user: User) => structuredClone(user) }
|
||||
);
|
||||
|
||||
@Output() onEditComplete = new EventEmitter<User>();
|
||||
|
||||
constructor(
|
||||
protected userDataService: UserDataService,
|
||||
private backendService: BackendService,
|
||||
private resetRegistryLockPasswordDialog: MatDialog,
|
||||
private registrarService: RegistrarService,
|
||||
private usersService: UsersService,
|
||||
private _snackBar: MatSnackBar
|
||||
) {}
|
||||
|
||||
saveEdit(e: SubmitEvent) {
|
||||
e.preventDefault();
|
||||
if (this.form.nativeElement.checkValidity()) {
|
||||
@@ -53,4 +106,34 @@ export class UserEditFormComponent {
|
||||
this.form.nativeElement.reportValidity();
|
||||
}
|
||||
}
|
||||
|
||||
sendRegistryLockPasswordResetRequest() {
|
||||
return this.backendService.requestRegistryLockPasswordReset(
|
||||
this.registrarService.registrarId(),
|
||||
this.user().registryLockEmailAddress!
|
||||
);
|
||||
}
|
||||
|
||||
requestRegistryLockPasswordReset() {
|
||||
const dialogRef = this.resetRegistryLockPasswordDialog.open(
|
||||
ResetRegistryLockPasswordComponent,
|
||||
{
|
||||
data: {
|
||||
registryLockEmailAddress: this.user().registryLockEmailAddress,
|
||||
},
|
||||
}
|
||||
);
|
||||
dialogRef
|
||||
.afterClosed()
|
||||
.pipe(
|
||||
take(1),
|
||||
filter((result) => !!result)
|
||||
)
|
||||
.pipe(switchMap((_) => this.sendRegistryLockPasswordResetRequest()))
|
||||
.subscribe({
|
||||
next: (_) => this.usersService.currentlyOpenUserEmail.set(''),
|
||||
error: (err: HttpErrorResponse) =>
|
||||
this._snackBar.open(err.error || err.message),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,7 +22,6 @@ import { RegistrarService } from '../registrar/registrar.service';
|
||||
import { SnackBarModule } from '../snackbar.module';
|
||||
import { UserDetailsComponent } from './userDetails.component';
|
||||
import { User, UsersService } from './users.service';
|
||||
import { UserDataService } from '../shared/services/userData.service';
|
||||
import { FormsModule } from '@angular/forms';
|
||||
import { UsersListComponent } from './usersList.component';
|
||||
import { MatSelectChange } from '@angular/material/select';
|
||||
@@ -55,7 +54,6 @@ export class UsersComponent {
|
||||
constructor(
|
||||
protected registrarService: RegistrarService,
|
||||
protected usersService: UsersService,
|
||||
private userDataService: UserDataService,
|
||||
private _snackBar: MatSnackBar
|
||||
) {
|
||||
effect(() => {
|
||||
|
||||
@@ -33,6 +33,7 @@ export interface User {
|
||||
emailAddress: string;
|
||||
role: string;
|
||||
password?: string;
|
||||
registryLockEmailAddress?: string;
|
||||
}
|
||||
|
||||
@Injectable()
|
||||
|
||||
@@ -30,7 +30,6 @@ def screenshotsForGoldensDir = "${project.buildDir}/screenshots_for_goldens"
|
||||
def newGoldensDir = "${project.buildDir}/new_golden_images"
|
||||
def goldensDir =
|
||||
"${javaTestDir}/google/registry/webdriver/goldens/chrome-linux"
|
||||
def jsDir = "${project.projectDir}/src/main/javascript"
|
||||
|
||||
// Tests that fail when running Gradle in a docker container, e. g. when
|
||||
// building the release artifacts in Google Cloud Build.
|
||||
@@ -55,9 +54,8 @@ def dockerIncompatibleTestPatterns = [
|
||||
// objects retained by frameworks.
|
||||
// TODO(weiminyu): identify cause and fix offending tests.
|
||||
def fragileTestPatterns = [
|
||||
// Changes cache timeouts and for some reason appears to have contention
|
||||
// with other tests.
|
||||
"google/registry/whois/WhoisCommandFactoryTest.*",
|
||||
// Breaks random other tests when running with standardTests.
|
||||
"google/registry/bsa/UploadBsaUnavailableDomainsActionTest.*",
|
||||
// Currently changes a global configuration parameter that for some reason
|
||||
// results in timestamp inversions for other tests. TODO(mmuller): fix.
|
||||
"google/registry/flows/host/HostInfoFlowTest.*",
|
||||
@@ -112,7 +110,7 @@ configurations {
|
||||
// for details.
|
||||
nomulus_test
|
||||
|
||||
// Exclude non-canonical servlet-api jars. Our AppEngine deployment uses
|
||||
// Exclude non-canonical servlet-api jars. Our deployment uses
|
||||
// javax.servlet:servlet-api:2.5
|
||||
// For reasons we do not understand, marking the following dependencies as
|
||||
// compileOnly instead of compile does not exclude them from runtimeClasspath.
|
||||
@@ -272,7 +270,6 @@ dependencies {
|
||||
testImplementation deps['org.hamcrest:hamcrest']
|
||||
testImplementation deps['org.hamcrest:hamcrest-core']
|
||||
testImplementation deps['org.hamcrest:hamcrest-library']
|
||||
testImplementation deps['junit:junit']
|
||||
testImplementation deps['org.junit.jupiter:junit-jupiter-api']
|
||||
testImplementation deps['org.junit.jupiter:junit-jupiter-engine']
|
||||
testImplementation deps['org.junit.jupiter:junit-jupiter-migrationsupport']
|
||||
@@ -649,23 +646,6 @@ artifacts {
|
||||
nomulus_test testUberJar
|
||||
}
|
||||
|
||||
publishing {
|
||||
repositories {
|
||||
maven {
|
||||
url project.publish_repo
|
||||
}
|
||||
}
|
||||
publications {
|
||||
nomulusTestsPublication(MavenPublication) {
|
||||
groupId 'google.registry'
|
||||
artifactId 'nomulus_test'
|
||||
version project.nomulus_version
|
||||
artifact nomulusFossJar
|
||||
artifact testUberJar
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
task buildToolImage(dependsOn: nomulus, type: Exec) {
|
||||
commandLine 'docker', 'build', '-t', 'nomulus-tool', '.'
|
||||
}
|
||||
|
||||
@@ -4,20 +4,19 @@
|
||||
aopalliance:aopalliance:1.0=annotationProcessor,compileClasspath,deploy_jar,errorprone,nonprodAnnotationProcessor,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,soy,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
args4j:args4j:2.33=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,soy,testCompileClasspath,testRuntimeClasspath
|
||||
com.charleskorn.kaml:kaml:0.20.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.core:jackson-annotations:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.core:jackson-core:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.core:jackson-databind:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.dataformat:jackson-dataformat-toml:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.dataformat:jackson-dataformat-yaml:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.datatype:jackson-datatype-joda:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson:jackson-bom:2.18.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.core:jackson-annotations:2.20-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.core:jackson-core:2.20.0-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.core:jackson-databind:2.20.0-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.dataformat:jackson-dataformat-yaml:2.20.0-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.datatype:jackson-datatype-joda:2.20.0-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.20.0-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml.jackson:jackson-bom:2.20.0-rc1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.fasterxml:classmate:1.5.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.github.ben-manes.caffeine:caffeine:3.0.5=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.github.ben-manes.caffeine:caffeine:3.2.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.docker-java:docker-java-api:3.4.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.docker-java:docker-java-transport-zerodep:3.4.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.docker-java:docker-java-transport:3.4.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.ben-manes.caffeine:caffeine:3.2.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.docker-java:docker-java-api:3.4.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.docker-java:docker-java-transport-zerodep:3.4.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.docker-java:docker-java-transport:3.4.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.jnr:jffi:1.3.13=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.jnr:jnr-a64asm:1.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.github.jnr:jnr-constants:0.10.4=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
@@ -32,85 +31,80 @@ com.google.api-client:google-api-client-jackson2:2.0.1=compileClasspath,nonprodC
|
||||
com.google.api-client:google-api-client-jackson2:2.7.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api-client:google-api-client-java6:2.1.4=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api-client:google-api-client-servlet:2.7.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api-client:google-api-client-servlet:2.7.2=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api-client:google-api-client:2.7.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api-client:google-api-client-servlet:2.8.1=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api-client:google-api-client:2.8.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:gapic-google-cloud-storage-v2:2.44.1-beta=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:gapic-google-cloud-storage-v2:2.50.0=testCompileClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigquerystorage-v1:3.11.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigquerystorage-v1beta1:0.183.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigquerystorage-v1beta2:0.183.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigtable-v2:2.51.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-pubsub-v1:1.118.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-pubsublite-v1:1.15.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-spanner-admin-database-v1:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-spanner-admin-instance-v1:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-spanner-v1:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:gapic-google-cloud-storage-v2:2.55.0=testCompileClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigquerystorage-v1:3.15.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigquerystorage-v1beta1:0.187.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigquerystorage-v1beta2:0.187.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-bigtable-v2:2.60.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-pubsub-v1:1.122.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-pubsublite-v1:1.15.9=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-spanner-admin-database-v1:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-spanner-admin-instance-v1:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-spanner-v1:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-storage-control-v2:2.44.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-storage-v2:2.44.1-beta=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-storage-v2:2.50.0=testCompileClasspath
|
||||
com.google.api.grpc:grpc-google-common-protos:2.50.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1:3.11.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1alpha:3.11.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1beta1:0.183.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1beta2:0.183.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigtable-admin-v2:2.51.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigtable-v2:2.51.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-compute-v1:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-datastore-v1:0.116.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-firestore-v1:3.30.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-monitoring-v3:3.57.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-pubsub-v1:1.118.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-pubsublite-v1:1.15.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:grpc-google-cloud-storage-v2:2.55.0=testCompileClasspath
|
||||
com.google.api.grpc:grpc-google-common-protos:2.58.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1:3.15.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1alpha:3.15.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1beta1:0.187.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1beta2:0.187.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigquerystorage-v1beta:3.15.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigtable-admin-v2:2.60.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-bigtable-v2:2.60.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-compute-v1:1.82.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-datastore-v1:0.120.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-firestore-v1:3.31.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-monitoring-v3:3.65.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-pubsub-v1:1.122.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-pubsublite-v1:1.15.9=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1:2.51.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1:2.59.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1beta1:2.59.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1:2.72.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1beta1:2.72.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1beta2:2.51.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1beta2:2.59.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-spanner-admin-database-v1:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-spanner-admin-instance-v1:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-spanner-v1:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-secretmanager-v1beta2:2.72.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-spanner-admin-database-v1:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-spanner-admin-instance-v1:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-spanner-v1:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-storage-control-v2:2.44.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-storage-v2:2.44.1-beta=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-storage-v2:2.50.0=testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-storage-v2:2.55.0=testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2:2.51.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2:2.59.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2:2.72.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2beta2:0.141.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2beta2:0.149.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2beta2:0.162.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2beta3:0.141.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2beta3:0.149.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-common-protos:2.53.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-common-protos:2.54.1=testCompileClasspath
|
||||
com.google.api.grpc:proto-google-iam-v1:1.45.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-iam-v1:1.48.0=compileClasspath,nonprodCompileClasspath
|
||||
com.google.api.grpc:proto-google-iam-v1:1.49.1=testCompileClasspath
|
||||
com.google.api:api-common:2.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api:api-common:2.46.1=testCompileClasspath
|
||||
com.google.api:gax-grpc:2.59.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api:gax-grpc:2.62.0=compileClasspath,nonprodCompileClasspath
|
||||
com.google.api:gax-grpc:2.63.1=testCompileClasspath
|
||||
com.google.api:gax-httpjson:2.62.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api:gax-httpjson:2.63.1=testCompileClasspath
|
||||
com.google.api:gax:2.62.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api:gax:2.63.1=testCompileClasspath
|
||||
com.google.apis:google-api-services-admin-directory:directory_v1-rev20250217-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-bigquery:v2-rev20241222-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-cloud-tasks-v2beta3:0.162.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api.grpc:proto-google-common-protos:2.60.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-iam-v1:1.53.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api.grpc:proto-google-iam-v1:1.55.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api:api-common:2.52.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api:gax-grpc:2.67.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.api:gax-grpc:2.69.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.api:gax-httpjson:2.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.api:gax:2.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-admin-directory:directory_v1-rev20250804-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-bigquery:v2-rev20250511-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-cloudresourcemanager:v1-rev20240310-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-dataflow:v1b3-rev20250310-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-dns:v1-rev20250227-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-drive:v3-rev20250220-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-gmail:v1-rev20240520-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-dataflow:v1b3-rev20250812-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-dns:v1-rev20250411-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-drive:v3-rev20250723-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-gmail:v1-rev20250630-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-groupssettings:v1-rev20220614-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-healthcare:v1-rev20240130-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-iam:v2-rev20250213-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-iam:v2-rev20250502-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-iamcredentials:v1-rev20211203-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-monitoring:v3-rev20250227-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-monitoring:v3-rev20250731-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-pubsub:v1-rev20220904-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-sheets:v4-rev20250211-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-sqladmin:v1beta4-rev20250205-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-storage:v1-rev20241206-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-storage:v1-rev20250224-2.0.0=testCompileClasspath
|
||||
com.google.auth:google-auth-library-credentials:1.33.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.auth:google-auth-library-oauth2-http:1.33.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-sheets:v4-rev20250616-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-sqladmin:v1beta4-rev20250613-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-storage:v1-rev20250524-2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.apis:google-api-services-storage:v1-rev20250718-2.0.0=testCompileClasspath
|
||||
com.google.auth:google-auth-library-credentials:1.37.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.auth:google-auth-library-oauth2-http:1.37.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.auto.service:auto-service-annotations:1.0.1=errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.google.auto.service:auto-service-annotations:1.1.1=annotationProcessor,compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.auto.service:auto-service:1.1.1=annotationProcessor
|
||||
@@ -121,50 +115,51 @@ com.google.auto:auto-common:1.2.1=annotationProcessor,errorprone,nonprodAnnotati
|
||||
com.google.cloud.bigdataoss:gcsio:2.2.26=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.bigdataoss:util:2.2.26=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.bigtable:bigtable-client-core-config:1.28.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.datastore:datastore-v1-proto-client:2.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.datastore:datastore-v1-proto-client:2.29.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.opentelemetry:detector-resources-support:0.33.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.opentelemetry:exporter-metrics:0.33.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.opentelemetry:shared-resourcemapping:0.33.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud.sql:jdbc-socket-factory-core:1.23.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.sql:postgres-socket-factory:1.23.1=deploy_jar,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-bigquerystorage:3.11.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-bigtable:2.51.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-compute:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core-grpc:2.49.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core-grpc:2.53.1=testCompileClasspath
|
||||
com.google.cloud.sql:jdbc-socket-factory-core:1.25.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud.sql:postgres-socket-factory:1.25.3=deploy_jar,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-bigquerystorage:3.15.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-bigtable:2.60.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-compute:1.82.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core-grpc:2.57.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core-grpc:2.59.0=testCompileClasspath
|
||||
com.google.cloud:google-cloud-core-http:2.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core-http:2.53.1=testCompileClasspath
|
||||
com.google.cloud:google-cloud-core:2.49.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core:2.53.1=testCompileClasspath
|
||||
com.google.cloud:google-cloud-firestore:3.30.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-monitoring:3.57.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core-http:2.59.0=testCompileClasspath
|
||||
com.google.cloud:google-cloud-core:2.57.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-core:2.59.0=testCompileClasspath
|
||||
com.google.cloud:google-cloud-firestore:3.31.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-monitoring:3.65.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-nio:0.127.24=testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-nio:0.127.33=testCompileClasspath
|
||||
com.google.cloud:google-cloud-pubsub:1.136.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-pubsublite:1.15.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-nio:0.128.2=testCompileClasspath
|
||||
com.google.cloud:google-cloud-pubsub:1.140.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-pubsublite:1.15.9=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-secretmanager:2.51.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-secretmanager:2.59.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.cloud:google-cloud-spanner:6.85.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-secretmanager:2.72.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.cloud:google-cloud-spanner:6.95.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-storage-control:2.44.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-storage:2.44.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-storage:2.50.0=testCompileClasspath
|
||||
com.google.cloud:google-cloud-storage:2.55.0=testCompileClasspath
|
||||
com.google.cloud:google-cloud-tasks:2.51.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:google-cloud-tasks:2.59.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.cloud:google-cloud-tasks:2.72.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.cloud:grpc-gcp:1.6.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:libraries-bom:26.48.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.cloud:proto-google-cloud-firestore-bundle-v1:3.30.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.cloud:proto-google-cloud-firestore-bundle-v1:3.31.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.code.findbugs:jsr305:3.0.2=annotationProcessor,checkstyle,compileClasspath,deploy_jar,errorprone,nonprodAnnotationProcessor,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,soy,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.code.gson:gson:2.10.1=soy
|
||||
com.google.code.gson:gson:2.12.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.common.html.types:types:1.0.8=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,soy,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.dagger:dagger-compiler:2.55=annotationProcessor,testAnnotationProcessor
|
||||
com.google.dagger:dagger-spi:2.55=annotationProcessor,testAnnotationProcessor
|
||||
com.google.dagger:dagger:2.55=annotationProcessor,compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.devtools.ksp:symbol-processing-api:2.0.21-1.0.28=annotationProcessor,testAnnotationProcessor
|
||||
com.google.dagger:dagger-compiler:2.57.1=annotationProcessor,testAnnotationProcessor
|
||||
com.google.dagger:dagger-spi:2.57.1=annotationProcessor,testAnnotationProcessor
|
||||
com.google.dagger:dagger:2.57=deploy_jar
|
||||
com.google.dagger:dagger:2.57.1=annotationProcessor,compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.devtools.ksp:symbol-processing-api:2.1.21-2.0.2=annotationProcessor,testAnnotationProcessor
|
||||
com.google.errorprone:error_prone_annotation:2.23.0=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.google.errorprone:error_prone_annotations:2.20.0=soy
|
||||
com.google.errorprone:error_prone_annotations:2.23.0=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.google.errorprone:error_prone_annotations:2.36.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.errorprone:error_prone_annotations:2.41.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.errorprone:error_prone_annotations:2.7.1=checkstyle
|
||||
com.google.errorprone:error_prone_check_api:2.23.0=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.google.errorprone:error_prone_core:2.23.0=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
@@ -181,25 +176,25 @@ com.google.flogger:google-extensions:0.7.4=soy
|
||||
com.google.flogger:google-extensions:0.8=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.googlejavaformat:google-java-format:1.5=annotationProcessor,testAnnotationProcessor
|
||||
com.google.guava:failureaccess:1.0.1=checkstyle,errorprone,nonprodAnnotationProcessor,soy
|
||||
com.google.guava:failureaccess:1.0.2=annotationProcessor,compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.guava:failureaccess:1.0.2=annotationProcessor,testAnnotationProcessor
|
||||
com.google.guava:failureaccess:1.0.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.guava:guava-parent:32.1.1-jre=errorprone,nonprodAnnotationProcessor,soy
|
||||
com.google.guava:guava-testlib:33.3.0-jre=testRuntimeClasspath
|
||||
com.google.guava:guava-testlib:33.4.0-jre=testCompileClasspath
|
||||
com.google.guava:guava-testlib:33.4.8-jre=testCompileClasspath
|
||||
com.google.guava:guava:31.0.1-jre=checkstyle
|
||||
com.google.guava:guava:32.1.1-jre=errorprone,nonprodAnnotationProcessor,soy
|
||||
com.google.guava:guava:33.0.0-jre=annotationProcessor,testAnnotationProcessor
|
||||
com.google.guava:guava:33.4.0-jre=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.guava:guava:33.4.8-jre=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.guava:listenablefuture:9999.0-empty-to-avoid-conflict-with-guava=annotationProcessor,checkstyle,compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.gwt:gwt-user:2.10.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-apache-v2:1.45.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-apache-v2:1.46.3=testCompileClasspath
|
||||
com.google.http-client:google-http-client-apache-v2:2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-appengine:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-appengine:1.46.3=testCompileClasspath
|
||||
com.google.http-client:google-http-client-gson:1.46.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-appengine:1.47.1=testCompileClasspath
|
||||
com.google.http-client:google-http-client-gson:2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-jackson2:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-jackson2:1.46.3=testCompileClasspath
|
||||
com.google.http-client:google-http-client-protobuf:1.45.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client:1.46.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client-jackson2:1.47.1=testCompileClasspath
|
||||
com.google.http-client:google-http-client-protobuf:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.http-client:google-http-client:2.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.inject:guice:5.1.0=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.google.inject:guice:7.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,soy,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.j2objc:j2objc-annotations:1.3=checkstyle
|
||||
@@ -215,13 +210,12 @@ com.google.oauth-client:google-oauth-client-jetty:1.36.0=deploy_jar,nonprodRunti
|
||||
com.google.oauth-client:google-oauth-client-jetty:1.39.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.oauth-client:google-oauth-client-servlet:1.36.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.oauth-client:google-oauth-client-servlet:1.39.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.oauth-client:google-oauth-client:1.37.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
com.google.oauth-client:google-oauth-client:1.39.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
com.google.protobuf:protobuf-java-util:4.29.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.oauth-client:google-oauth-client:1.39.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.protobuf:protobuf-java-util:4.29.4=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.protobuf:protobuf-java:3.19.6=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
com.google.protobuf:protobuf-java:3.21.7=soy
|
||||
com.google.protobuf:protobuf-java:3.25.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.re2j:re2j:1.7=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.protobuf:protobuf-java:3.25.8=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.re2j:re2j:1.8=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.template:soy:2024-02-26=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,soy,testCompileClasspath,testRuntimeClasspath
|
||||
com.google.truth:truth:1.4.4=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.googlecode.json-simple:json-simple:1.1.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
@@ -255,11 +249,12 @@ com.sun.istack:istack-commons-tools:4.1.2=jaxb
|
||||
com.sun.xml.bind.external:relaxng-datatype:4.0.5=jaxb
|
||||
com.sun.xml.bind.external:rngom:4.0.5=jaxb
|
||||
com.sun.xml.dtd-parser:dtd-parser:1.5.1=jaxb
|
||||
com.zaxxer:HikariCP:6.2.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
com.zaxxer:HikariCP:7.0.1=deploy_jar
|
||||
com.zaxxer:HikariCP:7.0.2=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
commons-beanutils:commons-beanutils:1.9.4=checkstyle
|
||||
commons-codec:commons-codec:1.18.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
commons-codec:commons-codec:1.19.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
commons-collections:commons-collections:3.2.2=checkstyle
|
||||
commons-io:commons-io:2.18.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
commons-io:commons-io:2.20.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
commons-logging:commons-logging:1.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
dnsjava:dnsjava:3.6.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
guru.nidi.com.eclipsesource.j2v8:j2v8_linux_x86_64:4.6.0=testRuntimeClasspath
|
||||
@@ -274,37 +269,27 @@ io.apicurio:apicurio-registry-protobuf-schema-utilities:3.0.0.M2=compileClasspat
|
||||
io.github.classgraph:classgraph:4.8.162=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.github.eisop:dataflow-errorprone:3.34.0-eisop1=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
io.github.java-diff-utils:java-diff-utils:4.12=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
io.github.java-diff-utils:java-diff-utils:4.15=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-alts:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-alts:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-api:1.70.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-auth:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-auth:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-census:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-context:1.70.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-core:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-core:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-googleapis:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-grpclb:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-grpclb:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-inprocess:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-inprocess:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-netty-shaded:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-netty-shaded:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-netty:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-opentelemetry:1.67.1=compileClasspath,nonprodCompileClasspath
|
||||
io.grpc:grpc-opentelemetry:1.68.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-opentelemetry:1.70.0=testCompileClasspath
|
||||
io.github.java-diff-utils:java-diff-utils:4.16=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-alts:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-api:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-auth:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-census:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-context:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-core:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-googleapis:1.71.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-grpclb:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-inprocess:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-netty-shaded:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-netty:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-opentelemetry:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-protobuf-lite:1.67.1=compileClasspath,nonprodCompileClasspath
|
||||
io.grpc:grpc-protobuf-lite:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-protobuf:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-protobuf:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-rls:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-services:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-stub:1.69.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-stub:1.70.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
io.grpc:grpc-util:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-xds:1.69.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-protobuf-lite:1.71.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-protobuf:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-rls:1.71.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-services:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-stub:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-util:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.grpc:grpc-xds:1.71.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.netty:netty-buffer:4.1.110.Final=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.netty:netty-codec-http2:4.1.110.Final=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.netty:netty-codec-http:4.1.110.Final=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
@@ -334,38 +319,29 @@ io.opentelemetry.contrib:opentelemetry-gcp-resources:1.37.0-alpha=compileClasspa
|
||||
io.opentelemetry.instrumentation:opentelemetry-grpc-1.6:2.1.0-alpha=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry.instrumentation:opentelemetry-instrumentation-api-incubator:2.1.0-alpha=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry.instrumentation:opentelemetry-instrumentation-api:2.1.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry.semconv:opentelemetry-semconv:1.27.0-alpha=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry.semconv:opentelemetry-semconv:1.28.0-alpha=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-api-incubator:1.45.0-alpha=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-api-incubator:1.46.0-alpha=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-api:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-api:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-api:1.47.0=testCompileClasspath
|
||||
io.opentelemetry.semconv:opentelemetry-semconv:1.29.0-alpha=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-api-incubator:1.42.1-alpha=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-api:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-api:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-bom:1.42.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-context:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-context:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-context:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-exporter-logging:1.46.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-common:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-context:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-context:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-exporter-logging:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-extension-incubator:1.35.0-alpha=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-common:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-common:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-common:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-common:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-common:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-extension-autoconfigure-spi:1.42.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-extension-autoconfigure-spi:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-extension-autoconfigure-spi:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-extension-autoconfigure:1.46.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-logs:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-logs:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-logs:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-metrics:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-metrics:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-metrics:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-trace:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-trace:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-trace:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-sdk:1.45.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk:1.46.0=testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk:1.47.0=testCompileClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-extension-autoconfigure-spi:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-extension-autoconfigure:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-logs:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-logs:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-metrics:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-metrics:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-trace:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk-trace:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk:1.47.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
io.opentelemetry:opentelemetry-sdk:1.53.0=testCompileClasspath,testRuntimeClasspath
|
||||
io.opentelemetry:opentelemetry-semconv:1.26.0-alpha=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
io.outfoxx:swiftpoet:1.3.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
io.perfmark:perfmark-api:0.27.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
@@ -387,10 +363,10 @@ javax.validation:validation-api:1.0.0.GA=compileClasspath,deploy_jar,nonprodComp
|
||||
joda-time:joda-time:2.12.7=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
junit:junit:4.13.2=nonprodCompileClasspath,nonprodRuntimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
net.arnx:nashorn-promise:0.1.1=testRuntimeClasspath
|
||||
net.bytebuddy:byte-buddy-agent:1.15.11=testCompileClasspath,testRuntimeClasspath
|
||||
net.bytebuddy:byte-buddy-agent:1.17.6=testCompileClasspath,testRuntimeClasspath
|
||||
net.bytebuddy:byte-buddy:1.14.12=compileClasspath,nonprodCompileClasspath
|
||||
net.bytebuddy:byte-buddy:1.14.15=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath
|
||||
net.bytebuddy:byte-buddy:1.15.11=testCompileClasspath,testRuntimeClasspath
|
||||
net.bytebuddy:byte-buddy:1.17.6=testCompileClasspath,testRuntimeClasspath
|
||||
net.java.dev.jna:jna:5.13.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
net.ltgt.gradle.incap:incap:0.2=annotationProcessor,testAnnotationProcessor
|
||||
net.sf.saxon:Saxon-HE:10.6=checkstyle
|
||||
@@ -404,33 +380,33 @@ org.apache.arrow:arrow-format:15.0.2=compileClasspath,deploy_jar,nonprodCompileC
|
||||
org.apache.arrow:arrow-memory-core:15.0.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.arrow:arrow-vector:15.0.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.avro:avro:1.11.4=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-model-fn-execution:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-model-job-management:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-model-pipeline:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-model-fn-execution:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-model-job-management:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-model-pipeline:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-core-construction-java:2.54.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-core-java:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-direct-java:2.63.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-google-cloud-dataflow-java:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-java-fn-execution:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-core:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-expansion-service:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-arrow:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-avro:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-google-cloud-platform-core:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-protobuf:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-core-java:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-direct-java:2.67.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-google-cloud-dataflow-java:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-runners-java-fn-execution:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-core:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-expansion-service:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-arrow:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-avro:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-google-cloud-platform-core:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-extensions-protobuf:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-fn-execution:2.54.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-harness:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-io-google-cloud-platform:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-transform-service-launcher:2.63.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-harness:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-io-google-cloud-platform:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-sdks-java-transform-service-launcher:2.67.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-vendor-grpc-1_60_1:0.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-vendor-grpc-1_69_0:0.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.beam:beam-vendor-guava-32_1_2-jre:0.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-compress:1.26.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-csv:1.13.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-exec:1.4.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-csv:1.14.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-exec:1.5.0=testRuntimeClasspath
|
||||
org.apache.commons:commons-lang3:3.14.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath
|
||||
org.apache.commons:commons-lang3:3.17.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-text:1.13.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-lang3:3.18.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.commons:commons-text:1.14.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.ftpserver:ftplet-api:1.2.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.ftpserver:ftpserver-core:1.2.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.httpcomponents:httpclient:4.5.14=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
@@ -440,37 +416,39 @@ org.apache.sshd:sshd-common:2.15.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.sshd:sshd-core:2.15.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.sshd:sshd-scp:2.15.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.sshd:sshd-sftp:2.15.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.tomcat:tomcat-annotations-api:11.0.5=testCompileClasspath,testRuntimeClasspath
|
||||
org.apache.tomcat:tomcat-annotations-api:11.0.10=testCompileClasspath,testRuntimeClasspath
|
||||
org.apiguardian:apiguardian-api:1.1.2=testCompileClasspath
|
||||
org.bouncycastle:bcpg-jdk18on:1.80=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.bouncycastle:bcpkix-jdk18on:1.80=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.bouncycastle:bcprov-jdk18on:1.80=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.bouncycastle:bcutil-jdk18on:1.80=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.checkerframework:checker-compat-qual:2.5.3=compileClasspath,nonprodCompileClasspath,soy,testCompileClasspath
|
||||
org.checkerframework:checker-compat-qual:2.5.5=annotationProcessor,testAnnotationProcessor
|
||||
org.bouncycastle:bcpg-jdk18on:1.81=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.bouncycastle:bcpkix-jdk18on:1.81=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.bouncycastle:bcprov-jdk18on:1.81=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.bouncycastle:bcutil-jdk18on:1.81=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.checkerframework:checker-compat-qual:2.5.3=annotationProcessor,compileClasspath,nonprodCompileClasspath,soy,testAnnotationProcessor,testCompileClasspath
|
||||
org.checkerframework:checker-compat-qual:2.5.6=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.checkerframework:checker-qual:3.12.0=checkstyle
|
||||
org.checkerframework:checker-qual:3.33.0=errorprone,nonprodAnnotationProcessor,soy
|
||||
org.checkerframework:checker-qual:3.41.0=annotationProcessor,testAnnotationProcessor
|
||||
org.checkerframework:checker-qual:3.49.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.checkerframework:checker-qual:3.49.0=compileClasspath,nonprodCompileClasspath,testCompileClasspath
|
||||
org.checkerframework:checker-qual:3.49.3=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.codehaus.mojo:animal-sniffer-annotations:1.24=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.conscrypt:conscrypt-openjdk-uber:2.5.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.angus:angus-activation:2.0.2=deploy_jar,jaxb,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.eclipse.angus:jakarta.mail:2.0.3=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.eclipse.angus:jakarta.mail:2.0.4=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.eclipse.collections:eclipse-collections-api:11.1.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.collections:eclipse-collections:11.1.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty.ee10:jetty-ee10-servlet:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty.ee10:jetty-ee10-webapp:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-ee:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-http:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-io:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-security:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-server:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-session:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-util:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-xml:12.1.0.alpha1=testCompileClasspath,testRuntimeClasspath
|
||||
org.flywaydb:flyway-core:11.4.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.flywaydb:flyway-database-postgresql:11.4.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty.ee10:jetty-ee10-servlet:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty.ee10:jetty-ee10-webapp:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty.ee:jetty-ee-webapp:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-http:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-io:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-security:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-server:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-session:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-util:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.eclipse.jetty:jetty-xml:12.1.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.flywaydb:flyway-core:11.11.1=deploy_jar
|
||||
org.flywaydb:flyway-core:11.11.2=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.flywaydb:flyway-database-postgresql:11.11.1=deploy_jar
|
||||
org.flywaydb:flyway-database-postgresql:11.11.2=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.glassfish.jaxb:codemodel:4.0.5=jaxb
|
||||
org.glassfish.jaxb:jaxb-core:4.0.2=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.glassfish.jaxb:jaxb-core:4.0.5=jaxb
|
||||
@@ -498,6 +476,7 @@ org.javassist:javassist:3.28.0-GA=checkstyle
|
||||
org.jboss.logging:jboss-logging:3.5.0.Final=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.jcommander:jcommander:2.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlin:kotlin-bom:1.4.0=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlin:kotlin-metadata-jvm:2.1.21=annotationProcessor,testAnnotationProcessor
|
||||
org.jetbrains.kotlin:kotlin-reflect:1.6.10=annotationProcessor,testAnnotationProcessor
|
||||
org.jetbrains.kotlin:kotlin-reflect:1.9.20=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlin:kotlin-stdlib-common:1.9.20=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
@@ -506,7 +485,7 @@ org.jetbrains.kotlin:kotlin-stdlib-jdk7:1.9.10=compileClasspath,deploy_jar,nonpr
|
||||
org.jetbrains.kotlin:kotlin-stdlib-jdk8:1.8.0=annotationProcessor,testAnnotationProcessor
|
||||
org.jetbrains.kotlin:kotlin-stdlib-jdk8:1.9.10=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlin:kotlin-stdlib:1.9.20=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlin:kotlin-stdlib:2.0.21=annotationProcessor,testAnnotationProcessor
|
||||
org.jetbrains.kotlin:kotlin-stdlib:2.1.21=annotationProcessor,testAnnotationProcessor
|
||||
org.jetbrains.kotlinx:kotlinx-coroutines-core-jvm:1.5.2=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlinx:kotlinx-coroutines-core:1.5.2=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.jetbrains.kotlinx:kotlinx-datetime-jvm:0.4.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
@@ -515,26 +494,26 @@ org.jetbrains.kotlinx:kotlinx-serialization-core-jvm:1.0.1=deploy_jar,nonprodRun
|
||||
org.jetbrains.kotlinx:kotlinx-serialization-core:1.0.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.jetbrains:annotations:13.0=annotationProcessor,testAnnotationProcessor
|
||||
org.jetbrains:annotations:17.0.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jline:jline:3.29.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.joda:joda-money:2.0.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jline:jline:3.30.5=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.joda:joda-money:2.0.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.json:json:20230618=soy
|
||||
org.json:json:20250107=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jsoup:jsoup:1.19.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jsoup:jsoup:1.21.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.jspecify:jspecify:1.0.0=annotationProcessor,compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testAnnotationProcessor,testCompileClasspath,testRuntimeClasspath
|
||||
org.junit-pioneer:junit-pioneer:2.3.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-api:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-engine:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-migrationsupport:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-params:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-commons:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-engine:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-launcher:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-runner:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-suite-api:1.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-suite-commons:1.12.1=testRuntimeClasspath
|
||||
org.junit:junit-bom:5.12.1=testCompileClasspath,testRuntimeClasspath
|
||||
org.mockito:mockito-core:5.16.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.mockito:mockito-junit-jupiter:5.16.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-api:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-engine:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-migrationsupport:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.jupiter:junit-jupiter-params:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-commons:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-engine:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-launcher:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-runner:1.13.3=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-suite-api:1.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.junit.platform:junit-platform-suite-commons:1.13.4=testRuntimeClasspath
|
||||
org.junit:junit-bom:5.13.4=testCompileClasspath,testRuntimeClasspath
|
||||
org.mockito:mockito-core:5.19.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.mockito:mockito-junit-jupiter:5.19.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.objenesis:objenesis:3.3=testRuntimeClasspath
|
||||
org.ogce:xpp3:1.1.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.opentest4j:opentest4j:1.3.0=testCompileClasspath,testRuntimeClasspath
|
||||
@@ -552,50 +531,58 @@ org.ow2.asm:asm:9.5=soy
|
||||
org.ow2.asm:asm:9.7=jacocoAnt
|
||||
org.ow2.asm:asm:9.7.1=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.pcollections:pcollections:3.1.4=annotationProcessor,errorprone,nonprodAnnotationProcessor,testAnnotationProcessor
|
||||
org.postgresql:postgresql:42.7.5=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.postgresql:postgresql:42.7.7=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.reflections:reflections:0.10.2=checkstyle
|
||||
org.rnorth.duct-tape:duct-tape:1.0.8=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-api:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-chrome-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-chromium-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v131:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v132:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v133:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v85:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-edge-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-firefox-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-http:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-ie-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-java:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-json:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-manager:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-os:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-remote-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-safari-driver:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-support:4.29.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-api:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-chrome-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-chromium-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v137:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v138:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-devtools-v139:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-edge-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-firefox-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-http:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-ie-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-java:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-json:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-manager:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-os:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-remote-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-safari-driver:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.seleniumhq.selenium:selenium-support:4.35.0=testCompileClasspath,testRuntimeClasspath
|
||||
org.slf4j:jcl-over-slf4j:1.7.36=testCompileClasspath,testRuntimeClasspath
|
||||
org.slf4j:jul-to-slf4j:1.7.30=testRuntimeClasspath
|
||||
org.slf4j:slf4j-api:2.0.16=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.slf4j:slf4j-jdk14:2.0.16=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.slf4j:slf4j-api:2.0.17=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.slf4j:slf4j-jdk14:2.0.17=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.snakeyaml:snakeyaml-engine:2.1=deploy_jar,nonprodRuntimeClasspath,runtimeClasspath,testRuntimeClasspath
|
||||
org.testcontainers:database-commons:1.20.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:jdbc:1.20.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:junit-jupiter:1.20.6=testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:postgresql:1.20.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:selenium:1.20.6=testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:testcontainers:1.20.6=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:database-commons:1.21.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:jdbc:1.21.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:junit-jupiter:1.21.3=testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:postgresql:1.21.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:selenium:1.21.3=testCompileClasspath,testRuntimeClasspath
|
||||
org.testcontainers:testcontainers:1.21.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.threeten:threetenbp:1.7.0=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.w3c.css:sac:1.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.webjars.npm:viz.js-graphviz-java:2.1.3=testRuntimeClasspath
|
||||
org.xerial.snappy:snappy-java:1.1.10.4=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.yaml:snakeyaml:2.3=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-api:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-diagram:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-loader:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-postgresql:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-text:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-tools:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-utility:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler:16.25.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
org.yaml:snakeyaml:2.4=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-api:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-api:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-diagram:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-diagram:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-loader:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-loader:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-operations:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-postgresql:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-postgresql:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-text:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-text:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-tools:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-tools:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler-utility:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler-utility:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
us.fatehi:schemacrawler:16.26.3=deploy_jar
|
||||
us.fatehi:schemacrawler:16.27.1=compileClasspath,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
xerces:xmlParserAPIs:2.6.2=compileClasspath,deploy_jar,nonprodCompileClasspath,nonprodRuntimeClasspath,runtimeClasspath,testCompileClasspath,testRuntimeClasspath
|
||||
empty=devtool,nomulus_test
|
||||
|
||||
@@ -28,11 +28,20 @@ import static google.registry.request.RequestParameters.extractRequiredDatetimeP
|
||||
import static google.registry.request.RequestParameters.extractRequiredParameter;
|
||||
import static google.registry.request.RequestParameters.extractSetOfDatetimeParameters;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.google.common.collect.ImmutableSet;
|
||||
import com.google.common.util.concurrent.RateLimiter;
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import dagger.Module;
|
||||
import dagger.Provides;
|
||||
import google.registry.request.HttpException.BadRequestException;
|
||||
import google.registry.request.OptionalJsonPayload;
|
||||
import google.registry.request.Parameter;
|
||||
import jakarta.inject.Named;
|
||||
import jakarta.servlet.http.HttpServletRequest;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
@@ -42,6 +51,8 @@ public class BatchModule {
|
||||
|
||||
public static final String PARAM_FAST = "fast";
|
||||
|
||||
static final int DEFAULT_MAX_QPS = 10;
|
||||
|
||||
@Provides
|
||||
@Parameter("url")
|
||||
static String provideUrl(HttpServletRequest req) {
|
||||
@@ -137,4 +148,50 @@ public class BatchModule {
|
||||
static boolean provideIsFast(HttpServletRequest req) {
|
||||
return extractBooleanParameter(req, PARAM_FAST);
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Parameter("maxQps")
|
||||
static int provideMaxQps(HttpServletRequest req) {
|
||||
return extractOptionalIntParameter(req, "maxQps").orElse(DEFAULT_MAX_QPS);
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Named("standardRateLimiter")
|
||||
static RateLimiter provideStandardRateLimiter(@Parameter("maxQps") int maxQps) {
|
||||
return RateLimiter.create(maxQps);
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Parameter("gainingRegistrarId")
|
||||
static String provideGainingRegistrarId(HttpServletRequest req) {
|
||||
return extractRequiredParameter(req, "gainingRegistrarId");
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Parameter("losingRegistrarId")
|
||||
static String provideLosingRegistrarId(HttpServletRequest req) {
|
||||
return extractRequiredParameter(req, "losingRegistrarId");
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Parameter("bulkTransferDomainNames")
|
||||
static ImmutableList<String> provideBulkTransferDomainNames(
|
||||
Gson gson, @OptionalJsonPayload Optional<JsonElement> optionalJsonElement) {
|
||||
return optionalJsonElement
|
||||
.map(je -> ImmutableList.copyOf(gson.fromJson(je, new TypeToken<List<String>>() {})))
|
||||
.orElseThrow(
|
||||
() -> new BadRequestException("Missing POST body of bulk transfer domain names"));
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Parameter("requestedByRegistrar")
|
||||
static boolean provideRequestedByRegistrar(HttpServletRequest req) {
|
||||
return extractBooleanParameter(req, "requestedByRegistrar");
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Parameter("reason")
|
||||
static String provideReason(HttpServletRequest req) {
|
||||
return extractRequiredParameter(req, "reason");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,242 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package google.registry.batch;
|
||||
|
||||
import static com.google.common.net.MediaType.PLAIN_TEXT_UTF_8;
|
||||
import static google.registry.flows.FlowUtils.marshalWithLenientRetry;
|
||||
import static google.registry.persistence.transaction.TransactionManagerFactory.tm;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_NO_CONTENT;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_OK;
|
||||
import static java.nio.charset.StandardCharsets.US_ASCII;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.google.common.flogger.FluentLogger;
|
||||
import com.google.common.util.concurrent.RateLimiter;
|
||||
import google.registry.flows.EppController;
|
||||
import google.registry.flows.EppRequestSource;
|
||||
import google.registry.flows.PasswordOnlyTransportCredentials;
|
||||
import google.registry.flows.StatelessRequestSessionMetadata;
|
||||
import google.registry.model.ForeignKeyUtils;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.eppcommon.ProtocolDefinition;
|
||||
import google.registry.model.eppcommon.StatusValue;
|
||||
import google.registry.model.eppoutput.EppOutput;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.request.lock.LockHandler;
|
||||
import google.registry.util.DateTimeUtils;
|
||||
import jakarta.inject.Inject;
|
||||
import jakarta.inject.Named;
|
||||
import java.util.Optional;
|
||||
import java.util.concurrent.Callable;
|
||||
import java.util.logging.Level;
|
||||
import org.joda.time.Duration;
|
||||
|
||||
/**
|
||||
* An action that transfers a set of domains from one registrar to another.
|
||||
*
|
||||
* <p>This should be used as part of the BTAPPA (Bulk Transfer After a Partial Portfolio
|
||||
* Acquisition) process in order to transfer a (possibly large) list of domains from one registrar
|
||||
* to another, though it may be used in other situations as well.
|
||||
*
|
||||
* <p>The body of the HTTP post request should be a JSON list of the domains to be transferred.
|
||||
* Because the list of domains to process can be quite large, this action should be called by a tool
|
||||
* that batches the list of domains into reasonable sizes if necessary. The recommended usage path
|
||||
* is to call this through the {@link google.registry.tools.BulkDomainTransferCommand}, which
|
||||
* handles batching and input handling.
|
||||
*
|
||||
* <p>This runs as a single-threaded idempotent action that runs a superuser domain transfer on each
|
||||
* domain to process. We go through the standard EPP process to make sure that we have an accurate
|
||||
* historical representation of events (rather than force-modifying the domains in place).
|
||||
*
|
||||
* <p>Consider passing in an "maxQps" parameter based on the number of domains being transferred,
|
||||
* otherwise the default is {@link BatchModule#DEFAULT_MAX_QPS}.
|
||||
*/
|
||||
@Action(
|
||||
service = Action.Service.BACKEND,
|
||||
path = BulkDomainTransferAction.PATH,
|
||||
method = Action.Method.POST,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class BulkDomainTransferAction implements Runnable {
|
||||
|
||||
public static final String PATH = "/_dr/task/bulkDomainTransfer";
|
||||
|
||||
private static final String SUPERUSER_TRANSFER_XML_FORMAT =
|
||||
"""
|
||||
<epp xmlns="urn:ietf:params:xml:ns:epp-1.0">
|
||||
<command>
|
||||
<transfer op="request">
|
||||
<domain:transfer xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
|
||||
<domain:name>%DOMAIN_NAME%</domain:name>
|
||||
</domain:transfer>
|
||||
</transfer>
|
||||
<extension>
|
||||
<superuser:domainTransferRequest xmlns:superuser="urn:google:params:xml:ns:superuser-1.0">
|
||||
<superuser:renewalPeriod unit="y">0</superuser:renewalPeriod>
|
||||
<superuser:automaticTransferLength>0</superuser:automaticTransferLength>
|
||||
</superuser:domainTransferRequest>
|
||||
<metadata:metadata xmlns:metadata="urn:google:params:xml:ns:metadata-1.0">
|
||||
<metadata:reason>%REASON%</metadata:reason>
|
||||
<metadata:requestedByRegistrar>%REQUESTED_BY_REGISTRAR%</metadata:requestedByRegistrar>
|
||||
</metadata:metadata>
|
||||
</extension>
|
||||
<clTRID>BulkDomainTransferAction</clTRID>
|
||||
</command>
|
||||
</epp>
|
||||
""";
|
||||
|
||||
private static final String LOCK_NAME = "Domain bulk transfer";
|
||||
|
||||
private static final FluentLogger logger = FluentLogger.forEnclosingClass();
|
||||
|
||||
private final EppController eppController;
|
||||
private final LockHandler lockHandler;
|
||||
private final RateLimiter rateLimiter;
|
||||
private final ImmutableList<String> bulkTransferDomainNames;
|
||||
private final String gainingRegistrarId;
|
||||
private final String losingRegistrarId;
|
||||
private final boolean requestedByRegistrar;
|
||||
private final String reason;
|
||||
private final Response response;
|
||||
|
||||
private int successes = 0;
|
||||
private int alreadyTransferred = 0;
|
||||
private int pendingDelete = 0;
|
||||
private int missingDomains = 0;
|
||||
private int errors = 0;
|
||||
|
||||
@Inject
|
||||
BulkDomainTransferAction(
|
||||
EppController eppController,
|
||||
LockHandler lockHandler,
|
||||
@Named("standardRateLimiter") RateLimiter rateLimiter,
|
||||
@Parameter("bulkTransferDomainNames") ImmutableList<String> bulkTransferDomainNames,
|
||||
@Parameter("gainingRegistrarId") String gainingRegistrarId,
|
||||
@Parameter("losingRegistrarId") String losingRegistrarId,
|
||||
@Parameter("requestedByRegistrar") boolean requestedByRegistrar,
|
||||
@Parameter("reason") String reason,
|
||||
Response response) {
|
||||
this.eppController = eppController;
|
||||
this.lockHandler = lockHandler;
|
||||
this.rateLimiter = rateLimiter;
|
||||
this.bulkTransferDomainNames = bulkTransferDomainNames;
|
||||
this.gainingRegistrarId = gainingRegistrarId;
|
||||
this.losingRegistrarId = losingRegistrarId;
|
||||
this.requestedByRegistrar = requestedByRegistrar;
|
||||
this.reason = reason;
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
response.setContentType(PLAIN_TEXT_UTF_8);
|
||||
Callable<Void> runner =
|
||||
() -> {
|
||||
try {
|
||||
runLocked();
|
||||
response.setStatus(SC_OK);
|
||||
} catch (Exception e) {
|
||||
logger.atSevere().withCause(e).log("Errored out during execution.");
|
||||
response.setStatus(SC_INTERNAL_SERVER_ERROR);
|
||||
response.setPayload(String.format("Errored out with cause: %s", e));
|
||||
}
|
||||
return null;
|
||||
};
|
||||
|
||||
if (!lockHandler.executeWithLocks(runner, null, Duration.standardHours(1), LOCK_NAME)) {
|
||||
// Send a 200-series status code to prevent this conflicting action from retrying.
|
||||
response.setStatus(SC_NO_CONTENT);
|
||||
response.setPayload("Could not acquire lock; already running?");
|
||||
}
|
||||
}
|
||||
|
||||
private void runLocked() {
|
||||
logger.atInfo().log("Attempting to transfer %d domains.", bulkTransferDomainNames.size());
|
||||
for (String domainName : bulkTransferDomainNames) {
|
||||
rateLimiter.acquire();
|
||||
tm().transact(() -> runTransferFlowInTransaction(domainName));
|
||||
}
|
||||
|
||||
String msg =
|
||||
String.format(
|
||||
"Finished; %d domains were successfully transferred, %d were previously transferred, %s"
|
||||
+ " were missing domains, %s are pending delete, and %d errored out.",
|
||||
successes, alreadyTransferred, missingDomains, pendingDelete, errors);
|
||||
logger.at(errors + missingDomains == 0 ? Level.INFO : Level.WARNING).log(msg);
|
||||
response.setPayload(msg);
|
||||
}
|
||||
|
||||
private void runTransferFlowInTransaction(String domainName) {
|
||||
if (shouldSkipDomain(domainName)) {
|
||||
return;
|
||||
}
|
||||
String xml =
|
||||
SUPERUSER_TRANSFER_XML_FORMAT
|
||||
.replace("%DOMAIN_NAME%", domainName)
|
||||
.replace("%REASON%", reason)
|
||||
.replace("%REQUESTED_BY_REGISTRAR%", String.valueOf(requestedByRegistrar));
|
||||
EppOutput output =
|
||||
eppController.handleEppCommand(
|
||||
new StatelessRequestSessionMetadata(
|
||||
gainingRegistrarId, ProtocolDefinition.getVisibleServiceExtensionUris()),
|
||||
new PasswordOnlyTransportCredentials(),
|
||||
EppRequestSource.TOOL,
|
||||
false,
|
||||
true,
|
||||
xml.getBytes(US_ASCII));
|
||||
if (output.isSuccess()) {
|
||||
logger.atInfo().log("Successfully transferred domain '%s'.", domainName);
|
||||
successes++;
|
||||
} else {
|
||||
logger.atWarning().log(
|
||||
"Failed transferring domain '%s' with error '%s'.",
|
||||
domainName, new String(marshalWithLenientRetry(output), US_ASCII));
|
||||
errors++;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean shouldSkipDomain(String domainName) {
|
||||
Optional<Domain> maybeDomain =
|
||||
ForeignKeyUtils.loadResource(Domain.class, domainName, tm().getTransactionTime());
|
||||
if (maybeDomain.isEmpty()) {
|
||||
logger.atWarning().log("Domain '%s' was already deleted", domainName);
|
||||
missingDomains++;
|
||||
return true;
|
||||
}
|
||||
Domain domain = maybeDomain.get();
|
||||
String currentRegistrarId = domain.getCurrentSponsorRegistrarId();
|
||||
if (currentRegistrarId.equals(gainingRegistrarId)) {
|
||||
logger.atInfo().log("Domain '%s' was already transferred", domainName);
|
||||
alreadyTransferred++;
|
||||
return true;
|
||||
}
|
||||
if (!currentRegistrarId.equals(losingRegistrarId)) {
|
||||
logger.atWarning().log(
|
||||
"Domain '%s' had unexpected registrar '%s'", domainName, currentRegistrarId);
|
||||
errors++;
|
||||
return true;
|
||||
}
|
||||
if (domain.getStatusValues().contains(StatusValue.PENDING_DELETE)
|
||||
|| !domain.getDeletionTime().equals(DateTimeUtils.END_OF_TIME)) {
|
||||
logger.atWarning().log("Domain '%s' is in PENDING_DELETE", domainName);
|
||||
pendingDelete++;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -20,7 +20,6 @@ import static java.nio.charset.StandardCharsets.UTF_8;
|
||||
|
||||
import com.google.common.flogger.FluentLogger;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.UrlConnectionService;
|
||||
@@ -43,7 +42,7 @@ import javax.net.ssl.HttpsURLConnection;
|
||||
* --service BACKEND -X POST -u '/_dr/task/executeCannedScript}'}
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/executeCannedScript",
|
||||
method = {POST, GET},
|
||||
automaticallyPrintOk = true,
|
||||
|
||||
@@ -27,7 +27,6 @@ import google.registry.model.domain.token.AllocationToken;
|
||||
import google.registry.model.domain.token.BulkPricingPackage;
|
||||
import google.registry.model.registrar.Registrar;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.ui.server.SendEmailUtils;
|
||||
import google.registry.util.Clock;
|
||||
@@ -39,7 +38,10 @@ import org.joda.time.Days;
|
||||
* An action that checks all {@link BulkPricingPackage} objects for compliance with their max create
|
||||
* limit.
|
||||
*/
|
||||
@Action(service = GaeService.BACKEND, path = CheckBulkComplianceAction.PATH, auth = Auth.AUTH_ADMIN)
|
||||
@Action(
|
||||
service = Action.Service.BACKEND,
|
||||
path = CheckBulkComplianceAction.PATH,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class CheckBulkComplianceAction implements Runnable {
|
||||
|
||||
public static final String PATH = "/_dr/task/checkBulkCompliance";
|
||||
|
||||
@@ -43,7 +43,6 @@ import google.registry.config.CredentialModule.ApplicationDefaultCredential;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.Method;
|
||||
import google.registry.request.Action.Service;
|
||||
import google.registry.util.Clock;
|
||||
import google.registry.util.CollectionUtils;
|
||||
import google.registry.util.GoogleCredentialsBundle;
|
||||
@@ -56,8 +55,6 @@ import java.nio.charset.StandardCharsets;
|
||||
import java.util.Arrays;
|
||||
import java.util.Optional;
|
||||
import java.util.Random;
|
||||
import java.util.function.BiConsumer;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Supplier;
|
||||
import org.joda.time.Duration;
|
||||
|
||||
@@ -119,19 +116,13 @@ public class CloudTasksUtils implements Serializable {
|
||||
* <p>For GET requests we add them on to the URL, and for POST requests we add them in the body of
|
||||
* the request.
|
||||
*
|
||||
* <p>The parameters {@code putHeadersFunction} and {@code setBodyFunction} are used so that this
|
||||
* method can be called with either an AppEngine HTTP request or a standard non-AppEngine HTTP
|
||||
* request. The two objects do not have the same methods, but both have ways of setting headers /
|
||||
* body.
|
||||
*
|
||||
* @return the resulting path (unchanged for POST requests, with params added for GET requests)
|
||||
*/
|
||||
private static String processRequestParameters(
|
||||
String path,
|
||||
Method method,
|
||||
Multimap<String, String> params,
|
||||
BiConsumer<String, String> putHeadersFunction,
|
||||
Consumer<ByteString> setBodyFunction) {
|
||||
HttpRequest.Builder requestBuilder) {
|
||||
if (CollectionUtils.isNullOrEmpty(params)) {
|
||||
return path;
|
||||
}
|
||||
@@ -149,8 +140,8 @@ public class CloudTasksUtils implements Serializable {
|
||||
if (method.equals(Method.GET)) {
|
||||
return String.format("%s?%s", path, encodedParams);
|
||||
}
|
||||
putHeadersFunction.accept(HttpHeaders.CONTENT_TYPE, MediaType.FORM_DATA.toString());
|
||||
setBodyFunction.accept(ByteString.copyFrom(encodedParams, StandardCharsets.UTF_8));
|
||||
requestBuilder.putHeaders(HttpHeaders.CONTENT_TYPE, MediaType.FORM_DATA.toString());
|
||||
requestBuilder.setBody(ByteString.copyFrom(encodedParams, StandardCharsets.UTF_8));
|
||||
return path;
|
||||
}
|
||||
|
||||
@@ -161,29 +152,26 @@ public class CloudTasksUtils implements Serializable {
|
||||
* default service account as the principal. That account must have permission to submit tasks to
|
||||
* Cloud Tasks.
|
||||
*
|
||||
* <p>The caller of this method is responsible for passing in the appropriate service based on the
|
||||
* runtime (GAE/GKE). Use the overload that takes an action class if possible.
|
||||
* <p>The caller of this method is responsible for passing in the appropriate service. Use the
|
||||
* overload that takes an action class if possible.
|
||||
*
|
||||
* @param path the relative URI (staring with a slash and ending without one).
|
||||
* @param method the HTTP method to be used for the request.
|
||||
* @param service the GAE/GKE service to route the request to.
|
||||
* @param service the service to route the request to.
|
||||
* @param params a multimap of URL query parameters. Duplicate keys are saved as is, and it is up
|
||||
* to the server to process the duplicate keys.
|
||||
* @return the enqueued task.
|
||||
* @see <a
|
||||
* href=ttps://cloud.google.com/appengine/docs/standard/java/taskqueue/push/creating-tasks#target>Specifyinig
|
||||
* the worker service</a>
|
||||
* @see <a href=https://docs.cloud.google.com/tasks/docs/creating-http-target-tasks#java>Creating
|
||||
* HTTP target tasks</a>
|
||||
*/
|
||||
protected Task createTask(
|
||||
String path, Method method, Service service, Multimap<String, String> params) {
|
||||
String path, Method method, Action.Service service, Multimap<String, String> params) {
|
||||
checkArgument(
|
||||
path != null && !path.isEmpty() && path.charAt(0) == '/',
|
||||
"The path must start with a '/'.");
|
||||
HttpRequest.Builder requestBuilder =
|
||||
HttpRequest.newBuilder().setHttpMethod(HttpMethod.valueOf(method.name()));
|
||||
path =
|
||||
processRequestParameters(
|
||||
path, method, params, requestBuilder::putHeaders, requestBuilder::setBody);
|
||||
path = processRequestParameters(path, method, params, requestBuilder);
|
||||
OidcToken.Builder oidcTokenBuilder =
|
||||
OidcToken.newBuilder()
|
||||
.setServiceAccountEmail(credential.serviceAccount())
|
||||
@@ -205,16 +193,15 @@ public class CloudTasksUtils implements Serializable {
|
||||
* Cloud Tasks.
|
||||
*
|
||||
* <p>Prefer this overload over the one where the path and service are explicitly defined, as this
|
||||
* class will automatically determine the service to use based on the action and the runtime.
|
||||
* class will automatically determine the service to use based on the action.
|
||||
*
|
||||
* @param actionClazz the action class to run, must be annotated with {@link Action}.
|
||||
* @param method the HTTP method to be used for the request.
|
||||
* @param params a multimap of URL query parameters. Duplicate keys are saved as is, and it is up
|
||||
* to the server to process the duplicate keys.
|
||||
* @return the enqueued task.
|
||||
* @see <a
|
||||
* href=ttps://cloud.google.com/appengine/docs/standard/java/taskqueue/push/creating-tasks#target>Specifyinig
|
||||
* the worker service</a>
|
||||
* @see <a href=https://docs.cloud.google.com/tasks/docs/creating-http-target-tasks#java>Creating
|
||||
* HTTP target tasks</a>
|
||||
*/
|
||||
public Task createTask(
|
||||
Class<? extends Runnable> actionClazz, Method method, Multimap<String, String> params) {
|
||||
@@ -231,32 +218,29 @@ public class CloudTasksUtils implements Serializable {
|
||||
method,
|
||||
actionClazz.getSimpleName(),
|
||||
allowedMethods);
|
||||
Service service =
|
||||
RegistryEnvironment.isOnJetty() ? Action.ServiceGetter.get(action) : action.service();
|
||||
return createTask(path, method, service, params);
|
||||
return createTask(path, method, action.service(), params);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a {@link Task} to be enqueued with a random delay up to {@code jitterSeconds}.
|
||||
*
|
||||
* <p>The caller of this method is responsible for passing in the appropriate service based on the
|
||||
* runtime (GAE/GKE). Use the overload that takes an action class if possible.
|
||||
* <p>The caller of this method is responsible for passing in the appropriate service. Use the
|
||||
* overload that takes an action class if possible.
|
||||
*
|
||||
* @param path the relative URI (staring with a slash and ending without one).
|
||||
* @param method the HTTP method to be used for the request.
|
||||
* @param service the GAE/GKE service to route the request to.
|
||||
* @param service the service to route the request to.
|
||||
* @param params a multimap of URL query parameters. Duplicate keys are saved as is, and it is up
|
||||
* to the server to process the duplicate keys.
|
||||
* @param jitterSeconds the number of seconds that a task is randomly delayed up to.
|
||||
* @return the enqueued task.
|
||||
* @see <a
|
||||
* href=ttps://cloud.google.com/appengine/docs/standard/java/taskqueue/push/creating-tasks#target>Specifyinig
|
||||
* the worker service</a>
|
||||
* @see <a href=https://docs.cloud.google.com/tasks/docs/creating-http-target-tasks#java>Creating
|
||||
* HTTP target tasks</a>
|
||||
*/
|
||||
public Task createTaskWithJitter(
|
||||
String path,
|
||||
Method method,
|
||||
Service service,
|
||||
Action.Service service,
|
||||
Multimap<String, String> params,
|
||||
Optional<Integer> jitterSeconds) {
|
||||
if (jitterSeconds.isEmpty() || jitterSeconds.get() <= 0) {
|
||||
@@ -274,7 +258,7 @@ public class CloudTasksUtils implements Serializable {
|
||||
* Create a {@link Task} to be enqueued with a random delay up to {@code jitterSeconds}.
|
||||
*
|
||||
* <p>Prefer this overload over the one where the path and service are explicitly defined, as this
|
||||
* class will automatically determine the service to use based on the action and the runtime.
|
||||
* class will automatically determine the service to use based on the action.
|
||||
*
|
||||
* @param actionClazz the action class to run, must be annotated with {@link Action}.
|
||||
* @param method the HTTP method to be used for the request.
|
||||
@@ -282,9 +266,8 @@ public class CloudTasksUtils implements Serializable {
|
||||
* to the server to process the duplicate keys.
|
||||
* @param jitterSeconds the number of seconds that a task is randomly delayed up to.
|
||||
* @return the enqueued task.
|
||||
* @see <a
|
||||
* href=ttps://cloud.google.com/appengine/docs/standard/java/taskqueue/push/creating-tasks#target>Specifyinig
|
||||
* the worker service</a>
|
||||
* @see <a href=https://docs.cloud.google.com/tasks/docs/creating-http-target-tasks#java>Creating
|
||||
* HTTP target tasks</a>
|
||||
*/
|
||||
public Task createTaskWithJitter(
|
||||
Class<? extends Runnable> actionClazz,
|
||||
@@ -297,9 +280,7 @@ public class CloudTasksUtils implements Serializable {
|
||||
"Action class %s is not annotated with @Action",
|
||||
actionClazz.getSimpleName());
|
||||
String path = action.path();
|
||||
Service service =
|
||||
RegistryEnvironment.isOnJetty() ? Action.ServiceGetter.get(action) : action.service();
|
||||
return createTaskWithJitter(path, method, service, params, jitterSeconds);
|
||||
return createTaskWithJitter(path, method, action.service(), params, jitterSeconds);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -307,19 +288,18 @@ public class CloudTasksUtils implements Serializable {
|
||||
*
|
||||
* @param path the relative URI (staring with a slash and ending without one).
|
||||
* @param method the HTTP method to be used for the request.
|
||||
* @param service the GAE/GKE service to route the request to.
|
||||
* @param service the service to route the request to.
|
||||
* @param params a multimap of URL query parameters. Duplicate keys are saved as is, and it is up
|
||||
* to the server to process the duplicate keys.
|
||||
* @param delay the amount of time that a task needs to be delayed for.
|
||||
* @return the enqueued task.
|
||||
* @see <a
|
||||
* href=ttps://cloud.google.com/appengine/docs/standard/java/taskqueue/push/creating-tasks#target>Specifyinig
|
||||
* the worker service</a>
|
||||
* @see <a href=https://docs.cloud.google.com/tasks/docs/creating-http-target-tasks#java>Creating
|
||||
* HTTP target tasks</a>
|
||||
*/
|
||||
private Task createTaskWithDelay(
|
||||
String path,
|
||||
Method method,
|
||||
Service service,
|
||||
Action.Service service,
|
||||
Multimap<String, String> params,
|
||||
Duration delay) {
|
||||
if (delay.isEqual(Duration.ZERO)) {
|
||||
@@ -335,7 +315,7 @@ public class CloudTasksUtils implements Serializable {
|
||||
* Create a {@link Task} to be enqueued with delay of {@code duration}.
|
||||
*
|
||||
* <p>Prefer this overload over the one where the path and service are explicitly defined, as this
|
||||
* class will automatically determine the service to use based on the action and the runtime.
|
||||
* class will automatically determine the service to use based on the action.
|
||||
*
|
||||
* @param actionClazz the action class to run, must be annotated with {@link Action}.
|
||||
* @param method the HTTP method to be used for the request.
|
||||
@@ -343,9 +323,8 @@ public class CloudTasksUtils implements Serializable {
|
||||
* to the server to process the duplicate keys.
|
||||
* @param delay the amount of time that a task needs to be delayed for.
|
||||
* @return the enqueued task.
|
||||
* @see <a
|
||||
* href=ttps://cloud.google.com/appengine/docs/standard/java/taskqueue/push/creating-tasks#target>Specifyinig
|
||||
* the worker service</a>
|
||||
* @see <a href=https://docs.cloud.google.com/tasks/docs/creating-http-target-tasks#java>Creating
|
||||
* HTTP target tasks</a>
|
||||
*/
|
||||
public Task createTaskWithDelay(
|
||||
Class<? extends Runnable> actionClazz,
|
||||
@@ -354,9 +333,7 @@ public class CloudTasksUtils implements Serializable {
|
||||
Duration delay) {
|
||||
Action action = getAction(actionClazz);
|
||||
String path = action.path();
|
||||
Service service =
|
||||
RegistryEnvironment.isOnJetty() ? Action.ServiceGetter.get(action) : action.service();
|
||||
return createTaskWithDelay(path, method, service, params, delay);
|
||||
return createTaskWithDelay(path, method, action.service(), params, delay);
|
||||
}
|
||||
|
||||
private static Action getAction(Class<? extends Runnable> actionClazz) {
|
||||
|
||||
@@ -37,7 +37,6 @@ import google.registry.model.eppcommon.ProtocolDefinition;
|
||||
import google.registry.model.eppoutput.EppOutput;
|
||||
import google.registry.persistence.transaction.QueryComposer.Comparator;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.request.lock.LockHandler;
|
||||
@@ -68,7 +67,7 @@ import org.joda.time.Duration;
|
||||
* this action runs, thus alerting us that human action is needed to correctly process the delete.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = DeleteExpiredDomainsAction.PATH,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class DeleteExpiredDomainsAction implements Runnable {
|
||||
|
||||
@@ -37,7 +37,6 @@ import google.registry.model.reporting.HistoryEntry;
|
||||
import google.registry.model.reporting.HistoryEntryDao;
|
||||
import google.registry.persistence.VKey;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.Clock;
|
||||
@@ -55,7 +54,7 @@ import jakarta.inject.Inject;
|
||||
* production.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/deleteLoadTestData",
|
||||
method = POST,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
|
||||
@@ -42,7 +42,6 @@ import google.registry.model.domain.Domain;
|
||||
import google.registry.model.domain.DomainHistory;
|
||||
import google.registry.model.tld.Tld.TldType;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.RegistryEnvironment;
|
||||
@@ -59,7 +58,7 @@ import org.joda.time.Duration;
|
||||
* billing events, along with their ForeignKeyDomainIndex entities.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/deleteProberData",
|
||||
method = POST,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
|
||||
@@ -35,7 +35,6 @@ import google.registry.model.billing.BillingEvent;
|
||||
import google.registry.model.billing.BillingRecurrence;
|
||||
import google.registry.model.common.Cursor;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
@@ -51,7 +50,7 @@ import org.joda.time.DateTime;
|
||||
* BillingRecurrence} billing events into synthetic {@link BillingEvent} events.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/expandBillingRecurrences",
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class ExpandBillingRecurrencesAction implements Runnable {
|
||||
|
||||
@@ -15,7 +15,6 @@
|
||||
package google.registry.batch;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkArgument;
|
||||
import static com.google.common.collect.ImmutableSet.toImmutableSet;
|
||||
import static google.registry.persistence.transaction.TransactionManagerFactory.tm;
|
||||
import static google.registry.request.Action.Method.POST;
|
||||
import static google.registry.tools.LockOrUnlockDomainCommand.REGISTRY_LOCK_STATUSES;
|
||||
@@ -30,12 +29,9 @@ import google.registry.groups.GmailClient;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.domain.RegistryLock;
|
||||
import google.registry.model.eppcommon.StatusValue;
|
||||
import google.registry.model.registrar.Registrar;
|
||||
import google.registry.model.registrar.RegistrarPoc;
|
||||
import google.registry.model.tld.RegistryLockDao;
|
||||
import google.registry.persistence.VKey;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
@@ -50,7 +46,7 @@ import org.joda.time.Duration;
|
||||
|
||||
/** Task that re-locks a previously-Registry-Locked domain after a predetermined period of time. */
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = RelockDomainAction.PATH,
|
||||
method = POST,
|
||||
automaticallyPrintOk = true,
|
||||
@@ -70,12 +66,14 @@ public class RelockDomainAction implements Runnable {
|
||||
"""
|
||||
The domain %s was successfully re-locked.
|
||||
|
||||
Please contact support at %s if you have any questions.""";
|
||||
Please contact support at %s if you have any questions.\
|
||||
""";
|
||||
private static final String RELOCK_NON_RETRYABLE_FAILURE_EMAIL_TEMPLATE =
|
||||
"""
|
||||
There was an error when automatically re-locking %s. Error message: %s
|
||||
|
||||
Please contact support at %s if you have any questions.""";
|
||||
Please contact support at %s if you have any questions.\
|
||||
""";
|
||||
private static final String RELOCK_TRANSIENT_FAILURE_EMAIL_TEMPLATE =
|
||||
"There was an unexpected error when automatically re-locking %s. We will continue retrying "
|
||||
+ "the lock for five hours. Please contact support at %s if you have any questions";
|
||||
@@ -114,11 +112,11 @@ public class RelockDomainAction implements Runnable {
|
||||
public void run() {
|
||||
/* We wish to manually control our retry behavior, in order to limit the number of retries
|
||||
* and/or notify registrars / support only after a certain number of retries, or only
|
||||
* with a certain type of failure. AppEngine will automatically retry on any non-2xx status
|
||||
* with a certain type of failure. Cloud Tasks will automatically retry on any non-2xx status
|
||||
* code, so return SC_NO_CONTENT (204) by default to avoid this auto-retry.
|
||||
*
|
||||
* See https://cloud.google.com/appengine/docs/standard/java/taskqueue/push/retrying-tasks
|
||||
* for more details on retry behavior. */
|
||||
* See https://docs.cloud.google.com/tasks/docs/configuring-queues#retry for more details on
|
||||
* retry behavior. */
|
||||
response.setStatus(SC_NO_CONTENT);
|
||||
response.setContentType(MediaType.PLAIN_TEXT_UTF_8);
|
||||
tm().transact(this::relockDomain);
|
||||
@@ -171,7 +169,7 @@ public class RelockDomainAction implements Runnable {
|
||||
domainLockUtils.administrativelyApplyLock(
|
||||
oldLock.getDomainName(),
|
||||
oldLock.getRegistrarId(),
|
||||
oldLock.getRegistrarPocId(),
|
||||
oldLock.getRegistryLockEmail(),
|
||||
oldLock.isSuperuser());
|
||||
logger.atInfo().log("Re-locked domain %s.", oldLock.getDomainName());
|
||||
response.setStatus(SC_OK);
|
||||
@@ -221,7 +219,7 @@ public class RelockDomainAction implements Runnable {
|
||||
EmailMessage.newBuilder()
|
||||
.setBody(body)
|
||||
.setSubject(String.format("Error re-locking domain %s", oldLock.getDomainName()))
|
||||
.setRecipients(getEmailRecipients(oldLock.getRegistrarId()))
|
||||
.setRecipients(ImmutableSet.of(getEmailRecipient(oldLock)))
|
||||
.build());
|
||||
}
|
||||
|
||||
@@ -250,7 +248,7 @@ public class RelockDomainAction implements Runnable {
|
||||
EmailMessage.newBuilder()
|
||||
.setBody(body)
|
||||
.setSubject(String.format("Successful re-lock of domain %s", oldLock.getDomainName()))
|
||||
.setRecipients(getEmailRecipients(oldLock.getRegistrarId()))
|
||||
.setRecipients(ImmutableSet.of(getEmailRecipient(oldLock)))
|
||||
.build());
|
||||
}
|
||||
|
||||
@@ -261,7 +259,7 @@ public class RelockDomainAction implements Runnable {
|
||||
// For an unexpected failure, notify both the lock-enabled contacts and our alerting email
|
||||
ImmutableSet<InternetAddress> allRecipients =
|
||||
new ImmutableSet.Builder<InternetAddress>()
|
||||
.addAll(getEmailRecipients(oldLock.getRegistrarId()))
|
||||
.add(getEmailRecipient(oldLock))
|
||||
.add(alertRecipientAddress)
|
||||
.build();
|
||||
gmailClient.sendEmail(
|
||||
@@ -281,31 +279,12 @@ public class RelockDomainAction implements Runnable {
|
||||
.build());
|
||||
}
|
||||
|
||||
private ImmutableSet<InternetAddress> getEmailRecipients(String registrarId) {
|
||||
Registrar registrar =
|
||||
Registrar.loadByRegistrarIdCached(registrarId)
|
||||
.orElseThrow(
|
||||
() ->
|
||||
new IllegalStateException(String.format("Unknown registrar %s", registrarId)));
|
||||
|
||||
ImmutableSet<String> registryLockEmailAddresses =
|
||||
registrar.getContacts().stream()
|
||||
.filter(RegistrarPoc::isRegistryLockAllowed)
|
||||
.map(RegistrarPoc::getRegistryLockEmailAddress)
|
||||
.filter(Optional::isPresent)
|
||||
.map(Optional::get)
|
||||
.collect(toImmutableSet());
|
||||
|
||||
ImmutableSet.Builder<InternetAddress> builder = new ImmutableSet.Builder<>();
|
||||
// can't use streams due to the 'throws' in the InternetAddress constructor
|
||||
for (String registryLockEmailAddress : registryLockEmailAddresses) {
|
||||
try {
|
||||
builder.add(new InternetAddress(registryLockEmailAddress));
|
||||
} catch (AddressException e) {
|
||||
// This shouldn't stop any other emails going out, so swallow it
|
||||
logger.atWarning().log("Invalid email address '%s'.", registryLockEmailAddress);
|
||||
}
|
||||
private InternetAddress getEmailRecipient(RegistryLock lock) {
|
||||
try {
|
||||
return new InternetAddress(lock.getRegistryLockEmail());
|
||||
} catch (AddressException e) {
|
||||
// this really shouldn't happen
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
return builder.build();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,238 @@
|
||||
// Copyright 2025 The Nomulus Authors. All Rights Reserved.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package google.registry.batch;
|
||||
|
||||
import static com.google.common.net.MediaType.PLAIN_TEXT_UTF_8;
|
||||
import static google.registry.flows.FlowUtils.marshalWithLenientRetry;
|
||||
import static google.registry.persistence.transaction.TransactionManagerFactory.tm;
|
||||
import static google.registry.util.DateTimeUtils.END_OF_TIME;
|
||||
import static google.registry.util.ResourceUtils.readResourceUtf8;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_NO_CONTENT;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_OK;
|
||||
import static java.nio.charset.StandardCharsets.US_ASCII;
|
||||
|
||||
import com.google.common.base.Ascii;
|
||||
import com.google.common.collect.ImmutableMap;
|
||||
import com.google.common.collect.ImmutableSet;
|
||||
import com.google.common.flogger.FluentLogger;
|
||||
import com.google.common.util.concurrent.RateLimiter;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.flows.EppController;
|
||||
import google.registry.flows.EppRequestSource;
|
||||
import google.registry.flows.PasswordOnlyTransportCredentials;
|
||||
import google.registry.flows.StatelessRequestSessionMetadata;
|
||||
import google.registry.model.contact.Contact;
|
||||
import google.registry.model.domain.DesignatedContact;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.eppcommon.ProtocolDefinition;
|
||||
import google.registry.model.eppoutput.EppOutput;
|
||||
import google.registry.persistence.VKey;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.request.lock.LockHandler;
|
||||
import jakarta.inject.Inject;
|
||||
import jakarta.inject.Named;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.Callable;
|
||||
import java.util.logging.Level;
|
||||
import javax.annotation.Nullable;
|
||||
import org.joda.time.Duration;
|
||||
|
||||
/**
|
||||
* An action that removes all contacts from all active (non-deleted) domains.
|
||||
*
|
||||
* <p>This implements part 1 of phase 3 of the Minimum Dataset migration, wherein we remove all uses
|
||||
* of contact objects in preparation for later removing all contact data from the system.
|
||||
*
|
||||
* <p>This runs as a singly threaded, resumable action that loads batches of domains still
|
||||
* containing contacts, and runs a superuser domain update on each one to remove the contacts,
|
||||
* leaving behind a record recording that update.
|
||||
*/
|
||||
@Action(
|
||||
service = Action.Service.BACKEND,
|
||||
path = RemoveAllDomainContactsAction.PATH,
|
||||
method = Action.Method.POST,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class RemoveAllDomainContactsAction implements Runnable {
|
||||
|
||||
public static final String PATH = "/_dr/task/removeAllDomainContacts";
|
||||
private static final String LOCK_NAME = "Remove all domain contacts";
|
||||
private static final String CONTACT_FMT = "<domain:contact type=\"%s\">%s</domain:contact>";
|
||||
|
||||
private static final FluentLogger logger = FluentLogger.forEnclosingClass();
|
||||
private final EppController eppController;
|
||||
private final String registryAdminClientId;
|
||||
private final LockHandler lockHandler;
|
||||
private final RateLimiter rateLimiter;
|
||||
private final Response response;
|
||||
private final String updateDomainXml;
|
||||
private int successes = 0;
|
||||
private int failures = 0;
|
||||
|
||||
private static final int BATCH_SIZE = 10000;
|
||||
|
||||
@Inject
|
||||
RemoveAllDomainContactsAction(
|
||||
EppController eppController,
|
||||
@Config("registryAdminClientId") String registryAdminClientId,
|
||||
LockHandler lockHandler,
|
||||
@Named("standardRateLimiter") RateLimiter rateLimiter,
|
||||
Response response) {
|
||||
this.eppController = eppController;
|
||||
this.registryAdminClientId = registryAdminClientId;
|
||||
this.lockHandler = lockHandler;
|
||||
this.rateLimiter = rateLimiter;
|
||||
this.response = response;
|
||||
this.updateDomainXml =
|
||||
readResourceUtf8(RemoveAllDomainContactsAction.class, "domain_remove_contacts.xml");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
response.setContentType(PLAIN_TEXT_UTF_8);
|
||||
Callable<Void> runner =
|
||||
() -> {
|
||||
try {
|
||||
runLocked();
|
||||
response.setStatus(SC_OK);
|
||||
} catch (Exception e) {
|
||||
logger.atSevere().withCause(e).log("Errored out during execution.");
|
||||
response.setStatus(SC_INTERNAL_SERVER_ERROR);
|
||||
response.setPayload(String.format("Errored out with cause: %s", e));
|
||||
}
|
||||
return null;
|
||||
};
|
||||
|
||||
if (!lockHandler.executeWithLocks(runner, null, Duration.standardHours(1), LOCK_NAME)) {
|
||||
// Send a 200-series status code to prevent this conflicting action from retrying.
|
||||
response.setStatus(SC_NO_CONTENT);
|
||||
response.setPayload("Could not acquire lock; already running?");
|
||||
}
|
||||
}
|
||||
|
||||
private void runLocked() {
|
||||
logger.atInfo().log("Removing contacts on all active domains.");
|
||||
|
||||
List<String> domainRepoIdsBatch;
|
||||
do {
|
||||
domainRepoIdsBatch =
|
||||
tm().<List<String>>transact(
|
||||
() ->
|
||||
tm().getEntityManager()
|
||||
.createQuery(
|
||||
"""
|
||||
SELECT repoId FROM Domain WHERE deletionTime = :end_of_time AND NOT (
|
||||
adminContact IS NULL AND billingContact IS NULL
|
||||
AND registrantContact IS NULL AND techContact IS NULL)
|
||||
""")
|
||||
.setParameter("end_of_time", END_OF_TIME)
|
||||
.setMaxResults(BATCH_SIZE)
|
||||
.getResultList());
|
||||
|
||||
for (String domainRepoId : domainRepoIdsBatch) {
|
||||
rateLimiter.acquire();
|
||||
runDomainUpdateFlow(domainRepoId);
|
||||
}
|
||||
} while (!domainRepoIdsBatch.isEmpty());
|
||||
String msg =
|
||||
String.format(
|
||||
"Finished; %d domains were successfully updated and %d errored out.",
|
||||
successes, failures);
|
||||
logger.at(failures == 0 ? Level.INFO : Level.WARNING).log(msg);
|
||||
response.setPayload(msg);
|
||||
}
|
||||
|
||||
private void runDomainUpdateFlow(String repoId) {
|
||||
// Create a new transaction that the flow's execution will be enlisted in that loads the domain
|
||||
// transactionally. This way we can ensure that nothing else has modified the domain in question
|
||||
// in the intervening period since the query above found it. If a single domain update fails
|
||||
// permanently, log it and move on to not block processing all the other domains.
|
||||
try {
|
||||
boolean success = tm().transact(() -> runDomainUpdateFlowInner(repoId));
|
||||
if (success) {
|
||||
successes++;
|
||||
} else {
|
||||
failures++;
|
||||
}
|
||||
} catch (Throwable t) {
|
||||
logger.atWarning().withCause(t).log(
|
||||
"Failed updating domain with repoId %s; skipping.", repoId);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs the actual domain update flow and returns whether the contact removals were successful.
|
||||
*/
|
||||
private boolean runDomainUpdateFlowInner(String repoId) {
|
||||
Domain domain = tm().loadByKey(VKey.create(Domain.class, repoId));
|
||||
if (!domain.getDeletionTime().equals(END_OF_TIME)) {
|
||||
// Domain has been deleted since the action began running; nothing further to be
|
||||
// done here.
|
||||
logger.atInfo().log("Nothing to process for deleted domain '%s'.", domain.getDomainName());
|
||||
return false;
|
||||
}
|
||||
logger.atInfo().log("Attempting to remove contacts on domain '%s'.", domain.getDomainName());
|
||||
|
||||
StringBuilder sb = new StringBuilder();
|
||||
ImmutableMap<VKey<? extends Contact>, Contact> contacts =
|
||||
tm().loadByKeys(
|
||||
domain.getContacts().stream()
|
||||
.map(DesignatedContact::getContactKey)
|
||||
.collect(ImmutableSet.toImmutableSet()));
|
||||
|
||||
// Collect all the (non-registrant) contacts referenced by the domain and compile an EPP XML
|
||||
// string that removes each one.
|
||||
for (DesignatedContact designatedContact : domain.getContacts()) {
|
||||
@Nullable Contact contact = contacts.get(designatedContact.getContactKey());
|
||||
if (contact == null) {
|
||||
logger.atWarning().log(
|
||||
"Domain '%s' referenced contact with repo ID '%s' that couldn't be" + " loaded.",
|
||||
domain.getDomainName(), designatedContact.getContactKey().getKey());
|
||||
continue;
|
||||
}
|
||||
sb.append(
|
||||
String.format(
|
||||
CONTACT_FMT,
|
||||
Ascii.toLowerCase(designatedContact.getType().name()),
|
||||
contact.getContactId()))
|
||||
.append("\n");
|
||||
}
|
||||
|
||||
String compiledXml =
|
||||
updateDomainXml
|
||||
.replace("%DOMAIN%", domain.getDomainName())
|
||||
.replace("%CONTACTS%", sb.toString());
|
||||
EppOutput output =
|
||||
eppController.handleEppCommand(
|
||||
new StatelessRequestSessionMetadata(
|
||||
registryAdminClientId, ProtocolDefinition.getVisibleServiceExtensionUris()),
|
||||
new PasswordOnlyTransportCredentials(),
|
||||
EppRequestSource.BACKEND,
|
||||
false,
|
||||
true,
|
||||
compiledXml.getBytes(US_ASCII));
|
||||
if (output.isSuccess()) {
|
||||
logger.atInfo().log(
|
||||
"Successfully removed contacts from domain '%s'.", domain.getDomainName());
|
||||
} else {
|
||||
logger.atWarning().log(
|
||||
"Failed removing contacts from domain '%s' with error %s.",
|
||||
domain.getDomainName(), new String(marshalWithLenientRetry(output), US_ASCII));
|
||||
}
|
||||
return output.isSuccess();
|
||||
}
|
||||
}
|
||||
@@ -28,7 +28,6 @@ import com.google.common.flogger.FluentLogger;
|
||||
import com.google.common.net.MediaType;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
@@ -54,7 +53,7 @@ import jakarta.inject.Inject;
|
||||
* <p>This runs the {@link google.registry.beam.resave.ResaveAllEppResourcesPipeline}.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = ResaveAllEppResourcesPipelineAction.PATH,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class ResaveAllEppResourcesPipelineAction implements Runnable {
|
||||
|
||||
@@ -25,7 +25,6 @@ import com.google.common.flogger.FluentLogger;
|
||||
import google.registry.model.EppResource;
|
||||
import google.registry.persistence.VKey;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Action.Method;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
@@ -40,7 +39,7 @@ import org.joda.time.DateTime;
|
||||
* <p>{@link EppResource}s will be projected forward to the current time.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = ResaveEntityAction.PATH,
|
||||
auth = Auth.AUTH_ADMIN,
|
||||
method = Method.POST)
|
||||
|
||||
@@ -35,7 +35,6 @@ import google.registry.model.registrar.Registrar;
|
||||
import google.registry.model.registrar.RegistrarPoc;
|
||||
import google.registry.model.registrar.RegistrarPoc.Type;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.EmailMessage;
|
||||
@@ -50,7 +49,7 @@ import org.joda.time.format.DateTimeFormatter;
|
||||
|
||||
/** An action that sends notification emails to registrars whose certificates are expiring soon. */
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = SendExpiringCertificateNotificationEmailAction.PATH,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class SendExpiringCertificateNotificationEmailAction implements Runnable {
|
||||
@@ -275,7 +274,7 @@ public class SendExpiringCertificateNotificationEmailAction implements Runnable
|
||||
*/
|
||||
@VisibleForTesting
|
||||
ImmutableSet<InternetAddress> getEmailAddresses(Registrar registrar, Type contactType) {
|
||||
ImmutableSortedSet<RegistrarPoc> contacts = registrar.getContactsOfType(contactType);
|
||||
ImmutableSortedSet<RegistrarPoc> contacts = registrar.getPocsOfType(contactType);
|
||||
ImmutableSet.Builder<InternetAddress> recipientEmails = new ImmutableSet.Builder<>();
|
||||
for (RegistrarPoc contact : contacts) {
|
||||
try {
|
||||
|
||||
@@ -30,7 +30,6 @@ import google.registry.beam.wipeout.WipeOutContactHistoryPiiPipeline;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.model.contact.ContactHistory;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
@@ -49,7 +48,7 @@ import org.joda.time.DateTime;
|
||||
* time.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = WipeOutContactHistoryPiiAction.PATH,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
public class WipeOutContactHistoryPiiAction implements Runnable {
|
||||
|
||||
@@ -40,8 +40,6 @@ public class RegistryPipelineWorkerInitializer implements JvmInitializer {
|
||||
|
||||
@Override
|
||||
public void beforeProcessing(PipelineOptions options) {
|
||||
// TODO(b/416299900): remove next line after GAE is removed.
|
||||
System.setProperty("google.registry.jetty", "true");
|
||||
RegistryPipelineOptions registryOptions = options.as(RegistryPipelineOptions.class);
|
||||
RegistryEnvironment environment = registryOptions.getRegistryEnvironment();
|
||||
if (environment == null || environment.equals(RegistryEnvironment.UNITTEST)) {
|
||||
|
||||
@@ -184,10 +184,10 @@ public class RdePipeline implements Serializable {
|
||||
private final CloudTasksUtils cloudTasksUtils;
|
||||
private final RdeMarshaller marshaller;
|
||||
|
||||
// Registrars to be excluded from data escrow. Not including the sandbox-only OTE type so that
|
||||
// if sneaks into production we would get an extra signal.
|
||||
// Registrars to be excluded from data escrow (i.e. all registrar types that have a null IANA
|
||||
// identifier and thus would not be valid according to the RDE schema).
|
||||
private static final ImmutableSet<Type> IGNORED_REGISTRAR_TYPES =
|
||||
Sets.immutableEnumSet(Registrar.Type.MONITORING, Registrar.Type.TEST);
|
||||
Sets.immutableEnumSet(Registrar.Type.MONITORING, Registrar.Type.OTE, Registrar.Type.TEST);
|
||||
|
||||
private static final FluentLogger logger = FluentLogger.forEnclosingClass();
|
||||
|
||||
|
||||
@@ -279,20 +279,6 @@ public class BigqueryConnection implements AutoCloseable {
|
||||
private TableReference getTableReference() {
|
||||
return table.getTableReference().clone();
|
||||
}
|
||||
|
||||
/** Returns a string representation of the TableReference for the wrapped table. */
|
||||
public String getStringReference() {
|
||||
return tableReferenceToString(table.getTableReference());
|
||||
}
|
||||
|
||||
/** Returns a string representation of the given TableReference. */
|
||||
private static String tableReferenceToString(TableReference tableRef) {
|
||||
return String.format(
|
||||
"%s:%s.%s",
|
||||
tableRef.getProjectId(),
|
||||
tableRef.getDatasetId(),
|
||||
tableRef.getTableId());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -398,29 +384,12 @@ public class BigqueryConnection implements AutoCloseable {
|
||||
}
|
||||
|
||||
/**
|
||||
* Starts an asynchronous query job to dump the results of the specified query into a local
|
||||
* ImmutableTable object, row-keyed by the row number (indexed from 1), column-keyed by the
|
||||
* TableFieldSchema for that column, and with the value object as the cell value. Note that null
|
||||
* values will not actually be null, but they can be checked for using Data.isNull().
|
||||
* Dumps the results of the specified query into a local ImmutableTable object, row-keyed by the
|
||||
* row number (indexed from 1), column-keyed by the TableFieldSchema for that column, and with the
|
||||
* value object as the cell value.
|
||||
*
|
||||
* <p>Returns a ListenableFuture that holds the ImmutableTable on success.
|
||||
*/
|
||||
public ListenableFuture<ImmutableTable<Integer, TableFieldSchema, Object>>
|
||||
queryToLocalTable(String querySql) {
|
||||
Job job = new Job()
|
||||
.setConfiguration(new JobConfiguration()
|
||||
.setQuery(new JobConfigurationQuery()
|
||||
.setQuery(querySql)
|
||||
.setDefaultDataset(getDataset())));
|
||||
return transform(runJobToCompletion(job), this::getQueryResults, directExecutor());
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the result of calling queryToLocalTable, but synchronously to avoid spawning new
|
||||
* background threads, which App Engine doesn't support.
|
||||
*
|
||||
* @see <a href="https://cloud.google.com/appengine/docs/standard/java/runtime#Threads">App Engine
|
||||
* Runtime</a>
|
||||
* <p>Note that null values will not actually be null, but they can be checked for using
|
||||
* Data.isNull()
|
||||
*/
|
||||
public ImmutableTable<Integer, TableFieldSchema, Object> queryToLocalTableSync(String querySql) {
|
||||
Job job = new Job()
|
||||
@@ -634,10 +603,6 @@ public class BigqueryConnection implements AutoCloseable {
|
||||
});
|
||||
}
|
||||
|
||||
private ListenableFuture<Job> runJobToCompletion(final Job job) {
|
||||
return service.submit(() -> runJob(job, null));
|
||||
}
|
||||
|
||||
/** Helper that returns true if a dataset with this name exists. */
|
||||
public boolean checkDatasetExists(String datasetName) throws IOException {
|
||||
try {
|
||||
@@ -676,14 +641,6 @@ public class BigqueryConnection implements AutoCloseable {
|
||||
.setDatasetId(getDatasetId());
|
||||
}
|
||||
|
||||
/** Returns table reference with the projectId and datasetId filled out for you. */
|
||||
public TableReference getTable(String tableName) {
|
||||
return new TableReference()
|
||||
.setProjectId(getProjectId())
|
||||
.setDatasetId(getDatasetId())
|
||||
.setTableId(tableName);
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper that creates a dataset with this name if it doesn't already exist, and returns true if
|
||||
* creation took place.
|
||||
|
||||
@@ -71,9 +71,7 @@ class BsaDiffCreator {
|
||||
Optional<String> previousJobName = schedule.latestCompleted().map(CompletedJob::jobName);
|
||||
/*
|
||||
* Memory usage is a concern when creating a diff, when the newest download needs to be held in
|
||||
* memory in its entirety. The top-grade AppEngine VM has 3GB of memory, leaving less than 1.5GB
|
||||
* to application memory footprint after subtracting overheads due to copying garbage collection
|
||||
* and non-heap data etc. Assuming 400K labels, each of which on average included in 5 orders,
|
||||
* memory in its entirety. Assuming 400K labels, each of which on average included in 5 orders,
|
||||
* the memory footprint is at least 300MB when loaded into a Hashset-backed Multimap (64-bit
|
||||
* JVM, with 12-byte object header, 16-byte array header, and 16-byte alignment).
|
||||
*
|
||||
|
||||
@@ -41,7 +41,6 @@ import google.registry.bsa.persistence.DownloadScheduler;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.model.tld.Tlds;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.Clock;
|
||||
@@ -51,7 +50,7 @@ import java.util.Optional;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
@Action(
|
||||
service = GaeService.BSA,
|
||||
service = Action.Service.BACKEND,
|
||||
path = BsaDownloadAction.PATH,
|
||||
method = {GET, POST},
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
|
||||
@@ -31,7 +31,6 @@ import google.registry.bsa.persistence.RefreshScheduler;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.model.tld.Tlds;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.BatchedStreams;
|
||||
@@ -42,7 +41,7 @@ import java.util.stream.Stream;
|
||||
import org.joda.time.Duration;
|
||||
|
||||
@Action(
|
||||
service = GaeService.BSA,
|
||||
service = Action.Service.BACKEND,
|
||||
path = BsaRefreshAction.PATH,
|
||||
method = {GET, POST},
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
|
||||
@@ -28,7 +28,6 @@ import static google.registry.bsa.persistence.Queries.queryMissedRegisteredUnblo
|
||||
import static google.registry.bsa.persistence.Queries.queryUnblockableDomainByLabels;
|
||||
import static google.registry.model.tld.Tld.isEnrolledWithBsa;
|
||||
import static google.registry.model.tld.Tlds.getTldEntitiesOfType;
|
||||
import static google.registry.persistence.transaction.TransactionManagerFactory.replicaTm;
|
||||
import static google.registry.request.Action.Method.GET;
|
||||
import static google.registry.request.Action.Method.POST;
|
||||
import static google.registry.util.BatchedStreams.toBatches;
|
||||
@@ -53,9 +52,7 @@ import google.registry.model.ForeignKeyUtils;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.tld.Tld;
|
||||
import google.registry.model.tld.Tld.TldType;
|
||||
import google.registry.persistence.VKey;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.Clock;
|
||||
@@ -68,7 +65,7 @@ import org.joda.time.Duration;
|
||||
|
||||
/** Validates the BSA data in the database against the most recent block lists. */
|
||||
@Action(
|
||||
service = GaeService.BSA,
|
||||
service = Action.Service.BACKEND,
|
||||
path = BsaValidateAction.PATH,
|
||||
method = {GET, POST},
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
@@ -185,8 +182,8 @@ public class BsaValidateAction implements Runnable {
|
||||
ImmutableList<UnblockableDomain> batch;
|
||||
do {
|
||||
batch = Queries.batchReadUnblockableDomains(lastRead, transactionBatchSize);
|
||||
ImmutableMap<String, VKey<Domain>> activeDomains =
|
||||
ForeignKeyUtils.load(
|
||||
ImmutableMap<String, Domain> activeDomains =
|
||||
ForeignKeyUtils.loadResources(
|
||||
Domain.class,
|
||||
batch.stream().map(UnblockableDomain::domainName).collect(toImmutableList()),
|
||||
clock.nowUtc());
|
||||
@@ -201,7 +198,7 @@ public class BsaValidateAction implements Runnable {
|
||||
}
|
||||
|
||||
Optional<String> verifyDomainStillUnblockableWithReason(
|
||||
UnblockableDomain domain, ImmutableMap<String, VKey<Domain>> activeDomains) {
|
||||
UnblockableDomain domain, ImmutableMap<String, Domain> activeDomains) {
|
||||
DateTime now = clock.nowUtc();
|
||||
boolean isRegistered = activeDomains.containsKey(domain.domainName());
|
||||
boolean isReserved = isReservedDomain(domain.domainName(), now);
|
||||
@@ -215,10 +212,12 @@ public class BsaValidateAction implements Runnable {
|
||||
if (Objects.equals(expectedReason, domain.reason())) {
|
||||
return Optional.empty();
|
||||
}
|
||||
if (isRegistered || domain.reason().equals(Reason.REGISTERED)) {
|
||||
if (isStalenessAllowed(isRegistered, activeDomains.get(domain.domainName()))) {
|
||||
// Registered name still reported with other reasons: Don't report if registration is recent.
|
||||
// Note that staleness is not tolerated if deregistered name is still reported as registered:
|
||||
// in this case we do not have the VKey on hand, and it is not worth the effort to find it
|
||||
// out.
|
||||
if (isRegistered && isStalenessAllowed(activeDomains.get(domain.domainName()))) {
|
||||
return Optional.empty();
|
||||
}
|
||||
}
|
||||
return Optional.of(
|
||||
String.format(
|
||||
@@ -228,15 +227,8 @@ public class BsaValidateAction implements Runnable {
|
||||
domain.reason()));
|
||||
}
|
||||
|
||||
boolean isStalenessAllowed(boolean isNewDomain, VKey<Domain> domainVKey) {
|
||||
Domain domain = bsaQuery(() -> replicaTm().loadByKey(domainVKey));
|
||||
var now = clock.nowUtc();
|
||||
if (isNewDomain) {
|
||||
return domain.getCreationTime().plus(maxStaleness).isAfter(now);
|
||||
} else {
|
||||
return domain.getDeletionTime().isBefore(now)
|
||||
&& domain.getDeletionTime().plus(maxStaleness).isAfter(now);
|
||||
}
|
||||
boolean isStalenessAllowed(Domain domain) {
|
||||
return domain.getCreationTime().plus(maxStaleness).isAfter(clock.nowUtc());
|
||||
}
|
||||
|
||||
/** Returns unique labels across all block lists in the download specified by {@code jobName}. */
|
||||
|
||||
@@ -25,16 +25,16 @@ import static google.registry.request.Action.Method.GET;
|
||||
import static google.registry.request.Action.Method.POST;
|
||||
import static jakarta.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
|
||||
import static java.nio.charset.StandardCharsets.US_ASCII;
|
||||
import static java.nio.charset.StandardCharsets.UTF_8;
|
||||
|
||||
import com.google.cloud.storage.BlobId;
|
||||
import com.google.common.base.Joiner;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
import com.google.common.collect.ImmutableSet;
|
||||
import com.google.common.collect.ImmutableSortedSet;
|
||||
import com.google.common.collect.Ordering;
|
||||
import com.google.common.flogger.FluentLogger;
|
||||
import com.google.common.hash.Hasher;
|
||||
import com.google.common.hash.Hashing;
|
||||
import com.google.common.io.ByteSource;
|
||||
import google.registry.bsa.api.BsaCredential;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.gcs.GcsUtils;
|
||||
@@ -42,15 +42,17 @@ import google.registry.model.tld.Tld;
|
||||
import google.registry.model.tld.Tld.TldType;
|
||||
import google.registry.model.tld.label.ReservedList;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.Clock;
|
||||
import jakarta.inject.Inject;
|
||||
import jakarta.persistence.TypedQuery;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.BufferedInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
import java.io.OutputStreamWriter;
|
||||
import java.io.PipedInputStream;
|
||||
import java.io.PipedOutputStream;
|
||||
import java.io.Writer;
|
||||
import java.util.Optional;
|
||||
import java.util.zip.GZIPOutputStream;
|
||||
@@ -60,19 +62,22 @@ import okhttp3.OkHttpClient;
|
||||
import okhttp3.Request;
|
||||
import okhttp3.RequestBody;
|
||||
import okhttp3.Response;
|
||||
import okio.BufferedSink;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
/**
|
||||
* Daily action that uploads unavailable domain names on applicable TLDs to BSA.
|
||||
*
|
||||
* <p>The upload is a single zipped text file containing combined details for all BSA-enrolled TLDs.
|
||||
* The text is a newline-delimited list of punycoded fully qualified domain names, and contains all
|
||||
* domains on each TLD that are registered and/or reserved.
|
||||
* The text is a newline-delimited list of punycoded fully qualified domain names with a trailing
|
||||
* newline at the end, and contains all domains on each TLD that are registered and/or reserved.
|
||||
*
|
||||
* <p>The file is also uploaded to GCS to preserve it as a record for ourselves.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BSA,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/uploadBsaUnavailableNames",
|
||||
method = {GET, POST},
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
@@ -118,7 +123,7 @@ public class UploadBsaUnavailableDomainsAction implements Runnable {
|
||||
// TODO(mcilwain): Implement a date Cursor, have the cronjob run frequently, and short-circuit
|
||||
// the run if the daily upload is already completed.
|
||||
DateTime runTime = clock.nowUtc();
|
||||
String unavailableDomains = Joiner.on("\n").join(getUnavailableDomains(runTime));
|
||||
ImmutableSortedSet<String> unavailableDomains = getUnavailableDomains(runTime);
|
||||
if (unavailableDomains.isEmpty()) {
|
||||
logger.atWarning().log("No unavailable domains found; terminating.");
|
||||
emailSender.sendNotification(
|
||||
@@ -136,12 +141,16 @@ public class UploadBsaUnavailableDomainsAction implements Runnable {
|
||||
}
|
||||
|
||||
/** Uploads the unavailable domains list to GCS in the unavailable domains bucket. */
|
||||
boolean uploadToGcs(String unavailableDomains, DateTime runTime) {
|
||||
boolean uploadToGcs(ImmutableSortedSet<String> unavailableDomains, DateTime runTime) {
|
||||
logger.atInfo().log("Uploading unavailable names file to GCS in bucket %s", gcsBucket);
|
||||
BlobId blobId = BlobId.of(gcsBucket, createFilename(runTime));
|
||||
// `gcsUtils.openOutputStream` returns a buffered stream
|
||||
try (OutputStream gcsOutput = gcsUtils.openOutputStream(blobId);
|
||||
Writer osWriter = new OutputStreamWriter(gcsOutput, US_ASCII)) {
|
||||
osWriter.write(unavailableDomains);
|
||||
for (var domainName : unavailableDomains) {
|
||||
osWriter.write(domainName);
|
||||
osWriter.write("\n");
|
||||
}
|
||||
return true;
|
||||
} catch (Exception e) {
|
||||
logger.atSevere().withCause(e).log(
|
||||
@@ -150,10 +159,14 @@ public class UploadBsaUnavailableDomainsAction implements Runnable {
|
||||
}
|
||||
}
|
||||
|
||||
boolean uploadToBsa(String unavailableDomains, DateTime runTime) {
|
||||
boolean uploadToBsa(ImmutableSortedSet<String> unavailableDomains, DateTime runTime) {
|
||||
try {
|
||||
byte[] gzippedContents = gzipUnavailableDomains(unavailableDomains);
|
||||
String sha512Hash = ByteSource.wrap(gzippedContents).hash(Hashing.sha512()).toString();
|
||||
Hasher sha512Hasher = Hashing.sha512().newHasher();
|
||||
unavailableDomains.stream()
|
||||
.map(name -> name + "\n")
|
||||
.forEachOrdered(line -> sha512Hasher.putString(line, UTF_8));
|
||||
String sha512Hash = sha512Hasher.hash().toString();
|
||||
|
||||
String filename = createFilename(runTime);
|
||||
OkHttpClient client = new OkHttpClient().newBuilder().build();
|
||||
|
||||
@@ -169,7 +182,9 @@ public class UploadBsaUnavailableDomainsAction implements Runnable {
|
||||
.addFormDataPart(
|
||||
"file",
|
||||
String.format("%s.gz", filename),
|
||||
RequestBody.create(gzippedContents, MediaType.parse("application/octet-stream")))
|
||||
new StreamingRequestBody(
|
||||
gzippedStream(unavailableDomains),
|
||||
MediaType.parse("application/octet-stream")))
|
||||
.build();
|
||||
|
||||
Request request =
|
||||
@@ -196,15 +211,6 @@ public class UploadBsaUnavailableDomainsAction implements Runnable {
|
||||
}
|
||||
}
|
||||
|
||||
private byte[] gzipUnavailableDomains(String unavailableDomains) throws IOException {
|
||||
try (ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream()) {
|
||||
try (GZIPOutputStream gzipOutputStream = new GZIPOutputStream(byteArrayOutputStream)) {
|
||||
gzipOutputStream.write(unavailableDomains.getBytes(US_ASCII));
|
||||
}
|
||||
return byteArrayOutputStream.toByteArray();
|
||||
}
|
||||
}
|
||||
|
||||
private static String createFilename(DateTime runTime) {
|
||||
return String.format("unavailable_domains_%s.txt", runTime.toString());
|
||||
}
|
||||
@@ -280,4 +286,65 @@ public class UploadBsaUnavailableDomainsAction implements Runnable {
|
||||
private static String toDomain(String domainLabel, Tld tld) {
|
||||
return String.format("%s.%s", domainLabel, tld.getTldStr());
|
||||
}
|
||||
|
||||
private InputStream gzippedStream(ImmutableSortedSet<String> unavailableDomains)
|
||||
throws IOException {
|
||||
PipedInputStream inputStream = new PipedInputStream();
|
||||
PipedOutputStream outputStream = new PipedOutputStream(inputStream);
|
||||
|
||||
new Thread(
|
||||
() -> {
|
||||
try {
|
||||
gzipUnavailableDomains(outputStream, unavailableDomains);
|
||||
} catch (Throwable e) {
|
||||
logger.atSevere().withCause(e).log("Failed to gzip unavailable domains.");
|
||||
try {
|
||||
// This will cause the next read to throw an IOException.
|
||||
inputStream.close();
|
||||
} catch (IOException ignore) {
|
||||
// Won't happen for `PipedInputStream.close()`
|
||||
}
|
||||
}
|
||||
})
|
||||
.start();
|
||||
|
||||
return inputStream;
|
||||
}
|
||||
|
||||
private void gzipUnavailableDomains(
|
||||
PipedOutputStream outputStream, ImmutableSortedSet<String> unavailableDomains)
|
||||
throws IOException {
|
||||
// `GZIPOutputStream` is buffered.
|
||||
try (GZIPOutputStream gzipOutputStream = new GZIPOutputStream(outputStream)) {
|
||||
for (String name : unavailableDomains) {
|
||||
var line = name + "\n";
|
||||
gzipOutputStream.write(line.getBytes(US_ASCII));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static class StreamingRequestBody extends RequestBody {
|
||||
private final BufferedInputStream inputStream;
|
||||
private final MediaType mediaType;
|
||||
|
||||
StreamingRequestBody(InputStream inputStream, MediaType mediaType) {
|
||||
this.inputStream = new BufferedInputStream(inputStream);
|
||||
this.mediaType = mediaType;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public MediaType contentType() {
|
||||
return mediaType;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeTo(@NotNull BufferedSink bufferedSink) throws IOException {
|
||||
byte[] buffer = new byte[2048];
|
||||
int bytesRead;
|
||||
while ((bytesRead = inputStream.read(buffer)) != -1) {
|
||||
bufferedSink.write(buffer, 0, bytesRead);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -156,7 +156,7 @@ public final class DomainsRefresher {
|
||||
.collect(toImmutableSet());
|
||||
ImmutableSet<String> currRegistered =
|
||||
ImmutableSet.copyOf(
|
||||
ForeignKeyUtils.load(Domain.class, nameToEntity.keySet(), now).keySet());
|
||||
ForeignKeyUtils.loadKeys(Domain.class, nameToEntity.keySet(), now).keySet());
|
||||
SetView<String> noLongerRegistered = Sets.difference(prevRegistered, currRegistered);
|
||||
SetView<String> newlyRegistered = Sets.difference(currRegistered, prevRegistered);
|
||||
|
||||
|
||||
@@ -145,11 +145,10 @@ public final class LabelDiffUpdates {
|
||||
|
||||
ImmutableSet<String> validDomainNames =
|
||||
labels.stream()
|
||||
.map(label -> validDomainNamesForLabel(label, idnChecker))
|
||||
.flatMap(x -> x)
|
||||
.flatMap(label -> validDomainNamesForLabel(label, idnChecker))
|
||||
.collect(toImmutableSet());
|
||||
ImmutableSet<String> registeredDomainNames =
|
||||
ImmutableSet.copyOf(ForeignKeyUtils.load(Domain.class, validDomainNames, now).keySet());
|
||||
ForeignKeyUtils.loadKeys(Domain.class, validDomainNames, now).keySet();
|
||||
for (String domain : registeredDomainNames) {
|
||||
nonBlockedDomains.add(new UnblockableDomain(domain, Reason.REGISTERED));
|
||||
tm().put(BsaUnblockableDomain.of(domain, BsaUnblockableDomain.Reason.REGISTERED));
|
||||
|
||||
@@ -44,8 +44,6 @@ public abstract class CredentialModule {
|
||||
* <p>The credential returned by the Cloud Runtime depends on the runtime environment:
|
||||
*
|
||||
* <ul>
|
||||
* <li>On App Engine, returns a scope-less {@code ComputeEngineCredentials} for
|
||||
* PROJECT_ID@appspot.gserviceaccount.com
|
||||
* <li>On Compute Engine, returns a scope-less {@code ComputeEngineCredentials} for
|
||||
* PROJECT_NUMBER-compute@developer.gserviceaccount.com
|
||||
* <li>On end user host, this returns the credential downloaded by gcloud. Please refer to <a
|
||||
@@ -87,8 +85,8 @@ public abstract class CredentialModule {
|
||||
* the application default credential user.
|
||||
*
|
||||
* <p>The Workspace domain must grant delegated admin access to the default service account user
|
||||
* (project-id@appspot.gserviceaccount.com on AppEngine) with all scopes in {@code defaultScopes}
|
||||
* and {@code delegationScopes}.
|
||||
* (nomulus-service-account@{project-id}.iam.gserviceaccount.com on GCP) with all scopes in {@code
|
||||
* defaultScopes} and {@code delegationScopes}.
|
||||
*/
|
||||
@AdcDelegatedCredential
|
||||
@Provides
|
||||
@@ -113,9 +111,9 @@ public abstract class CredentialModule {
|
||||
* Provides a {@link GoogleCredentialsBundle} for sending emails through Google Workspace.
|
||||
*
|
||||
* <p>The Workspace domain must grant delegated admin access to the default service account user
|
||||
* (project-id@appspot.gserviceaccount.com on AppEngine) with all scopes in {@code defaultScopes}
|
||||
* and {@code delegationScopes}. In addition, the user {@code gSuiteOutgoingEmailAddress} must
|
||||
* have the permission to send emails.
|
||||
* (nomulus-service-account@{project-id}.iam.gserviceaccount.com on GCP) with all scopes in {@code
|
||||
* defaultScopes} and {@code delegationScopes}. In addition, the user {@code
|
||||
* gSuiteOutgoingEmailAddress} must have the permission to send emails.
|
||||
*/
|
||||
@GmailDelegatedCredential
|
||||
@Provides
|
||||
|
||||
@@ -55,8 +55,9 @@ import org.apache.commons.codec.binary.Base64;
|
||||
*
|
||||
* <p>This class accepts the application-default-credential as {@code ServiceAccountSigner},
|
||||
* avoiding the need for exported private keys. In this case, the default credential user itself
|
||||
* (project-id@appspot.gserviceaccount.com on AppEngine) must have domain-wide delegation to the
|
||||
* Workspace APIs. The default credential user also must have the Token Creator role to itself.
|
||||
* (nomulus-service-account@{project-id}.iam.gserviceaccount.com on GCP) must have domain-wide
|
||||
* delegation to the Workspace APIs. The default credential user also must have the Token Creator
|
||||
* role to itself.
|
||||
*
|
||||
* <p>If the user provides a credential {@code S} that carries its own private key, such as {@link
|
||||
* com.google.auth.oauth2.ServiceAccountCredentials}, this class can use {@code S} to impersonate
|
||||
|
||||
@@ -36,8 +36,9 @@ import dagger.Provides;
|
||||
import google.registry.bsa.UploadBsaUnavailableDomainsAction;
|
||||
import google.registry.dns.ReadDnsRefreshRequestsAction;
|
||||
import google.registry.model.common.DnsRefreshRequest;
|
||||
import google.registry.mosapi.MosApiClient;
|
||||
import google.registry.persistence.transaction.JpaTransactionManager;
|
||||
import google.registry.request.Action.GkeService;
|
||||
import google.registry.request.Action.Service;
|
||||
import google.registry.util.RegistryEnvironment;
|
||||
import google.registry.util.YamlUtils;
|
||||
import jakarta.inject.Named;
|
||||
@@ -961,7 +962,7 @@ public final class RegistryConfig {
|
||||
}
|
||||
|
||||
/**
|
||||
* Number of times to retry a GAE operation when {@code TransientFailureException} is thrown.
|
||||
* Number of times to retry an operation when {@code TransientFailureException} is thrown.
|
||||
*
|
||||
* <p>The number of milliseconds it'll sleep before giving up is {@code (2^n - 2) * 100}.
|
||||
*
|
||||
@@ -976,17 +977,6 @@ public final class RegistryConfig {
|
||||
return config.misc.transientFailureRetries;
|
||||
}
|
||||
|
||||
/**
|
||||
* Amount of time public HTTP proxies are permitted to cache our WHOIS responses.
|
||||
*
|
||||
* @see google.registry.whois.WhoisHttpAction
|
||||
*/
|
||||
@Provides
|
||||
@Config("whoisHttpExpires")
|
||||
public static Duration provideWhoisHttpExpires() {
|
||||
return Duration.standardDays(1);
|
||||
}
|
||||
|
||||
/**
|
||||
* Maximum number of results to return for an RDAP search query
|
||||
*
|
||||
@@ -998,39 +988,6 @@ public final class RegistryConfig {
|
||||
return 100;
|
||||
}
|
||||
|
||||
/**
|
||||
* Redaction text for email address in WHOIS
|
||||
*
|
||||
* @see google.registry.whois.WhoisResponse
|
||||
*/
|
||||
@Provides
|
||||
@Config("whoisRedactedEmailText")
|
||||
public static String provideWhoisRedactedEmailText(RegistryConfigSettings config) {
|
||||
return config.registryPolicy.whoisRedactedEmailText;
|
||||
}
|
||||
|
||||
/**
|
||||
* Disclaimer displayed at the end of WHOIS query results.
|
||||
*
|
||||
* @see google.registry.whois.WhoisResponse
|
||||
*/
|
||||
@Provides
|
||||
@Config("whoisDisclaimer")
|
||||
public static String provideWhoisDisclaimer(RegistryConfigSettings config) {
|
||||
return config.registryPolicy.whoisDisclaimer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Message template for whois response when queried domain is blocked by BSA.
|
||||
*
|
||||
* @see google.registry.whois.WhoisResponse
|
||||
*/
|
||||
@Provides
|
||||
@Config("domainBlockedByBsaTemplate")
|
||||
public static String provideDomainBlockedByBsaTemplate(RegistryConfigSettings config) {
|
||||
return config.registryPolicy.domainBlockedByBsaTemplate;
|
||||
}
|
||||
|
||||
/**
|
||||
* Maximum QPS for the Google Cloud Monitoring V3 (aka Stackdriver) API. The QPS limit can be
|
||||
* adjusted by contacting Cloud Support.
|
||||
@@ -1105,12 +1062,6 @@ public final class RegistryConfig {
|
||||
return config.registryPolicy.customLogicFactoryClass;
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("whoisCommandFactoryClass")
|
||||
public static String provideWhoisCommandFactoryClass(RegistryConfigSettings config) {
|
||||
return config.registryPolicy.whoisCommandFactoryClass;
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("dnsCountQueryCoordinatorClass")
|
||||
public static String dnsCountQueryCoordinatorClass(RegistryConfigSettings config) {
|
||||
@@ -1465,6 +1416,58 @@ public final class RegistryConfig {
|
||||
return config.bsa.uploadUnavailableDomainsUrl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the URL we send HTTP requests for MoSAPI.
|
||||
*
|
||||
* @see MosApiClient
|
||||
*/
|
||||
@Provides
|
||||
@Config("mosapiServiceUrl")
|
||||
public static String provideMosapiServiceUrl(RegistryConfigSettings config) {
|
||||
return config.mosapi.serviceUrl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the entityType we send HTTP requests for MoSAPI.
|
||||
*
|
||||
* @see MosApiClient
|
||||
*/
|
||||
@Provides
|
||||
@Config("mosapiEntityType")
|
||||
public static String provideMosapiEntityType(RegistryConfigSettings config) {
|
||||
return config.mosapi.entityType;
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("mosapiTlsCertSecretName")
|
||||
public static String provideMosapiTlsCertSecretName(RegistryConfigSettings config) {
|
||||
return config.mosapi.tlsCertSecretName;
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("mosapiTlsKeySecretName")
|
||||
public static String provideMosapiTlsKeySecretName(RegistryConfigSettings config) {
|
||||
return config.mosapi.tlsKeySecretName;
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("mosapiTlds")
|
||||
public static ImmutableSet<String> provideMosapiTlds(RegistryConfigSettings config) {
|
||||
return ImmutableSet.copyOf(config.mosapi.tlds);
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("mosapiServices")
|
||||
public static ImmutableSet<String> provideMosapiServices(RegistryConfigSettings config) {
|
||||
return ImmutableSet.copyOf(config.mosapi.services);
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Config("mosapiTldThreadCnt")
|
||||
public static int provideMosapiTldThreads(RegistryConfigSettings config) {
|
||||
return config.mosapi.tldThreadCnt;
|
||||
}
|
||||
|
||||
private static String formatComments(String text) {
|
||||
return Splitter.on('\n').omitEmptyStrings().trimResults().splitToList(text).stream()
|
||||
.map(s -> "# " + s)
|
||||
@@ -1472,7 +1475,7 @@ public final class RegistryConfig {
|
||||
}
|
||||
}
|
||||
|
||||
/** Returns the App Engine project ID, which is based off the environment name. */
|
||||
/** Returns the project ID, which is based off the environment name. */
|
||||
public static String getProjectId() {
|
||||
return CONFIG_SETTINGS.get().gcpProject.projectId;
|
||||
}
|
||||
@@ -1494,55 +1497,10 @@ public final class RegistryConfig {
|
||||
return CONFIG_SETTINGS.get().gcpProject.baseDomain;
|
||||
}
|
||||
|
||||
public static URL getServiceUrl(GkeService service) {
|
||||
public static URL getServiceUrl(Service service) {
|
||||
return makeUrl(String.format("https://%s.%s", service.getServiceId(), getBaseDomain()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the address of the Nomulus app default HTTP server.
|
||||
*
|
||||
* <p>This is used by the {@code nomulus} tool to connect to the App Engine remote API.
|
||||
*/
|
||||
public static URL getDefaultServer() {
|
||||
return makeUrl(CONFIG_SETTINGS.get().gcpProject.defaultServiceUrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the address of the Nomulus app backend HTTP server.
|
||||
*
|
||||
* <p>This is used by the {@code nomulus} tool to connect to the App Engine remote API.
|
||||
*/
|
||||
public static URL getBackendServer() {
|
||||
return makeUrl(CONFIG_SETTINGS.get().gcpProject.backendServiceUrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the address of the Nomulus app bsa HTTP server.
|
||||
*
|
||||
* <p>This is used by the {@code nomulus} tool to connect to the App Engine remote API.
|
||||
*/
|
||||
public static URL getBsaServer() {
|
||||
return makeUrl(CONFIG_SETTINGS.get().gcpProject.bsaServiceUrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the address of the Nomulus app tools HTTP server.
|
||||
*
|
||||
* <p>This is used by the {@code nomulus} tool to connect to the App Engine remote API.
|
||||
*/
|
||||
public static URL getToolsServer() {
|
||||
return makeUrl(CONFIG_SETTINGS.get().gcpProject.toolsServiceUrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the address of the Nomulus app pubapi HTTP server.
|
||||
*
|
||||
* <p>This is used by the {@code nomulus} tool to connect to the App Engine remote API.
|
||||
*/
|
||||
public static URL getPubapiServer() {
|
||||
return makeUrl(CONFIG_SETTINGS.get().gcpProject.pubapiServiceUrl);
|
||||
}
|
||||
|
||||
/** Returns the amount of time a singleton should be cached, before expiring. */
|
||||
public static java.time.Duration getSingletonCacheRefreshDuration() {
|
||||
return java.time.Duration.ofSeconds(CONFIG_SETTINGS.get().caching.singletonCacheRefreshSeconds);
|
||||
@@ -1606,12 +1564,7 @@ public final class RegistryConfig {
|
||||
return CONFIG_SETTINGS.get().gSuite.outgoingEmailDisplayName;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns default WHOIS server to use when {@code Registrar#getWhoisServer()} is {@code null}.
|
||||
*
|
||||
* @see "google.registry.whois.DomainWhoisResponse"
|
||||
* @see "google.registry.whois.RegistrarWhoisResponse"
|
||||
*/
|
||||
/** Returns default WHOIS server to use when {@code Registrar#getWhoisServer()} is null. */
|
||||
public static String getDefaultRegistrarWhoisServer() {
|
||||
return CONFIG_SETTINGS.get().registryPolicy.defaultRegistrarWhoisServer;
|
||||
}
|
||||
|
||||
@@ -43,6 +43,7 @@ public class RegistryConfigSettings {
|
||||
public DnsUpdate dnsUpdate;
|
||||
public BulkPricingPackageMonitoring bulkPricingPackageMonitoring;
|
||||
public Bsa bsa;
|
||||
public MosApi mosapi;
|
||||
|
||||
/** Configuration options that apply to the entire GCP project. */
|
||||
public static class GcpProject {
|
||||
@@ -50,11 +51,6 @@ public class RegistryConfigSettings {
|
||||
public long projectIdNumber;
|
||||
public String locationId;
|
||||
public boolean isLocal;
|
||||
public String defaultServiceUrl;
|
||||
public String backendServiceUrl;
|
||||
public String bsaServiceUrl;
|
||||
public String toolsServiceUrl;
|
||||
public String pubapiServiceUrl;
|
||||
public String baseDomain;
|
||||
}
|
||||
|
||||
@@ -90,7 +86,6 @@ public class RegistryConfigSettings {
|
||||
public String contactAndHostRoidSuffix;
|
||||
public String productName;
|
||||
public String customLogicFactoryClass;
|
||||
public String whoisCommandFactoryClass;
|
||||
public String dnsCountQueryCoordinatorClass;
|
||||
public int contactAutomaticTransferDays;
|
||||
public String greetingServerId;
|
||||
@@ -102,9 +97,6 @@ public class RegistryConfigSettings {
|
||||
public String registryAdminClientId;
|
||||
public String premiumTermsExportDisclaimer;
|
||||
public String reservedTermsExportDisclaimer;
|
||||
public String whoisRedactedEmailText;
|
||||
public String whoisDisclaimer;
|
||||
public String domainBlockedByBsaTemplate;
|
||||
public String rdapTos;
|
||||
public String rdapTosStaticUrl;
|
||||
public String registryName;
|
||||
@@ -271,4 +263,15 @@ public class RegistryConfigSettings {
|
||||
public String unblockableDomainsUrl;
|
||||
public String uploadUnavailableDomainsUrl;
|
||||
}
|
||||
|
||||
/** Configuration for Mosapi. */
|
||||
public static class MosApi {
|
||||
public String serviceUrl;
|
||||
public String tlsCertSecretName;
|
||||
public String tlsKeySecretName;
|
||||
public String entityType;
|
||||
public List<String> tlds;
|
||||
public List<String> services;
|
||||
public int tldThreadCnt;
|
||||
}
|
||||
}
|
||||
|
||||
13
core/src/main/java/google/registry/config/files/README.md
Normal file
13
core/src/main/java/google/registry/config/files/README.md
Normal file
@@ -0,0 +1,13 @@
|
||||
# Nomulus Environment Configuration
|
||||
|
||||
The configuration files for the different Nomulus environments are not included in this repository. To configure and run a specific environment, you will need to create the corresponding YAML configuration file in this directory.
|
||||
|
||||
The following is a list of the environment configuration files that you may need to create:
|
||||
|
||||
* `nomulus-config-alpha.yaml`
|
||||
* `nomulus-config-crash.yaml`
|
||||
* `nomulus-config-qa.yaml`
|
||||
* `nomulus-config-sandbox.yaml`
|
||||
* `nomulus-config-production.yaml`
|
||||
|
||||
Please create the relevant file for the environment you intend to use and populate it with the necessary configuration details.
|
||||
@@ -12,17 +12,11 @@ gcpProject:
|
||||
projectIdNumber: 123456789012
|
||||
# Location of the GCP project, note that us-central1 and europe-west1 are special in that
|
||||
# they are used without the trailing number in GCP commands and Google Cloud Console.
|
||||
# See: https://cloud.google.com/appengine/docs/locations as an example
|
||||
# See: https://docs.cloud.google.com/compute/docs/regions-zones as an example
|
||||
locationId: registry-location-id
|
||||
|
||||
# whether to use local/test credentials when connecting to the servers
|
||||
isLocal: true
|
||||
# URLs of the services for the project.
|
||||
defaultServiceUrl: https://default.example.com
|
||||
backendServiceUrl: https://backend.example.com
|
||||
bsaServiceUrl: https://bsa.example.com
|
||||
toolsServiceUrl: https://tools.example.com
|
||||
pubapiServiceUrl: https://pubapi.example.com
|
||||
|
||||
# The base domain name of the registry service. Services are reachable at [service].baseDomain.
|
||||
baseDomain: registry.test
|
||||
@@ -32,9 +26,9 @@ gSuite:
|
||||
domainName: domain-registry.example
|
||||
|
||||
# Display name and email address used on outgoing emails through G Suite.
|
||||
# The email address must be valid and have permission in the GAE app to send
|
||||
# emails. For more info see:
|
||||
# https://cloud.google.com/appengine/docs/standard/java/mail/#who_can_send_mail
|
||||
# The email address must be valid and the domain must be set up to send emails.
|
||||
# For more info see
|
||||
# https://docs.cloud.google.com/compute/docs/tutorials/sending-mail
|
||||
outgoingEmailDisplayName: Example Registry
|
||||
outgoingEmailAddress: noreply@project-id.appspotmail.com
|
||||
# TODO(b/279671974): reuse `outgoingEmailAddress` after migration
|
||||
@@ -65,10 +59,6 @@ registryPolicy:
|
||||
# See flows/custom/CustomLogicFactory.java
|
||||
customLogicFactoryClass: google.registry.flows.custom.CustomLogicFactory
|
||||
|
||||
# WHOIS command factory fully-qualified class name.
|
||||
# See whois/WhoisCommandFactory.java
|
||||
whoisCommandFactoryClass: google.registry.whois.WhoisCommandFactory
|
||||
|
||||
# Custom logic class for handling DNS query count reporting for ICANN.
|
||||
# See reporting/icann/DnsCountQueryCoordinator.java
|
||||
dnsCountQueryCoordinatorClass: google.registry.reporting.icann.DummyDnsCountQueryCoordinator
|
||||
@@ -114,31 +104,6 @@ registryPolicy:
|
||||
to publish. This list is subject to change. The most up-to-date source
|
||||
is always the registry itself, by sending domain check EPP commands.
|
||||
|
||||
# Redaction text for email address in WHOIS
|
||||
whoisRedactedEmailText: |
|
||||
Please query the WHOIS server of the owning registrar identified in this
|
||||
output for information on how to contact the Registrant, Admin, or Tech
|
||||
contact of the queried domain name.
|
||||
|
||||
# Disclaimer at the top of WHOIS results.
|
||||
whoisDisclaimer: |
|
||||
WHOIS information is provided by the registry solely for query-based,
|
||||
informational purposes. Any information provided is "as is" without any
|
||||
guarantee of accuracy. You may not use such information to (a) allow,
|
||||
enable, or otherwise support the transmission of mass unsolicited,
|
||||
commercial advertising or solicitations; (b) enable high volume, automated,
|
||||
electronic processes that access the registry's systems or any
|
||||
ICANN-Accredited Registrar, except as reasonably necessary to register
|
||||
domain names or modify existing registrations; or (c) engage in or support
|
||||
unlawful behavior. We reserve the right to restrict or deny your access to
|
||||
the WHOIS database, and may modify these terms at any time.
|
||||
|
||||
# BSA blocked domain name template.
|
||||
domainBlockedByBsaTemplate: |
|
||||
Domain Name: %s
|
||||
>>> This name is not available for registration.
|
||||
>>> This name has been blocked by a GlobalBlock service.
|
||||
|
||||
# RDAP Terms of Service text displayed at the /rdap/help/tos endpoint.
|
||||
rdapTos: >
|
||||
By querying our Domain Database as part of the RDAP pilot program (RDAP
|
||||
@@ -230,20 +195,18 @@ hibernate:
|
||||
# but lock tables explicitly, either using framework-dependent API, or execute
|
||||
# "select table for update" statements directly.
|
||||
connectionIsolation: TRANSACTION_SERIALIZABLE
|
||||
# Whether to log all SQL queries to App Engine logs. Overridable at runtime.
|
||||
# Whether to log all SQL queries. Overridable at runtime.
|
||||
logSqlQueries: false
|
||||
|
||||
# Connection pool configurations.
|
||||
hikariConnectionTimeout: 20000
|
||||
# Cloud SQL connections are a relatively scarce resource (maximum is 1000 as
|
||||
# of March 2021). The minimumIdle should be a small value so that machines may
|
||||
# release connections after a demand spike. The maximumPoolSize is set to 10
|
||||
# because that is the maximum number of concurrent requests a Nomulus server
|
||||
# instance can handle (as limited by AppEngine for basic/manual scaling). Note
|
||||
# that BEAM pipelines are not subject to the maximumPoolSize value defined
|
||||
# here. See PersistenceModule.java for more information.
|
||||
# release connections after a demand spike. Note that BEAM pipelines are not
|
||||
# subject to the maximumPoolSize value defined here. See PersistenceModule.java
|
||||
# for more information.
|
||||
hikariMinimumIdle: 1
|
||||
hikariMaximumPoolSize: 20
|
||||
hikariMaximumPoolSize: 40
|
||||
hikariIdleTimeout: 300000
|
||||
# The batch size is basically the number of insertions / updates in a single
|
||||
# transaction that will be batched together into one INSERT/UPDATE statement.
|
||||
@@ -255,7 +218,7 @@ hibernate:
|
||||
# The fetch size is the number of entities retrieved at a time from the
|
||||
# database cursor. Here we set a small default geared toward Nomulus server
|
||||
# transactions. Large queries can override the defaults on a per-query basis.
|
||||
jdbcFetchSize: 20
|
||||
jdbcFetchSize: 40
|
||||
|
||||
cloudSql:
|
||||
# jdbc url for the Cloud SQL database.
|
||||
@@ -293,8 +256,8 @@ caching:
|
||||
|
||||
# Maximum total number of static premium list entry entities to cache in
|
||||
# memory, across all premium lists for all TLDs. Tuning this up will use more
|
||||
# memory (and might require using larger App Engine instances). Note that
|
||||
# premium list entries that are absent are cached in addition to ones that are
|
||||
# memory (and might require using larger instances). Note that premium list
|
||||
# entries that are absent are cached in addition to ones that are
|
||||
# present, so the total cache size is not bounded by the total number of
|
||||
# premium price entries that exist.
|
||||
staticPremiumListMaxCachedEntries: 200000
|
||||
@@ -375,12 +338,8 @@ credentialOAuth:
|
||||
localCredentialOauthScopes:
|
||||
# View and manage data in all Google Cloud APIs.
|
||||
- https://www.googleapis.com/auth/cloud-platform
|
||||
# Call App Engine APIs locally.
|
||||
- https://www.googleapis.com/auth/appengine.apis
|
||||
# View your email address.
|
||||
- https://www.googleapis.com/auth/userinfo.email
|
||||
# View and manage your applications deployed on Google App Engine
|
||||
- https://www.googleapis.com/auth/appengine.admin
|
||||
# The lifetime of an access token generated by our custom credentials classes
|
||||
# Must be shorter than one hour.
|
||||
tokenRefreshDelaySeconds: 1800
|
||||
@@ -462,7 +421,7 @@ misc:
|
||||
spec11BccEmailAddresses:
|
||||
- abuse@example.com
|
||||
|
||||
# Number of times to retry a GAE operation when a transient exception is thrown.
|
||||
# Number of times to retry an operation when a transient exception is thrown.
|
||||
# The number of milliseconds it'll sleep before giving up is (2^n - 2) * 100.
|
||||
transientFailureRetries: 12
|
||||
|
||||
@@ -657,3 +616,34 @@ bsa:
|
||||
unblockableDomainsUrl: "https://"
|
||||
# API endpoint for uploading the list of unavailable domain names.
|
||||
uploadUnavailableDomainsUrl: "https://"
|
||||
|
||||
mosapi:
|
||||
# URL for the MosAPI
|
||||
serviceUrl: https://mosapi.icann.org
|
||||
# The type of entity being monitored.
|
||||
# For registries, this is 'ry'
|
||||
# For registrars, this is 'rr'
|
||||
entityType: ry
|
||||
# Add your List of TLDs to be monitored
|
||||
tlds:
|
||||
- your_tld1
|
||||
- your_tld2
|
||||
# Add tls cert secret name
|
||||
# you configured in secret manager
|
||||
tlsCertSecretName: YOUR_TLS_CERT_SECRET_NAME
|
||||
# Add tls key secret name
|
||||
# you configured in secret manager
|
||||
tlsKeySecretName: YOUR_TLS_KEY_SECRET_NAME
|
||||
# List of services to check for each TLD.
|
||||
services:
|
||||
- "dns"
|
||||
- "rdap"
|
||||
- "rdds"
|
||||
- "epp"
|
||||
- "dnssec"
|
||||
|
||||
# Provides a fixed thread pool for parallel TLD processing.
|
||||
# @see <a href="https://www.icann.org/mosapi-specification.pdf">
|
||||
# ICANN MoSAPI Specification, Section 12.3</a>
|
||||
tldThreadCnt: 4
|
||||
|
||||
|
||||
@@ -1 +0,0 @@
|
||||
# Add environment-specific configuration here.
|
||||
@@ -1 +0,0 @@
|
||||
# Add environment-specific configuration here.
|
||||
@@ -1 +0,0 @@
|
||||
# Add environment-specific configuration here.
|
||||
@@ -1 +0,0 @@
|
||||
# Add environment-specific configuration here.
|
||||
@@ -1 +0,0 @@
|
||||
# Add environment-specific configuration here.
|
||||
@@ -88,6 +88,7 @@
|
||||
should exist between the RECURRING_BILLING cursor's time and the execution
|
||||
time of the action.
|
||||
</description>
|
||||
<!-- Runs shortly after DeleteExpiredDomainsAction so it can delete domains before they renew -->
|
||||
<schedule>0 3 * * *</schedule>
|
||||
</task>
|
||||
|
||||
@@ -98,7 +99,8 @@
|
||||
This job runs an action that deletes domains that are past their
|
||||
autorenew end date.
|
||||
</description>
|
||||
<schedule>7 3 * * *</schedule>
|
||||
<!-- Runs shortly before ExpandBillingRecurrencesPipeline to catch and delete domains before they renew -->
|
||||
<schedule>45 2 * * *</schedule>
|
||||
</task>
|
||||
|
||||
<task>
|
||||
|
||||
@@ -146,6 +146,7 @@
|
||||
This job runs an action that deletes domains that are past their
|
||||
autorenew end date.
|
||||
</description>
|
||||
<schedule>7 3 * * *</schedule>
|
||||
<!-- Runs shortly before ExpandBillingRecurrencesPipeline to catch and delete domains before they renew -->
|
||||
<schedule>45 2 * * *</schedule>
|
||||
</task>
|
||||
</entries>
|
||||
|
||||
@@ -130,6 +130,7 @@
|
||||
should exist between the RECURRING_BILLING cursor's time and the execution
|
||||
time of the action.
|
||||
</description>
|
||||
<!-- Runs shortly after DeleteExpiredDomainsAction so it can delete domains before they renew -->
|
||||
<schedule>0 3 * * *</schedule>
|
||||
</task>
|
||||
|
||||
@@ -140,7 +141,8 @@
|
||||
This job runs an action that deletes domains that are past their
|
||||
autorenew end date.
|
||||
</description>
|
||||
<schedule>7 3 * * *</schedule>
|
||||
<!-- Runs shortly before ExpandBillingRecurrencesPipeline to catch and delete domains before they renew -->
|
||||
<schedule>45 2 * * *</schedule>
|
||||
</task>
|
||||
|
||||
<task>
|
||||
@@ -320,4 +322,15 @@
|
||||
<service>bsa</service>
|
||||
<schedule>23 8,20 * * *</schedule>
|
||||
</task>
|
||||
|
||||
<task>
|
||||
<url><![CDATA[/_dr/task/triggerMosApiServiceState]]></url>
|
||||
<name>triggerMosApiServiceState</name>
|
||||
<description>
|
||||
Fetches the service state from MosAPI and triggers the metrics status for all TLDs.
|
||||
</description>
|
||||
<!-- Runs every 5 minutes. -->
|
||||
<schedule>*/5 * * * *</schedule>
|
||||
</task>
|
||||
|
||||
</entries>
|
||||
|
||||
@@ -57,6 +57,7 @@
|
||||
This job runs an action that deletes domains that are past their
|
||||
autorenew end date.
|
||||
</description>
|
||||
<schedule>7 3 * * *</schedule>
|
||||
<!-- Runs shortly before ExpandBillingRecurrencesPipeline to catch and delete domains before they renew -->
|
||||
<schedule>45 2 * * *</schedule>
|
||||
</task>
|
||||
</entries>
|
||||
|
||||
@@ -90,6 +90,7 @@
|
||||
should exist between the RECURRING_BILLING cursor's time and the execution
|
||||
time of the action.
|
||||
</description>
|
||||
<!-- Runs shortly after DeleteExpiredDomainsAction so it can delete domains before they renew -->
|
||||
<schedule>0 3 * * *</schedule>
|
||||
</task>
|
||||
|
||||
@@ -113,7 +114,8 @@
|
||||
This job runs an action that deletes domains that are past their
|
||||
autorenew end date.
|
||||
</description>
|
||||
<schedule>7 3 * * *</schedule>
|
||||
<!-- Runs shortly before ExpandBillingRecurrencesPipeline to catch and delete domains before they renew -->
|
||||
<schedule>45 2 * * *</schedule>
|
||||
</task>
|
||||
|
||||
<task>
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
|
||||
addGracePeriodLength: "PT432000S"
|
||||
allowedFullyQualifiedHostNames: []
|
||||
allowedRegistrantContactIds: []
|
||||
anchorTenantAddGracePeriodLength: "PT2592000S"
|
||||
autoRenewGracePeriodLength: "PT3888000S"
|
||||
automaticTransferLength: "PT432000S"
|
||||
|
||||
@@ -40,14 +40,12 @@ import com.google.common.collect.Streams;
|
||||
import com.google.common.flogger.FluentLogger;
|
||||
import google.registry.batch.CloudTasksUtils;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Action.GkeService;
|
||||
import google.registry.request.Action.Service;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.ParameterMap;
|
||||
import google.registry.request.RequestParameters;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.RegistryEnvironment;
|
||||
import jakarta.inject.Inject;
|
||||
import java.util.Optional;
|
||||
import java.util.stream.Stream;
|
||||
@@ -59,8 +57,7 @@ import java.util.stream.Stream;
|
||||
*
|
||||
* <ul>
|
||||
* <li>{@code endpoint} (Required) URL path of servlet to launch. This may contain pathargs.
|
||||
* <li>{@code queue} (Required) Name of the App Engine push queue to which this task should be
|
||||
* sent.
|
||||
* <li>{@code queue} (Required) Name of the queue to which this task should be sent.
|
||||
* <li>{@code forEachRealTld} Launch the task in each real TLD namespace.
|
||||
* <li>{@code forEachTestTld} Launch the task in each test TLD namespace.
|
||||
* <li>{@code runInEmpty} Launch the task once, without the TLD argument.
|
||||
@@ -80,7 +77,7 @@ import java.util.stream.Stream;
|
||||
* </ul>
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Service.BACKEND,
|
||||
path = "/_dr/cron/fanout",
|
||||
automaticallyPrintOk = true,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
@@ -160,10 +157,6 @@ public final class TldFanoutAction implements Runnable {
|
||||
params.put(RequestParameters.PARAM_TLD, tld);
|
||||
}
|
||||
return cloudTasksUtils.createTaskWithJitter(
|
||||
endpoint,
|
||||
Action.Method.POST,
|
||||
RegistryEnvironment.isOnJetty() ? GkeService.BACKEND : GaeService.BACKEND,
|
||||
params,
|
||||
jitterSeconds);
|
||||
endpoint, Action.Method.POST, Service.BACKEND, params, jitterSeconds);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -25,7 +25,6 @@ import static google.registry.dns.DnsModule.PARAM_REFRESH_REQUEST_TIME;
|
||||
import static google.registry.dns.DnsUtils.DNS_PUBLISH_PUSH_QUEUE_NAME;
|
||||
import static google.registry.dns.DnsUtils.requestDomainDnsRefresh;
|
||||
import static google.registry.dns.DnsUtils.requestHostDnsRefresh;
|
||||
import static google.registry.model.EppResourceUtils.loadByForeignKey;
|
||||
import static google.registry.persistence.transaction.TransactionManagerFactory.tm;
|
||||
import static google.registry.request.Action.Method.POST;
|
||||
import static google.registry.request.RequestParameters.PARAM_TLD;
|
||||
@@ -46,13 +45,13 @@ import google.registry.dns.DnsMetrics.CommitStatus;
|
||||
import google.registry.dns.DnsMetrics.PublishStatus;
|
||||
import google.registry.dns.writer.DnsWriter;
|
||||
import google.registry.groups.GmailClient;
|
||||
import google.registry.model.ForeignKeyUtils;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.host.Host;
|
||||
import google.registry.model.registrar.Registrar;
|
||||
import google.registry.model.registrar.RegistrarPoc;
|
||||
import google.registry.model.tld.Tld;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Header;
|
||||
import google.registry.request.HttpException.ServiceUnavailableException;
|
||||
import google.registry.request.Parameter;
|
||||
@@ -72,7 +71,7 @@ import org.joda.time.Duration;
|
||||
|
||||
/** Task that sends domain and host updates to the DNS server. */
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = PublishDnsUpdatesAction.PATH,
|
||||
method = POST,
|
||||
automaticallyPrintOk = true,
|
||||
@@ -237,7 +236,8 @@ public final class PublishDnsUpdatesAction implements Runnable, Callable<Void> {
|
||||
.findFirst()
|
||||
.ifPresent(
|
||||
dn -> {
|
||||
Optional<Domain> domain = loadByForeignKey(Domain.class, dn, clock.nowUtc());
|
||||
Optional<Domain> domain =
|
||||
ForeignKeyUtils.loadResource(Domain.class, dn, clock.nowUtc());
|
||||
if (domain.isPresent()) {
|
||||
notifyWithEmailAboutDnsUpdateFailure(
|
||||
domain.get().getCurrentSponsorRegistrarId(), dn, false);
|
||||
@@ -250,7 +250,8 @@ public final class PublishDnsUpdatesAction implements Runnable, Callable<Void> {
|
||||
.findFirst()
|
||||
.ifPresent(
|
||||
hn -> {
|
||||
Optional<Host> host = loadByForeignKey(Host.class, hn, clock.nowUtc());
|
||||
Optional<Host> host =
|
||||
ForeignKeyUtils.loadResource(Host.class, hn, clock.nowUtc());
|
||||
if (host.isPresent()) {
|
||||
notifyWithEmailAboutDnsUpdateFailure(
|
||||
host.get().getPersistedCurrentSponsorRegistrarId(), hn, true);
|
||||
|
||||
@@ -45,7 +45,6 @@ import google.registry.dns.DnsUtils.TargetType;
|
||||
import google.registry.model.common.DnsRefreshRequest;
|
||||
import google.registry.model.tld.Tld;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.auth.Auth;
|
||||
import google.registry.util.Clock;
|
||||
@@ -60,7 +59,7 @@ import org.joda.time.Duration;
|
||||
* table.
|
||||
*/
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/readDnsRefreshRequests",
|
||||
automaticallyPrintOk = true,
|
||||
method = POST,
|
||||
|
||||
@@ -16,17 +16,16 @@ package google.registry.dns;
|
||||
|
||||
import static google.registry.dns.DnsUtils.requestDomainDnsRefresh;
|
||||
import static google.registry.dns.DnsUtils.requestHostDnsRefresh;
|
||||
import static google.registry.model.EppResourceUtils.loadByForeignKey;
|
||||
import static google.registry.persistence.transaction.TransactionManagerFactory.tm;
|
||||
|
||||
import google.registry.dns.DnsUtils.TargetType;
|
||||
import google.registry.model.EppResource;
|
||||
import google.registry.model.EppResource.ForeignKeyedEppResource;
|
||||
import google.registry.model.ForeignKeyUtils;
|
||||
import google.registry.model.annotations.ExternalMessagingName;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.host.Host;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.HttpException.BadRequestException;
|
||||
import google.registry.request.HttpException.NotFoundException;
|
||||
import google.registry.request.Parameter;
|
||||
@@ -36,7 +35,7 @@ import jakarta.inject.Inject;
|
||||
|
||||
/** Action that manually triggers refresh of DNS information. */
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = "/_dr/task/dnsRefresh",
|
||||
automaticallyPrintOk = true,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
@@ -79,7 +78,7 @@ public final class RefreshDnsAction implements Runnable {
|
||||
|
||||
private <T extends EppResource & ForeignKeyedEppResource>
|
||||
T loadAndVerifyExistence(Class<T> clazz, String foreignKey) {
|
||||
return loadByForeignKey(clazz, foreignKey, clock.nowUtc())
|
||||
return ForeignKeyUtils.loadResource(clazz, foreignKey, clock.nowUtc())
|
||||
.orElseThrow(
|
||||
() ->
|
||||
new NotFoundException(
|
||||
|
||||
@@ -26,7 +26,6 @@ import google.registry.model.domain.Domain;
|
||||
import google.registry.model.host.Host;
|
||||
import google.registry.persistence.VKey;
|
||||
import google.registry.request.Action;
|
||||
import google.registry.request.Action.GaeService;
|
||||
import google.registry.request.Parameter;
|
||||
import google.registry.request.Response;
|
||||
import google.registry.request.auth.Auth;
|
||||
@@ -34,7 +33,7 @@ import jakarta.inject.Inject;
|
||||
import org.joda.time.DateTime;
|
||||
|
||||
@Action(
|
||||
service = GaeService.BACKEND,
|
||||
service = Action.Service.BACKEND,
|
||||
path = PATH,
|
||||
method = Action.Method.POST,
|
||||
auth = Auth.AUTH_ADMIN)
|
||||
|
||||
@@ -17,7 +17,6 @@ package google.registry.dns.writer.clouddns;
|
||||
import static com.google.common.base.Preconditions.checkArgument;
|
||||
import static com.google.common.collect.ImmutableSet.toImmutableSet;
|
||||
import static google.registry.dns.DnsUtils.getDnsAPlusAAAATtlForHost;
|
||||
import static google.registry.model.EppResourceUtils.loadByForeignKey;
|
||||
import static google.registry.util.DomainNameUtils.getSecondLevelDomain;
|
||||
|
||||
import com.google.api.client.googleapis.json.GoogleJsonError;
|
||||
@@ -37,6 +36,7 @@ import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.dns.writer.BaseDnsWriter;
|
||||
import google.registry.dns.writer.DnsWriter;
|
||||
import google.registry.dns.writer.DnsWriterZone;
|
||||
import google.registry.model.ForeignKeyUtils;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.domain.secdns.DomainDsData;
|
||||
import google.registry.model.host.Host;
|
||||
@@ -123,7 +123,8 @@ public class CloudDnsWriter extends BaseDnsWriter {
|
||||
String absoluteDomainName = getAbsoluteHostName(domainName);
|
||||
|
||||
// Load the target domain. Note that it can be absent if this domain was just deleted.
|
||||
Optional<Domain> domain = loadByForeignKey(Domain.class, domainName, clock.nowUtc());
|
||||
Optional<Domain> domain =
|
||||
ForeignKeyUtils.loadResource(Domain.class, domainName, clock.nowUtc());
|
||||
|
||||
// Return early if no DNS records should be published.
|
||||
// desiredRecordsBuilder is populated with an empty set to indicate that all existing records
|
||||
@@ -189,7 +190,7 @@ public class CloudDnsWriter extends BaseDnsWriter {
|
||||
// Load the target host. Note that it can be absent if this host was just deleted.
|
||||
// desiredRecords is populated with an empty set to indicate that all existing records
|
||||
// should be deleted.
|
||||
Optional<Host> host = loadByForeignKey(Host.class, hostName, clock.nowUtc());
|
||||
Optional<Host> host = ForeignKeyUtils.loadResource(Host.class, hostName, clock.nowUtc());
|
||||
|
||||
// Return early if the host is deleted.
|
||||
if (host.isEmpty()) {
|
||||
|
||||
@@ -36,8 +36,10 @@ import org.xbill.DNS.Opcode;
|
||||
/**
|
||||
* A transport for DNS messages. Sends/receives DNS messages over TCP using old-style {@link Socket}
|
||||
* s and the message framing defined in <a href="https://tools.ietf.org/html/rfc1035">RFC 1035</a>.
|
||||
* We would like use the dnsjava library's {@link org.xbill.DNS.SimpleResolver} class for this, but
|
||||
* it requires {@link java.nio.channels.SocketChannel} which is not supported on AppEngine.
|
||||
*
|
||||
* <p>TODO(b/463732345): now that we're no longer on AppEngine, see if we can use the dnsjava
|
||||
* library's {@link org.xbill.DNS.SimpleResolver} class instead of this (that requires {@link
|
||||
* java.nio.channels.SocketChannel} which is not supported on AppEngine).
|
||||
*/
|
||||
public class DnsMessageTransport {
|
||||
|
||||
|
||||
@@ -19,7 +19,6 @@ import static com.google.common.base.Verify.verify;
|
||||
import static com.google.common.collect.Sets.intersection;
|
||||
import static com.google.common.collect.Sets.union;
|
||||
import static google.registry.dns.DnsUtils.getDnsAPlusAAAATtlForHost;
|
||||
import static google.registry.model.EppResourceUtils.loadByForeignKey;
|
||||
|
||||
import com.google.common.base.Joiner;
|
||||
import com.google.common.collect.ImmutableList;
|
||||
@@ -28,6 +27,7 @@ import com.google.common.net.InternetDomainName;
|
||||
import google.registry.config.RegistryConfig.Config;
|
||||
import google.registry.dns.writer.BaseDnsWriter;
|
||||
import google.registry.dns.writer.DnsWriterZone;
|
||||
import google.registry.model.ForeignKeyUtils;
|
||||
import google.registry.model.domain.Domain;
|
||||
import google.registry.model.domain.secdns.DomainDsData;
|
||||
import google.registry.model.host.Host;
|
||||
@@ -129,7 +129,8 @@ public class DnsUpdateWriter extends BaseDnsWriter {
|
||||
* this domain refresh request
|
||||
*/
|
||||
private void publishDomain(String domainName, String requestingHostName) {
|
||||
Optional<Domain> domainOptional = loadByForeignKey(Domain.class, domainName, clock.nowUtc());
|
||||
Optional<Domain> domainOptional =
|
||||
ForeignKeyUtils.loadResource(Domain.class, domainName, clock.nowUtc());
|
||||
update.delete(toAbsoluteName(domainName), Type.ANY);
|
||||
// If the domain is now deleted, then don't update DNS for it.
|
||||
if (domainOptional.isPresent()) {
|
||||
@@ -218,7 +219,7 @@ public class DnsUpdateWriter extends BaseDnsWriter {
|
||||
private void addInBailiwickNameServerSet(Domain domain, Update update) {
|
||||
for (String hostName :
|
||||
intersection(domain.loadNameserverHostNames(), domain.getSubordinateHosts())) {
|
||||
Optional<Host> host = loadByForeignKey(Host.class, hostName, clock.nowUtc());
|
||||
Optional<Host> host = ForeignKeyUtils.loadResource(Host.class, hostName, clock.nowUtc());
|
||||
checkState(host.isPresent(), "Host %s cannot be loaded", hostName);
|
||||
update.add(makeAddressSet(host.get()));
|
||||
update.add(makeV6AddressSet(host.get()));
|
||||
|
||||
@@ -1,28 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
|
||||
|
||||
<runtime>java21</runtime>
|
||||
<service>backend</service>
|
||||
<app-engine-apis>true</app-engine-apis>
|
||||
<sessions-enabled>true</sessions-enabled>
|
||||
<instance-class>B4</instance-class>
|
||||
<basic-scaling>
|
||||
<max-instances>100</max-instances>
|
||||
<idle-timeout>10m</idle-timeout>
|
||||
</basic-scaling>
|
||||
|
||||
<system-properties>
|
||||
<property name="java.util.logging.config.file"
|
||||
value="WEB-INF/logging.properties"/>
|
||||
<property name="google.registry.environment"
|
||||
value="alpha"/>
|
||||
</system-properties>
|
||||
|
||||
<env-variables>
|
||||
<env-var name="GOOGLE_APPLICATION_CREDENTIALS_SKIP_APP_ENGINE" value="true"/>
|
||||
</env-variables>
|
||||
|
||||
<static-files>
|
||||
<include path="/*.html" expiration="1m"/>
|
||||
</static-files>
|
||||
</appengine-web-app>
|
||||
@@ -1,34 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
|
||||
|
||||
<runtime>java21</runtime>
|
||||
<service>bsa</service>
|
||||
<app-engine-apis>true</app-engine-apis>
|
||||
<sessions-enabled>true</sessions-enabled>
|
||||
<instance-class>B4</instance-class>
|
||||
<basic-scaling>
|
||||
<max-instances>100</max-instances>
|
||||
<idle-timeout>10m</idle-timeout>
|
||||
</basic-scaling>
|
||||
|
||||
<system-properties>
|
||||
<property name="java.util.logging.config.file"
|
||||
value="WEB-INF/logging.properties"/>
|
||||
<property name="google.registry.environment"
|
||||
value="alpha"/>
|
||||
</system-properties>
|
||||
|
||||
<env-variables>
|
||||
<env-var name="GOOGLE_APPLICATION_CREDENTIALS_SKIP_APP_ENGINE" value="true"/>
|
||||
</env-variables>
|
||||
|
||||
<!-- Enable external traffic to go through VPC, required for static ip -->
|
||||
<vpc-access-connector>
|
||||
<name>projects/domain-registry-alpha/locations/us-central1/connectors/appengine-connector</name>
|
||||
<egress-setting>all-traffic</egress-setting>
|
||||
</vpc-access-connector>
|
||||
|
||||
<static-files>
|
||||
<include path="/*.html" expiration="1m"/>
|
||||
</static-files>
|
||||
</appengine-web-app>
|
||||
@@ -1,30 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
|
||||
|
||||
<runtime>java21</runtime>
|
||||
<service>default</service>
|
||||
<app-engine-apis>true</app-engine-apis>
|
||||
<sessions-enabled>true</sessions-enabled>
|
||||
<instance-class>B4</instance-class>
|
||||
<basic-scaling>
|
||||
<max-instances>8</max-instances>
|
||||
<idle-timeout>30m</idle-timeout>
|
||||
</basic-scaling>
|
||||
|
||||
<system-properties>
|
||||
<property name="java.util.logging.config.file"
|
||||
value="WEB-INF/logging.properties"/>
|
||||
<property name="google.registry.environment"
|
||||
value="alpha"/>
|
||||
</system-properties>
|
||||
|
||||
<env-variables>
|
||||
<env-var name="GOOGLE_APPLICATION_CREDENTIALS_SKIP_APP_ENGINE" value="true"/>
|
||||
</env-variables>
|
||||
|
||||
<static-files>
|
||||
<include path="/*.html" expiration="1m"/>
|
||||
<include path="/registrar/*.html" expiration="1m"/>
|
||||
|
||||
</static-files>
|
||||
</appengine-web-app>
|
||||
@@ -1,31 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
|
||||
|
||||
<runtime>java21</runtime>
|
||||
<service>pubapi</service>
|
||||
<app-engine-apis>true</app-engine-apis>
|
||||
<sessions-enabled>true</sessions-enabled>
|
||||
<instance-class>B4</instance-class>
|
||||
<basic-scaling>
|
||||
<max-instances>8</max-instances>
|
||||
<idle-timeout>10m</idle-timeout>
|
||||
</basic-scaling>
|
||||
|
||||
<system-properties>
|
||||
<property name="java.util.logging.config.file"
|
||||
value="WEB-INF/logging.properties"/>
|
||||
<property name="google.registry.environment"
|
||||
value="alpha"/>
|
||||
</system-properties>
|
||||
|
||||
<env-variables>
|
||||
<env-var name="GOOGLE_APPLICATION_CREDENTIALS_SKIP_APP_ENGINE" value="true"/>
|
||||
</env-variables>
|
||||
|
||||
<static-files>
|
||||
<include path="/*.html" expiration="1m"/>
|
||||
<include path="/assets/js/**" expiration="1m"/>
|
||||
<include path="/assets/css/**" expiration="1m"/>
|
||||
<include path="/assets/images/**" expiration="1m"/>
|
||||
</static-files>
|
||||
</appengine-web-app>
|
||||
@@ -1,31 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
|
||||
|
||||
<runtime>java21</runtime>
|
||||
<service>tools</service>
|
||||
<app-engine-apis>true</app-engine-apis>
|
||||
<sessions-enabled>true</sessions-enabled>
|
||||
<instance-class>B4</instance-class>
|
||||
<basic-scaling>
|
||||
<max-instances>5</max-instances>
|
||||
<idle-timeout>5m</idle-timeout>
|
||||
</basic-scaling>
|
||||
|
||||
<system-properties>
|
||||
<property name="java.util.logging.config.file"
|
||||
value="WEB-INF/logging.properties"/>
|
||||
<property name="google.registry.environment"
|
||||
value="alpha"/>
|
||||
</system-properties>
|
||||
|
||||
<env-variables>
|
||||
<env-var name="GOOGLE_APPLICATION_CREDENTIALS_SKIP_APP_ENGINE" value="true"/>
|
||||
</env-variables>
|
||||
|
||||
<static-files>
|
||||
<include path="/*.html" expiration="1m"/>
|
||||
<include path="/assets/js/**" expiration="1m"/>
|
||||
<include path="/assets/css/**" expiration="1m"/>
|
||||
<include path="/assets/images/**" expiration="1m"/>
|
||||
</static-files>
|
||||
</appengine-web-app>
|
||||
@@ -1,4 +0,0 @@
|
||||
<?xml version="1.0" encoding="utf-8" standalone="no"?>
|
||||
<appengine-application xmlns="http://appengine.google.com/ns/1.0">
|
||||
<application>domain-registry</application>
|
||||
</appengine-application>
|
||||
@@ -1,46 +0,0 @@
|
||||
<?xml version="1.0"
|
||||
encoding="UTF-8"?>
|
||||
|
||||
<application
|
||||
xmlns="http://java.sun.com/xml/ns/javaee"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
|
||||
http://java.sun.com/xml/ns/javaee/application_5.xsd"
|
||||
version="5">
|
||||
|
||||
<description>Google Registry</description>
|
||||
<display-name>Google Registry</display-name>
|
||||
|
||||
<!-- Modules -->
|
||||
<!-- The default module should be listed first -->
|
||||
<module>
|
||||
<web>
|
||||
<web-uri>default</web-uri>
|
||||
<context-root>default</context-root>
|
||||
</web>
|
||||
</module>
|
||||
<module>
|
||||
<web>
|
||||
<web-uri>pubapi</web-uri>
|
||||
<context-root>pubapi</context-root>
|
||||
</web>
|
||||
</module>
|
||||
<module>
|
||||
<web>
|
||||
<web-uri>backend</web-uri>
|
||||
<context-root>backend</context-root>
|
||||
</web>
|
||||
</module>
|
||||
<module>
|
||||
<web>
|
||||
<web-uri>bsa</web-uri>
|
||||
<context-root>bsa</context-root>
|
||||
</web>
|
||||
</module>
|
||||
<module>
|
||||
<web>
|
||||
<web-uri>tools</web-uri>
|
||||
<context-root>tools</context-root>
|
||||
</web>
|
||||
</module>
|
||||
</application>
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user