// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT License.
// Code generated by Microsoft (R) AutoRest Code Generator.

package com.azure.resourcemanager.workloads.models;

import com.azure.core.annotation.Fluent;
import com.azure.core.util.logging.ClientLogger;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonTypeInfo;
import com.fasterxml.jackson.annotation.JsonTypeName;

/**
 * Gets or sets the three tier SAP configuration. For prerequisites for creating the infrastructure, please see
 * [here](https://go.microsoft.com/fwlink/?linkid=2212611&amp;clcid=0x409).
 */
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "deploymentType")
@JsonTypeName("ThreeTier")
@Fluent
public final class ThreeTierConfiguration extends InfrastructureConfiguration {
    /*
     * Network configuration common to all servers
     */
    @JsonProperty(value = "networkConfiguration")
    private NetworkConfiguration networkConfiguration;

    /*
     * The central server configuration.
     */
    @JsonProperty(value = "centralServer", required = true)
    private CentralServerConfiguration centralServer;

    /*
     * The application server configuration.
     */
    @JsonProperty(value = "applicationServer", required = true)
    private ApplicationServerConfiguration applicationServer;

    /*
     * The database configuration.
     */
    @JsonProperty(value = "databaseServer", required = true)
    private DatabaseConfiguration databaseServer;

    /*
     * The high availability configuration.
     */
    @JsonProperty(value = "highAvailabilityConfig")
    private HighAvailabilityConfiguration highAvailabilityConfig;

    /*
     * The storage configuration.
     */
    @JsonProperty(value = "storageConfiguration")
    private StorageConfiguration storageConfiguration;

    /*
     * The set of custom names to be used for underlying azure resources that are part of the SAP system.
     */
    @JsonProperty(value = "customResourceNames")
    private ThreeTierCustomResourceNames customResourceNames;

    /** Creates an instance of ThreeTierConfiguration class. */
    public ThreeTierConfiguration() {
    }

    /**
     * Get the networkConfiguration property: Network configuration common to all servers.
     *
     * @return the networkConfiguration value.
     */
    public NetworkConfiguration networkConfiguration() {
        return this.networkConfiguration;
    }

    /**
     * Set the networkConfiguration property: Network configuration common to all servers.
     *
     * @param networkConfiguration the networkConfiguration value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withNetworkConfiguration(NetworkConfiguration networkConfiguration) {
        this.networkConfiguration = networkConfiguration;
        return this;
    }

    /**
     * Get the centralServer property: The central server configuration.
     *
     * @return the centralServer value.
     */
    public CentralServerConfiguration centralServer() {
        return this.centralServer;
    }

    /**
     * Set the centralServer property: The central server configuration.
     *
     * @param centralServer the centralServer value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withCentralServer(CentralServerConfiguration centralServer) {
        this.centralServer = centralServer;
        return this;
    }

    /**
     * Get the applicationServer property: The application server configuration.
     *
     * @return the applicationServer value.
     */
    public ApplicationServerConfiguration applicationServer() {
        return this.applicationServer;
    }

    /**
     * Set the applicationServer property: The application server configuration.
     *
     * @param applicationServer the applicationServer value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withApplicationServer(ApplicationServerConfiguration applicationServer) {
        this.applicationServer = applicationServer;
        return this;
    }

    /**
     * Get the databaseServer property: The database configuration.
     *
     * @return the databaseServer value.
     */
    public DatabaseConfiguration databaseServer() {
        return this.databaseServer;
    }

    /**
     * Set the databaseServer property: The database configuration.
     *
     * @param databaseServer the databaseServer value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withDatabaseServer(DatabaseConfiguration databaseServer) {
        this.databaseServer = databaseServer;
        return this;
    }

    /**
     * Get the highAvailabilityConfig property: The high availability configuration.
     *
     * @return the highAvailabilityConfig value.
     */
    public HighAvailabilityConfiguration highAvailabilityConfig() {
        return this.highAvailabilityConfig;
    }

    /**
     * Set the highAvailabilityConfig property: The high availability configuration.
     *
     * @param highAvailabilityConfig the highAvailabilityConfig value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withHighAvailabilityConfig(HighAvailabilityConfiguration highAvailabilityConfig) {
        this.highAvailabilityConfig = highAvailabilityConfig;
        return this;
    }

    /**
     * Get the storageConfiguration property: The storage configuration.
     *
     * @return the storageConfiguration value.
     */
    public StorageConfiguration storageConfiguration() {
        return this.storageConfiguration;
    }

    /**
     * Set the storageConfiguration property: The storage configuration.
     *
     * @param storageConfiguration the storageConfiguration value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withStorageConfiguration(StorageConfiguration storageConfiguration) {
        this.storageConfiguration = storageConfiguration;
        return this;
    }

    /**
     * Get the customResourceNames property: The set of custom names to be used for underlying azure resources that are
     * part of the SAP system.
     *
     * @return the customResourceNames value.
     */
    public ThreeTierCustomResourceNames customResourceNames() {
        return this.customResourceNames;
    }

    /**
     * Set the customResourceNames property: The set of custom names to be used for underlying azure resources that are
     * part of the SAP system.
     *
     * @param customResourceNames the customResourceNames value to set.
     * @return the ThreeTierConfiguration object itself.
     */
    public ThreeTierConfiguration withCustomResourceNames(ThreeTierCustomResourceNames customResourceNames) {
        this.customResourceNames = customResourceNames;
        return this;
    }

    /** {@inheritDoc} */
    @Override
    public ThreeTierConfiguration withAppResourceGroup(String appResourceGroup) {
        super.withAppResourceGroup(appResourceGroup);
        return this;
    }

    /**
     * Validates the instance.
     *
     * @throws IllegalArgumentException thrown if the instance is not valid.
     */
    @Override
    public void validate() {
        super.validate();
        if (networkConfiguration() != null) {
            networkConfiguration().validate();
        }
        if (centralServer() == null) {
            throw LOGGER
                .logExceptionAsError(
                    new IllegalArgumentException(
                        "Missing required property centralServer in model ThreeTierConfiguration"));
        } else {
            centralServer().validate();
        }
        if (applicationServer() == null) {
            throw LOGGER
                .logExceptionAsError(
                    new IllegalArgumentException(
                        "Missing required property applicationServer in model ThreeTierConfiguration"));
        } else {
            applicationServer().validate();
        }
        if (databaseServer() == null) {
            throw LOGGER
                .logExceptionAsError(
                    new IllegalArgumentException(
                        "Missing required property databaseServer in model ThreeTierConfiguration"));
        } else {
            databaseServer().validate();
        }
        if (highAvailabilityConfig() != null) {
            highAvailabilityConfig().validate();
        }
        if (storageConfiguration() != null) {
            storageConfiguration().validate();
        }
        if (customResourceNames() != null) {
            customResourceNames().validate();
        }
    }

    private static final ClientLogger LOGGER = new ClientLogger(ThreeTierConfiguration.class);
}
