google-nomulus/java/google/registry/flows/FlowModule.java
mmuller b70f57b7c7 Update copyright year on all license headers
-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=146111211
2017-02-02 16:27:22 -05:00

313 lines
8.8 KiB
Java

// Copyright 2017 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.flows;
import static com.google.common.base.Preconditions.checkState;
import static com.google.common.base.Strings.nullToEmpty;
import com.google.common.base.Optional;
import com.google.common.base.Strings;
import dagger.Module;
import dagger.Provides;
import google.registry.flows.picker.FlowPicker;
import google.registry.model.domain.launch.ApplicationIdTargetExtension;
import google.registry.model.domain.metadata.MetadataExtension;
import google.registry.model.eppcommon.AuthInfo;
import google.registry.model.eppcommon.Trid;
import google.registry.model.eppinput.EppInput;
import google.registry.model.eppinput.EppInput.Poll;
import google.registry.model.eppinput.EppInput.ResourceCommandWrapper;
import google.registry.model.eppinput.ResourceCommand;
import google.registry.model.eppinput.ResourceCommand.SingleResourceCommand;
import google.registry.model.eppoutput.EppResponse;
import google.registry.model.eppoutput.Result;
import google.registry.model.reporting.HistoryEntry;
import java.lang.annotation.Documented;
import javax.inject.Qualifier;
/** Module to choose and instantiate an EPP flow. */
@Module
public class FlowModule {
private EppInput eppInput;
private byte[] inputXmlBytes;
private SessionMetadata sessionMetadata;
private TransportCredentials credentials;
private boolean isDryRun;
private EppRequestSource eppRequestSource;
private boolean isSuperuser;
private FlowModule() {}
/** Builder for {@link FlowModule}. */
static class Builder {
FlowModule module = new FlowModule();
Builder setEppInput(EppInput eppInput) {
module.eppInput = eppInput;
return this;
}
Builder setInputXmlBytes(byte[] inputXmlBytes) {
module.inputXmlBytes = inputXmlBytes;
return this;
}
Builder setSessionMetadata(SessionMetadata sessionMetadata) {
module.sessionMetadata = sessionMetadata;
return this;
}
Builder setIsDryRun(boolean isDryRun) {
module.isDryRun = isDryRun;
return this;
}
Builder setIsSuperuser(boolean isSuperuser) {
module.isSuperuser = isSuperuser;
return this;
}
Builder setEppRequestSource(EppRequestSource eppRequestSource) {
module.eppRequestSource = eppRequestSource;
return this;
}
Builder setCredentials(TransportCredentials credentials) {
module.credentials = credentials;
return this;
}
FlowModule build() {
try {
checkState(module != null, "Already built");
return module;
} finally {
module = null;
}
}
}
@Provides
@FlowScope
@InputXml
byte[] provideInputXml() {
return inputXmlBytes;
}
@Provides
@FlowScope
EppInput provideEppInput() {
return eppInput;
}
@Provides
@FlowScope
SessionMetadata provideSessionMetadata() {
return sessionMetadata;
}
@Provides
@FlowScope
@DryRun
boolean provideIsDryRun() {
return isDryRun;
}
@Provides
@FlowScope
@Transactional
boolean provideIsTransactional(Class<? extends Flow> flowClass) {
return TransactionalFlow.class.isAssignableFrom(flowClass);
}
@Provides
@FlowScope
@Superuser
boolean provideIsSuperuser() {
return isSuperuser;
}
@Provides
@FlowScope
EppRequestSource provideEppRequestSource() {
return eppRequestSource;
}
@Provides
@FlowScope
TransportCredentials provideTransportCredentials() {
return credentials;
}
@Provides
@FlowScope
@ClientId
static String provideClientId(SessionMetadata sessionMetadata) {
// Treat a missing clientId as null so we can always inject a non-null value. All we do with the
// clientId is log it (as "") or detect its absence, both of which work fine with empty.
return Strings.nullToEmpty(sessionMetadata.getClientId());
}
@Provides
@FlowScope
static Trid provideTrid(EppInput eppInput) {
return Trid.create(eppInput.getCommandWrapper().getClTrid());
}
@Provides
@FlowScope
static Class<? extends Flow> provideFlowClass(EppInput eppInput) {
try {
return FlowPicker.getFlowClass(eppInput);
} catch (EppException e) {
throw new EppExceptionInProviderException(e);
}
}
@Provides
@FlowScope
static ResourceCommand provideResourceCommand(EppInput eppInput) {
return ((ResourceCommandWrapper) eppInput.getCommandWrapper().getCommand())
.getResourceCommand();
}
@Provides
@FlowScope
static AuthInfo provideAuthInfo(ResourceCommand resourceCommand) {
return ((SingleResourceCommand) resourceCommand).getAuthInfo();
}
@Provides
@FlowScope
static Optional<AuthInfo> provideOptionalAuthInfo(ResourceCommand resourceCommand) {
return Optional.fromNullable(((SingleResourceCommand) resourceCommand).getAuthInfo());
}
@Provides
@FlowScope
@TargetId
static String provideTargetId(ResourceCommand resourceCommand) {
return ((SingleResourceCommand) resourceCommand).getTargetId();
}
@Provides
@FlowScope
@ApplicationId
static String provideApplicationId(EppInput eppInput) {
// Treat a missing application id as empty so we can always inject a non-null value.
return nullToEmpty(
eppInput.getSingleExtension(ApplicationIdTargetExtension.class).getApplicationId());
}
@Provides
@FlowScope
@PollMessageId
static String providePollMessageId(EppInput eppInput) {
return Strings.nullToEmpty(((Poll) eppInput.getCommandWrapper().getCommand()).getMessageId());
}
/**
* Provides a partially filled in {@link HistoryEntry} builder.
*
* <p>This is not marked with {@link FlowScope} so that each retry gets a fresh one. Otherwise,
* the fact that the builder is one-use would cause NPEs.
*/
@Provides
static HistoryEntry.Builder provideHistoryEntryBuilder(
Trid trid,
@InputXml byte[] inputXmlBytes,
@Superuser boolean isSuperuser,
@ClientId String clientId,
EppInput eppInput) {
HistoryEntry.Builder historyBuilder = new HistoryEntry.Builder()
.setTrid(trid)
.setXmlBytes(inputXmlBytes)
.setBySuperuser(isSuperuser)
.setClientId(clientId);
MetadataExtension metadataExtension = eppInput.getSingleExtension(MetadataExtension.class);
if (metadataExtension != null) {
historyBuilder
.setReason(metadataExtension.getReason())
.setRequestedByRegistrar(metadataExtension.getRequestedByRegistrar());
}
return historyBuilder;
}
/**
* Provides a partially filled in {@link EppResponse} builder.
*
* <p>This is not marked with {@link FlowScope} so that each retry gets a fresh one. Otherwise,
* the fact that the builder is one-use would cause NPEs.
*/
@Provides
static EppResponse.Builder provideEppResponseBuilder(Trid trid) {
return new EppResponse.Builder()
.setTrid(trid)
.setResultFromCode(Result.Code.SUCCESS); // Default to success.
}
@Provides
static FlowMetadata provideFlowMetadata(@Superuser boolean isSuperuser) {
return FlowMetadata.newBuilder().setSuperuser(isSuperuser).build();
}
/** Wrapper class to carry an {@link EppException} to the calling code. */
static class EppExceptionInProviderException extends RuntimeException {
EppExceptionInProviderException(EppException exception) {
super(exception);
}
}
/** Dagger qualifier for inputXml. */
@Qualifier
@Documented
public @interface InputXml {}
/** Dagger qualifier for registrar client id. */
@Qualifier
@Documented
public @interface ClientId {}
/** Dagger qualifier for the target id (foreign key) for single resource flows. */
@Qualifier
@Documented
public @interface TargetId {}
/** Dagger qualifier for the application id for domain application flows. */
@Qualifier
@Documented
public @interface ApplicationId {}
/** Dagger qualifier for the message id for poll flows. */
@Qualifier
@Documented
public @interface PollMessageId {}
/** Dagger qualifier for whether a flow is in dry run mode. */
@Qualifier
@Documented
public @interface DryRun {}
/** Dagger qualifier for whether a flow is in superuser mode. */
@Qualifier
@Documented
public @interface Superuser {}
/** Dagger qualifier for whether a flow is transactional. */
@Qualifier
@Documented
public @interface Transactional {}
}