1
0
mirror of https://github.com/google/nomulus synced 2026-01-05 04:56:03 +00:00

Add console user role update and minor fixes to delete (#2610)

This commit is contained in:
Pavlo Tkach
2024-11-15 13:36:10 -05:00
committed by GitHub
parent e54075fea3
commit eeed166310
12 changed files with 380 additions and 183 deletions

View File

@@ -34,6 +34,7 @@ public @interface Action {
GET,
HEAD,
POST,
PUT,
DELETE
}

View File

@@ -20,6 +20,7 @@ import static google.registry.request.Action.Method.DELETE;
import static google.registry.request.Action.Method.GET;
import static google.registry.request.Action.Method.HEAD;
import static google.registry.request.Action.Method.POST;
import static google.registry.request.Action.Method.PUT;
import static jakarta.servlet.http.HttpServletResponse.SC_BAD_REQUEST;
import static jakarta.servlet.http.HttpServletResponse.SC_FORBIDDEN;
import static jakarta.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
@@ -87,6 +88,8 @@ public abstract class ConsoleApiAction implements Runnable {
if (verifyXSRF(user)) {
if (requestMethod.equals(DELETE.toString())) {
deleteHandler(user);
} else if (requestMethod.equals(PUT.toString())) {
putHandler(user);
} else {
postHandler(user);
}
@@ -117,6 +120,10 @@ public abstract class ConsoleApiAction implements Runnable {
throw new UnsupportedOperationException("Console API POST handler not implemented");
}
protected void putHandler(User user) {
throw new UnsupportedOperationException("Console API PUT handler not implemented");
}
protected void getHandler(User user) {
throw new UnsupportedOperationException("Console API GET handler not implemented");
}

View File

@@ -36,7 +36,7 @@ import google.registry.ui.server.SendEmailUtils;
import google.registry.ui.server.console.ConsoleEppPasswordAction.EppPasswordData;
import google.registry.ui.server.console.ConsoleOteAction.OteCreateData;
import google.registry.ui.server.console.ConsoleRegistryLockAction.ConsoleRegistryLockPostInput;
import google.registry.ui.server.console.ConsoleUsersAction.UserDeleteData;
import google.registry.ui.server.console.ConsoleUsersAction.UserData;
import jakarta.servlet.http.HttpServletRequest;
import java.util.Optional;
import org.joda.time.DateTime;
@@ -247,10 +247,10 @@ public final class ConsoleModule {
}
@Provides
@Parameter("userDeleteData")
public static Optional<UserDeleteData> provideUserDeleteData(
@Parameter("userData")
public static Optional<UserData> provideUserData(
Gson gson, @OptionalJsonPayload Optional<JsonElement> payload) {
return payload.map(s -> gson.fromJson(s, UserDeleteData.class));
return payload.map(s -> gson.fromJson(s, UserData.class));
}
@Provides

View File

@@ -21,6 +21,7 @@ import static google.registry.persistence.transaction.TransactionManagerFactory.
import static google.registry.request.Action.Method.DELETE;
import static google.registry.request.Action.Method.GET;
import static google.registry.request.Action.Method.POST;
import static google.registry.request.Action.Method.PUT;
import static jakarta.servlet.http.HttpServletResponse.SC_CREATED;
import static jakarta.servlet.http.HttpServletResponse.SC_FORBIDDEN;
import static jakarta.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
@@ -35,6 +36,7 @@ import com.google.gson.Gson;
import com.google.gson.annotations.Expose;
import google.registry.config.RegistryConfig.Config;
import google.registry.model.console.ConsolePermission;
import google.registry.model.console.RegistrarRole;
import google.registry.model.console.User;
import google.registry.model.console.UserRoles;
import google.registry.persistence.VKey;
@@ -50,6 +52,7 @@ import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;
import java.util.stream.IntStream;
import javax.annotation.Nullable;
import javax.inject.Inject;
import javax.inject.Named;
@@ -57,7 +60,7 @@ import javax.inject.Named;
service = Action.GaeService.DEFAULT,
gkeService = GkeService.CONSOLE,
path = ConsoleUsersAction.PATH,
method = {GET, POST, DELETE},
method = {GET, POST, DELETE, PUT},
auth = Auth.AUTH_PUBLIC_LOGGED_IN)
public class ConsoleUsersAction extends ConsoleApiAction {
static final String PATH = "/console-api/users";
@@ -68,7 +71,7 @@ public class ConsoleUsersAction extends ConsoleApiAction {
private final String registrarId;
private final Directory directory;
private final StringGenerator passwordGenerator;
private final Optional<UserDeleteData> userDeleteData;
private final Optional<UserData> userData;
private final Optional<String> maybeGroupEmailAddress;
private final IamClient iamClient;
private final String gSuiteDomainName;
@@ -82,14 +85,14 @@ public class ConsoleUsersAction extends ConsoleApiAction {
@Config("gSuiteDomainName") String gSuiteDomainName,
@Config("gSuiteConsoleUserGroupEmailAddress") Optional<String> maybeGroupEmailAddress,
@Named("base58StringGenerator") StringGenerator passwordGenerator,
@Parameter("userDeleteData") Optional<UserDeleteData> userDeleteData,
@Parameter("userData") Optional<UserData> userData,
@Parameter("registrarId") String registrarId) {
super(consoleApiParams);
this.gson = gson;
this.registrarId = registrarId;
this.directory = directory;
this.passwordGenerator = passwordGenerator;
this.userDeleteData = userDeleteData;
this.userData = userData;
this.maybeGroupEmailAddress = maybeGroupEmailAddress;
this.iamClient = iamClient;
this.gSuiteDomainName = gSuiteDomainName;
@@ -106,18 +109,28 @@ public class ConsoleUsersAction extends ConsoleApiAction {
}
}
@Override
protected void putHandler(User user) {
// Temporary flag while testing
if (user.getUserRoles().isAdmin()) {
checkPermission(user, registrarId, ConsolePermission.MANAGE_USERS);
tm().transact(() -> runUpdateInTransaction());
} else {
consoleApiParams.response().setStatus(SC_FORBIDDEN);
}
}
@Override
protected void getHandler(User user) {
checkPermission(user, registrarId, ConsolePermission.MANAGE_USERS);
List<ImmutableMap> users =
List<UserData> users =
getAllRegistrarUsers(registrarId).stream()
.map(
u ->
ImmutableMap.of(
"emailAddress",
new UserData(
u.getEmailAddress(),
"role",
u.getUserRoles().getRegistrarRoles().get(registrarId)))
u.getUserRoles().getRegistrarRoles().get(registrarId).toString(),
null))
.collect(Collectors.toList());
consoleApiParams.response().setPayload(gson.toJson(users));
@@ -136,22 +149,10 @@ public class ConsoleUsersAction extends ConsoleApiAction {
}
private void runDeleteInTransaction() throws IOException {
if (userDeleteData.isEmpty() || isNullOrEmpty(userDeleteData.get().userEmail)) {
throw new BadRequestException("Missing user data param");
}
String email = userDeleteData.get().userEmail;
User userToDelete =
tm().loadByKeyIfPresent(VKey.create(User.class, email))
.orElseThrow(
() -> new BadRequestException(String.format("User %s doesn't exist", email)));
if (!userToDelete.getUserRoles().getRegistrarRoles().containsKey(registrarId)) {
setFailedResponse(
String.format("Can't delete user not associated with registrarId %s", registrarId),
SC_FORBIDDEN);
if (!isModifyingRequestValid()) {
return;
}
String email = this.userData.get().emailAddress;
try {
directory.users().delete(email).execute();
} catch (IOException e) {
@@ -213,13 +214,50 @@ public class ConsoleUsersAction extends ConsoleApiAction {
.response()
.setPayload(
gson.toJson(
ImmutableMap.of(
"password",
newUser.getPassword(),
"emailAddress",
newUser.getPrimaryEmail(),
"role",
ACCOUNT_MANAGER)));
new UserData(
newUser.getPrimaryEmail(), ACCOUNT_MANAGER.toString(), newUser.getPassword())));
}
private void runUpdateInTransaction() {
if (!isModifyingRequestValid()) {
return;
}
UserData userData = this.userData.get();
UserRoles userRoles =
new UserRoles.Builder()
.setRegistrarRoles(ImmutableMap.of(registrarId, RegistrarRole.valueOf(userData.role)))
.build();
User updatedUser =
tm().loadByKeyIfPresent(VKey.create(User.class, userData.emailAddress))
.get()
.asBuilder()
.setUserRoles(userRoles)
.build();
tm().put(updatedUser);
consoleApiParams.response().setStatus(SC_OK);
}
private boolean isModifyingRequestValid() {
if (userData.isEmpty()
|| isNullOrEmpty(userData.get().emailAddress)
|| isNullOrEmpty(userData.get().role)) {
throw new BadRequestException("User data is missing or incomplete");
}
String email = userData.get().emailAddress;
User userToUpdate =
tm().loadByKeyIfPresent(VKey.create(User.class, email))
.orElseThrow(
() -> new BadRequestException(String.format("User %s doesn't exist", email)));
if (!userToUpdate.getUserRoles().getRegistrarRoles().containsKey(registrarId)) {
setFailedResponse(
String.format("Can't update user not associated with registrarId %s", registrarId),
SC_FORBIDDEN);
return false;
}
return true;
}
private ImmutableList<User> getAllRegistrarUsers(String registrarId) {
@@ -230,5 +268,6 @@ public class ConsoleUsersAction extends ConsoleApiAction {
.collect(toImmutableList()));
}
public record UserDeleteData(@Expose String userEmail) {}
public record UserData(
@Expose String emailAddress, @Expose String role, @Expose @Nullable String password) {}
}

View File

@@ -44,7 +44,7 @@ import google.registry.testing.DatabaseHelper;
import google.registry.testing.DeterministicStringGenerator;
import google.registry.testing.FakeResponse;
import google.registry.tools.IamClient;
import google.registry.ui.server.console.ConsoleUsersAction.UserDeleteData;
import google.registry.ui.server.console.ConsoleUsersAction.UserData;
import google.registry.util.StringGenerator;
import jakarta.servlet.http.HttpServletResponse;
import java.io.IOException;
@@ -176,7 +176,7 @@ class ConsoleUsersActionTest {
assertThat(response.getStatus()).isEqualTo(SC_CREATED);
assertThat(response.getPayload())
.contains(
"{\"password\":\"abcdefghijklmnop\",\"emailAddress\":\"TheRegistrar-user1@email.com\",\"role\":\"ACCOUNT_MANAGER\"}");
"{\"emailAddress\":\"TheRegistrar-user1@email.com\",\"role\":\"ACCOUNT_MANAGER\",\"password\":\"abcdefghijklmnop\"}");
}
@Test
@@ -192,14 +192,15 @@ class ConsoleUsersActionTest {
createAction(
Optional.of(ConsoleApiParamsUtils.createFake(authResult)),
Optional.of("DELETE"),
Optional.of(new UserDeleteData("test3@test.com")));
Optional.of(
new UserData("test3@test.com", RegistrarRole.ACCOUNT_MANAGER.toString(), null)));
when(directory.users()).thenReturn(users);
when(users.delete(any(String.class))).thenReturn(delete);
action.run();
var response = ((FakeResponse) consoleApiParams.response());
assertThat(response.getStatus()).isEqualTo(SC_FORBIDDEN);
assertThat(response.getPayload())
.contains("Can't delete user not associated with registrarId TheRegistrar");
.contains("Can't update user not associated with registrarId TheRegistrar");
}
@Test
@@ -210,7 +211,8 @@ class ConsoleUsersActionTest {
createAction(
Optional.of(ConsoleApiParamsUtils.createFake(authResult)),
Optional.of("DELETE"),
Optional.of(new UserDeleteData("email-1@email.com")));
Optional.of(
new UserData("email-1@email.com", RegistrarRole.ACCOUNT_MANAGER.toString(), null)));
when(directory.users()).thenReturn(users);
when(users.delete(any(String.class))).thenReturn(delete);
action.run();
@@ -232,7 +234,8 @@ class ConsoleUsersActionTest {
createAction(
Optional.of(ConsoleApiParamsUtils.createFake(authResult)),
Optional.of("DELETE"),
Optional.of(new UserDeleteData("test2@test.com")));
Optional.of(
new UserData("test2@test.com", RegistrarRole.ACCOUNT_MANAGER.toString(), null)));
action.cloudTasksUtils = cloudTasksHelper.getTestCloudTasksUtils();
when(directory.users()).thenReturn(users);
when(users.delete(any(String.class))).thenReturn(delete);
@@ -282,10 +285,66 @@ class ConsoleUsersActionTest {
assertThat(response.getPayload()).contains("Total users amount per registrar is limited to 4");
}
@Test
void testSuccess_updatesUserRole() throws IOException {
User user1 = DatabaseHelper.loadByKey(VKey.create(User.class, "test1@test.com"));
AuthResult authResult =
AuthResult.createUser(
user1
.asBuilder()
.setUserRoles(user1.getUserRoles().asBuilder().setIsAdmin(true).build())
.build());
assertThat(
DatabaseHelper.loadByKey(VKey.create(User.class, "test2@test.com"))
.getUserRoles()
.getRegistrarRoles()
.get("TheRegistrar"))
.isEqualTo(RegistrarRole.PRIMARY_CONTACT);
ConsoleUsersAction action =
createAction(
Optional.of(ConsoleApiParamsUtils.createFake(authResult)),
Optional.of("PUT"),
Optional.of(
new UserData("test2@test.com", RegistrarRole.ACCOUNT_MANAGER.toString(), null)));
action.cloudTasksUtils = cloudTasksHelper.getTestCloudTasksUtils();
action.run();
var response = ((FakeResponse) consoleApiParams.response());
assertThat(response.getStatus()).isEqualTo(SC_OK);
assertThat(
DatabaseHelper.loadByKey(VKey.create(User.class, "test2@test.com"))
.getUserRoles()
.getRegistrarRoles()
.get("TheRegistrar"))
.isEqualTo(RegistrarRole.ACCOUNT_MANAGER);
}
@Test
void testFailure_noPermissionToUpdateUser() throws IOException {
User user1 = DatabaseHelper.loadByKey(VKey.create(User.class, "test1@test.com"));
AuthResult authResult =
AuthResult.createUser(
user1
.asBuilder()
.setUserRoles(user1.getUserRoles().asBuilder().setIsAdmin(true).build())
.build());
ConsoleUsersAction action =
createAction(
Optional.of(ConsoleApiParamsUtils.createFake(authResult)),
Optional.of("PUT"),
Optional.of(
new UserData("test3@test.com", RegistrarRole.ACCOUNT_MANAGER.toString(), null)));
action.run();
var response = ((FakeResponse) consoleApiParams.response());
assertThat(response.getStatus()).isEqualTo(SC_FORBIDDEN);
assertThat(response.getPayload())
.contains("Can't update user not associated with registrarId TheRegistrar");
}
private ConsoleUsersAction createAction(
Optional<ConsoleApiParams> maybeConsoleApiParams,
Optional<String> method,
Optional<UserDeleteData> userDeleteData)
Optional<UserData> userData)
throws IOException {
consoleApiParams =
maybeConsoleApiParams.orElseGet(
@@ -299,7 +358,7 @@ class ConsoleUsersActionTest {
"email.com",
Optional.of("someRandomString"),
passwordGenerator,
userDeleteData,
userData,
"TheRegistrar");
}
}

View File

@@ -1,16 +1,16 @@
SERVICE PATH CLASS METHODS OK MIN USER_POLICY
FRONTEND /_dr/epp EppTlsAction POST n APP ADMIN
CONSOLE /console-api/domain ConsoleDomainGetAction GET n USER PUBLIC
CONSOLE /console-api/domain-list ConsoleDomainListAction GET n USER PUBLIC
CONSOLE /console-api/dum-download ConsoleDumDownloadAction GET n USER PUBLIC
CONSOLE /console-api/eppPassword ConsoleEppPasswordAction POST n USER PUBLIC
CONSOLE /console-api/ote ConsoleOteAction GET,POST n USER PUBLIC
CONSOLE /console-api/registrar ConsoleUpdateRegistrarAction POST n USER PUBLIC
CONSOLE /console-api/registrars RegistrarsAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock ConsoleRegistryLockAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock-verify ConsoleRegistryLockVerifyAction GET n USER PUBLIC
CONSOLE /console-api/settings/contacts ContactAction GET,POST n USER PUBLIC
CONSOLE /console-api/settings/security SecurityAction POST n USER PUBLIC
CONSOLE /console-api/settings/whois-fields WhoisRegistrarFieldsAction POST n USER PUBLIC
CONSOLE /console-api/userdata ConsoleUserDataAction GET n USER PUBLIC
CONSOLE /console-api/users ConsoleUsersAction GET,POST,DELETE n USER PUBLIC
SERVICE PATH CLASS METHODS OK MIN USER_POLICY
FRONTEND /_dr/epp EppTlsAction POST n APP ADMIN
CONSOLE /console-api/domain ConsoleDomainGetAction GET n USER PUBLIC
CONSOLE /console-api/domain-list ConsoleDomainListAction GET n USER PUBLIC
CONSOLE /console-api/dum-download ConsoleDumDownloadAction GET n USER PUBLIC
CONSOLE /console-api/eppPassword ConsoleEppPasswordAction POST n USER PUBLIC
CONSOLE /console-api/ote ConsoleOteAction GET,POST n USER PUBLIC
CONSOLE /console-api/registrar ConsoleUpdateRegistrarAction POST n USER PUBLIC
CONSOLE /console-api/registrars RegistrarsAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock ConsoleRegistryLockAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock-verify ConsoleRegistryLockVerifyAction GET n USER PUBLIC
CONSOLE /console-api/settings/contacts ContactAction GET,POST n USER PUBLIC
CONSOLE /console-api/settings/security SecurityAction POST n USER PUBLIC
CONSOLE /console-api/settings/whois-fields WhoisRegistrarFieldsAction POST n USER PUBLIC
CONSOLE /console-api/userdata ConsoleUserDataAction GET n USER PUBLIC
CONSOLE /console-api/users ConsoleUsersAction GET,POST,DELETE,PUT n USER PUBLIC

View File

@@ -1,82 +1,82 @@
SERVICE PATH CLASS METHODS OK MIN USER_POLICY
FRONTEND /_dr/epp EppTlsAction POST n APP ADMIN
BACKEND /_dr/admin/createGroups CreateGroupsAction POST n APP ADMIN
BACKEND /_dr/admin/list/domains ListDomainsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/hosts ListHostsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/premiumLists ListPremiumListsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/registrars ListRegistrarsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/reservedLists ListReservedListsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/tlds ListTldsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/updateUserGroup UpdateUserGroupAction POST n APP ADMIN
BACKEND /_dr/admin/verifyOte VerifyOteAction POST n APP ADMIN
BACKEND /_dr/cron/fanout TldFanoutAction GET y APP ADMIN
BACKEND /_dr/epptool EppToolAction POST n APP ADMIN
BACKEND /_dr/loadtest LoadTestAction POST y APP ADMIN
BACKEND /_dr/task/brdaCopy BrdaCopyAction POST y APP ADMIN
BACKEND /_dr/task/bsaDownload BsaDownloadAction GET,POST n APP ADMIN
BACKEND /_dr/task/bsaRefresh BsaRefreshAction GET,POST n APP ADMIN
BACKEND /_dr/task/bsaValidate BsaValidateAction GET,POST n APP ADMIN
BACKEND /_dr/task/copyDetailReports CopyDetailReportsAction POST n APP ADMIN
BACKEND /_dr/task/deleteExpiredDomains DeleteExpiredDomainsAction GET n APP ADMIN
BACKEND /_dr/task/deleteLoadTestData DeleteLoadTestDataAction POST n APP ADMIN
BACKEND /_dr/task/deleteProberData DeleteProberDataAction POST n APP ADMIN
BACKEND /_dr/task/dnsRefresh RefreshDnsAction GET y APP ADMIN
BACKEND /_dr/task/executeCannedScript CannedScriptExecutionAction POST,GET y APP ADMIN
BACKEND /_dr/task/expandBillingRecurrences ExpandBillingRecurrencesAction GET n APP ADMIN
BACKEND /_dr/task/exportDomainLists ExportDomainListsAction POST n APP ADMIN
BACKEND /_dr/task/exportPremiumTerms ExportPremiumTermsAction POST n APP ADMIN
BACKEND /_dr/task/exportReservedTerms ExportReservedTermsAction POST n APP ADMIN
BACKEND /_dr/task/generateInvoices GenerateInvoicesAction POST n APP ADMIN
BACKEND /_dr/task/generateSpec11 GenerateSpec11ReportAction POST n APP ADMIN
BACKEND /_dr/task/generateZoneFiles GenerateZoneFilesAction POST n APP ADMIN
BACKEND /_dr/task/icannReportingStaging IcannReportingStagingAction POST n APP ADMIN
BACKEND /_dr/task/icannReportingUpload IcannReportingUploadAction POST n APP ADMIN
BACKEND /_dr/task/nordnUpload NordnUploadAction POST y APP ADMIN
BACKEND /_dr/task/nordnVerify NordnVerifyAction POST y APP ADMIN
BACKEND /_dr/task/publishDnsUpdates PublishDnsUpdatesAction POST y APP ADMIN
BACKEND /_dr/task/publishInvoices PublishInvoicesAction POST n APP ADMIN
BACKEND /_dr/task/publishSpec11 PublishSpec11ReportAction POST n APP ADMIN
BACKEND /_dr/task/rdeReport RdeReportAction POST n APP ADMIN
BACKEND /_dr/task/rdeStaging RdeStagingAction GET,POST n APP ADMIN
BACKEND /_dr/task/rdeUpload RdeUploadAction POST n APP ADMIN
BACKEND /_dr/task/readDnsRefreshRequests ReadDnsRefreshRequestsAction POST y APP ADMIN
BACKEND /_dr/task/refreshDnsForAllDomains RefreshDnsForAllDomainsAction GET n APP ADMIN
BACKEND /_dr/task/refreshDnsOnHostRename RefreshDnsOnHostRenameAction POST n APP ADMIN
BACKEND /_dr/task/relockDomain RelockDomainAction POST y APP ADMIN
BACKEND /_dr/task/resaveAllEppResourcesPipeline ResaveAllEppResourcesPipelineAction GET n APP ADMIN
BACKEND /_dr/task/resaveEntity ResaveEntityAction POST n APP ADMIN
BACKEND /_dr/task/sendExpiringCertificateNotificationEmail SendExpiringCertificateNotificationEmailAction GET n APP ADMIN
BACKEND /_dr/task/syncGroupMembers SyncGroupMembersAction POST n APP ADMIN
BACKEND /_dr/task/syncRegistrarsSheet SyncRegistrarsSheetAction POST n APP ADMIN
BACKEND /_dr/task/tmchCrl TmchCrlAction POST y APP ADMIN
BACKEND /_dr/task/tmchDnl TmchDnlAction POST y APP ADMIN
BACKEND /_dr/task/tmchSmdrl TmchSmdrlAction POST y APP ADMIN
BACKEND /_dr/task/updateRegistrarRdapBaseUrls UpdateRegistrarRdapBaseUrlsAction GET y APP ADMIN
BACKEND /_dr/task/uploadBsaUnavailableNames UploadBsaUnavailableDomainsAction GET,POST n APP ADMIN
BACKEND /_dr/task/wipeOutContactHistoryPii WipeOutContactHistoryPiiAction GET n APP ADMIN
PUBAPI /_dr/whois WhoisAction POST n APP ADMIN
PUBAPI /check CheckApiAction GET n NONE PUBLIC
PUBAPI /rdap/autnum/(*) RdapAutnumAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/domain/(*) RdapDomainAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/domains RdapDomainSearchAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/entities RdapEntitySearchAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/entity/(*) RdapEntityAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/help(*) RdapHelpAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/ip/(*) RdapIpAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/nameserver/(*) RdapNameserverAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/nameservers RdapNameserverSearchAction GET,HEAD n NONE PUBLIC
PUBAPI /whois/(*) WhoisHttpAction GET n NONE PUBLIC
CONSOLE /console-api/domain ConsoleDomainGetAction GET n USER PUBLIC
CONSOLE /console-api/domain-list ConsoleDomainListAction GET n USER PUBLIC
CONSOLE /console-api/dum-download ConsoleDumDownloadAction GET n USER PUBLIC
CONSOLE /console-api/eppPassword ConsoleEppPasswordAction POST n USER PUBLIC
CONSOLE /console-api/ote ConsoleOteAction GET,POST n USER PUBLIC
CONSOLE /console-api/registrar ConsoleUpdateRegistrarAction POST n USER PUBLIC
CONSOLE /console-api/registrars RegistrarsAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock ConsoleRegistryLockAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock-verify ConsoleRegistryLockVerifyAction GET n USER PUBLIC
CONSOLE /console-api/settings/contacts ContactAction GET,POST n USER PUBLIC
CONSOLE /console-api/settings/security SecurityAction POST n USER PUBLIC
CONSOLE /console-api/settings/whois-fields WhoisRegistrarFieldsAction POST n USER PUBLIC
CONSOLE /console-api/userdata ConsoleUserDataAction GET n USER PUBLIC
CONSOLE /console-api/users ConsoleUsersAction GET,POST,DELETE n USER PUBLIC
SERVICE PATH CLASS METHODS OK MIN USER_POLICY
FRONTEND /_dr/epp EppTlsAction POST n APP ADMIN
BACKEND /_dr/admin/createGroups CreateGroupsAction POST n APP ADMIN
BACKEND /_dr/admin/list/domains ListDomainsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/hosts ListHostsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/premiumLists ListPremiumListsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/registrars ListRegistrarsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/reservedLists ListReservedListsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/list/tlds ListTldsAction GET,POST n APP ADMIN
BACKEND /_dr/admin/updateUserGroup UpdateUserGroupAction POST n APP ADMIN
BACKEND /_dr/admin/verifyOte VerifyOteAction POST n APP ADMIN
BACKEND /_dr/cron/fanout TldFanoutAction GET y APP ADMIN
BACKEND /_dr/epptool EppToolAction POST n APP ADMIN
BACKEND /_dr/loadtest LoadTestAction POST y APP ADMIN
BACKEND /_dr/task/brdaCopy BrdaCopyAction POST y APP ADMIN
BACKEND /_dr/task/bsaDownload BsaDownloadAction GET,POST n APP ADMIN
BACKEND /_dr/task/bsaRefresh BsaRefreshAction GET,POST n APP ADMIN
BACKEND /_dr/task/bsaValidate BsaValidateAction GET,POST n APP ADMIN
BACKEND /_dr/task/copyDetailReports CopyDetailReportsAction POST n APP ADMIN
BACKEND /_dr/task/deleteExpiredDomains DeleteExpiredDomainsAction GET n APP ADMIN
BACKEND /_dr/task/deleteLoadTestData DeleteLoadTestDataAction POST n APP ADMIN
BACKEND /_dr/task/deleteProberData DeleteProberDataAction POST n APP ADMIN
BACKEND /_dr/task/dnsRefresh RefreshDnsAction GET y APP ADMIN
BACKEND /_dr/task/executeCannedScript CannedScriptExecutionAction POST,GET y APP ADMIN
BACKEND /_dr/task/expandBillingRecurrences ExpandBillingRecurrencesAction GET n APP ADMIN
BACKEND /_dr/task/exportDomainLists ExportDomainListsAction POST n APP ADMIN
BACKEND /_dr/task/exportPremiumTerms ExportPremiumTermsAction POST n APP ADMIN
BACKEND /_dr/task/exportReservedTerms ExportReservedTermsAction POST n APP ADMIN
BACKEND /_dr/task/generateInvoices GenerateInvoicesAction POST n APP ADMIN
BACKEND /_dr/task/generateSpec11 GenerateSpec11ReportAction POST n APP ADMIN
BACKEND /_dr/task/generateZoneFiles GenerateZoneFilesAction POST n APP ADMIN
BACKEND /_dr/task/icannReportingStaging IcannReportingStagingAction POST n APP ADMIN
BACKEND /_dr/task/icannReportingUpload IcannReportingUploadAction POST n APP ADMIN
BACKEND /_dr/task/nordnUpload NordnUploadAction POST y APP ADMIN
BACKEND /_dr/task/nordnVerify NordnVerifyAction POST y APP ADMIN
BACKEND /_dr/task/publishDnsUpdates PublishDnsUpdatesAction POST y APP ADMIN
BACKEND /_dr/task/publishInvoices PublishInvoicesAction POST n APP ADMIN
BACKEND /_dr/task/publishSpec11 PublishSpec11ReportAction POST n APP ADMIN
BACKEND /_dr/task/rdeReport RdeReportAction POST n APP ADMIN
BACKEND /_dr/task/rdeStaging RdeStagingAction GET,POST n APP ADMIN
BACKEND /_dr/task/rdeUpload RdeUploadAction POST n APP ADMIN
BACKEND /_dr/task/readDnsRefreshRequests ReadDnsRefreshRequestsAction POST y APP ADMIN
BACKEND /_dr/task/refreshDnsForAllDomains RefreshDnsForAllDomainsAction GET n APP ADMIN
BACKEND /_dr/task/refreshDnsOnHostRename RefreshDnsOnHostRenameAction POST n APP ADMIN
BACKEND /_dr/task/relockDomain RelockDomainAction POST y APP ADMIN
BACKEND /_dr/task/resaveAllEppResourcesPipeline ResaveAllEppResourcesPipelineAction GET n APP ADMIN
BACKEND /_dr/task/resaveEntity ResaveEntityAction POST n APP ADMIN
BACKEND /_dr/task/sendExpiringCertificateNotificationEmail SendExpiringCertificateNotificationEmailAction GET n APP ADMIN
BACKEND /_dr/task/syncGroupMembers SyncGroupMembersAction POST n APP ADMIN
BACKEND /_dr/task/syncRegistrarsSheet SyncRegistrarsSheetAction POST n APP ADMIN
BACKEND /_dr/task/tmchCrl TmchCrlAction POST y APP ADMIN
BACKEND /_dr/task/tmchDnl TmchDnlAction POST y APP ADMIN
BACKEND /_dr/task/tmchSmdrl TmchSmdrlAction POST y APP ADMIN
BACKEND /_dr/task/updateRegistrarRdapBaseUrls UpdateRegistrarRdapBaseUrlsAction GET y APP ADMIN
BACKEND /_dr/task/uploadBsaUnavailableNames UploadBsaUnavailableDomainsAction GET,POST n APP ADMIN
BACKEND /_dr/task/wipeOutContactHistoryPii WipeOutContactHistoryPiiAction GET n APP ADMIN
PUBAPI /_dr/whois WhoisAction POST n APP ADMIN
PUBAPI /check CheckApiAction GET n NONE PUBLIC
PUBAPI /rdap/autnum/(*) RdapAutnumAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/domain/(*) RdapDomainAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/domains RdapDomainSearchAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/entities RdapEntitySearchAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/entity/(*) RdapEntityAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/help(*) RdapHelpAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/ip/(*) RdapIpAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/nameserver/(*) RdapNameserverAction GET,HEAD n NONE PUBLIC
PUBAPI /rdap/nameservers RdapNameserverSearchAction GET,HEAD n NONE PUBLIC
PUBAPI /whois/(*) WhoisHttpAction GET n NONE PUBLIC
CONSOLE /console-api/domain ConsoleDomainGetAction GET n USER PUBLIC
CONSOLE /console-api/domain-list ConsoleDomainListAction GET n USER PUBLIC
CONSOLE /console-api/dum-download ConsoleDumDownloadAction GET n USER PUBLIC
CONSOLE /console-api/eppPassword ConsoleEppPasswordAction POST n USER PUBLIC
CONSOLE /console-api/ote ConsoleOteAction GET,POST n USER PUBLIC
CONSOLE /console-api/registrar ConsoleUpdateRegistrarAction POST n USER PUBLIC
CONSOLE /console-api/registrars RegistrarsAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock ConsoleRegistryLockAction GET,POST n USER PUBLIC
CONSOLE /console-api/registry-lock-verify ConsoleRegistryLockVerifyAction GET n USER PUBLIC
CONSOLE /console-api/settings/contacts ContactAction GET,POST n USER PUBLIC
CONSOLE /console-api/settings/security SecurityAction POST n USER PUBLIC
CONSOLE /console-api/settings/whois-fields WhoisRegistrarFieldsAction POST n USER PUBLIC
CONSOLE /console-api/userdata ConsoleUserDataAction GET n USER PUBLIC
CONSOLE /console-api/users ConsoleUsersAction GET,POST,DELETE,PUT n USER PUBLIC