package containerservice

// Copyright (c) Microsoft and contributors.  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.
//
// Code generated by Microsoft (R) AutoRest Code Generator.
// Changes may cause incorrect behavior and will be lost if the code is regenerated.

import (
	"context"
	"encoding/json"
	"github.com/Azure/go-autorest/autorest"
	"github.com/Azure/go-autorest/autorest/azure"
	"github.com/Azure/go-autorest/autorest/to"
	"github.com/Azure/go-autorest/tracing"
	"net/http"
)

// The package's fully qualified name.
const fqdn = "github.com/Azure/azure-sdk-for-go/services/containerservice/mgmt/2018-03-31/containerservice"

// AccessProfile profile for enabling a user to access a managed cluster.
type AccessProfile struct {
	// KubeConfig - Base64-encoded Kubernetes configuration file.
	KubeConfig *[]byte `json:"kubeConfig,omitempty"`
}

// AgentPoolProfile profile for the container service agent pool.
type AgentPoolProfile struct {
	// Name - Unique name of the agent pool profile in the context of the subscription and resource group.
	Name *string `json:"name,omitempty"`
	// Count - Number of agents (VMs) to host docker containers. Allowed values must be in the range of 1 to 100 (inclusive). The default value is 1.
	Count *int32 `json:"count,omitempty"`
	// VMSize - Size of agent VMs. Possible values include: 'StandardA1', 'StandardA10', 'StandardA11', 'StandardA1V2', 'StandardA2', 'StandardA2V2', 'StandardA2mV2', 'StandardA3', 'StandardA4', 'StandardA4V2', 'StandardA4mV2', 'StandardA5', 'StandardA6', 'StandardA7', 'StandardA8', 'StandardA8V2', 'StandardA8mV2', 'StandardA9', 'StandardB2ms', 'StandardB2s', 'StandardB4ms', 'StandardB8ms', 'StandardD1', 'StandardD11', 'StandardD11V2', 'StandardD11V2Promo', 'StandardD12', 'StandardD12V2', 'StandardD12V2Promo', 'StandardD13', 'StandardD13V2', 'StandardD13V2Promo', 'StandardD14', 'StandardD14V2', 'StandardD14V2Promo', 'StandardD15V2', 'StandardD16V3', 'StandardD16sV3', 'StandardD1V2', 'StandardD2', 'StandardD2V2', 'StandardD2V2Promo', 'StandardD2V3', 'StandardD2sV3', 'StandardD3', 'StandardD32V3', 'StandardD32sV3', 'StandardD3V2', 'StandardD3V2Promo', 'StandardD4', 'StandardD4V2', 'StandardD4V2Promo', 'StandardD4V3', 'StandardD4sV3', 'StandardD5V2', 'StandardD5V2Promo', 'StandardD64V3', 'StandardD64sV3', 'StandardD8V3', 'StandardD8sV3', 'StandardDS1', 'StandardDS11', 'StandardDS11V2', 'StandardDS11V2Promo', 'StandardDS12', 'StandardDS12V2', 'StandardDS12V2Promo', 'StandardDS13', 'StandardDS132V2', 'StandardDS134V2', 'StandardDS13V2', 'StandardDS13V2Promo', 'StandardDS14', 'StandardDS144V2', 'StandardDS148V2', 'StandardDS14V2', 'StandardDS14V2Promo', 'StandardDS15V2', 'StandardDS1V2', 'StandardDS2', 'StandardDS2V2', 'StandardDS2V2Promo', 'StandardDS3', 'StandardDS3V2', 'StandardDS3V2Promo', 'StandardDS4', 'StandardDS4V2', 'StandardDS4V2Promo', 'StandardDS5V2', 'StandardDS5V2Promo', 'StandardE16V3', 'StandardE16sV3', 'StandardE2V3', 'StandardE2sV3', 'StandardE3216sV3', 'StandardE328sV3', 'StandardE32V3', 'StandardE32sV3', 'StandardE4V3', 'StandardE4sV3', 'StandardE6416sV3', 'StandardE6432sV3', 'StandardE64V3', 'StandardE64sV3', 'StandardE8V3', 'StandardE8sV3', 'StandardF1', 'StandardF16', 'StandardF16s', 'StandardF16sV2', 'StandardF1s', 'StandardF2', 'StandardF2s', 'StandardF2sV2', 'StandardF32sV2', 'StandardF4', 'StandardF4s', 'StandardF4sV2', 'StandardF64sV2', 'StandardF72sV2', 'StandardF8', 'StandardF8s', 'StandardF8sV2', 'StandardG1', 'StandardG2', 'StandardG3', 'StandardG4', 'StandardG5', 'StandardGS1', 'StandardGS2', 'StandardGS3', 'StandardGS4', 'StandardGS44', 'StandardGS48', 'StandardGS5', 'StandardGS516', 'StandardGS58', 'StandardH16', 'StandardH16m', 'StandardH16mr', 'StandardH16r', 'StandardH8', 'StandardH8m', 'StandardL16s', 'StandardL32s', 'StandardL4s', 'StandardL8s', 'StandardM12832ms', 'StandardM12864ms', 'StandardM128ms', 'StandardM128s', 'StandardM6416ms', 'StandardM6432ms', 'StandardM64ms', 'StandardM64s', 'StandardNC12', 'StandardNC12sV2', 'StandardNC12sV3', 'StandardNC24', 'StandardNC24r', 'StandardNC24rsV2', 'StandardNC24rsV3', 'StandardNC24sV2', 'StandardNC24sV3', 'StandardNC6', 'StandardNC6sV2', 'StandardNC6sV3', 'StandardND12s', 'StandardND24rs', 'StandardND24s', 'StandardND6s', 'StandardNV12', 'StandardNV24', 'StandardNV6'
	VMSize VMSizeTypes `json:"vmSize,omitempty"`
	// OsDiskSizeGB - OS Disk Size in GB to be used to specify the disk size for every machine in this master/agent pool. If you specify 0, it will apply the default osDisk size according to the vmSize specified.
	OsDiskSizeGB *int32 `json:"osDiskSizeGB,omitempty"`
	// DNSPrefix - DNS prefix to be used to create the FQDN for the agent pool.
	DNSPrefix *string `json:"dnsPrefix,omitempty"`
	// Fqdn - READ-ONLY; FQDN for the agent pool.
	Fqdn *string `json:"fqdn,omitempty"`
	// Ports - Ports number array used to expose on this agent pool. The default opened ports are different based on your choice of orchestrator.
	Ports *[]int32 `json:"ports,omitempty"`
	// StorageProfile - Storage profile specifies what kind of storage used. Choose from StorageAccount and ManagedDisks. Leave it empty, we will choose for you based on the orchestrator choice. Possible values include: 'StorageAccount', 'ManagedDisks'
	StorageProfile StorageProfileTypes `json:"storageProfile,omitempty"`
	// VnetSubnetID - VNet SubnetID specifies the VNet's subnet identifier.
	VnetSubnetID *string `json:"vnetSubnetID,omitempty"`
	// OsType - OsType to be used to specify os type. Choose from Linux and Windows. Default to Linux. Possible values include: 'Linux', 'Windows'
	OsType OSType `json:"osType,omitempty"`
}

// MarshalJSON is the custom marshaler for AgentPoolProfile.
func (app AgentPoolProfile) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if app.Name != nil {
		objectMap["name"] = app.Name
	}
	if app.Count != nil {
		objectMap["count"] = app.Count
	}
	if app.VMSize != "" {
		objectMap["vmSize"] = app.VMSize
	}
	if app.OsDiskSizeGB != nil {
		objectMap["osDiskSizeGB"] = app.OsDiskSizeGB
	}
	if app.DNSPrefix != nil {
		objectMap["dnsPrefix"] = app.DNSPrefix
	}
	if app.Ports != nil {
		objectMap["ports"] = app.Ports
	}
	if app.StorageProfile != "" {
		objectMap["storageProfile"] = app.StorageProfile
	}
	if app.VnetSubnetID != nil {
		objectMap["vnetSubnetID"] = app.VnetSubnetID
	}
	if app.OsType != "" {
		objectMap["osType"] = app.OsType
	}
	return json.Marshal(objectMap)
}

// ContainerService container service.
type ContainerService struct {
	autorest.Response `json:"-"`
	// Properties - Properties of the container service.
	*Properties `json:"properties,omitempty"`
	// ID - READ-ONLY; Resource Id
	ID *string `json:"id,omitempty"`
	// Name - READ-ONLY; Resource name
	Name *string `json:"name,omitempty"`
	// Type - READ-ONLY; Resource type
	Type *string `json:"type,omitempty"`
	// Location - Resource location
	Location *string `json:"location,omitempty"`
	// Tags - Resource tags
	Tags map[string]*string `json:"tags"`
}

// MarshalJSON is the custom marshaler for ContainerService.
func (cs ContainerService) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if cs.Properties != nil {
		objectMap["properties"] = cs.Properties
	}
	if cs.Location != nil {
		objectMap["location"] = cs.Location
	}
	if cs.Tags != nil {
		objectMap["tags"] = cs.Tags
	}
	return json.Marshal(objectMap)
}

// UnmarshalJSON is the custom unmarshaler for ContainerService struct.
func (cs *ContainerService) UnmarshalJSON(body []byte) error {
	var m map[string]*json.RawMessage
	err := json.Unmarshal(body, &m)
	if err != nil {
		return err
	}
	for k, v := range m {
		switch k {
		case "properties":
			if v != nil {
				var properties Properties
				err = json.Unmarshal(*v, &properties)
				if err != nil {
					return err
				}
				cs.Properties = &properties
			}
		case "id":
			if v != nil {
				var ID string
				err = json.Unmarshal(*v, &ID)
				if err != nil {
					return err
				}
				cs.ID = &ID
			}
		case "name":
			if v != nil {
				var name string
				err = json.Unmarshal(*v, &name)
				if err != nil {
					return err
				}
				cs.Name = &name
			}
		case "type":
			if v != nil {
				var typeVar string
				err = json.Unmarshal(*v, &typeVar)
				if err != nil {
					return err
				}
				cs.Type = &typeVar
			}
		case "location":
			if v != nil {
				var location string
				err = json.Unmarshal(*v, &location)
				if err != nil {
					return err
				}
				cs.Location = &location
			}
		case "tags":
			if v != nil {
				var tags map[string]*string
				err = json.Unmarshal(*v, &tags)
				if err != nil {
					return err
				}
				cs.Tags = tags
			}
		}
	}

	return nil
}

// ContainerServicesCreateOrUpdateFutureType an abstraction for monitoring and retrieving the results of a
// long-running operation.
type ContainerServicesCreateOrUpdateFutureType struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ContainerServicesClient) (ContainerService, error)
}

// ContainerServicesDeleteFutureType an abstraction for monitoring and retrieving the results of a
// long-running operation.
type ContainerServicesDeleteFutureType struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ContainerServicesClient) (autorest.Response, error)
}

// CredentialResult the credential result response.
type CredentialResult struct {
	// Name - READ-ONLY; The name of the credential.
	Name *string `json:"name,omitempty"`
	// Value - READ-ONLY; Base64-encoded Kubernetes configuration file.
	Value *[]byte `json:"value,omitempty"`
}

// CredentialResults the list of credential result response.
type CredentialResults struct {
	autorest.Response `json:"-"`
	// Kubeconfigs - READ-ONLY; Base64-encoded Kubernetes configuration file.
	Kubeconfigs *[]CredentialResult `json:"kubeconfigs,omitempty"`
}

// CustomProfile properties to configure a custom container service cluster.
type CustomProfile struct {
	// Orchestrator - The name of the custom orchestrator to use.
	Orchestrator *string `json:"orchestrator,omitempty"`
}

// DiagnosticsProfile profile for diagnostics on the container service cluster.
type DiagnosticsProfile struct {
	// VMDiagnostics - Profile for diagnostics on the container service VMs.
	VMDiagnostics *VMDiagnostics `json:"vmDiagnostics,omitempty"`
}

// KeyVaultSecretRef reference to a secret stored in Azure Key Vault.
type KeyVaultSecretRef struct {
	// VaultID - Key vault identifier.
	VaultID *string `json:"vaultID,omitempty"`
	// SecretName - The secret name.
	SecretName *string `json:"secretName,omitempty"`
	// Version - The secret version.
	Version *string `json:"version,omitempty"`
}

// LinuxProfile profile for Linux VMs in the container service cluster.
type LinuxProfile struct {
	// AdminUsername - The administrator username to use for Linux VMs.
	AdminUsername *string `json:"adminUsername,omitempty"`
	// SSH - SSH configuration for Linux-based VMs running on Azure.
	SSH *SSHConfiguration `json:"ssh,omitempty"`
}

// ListResult the response from the List Container Services operation.
type ListResult struct {
	autorest.Response `json:"-"`
	// Value - The list of container services.
	Value *[]ContainerService `json:"value,omitempty"`
	// NextLink - READ-ONLY; The URL to get the next set of container service results.
	NextLink *string `json:"nextLink,omitempty"`
}

// MarshalJSON is the custom marshaler for ListResult.
func (lr ListResult) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if lr.Value != nil {
		objectMap["value"] = lr.Value
	}
	return json.Marshal(objectMap)
}

// ListResultIterator provides access to a complete listing of ContainerService values.
type ListResultIterator struct {
	i    int
	page ListResultPage
}

// NextWithContext advances to the next value.  If there was an error making
// the request the iterator does not advance and the error is returned.
func (iter *ListResultIterator) NextWithContext(ctx context.Context) (err error) {
	if tracing.IsEnabled() {
		ctx = tracing.StartSpan(ctx, fqdn+"/ListResultIterator.NextWithContext")
		defer func() {
			sc := -1
			if iter.Response().Response.Response != nil {
				sc = iter.Response().Response.Response.StatusCode
			}
			tracing.EndSpan(ctx, sc, err)
		}()
	}
	iter.i++
	if iter.i < len(iter.page.Values()) {
		return nil
	}
	err = iter.page.NextWithContext(ctx)
	if err != nil {
		iter.i--
		return err
	}
	iter.i = 0
	return nil
}

// Next advances to the next value.  If there was an error making
// the request the iterator does not advance and the error is returned.
// Deprecated: Use NextWithContext() instead.
func (iter *ListResultIterator) Next() error {
	return iter.NextWithContext(context.Background())
}

// NotDone returns true if the enumeration should be started or is not yet complete.
func (iter ListResultIterator) NotDone() bool {
	return iter.page.NotDone() && iter.i < len(iter.page.Values())
}

// Response returns the raw server response from the last page request.
func (iter ListResultIterator) Response() ListResult {
	return iter.page.Response()
}

// Value returns the current value or a zero-initialized value if the
// iterator has advanced beyond the end of the collection.
func (iter ListResultIterator) Value() ContainerService {
	if !iter.page.NotDone() {
		return ContainerService{}
	}
	return iter.page.Values()[iter.i]
}

// Creates a new instance of the ListResultIterator type.
func NewListResultIterator(page ListResultPage) ListResultIterator {
	return ListResultIterator{page: page}
}

// IsEmpty returns true if the ListResult contains no values.
func (lr ListResult) IsEmpty() bool {
	return lr.Value == nil || len(*lr.Value) == 0
}

// hasNextLink returns true if the NextLink is not empty.
func (lr ListResult) hasNextLink() bool {
	return lr.NextLink != nil && len(*lr.NextLink) != 0
}

// listResultPreparer prepares a request to retrieve the next set of results.
// It returns nil if no more results exist.
func (lr ListResult) listResultPreparer(ctx context.Context) (*http.Request, error) {
	if !lr.hasNextLink() {
		return nil, nil
	}
	return autorest.Prepare((&http.Request{}).WithContext(ctx),
		autorest.AsJSON(),
		autorest.AsGet(),
		autorest.WithBaseURL(to.String(lr.NextLink)))
}

// ListResultPage contains a page of ContainerService values.
type ListResultPage struct {
	fn func(context.Context, ListResult) (ListResult, error)
	lr ListResult
}

// NextWithContext advances to the next page of values.  If there was an error making
// the request the page does not advance and the error is returned.
func (page *ListResultPage) NextWithContext(ctx context.Context) (err error) {
	if tracing.IsEnabled() {
		ctx = tracing.StartSpan(ctx, fqdn+"/ListResultPage.NextWithContext")
		defer func() {
			sc := -1
			if page.Response().Response.Response != nil {
				sc = page.Response().Response.Response.StatusCode
			}
			tracing.EndSpan(ctx, sc, err)
		}()
	}
	for {
		next, err := page.fn(ctx, page.lr)
		if err != nil {
			return err
		}
		page.lr = next
		if !next.hasNextLink() || !next.IsEmpty() {
			break
		}
	}
	return nil
}

// Next advances to the next page of values.  If there was an error making
// the request the page does not advance and the error is returned.
// Deprecated: Use NextWithContext() instead.
func (page *ListResultPage) Next() error {
	return page.NextWithContext(context.Background())
}

// NotDone returns true if the page enumeration should be started or is not yet complete.
func (page ListResultPage) NotDone() bool {
	return !page.lr.IsEmpty()
}

// Response returns the raw server response from the last page request.
func (page ListResultPage) Response() ListResult {
	return page.lr
}

// Values returns the slice of values for the current page or nil if there are no values.
func (page ListResultPage) Values() []ContainerService {
	if page.lr.IsEmpty() {
		return nil
	}
	return *page.lr.Value
}

// Creates a new instance of the ListResultPage type.
func NewListResultPage(cur ListResult, getNextPage func(context.Context, ListResult) (ListResult, error)) ListResultPage {
	return ListResultPage{
		fn: getNextPage,
		lr: cur,
	}
}

// ManagedCluster managed cluster.
type ManagedCluster struct {
	autorest.Response `json:"-"`
	// ManagedClusterProperties - Properties of a managed cluster.
	*ManagedClusterProperties `json:"properties,omitempty"`
	// ID - READ-ONLY; Resource Id
	ID *string `json:"id,omitempty"`
	// Name - READ-ONLY; Resource name
	Name *string `json:"name,omitempty"`
	// Type - READ-ONLY; Resource type
	Type *string `json:"type,omitempty"`
	// Location - Resource location
	Location *string `json:"location,omitempty"`
	// Tags - Resource tags
	Tags map[string]*string `json:"tags"`
}

// MarshalJSON is the custom marshaler for ManagedCluster.
func (mc ManagedCluster) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mc.ManagedClusterProperties != nil {
		objectMap["properties"] = mc.ManagedClusterProperties
	}
	if mc.Location != nil {
		objectMap["location"] = mc.Location
	}
	if mc.Tags != nil {
		objectMap["tags"] = mc.Tags
	}
	return json.Marshal(objectMap)
}

// UnmarshalJSON is the custom unmarshaler for ManagedCluster struct.
func (mc *ManagedCluster) UnmarshalJSON(body []byte) error {
	var m map[string]*json.RawMessage
	err := json.Unmarshal(body, &m)
	if err != nil {
		return err
	}
	for k, v := range m {
		switch k {
		case "properties":
			if v != nil {
				var managedClusterProperties ManagedClusterProperties
				err = json.Unmarshal(*v, &managedClusterProperties)
				if err != nil {
					return err
				}
				mc.ManagedClusterProperties = &managedClusterProperties
			}
		case "id":
			if v != nil {
				var ID string
				err = json.Unmarshal(*v, &ID)
				if err != nil {
					return err
				}
				mc.ID = &ID
			}
		case "name":
			if v != nil {
				var name string
				err = json.Unmarshal(*v, &name)
				if err != nil {
					return err
				}
				mc.Name = &name
			}
		case "type":
			if v != nil {
				var typeVar string
				err = json.Unmarshal(*v, &typeVar)
				if err != nil {
					return err
				}
				mc.Type = &typeVar
			}
		case "location":
			if v != nil {
				var location string
				err = json.Unmarshal(*v, &location)
				if err != nil {
					return err
				}
				mc.Location = &location
			}
		case "tags":
			if v != nil {
				var tags map[string]*string
				err = json.Unmarshal(*v, &tags)
				if err != nil {
					return err
				}
				mc.Tags = tags
			}
		}
	}

	return nil
}

// ManagedClusterAADProfile aADProfile specifies attributes for Azure Active Directory integration.
type ManagedClusterAADProfile struct {
	// ClientAppID - The client AAD application ID.
	ClientAppID *string `json:"clientAppID,omitempty"`
	// ServerAppID - The server AAD application ID.
	ServerAppID *string `json:"serverAppID,omitempty"`
	// ServerAppSecret - The server AAD application secret.
	ServerAppSecret *string `json:"serverAppSecret,omitempty"`
	// TenantID - The AAD tenant ID to use for authentication. If not specified, will use the tenant of the deployment subscription.
	TenantID *string `json:"tenantID,omitempty"`
}

// ManagedClusterAccessProfile managed cluster Access Profile.
type ManagedClusterAccessProfile struct {
	autorest.Response `json:"-"`
	// AccessProfile - AccessProfile of a managed cluster.
	*AccessProfile `json:"properties,omitempty"`
	// ID - READ-ONLY; Resource Id
	ID *string `json:"id,omitempty"`
	// Name - READ-ONLY; Resource name
	Name *string `json:"name,omitempty"`
	// Type - READ-ONLY; Resource type
	Type *string `json:"type,omitempty"`
	// Location - Resource location
	Location *string `json:"location,omitempty"`
	// Tags - Resource tags
	Tags map[string]*string `json:"tags"`
}

// MarshalJSON is the custom marshaler for ManagedClusterAccessProfile.
func (mcap ManagedClusterAccessProfile) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mcap.AccessProfile != nil {
		objectMap["properties"] = mcap.AccessProfile
	}
	if mcap.Location != nil {
		objectMap["location"] = mcap.Location
	}
	if mcap.Tags != nil {
		objectMap["tags"] = mcap.Tags
	}
	return json.Marshal(objectMap)
}

// UnmarshalJSON is the custom unmarshaler for ManagedClusterAccessProfile struct.
func (mcap *ManagedClusterAccessProfile) UnmarshalJSON(body []byte) error {
	var m map[string]*json.RawMessage
	err := json.Unmarshal(body, &m)
	if err != nil {
		return err
	}
	for k, v := range m {
		switch k {
		case "properties":
			if v != nil {
				var accessProfile AccessProfile
				err = json.Unmarshal(*v, &accessProfile)
				if err != nil {
					return err
				}
				mcap.AccessProfile = &accessProfile
			}
		case "id":
			if v != nil {
				var ID string
				err = json.Unmarshal(*v, &ID)
				if err != nil {
					return err
				}
				mcap.ID = &ID
			}
		case "name":
			if v != nil {
				var name string
				err = json.Unmarshal(*v, &name)
				if err != nil {
					return err
				}
				mcap.Name = &name
			}
		case "type":
			if v != nil {
				var typeVar string
				err = json.Unmarshal(*v, &typeVar)
				if err != nil {
					return err
				}
				mcap.Type = &typeVar
			}
		case "location":
			if v != nil {
				var location string
				err = json.Unmarshal(*v, &location)
				if err != nil {
					return err
				}
				mcap.Location = &location
			}
		case "tags":
			if v != nil {
				var tags map[string]*string
				err = json.Unmarshal(*v, &tags)
				if err != nil {
					return err
				}
				mcap.Tags = tags
			}
		}
	}

	return nil
}

// ManagedClusterAddonProfile a Kubernetes add-on profile for a managed cluster.
type ManagedClusterAddonProfile struct {
	// Enabled - Whether the add-on is enabled or not.
	Enabled *bool `json:"enabled,omitempty"`
	// Config - Key-value pairs for configuring an add-on.
	Config map[string]*string `json:"config"`
}

// MarshalJSON is the custom marshaler for ManagedClusterAddonProfile.
func (mcap ManagedClusterAddonProfile) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mcap.Enabled != nil {
		objectMap["enabled"] = mcap.Enabled
	}
	if mcap.Config != nil {
		objectMap["config"] = mcap.Config
	}
	return json.Marshal(objectMap)
}

// ManagedClusterAgentPoolProfile profile for the container service agent pool.
type ManagedClusterAgentPoolProfile struct {
	// Name - Unique name of the agent pool profile in the context of the subscription and resource group.
	Name *string `json:"name,omitempty"`
	// Count - Number of agents (VMs) to host docker containers. Allowed values must be in the range of 1 to 100 (inclusive). The default value is 1.
	Count *int32 `json:"count,omitempty"`
	// VMSize - Size of agent VMs. Possible values include: 'StandardA1', 'StandardA10', 'StandardA11', 'StandardA1V2', 'StandardA2', 'StandardA2V2', 'StandardA2mV2', 'StandardA3', 'StandardA4', 'StandardA4V2', 'StandardA4mV2', 'StandardA5', 'StandardA6', 'StandardA7', 'StandardA8', 'StandardA8V2', 'StandardA8mV2', 'StandardA9', 'StandardB2ms', 'StandardB2s', 'StandardB4ms', 'StandardB8ms', 'StandardD1', 'StandardD11', 'StandardD11V2', 'StandardD11V2Promo', 'StandardD12', 'StandardD12V2', 'StandardD12V2Promo', 'StandardD13', 'StandardD13V2', 'StandardD13V2Promo', 'StandardD14', 'StandardD14V2', 'StandardD14V2Promo', 'StandardD15V2', 'StandardD16V3', 'StandardD16sV3', 'StandardD1V2', 'StandardD2', 'StandardD2V2', 'StandardD2V2Promo', 'StandardD2V3', 'StandardD2sV3', 'StandardD3', 'StandardD32V3', 'StandardD32sV3', 'StandardD3V2', 'StandardD3V2Promo', 'StandardD4', 'StandardD4V2', 'StandardD4V2Promo', 'StandardD4V3', 'StandardD4sV3', 'StandardD5V2', 'StandardD5V2Promo', 'StandardD64V3', 'StandardD64sV3', 'StandardD8V3', 'StandardD8sV3', 'StandardDS1', 'StandardDS11', 'StandardDS11V2', 'StandardDS11V2Promo', 'StandardDS12', 'StandardDS12V2', 'StandardDS12V2Promo', 'StandardDS13', 'StandardDS132V2', 'StandardDS134V2', 'StandardDS13V2', 'StandardDS13V2Promo', 'StandardDS14', 'StandardDS144V2', 'StandardDS148V2', 'StandardDS14V2', 'StandardDS14V2Promo', 'StandardDS15V2', 'StandardDS1V2', 'StandardDS2', 'StandardDS2V2', 'StandardDS2V2Promo', 'StandardDS3', 'StandardDS3V2', 'StandardDS3V2Promo', 'StandardDS4', 'StandardDS4V2', 'StandardDS4V2Promo', 'StandardDS5V2', 'StandardDS5V2Promo', 'StandardE16V3', 'StandardE16sV3', 'StandardE2V3', 'StandardE2sV3', 'StandardE3216sV3', 'StandardE328sV3', 'StandardE32V3', 'StandardE32sV3', 'StandardE4V3', 'StandardE4sV3', 'StandardE6416sV3', 'StandardE6432sV3', 'StandardE64V3', 'StandardE64sV3', 'StandardE8V3', 'StandardE8sV3', 'StandardF1', 'StandardF16', 'StandardF16s', 'StandardF16sV2', 'StandardF1s', 'StandardF2', 'StandardF2s', 'StandardF2sV2', 'StandardF32sV2', 'StandardF4', 'StandardF4s', 'StandardF4sV2', 'StandardF64sV2', 'StandardF72sV2', 'StandardF8', 'StandardF8s', 'StandardF8sV2', 'StandardG1', 'StandardG2', 'StandardG3', 'StandardG4', 'StandardG5', 'StandardGS1', 'StandardGS2', 'StandardGS3', 'StandardGS4', 'StandardGS44', 'StandardGS48', 'StandardGS5', 'StandardGS516', 'StandardGS58', 'StandardH16', 'StandardH16m', 'StandardH16mr', 'StandardH16r', 'StandardH8', 'StandardH8m', 'StandardL16s', 'StandardL32s', 'StandardL4s', 'StandardL8s', 'StandardM12832ms', 'StandardM12864ms', 'StandardM128ms', 'StandardM128s', 'StandardM6416ms', 'StandardM6432ms', 'StandardM64ms', 'StandardM64s', 'StandardNC12', 'StandardNC12sV2', 'StandardNC12sV3', 'StandardNC24', 'StandardNC24r', 'StandardNC24rsV2', 'StandardNC24rsV3', 'StandardNC24sV2', 'StandardNC24sV3', 'StandardNC6', 'StandardNC6sV2', 'StandardNC6sV3', 'StandardND12s', 'StandardND24rs', 'StandardND24s', 'StandardND6s', 'StandardNV12', 'StandardNV24', 'StandardNV6'
	VMSize VMSizeTypes `json:"vmSize,omitempty"`
	// OsDiskSizeGB - OS Disk Size in GB to be used to specify the disk size for every machine in this master/agent pool. If you specify 0, it will apply the default osDisk size according to the vmSize specified.
	OsDiskSizeGB *int32 `json:"osDiskSizeGB,omitempty"`
	// StorageProfile - READ-ONLY; Storage profile specifies what kind of storage used. Defaults to ManagedDisks. Possible values include: 'StorageAccount', 'ManagedDisks'
	StorageProfile StorageProfileTypes `json:"storageProfile,omitempty"`
	// VnetSubnetID - VNet SubnetID specifies the VNet's subnet identifier.
	VnetSubnetID *string `json:"vnetSubnetID,omitempty"`
	// MaxPods - Maximum number of pods that can run on a node.
	MaxPods *int32 `json:"maxPods,omitempty"`
	// OsType - OsType to be used to specify os type. Choose from Linux and Windows. Default to Linux. Possible values include: 'Linux', 'Windows'
	OsType OSType `json:"osType,omitempty"`
}

// MarshalJSON is the custom marshaler for ManagedClusterAgentPoolProfile.
func (mcapp ManagedClusterAgentPoolProfile) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mcapp.Name != nil {
		objectMap["name"] = mcapp.Name
	}
	if mcapp.Count != nil {
		objectMap["count"] = mcapp.Count
	}
	if mcapp.VMSize != "" {
		objectMap["vmSize"] = mcapp.VMSize
	}
	if mcapp.OsDiskSizeGB != nil {
		objectMap["osDiskSizeGB"] = mcapp.OsDiskSizeGB
	}
	if mcapp.VnetSubnetID != nil {
		objectMap["vnetSubnetID"] = mcapp.VnetSubnetID
	}
	if mcapp.MaxPods != nil {
		objectMap["maxPods"] = mcapp.MaxPods
	}
	if mcapp.OsType != "" {
		objectMap["osType"] = mcapp.OsType
	}
	return json.Marshal(objectMap)
}

// ManagedClusterListResult the response from the List Managed Clusters operation.
type ManagedClusterListResult struct {
	autorest.Response `json:"-"`
	// Value - The list of managed clusters.
	Value *[]ManagedCluster `json:"value,omitempty"`
	// NextLink - READ-ONLY; The URL to get the next set of managed cluster results.
	NextLink *string `json:"nextLink,omitempty"`
}

// MarshalJSON is the custom marshaler for ManagedClusterListResult.
func (mclr ManagedClusterListResult) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mclr.Value != nil {
		objectMap["value"] = mclr.Value
	}
	return json.Marshal(objectMap)
}

// ManagedClusterListResultIterator provides access to a complete listing of ManagedCluster values.
type ManagedClusterListResultIterator struct {
	i    int
	page ManagedClusterListResultPage
}

// NextWithContext advances to the next value.  If there was an error making
// the request the iterator does not advance and the error is returned.
func (iter *ManagedClusterListResultIterator) NextWithContext(ctx context.Context) (err error) {
	if tracing.IsEnabled() {
		ctx = tracing.StartSpan(ctx, fqdn+"/ManagedClusterListResultIterator.NextWithContext")
		defer func() {
			sc := -1
			if iter.Response().Response.Response != nil {
				sc = iter.Response().Response.Response.StatusCode
			}
			tracing.EndSpan(ctx, sc, err)
		}()
	}
	iter.i++
	if iter.i < len(iter.page.Values()) {
		return nil
	}
	err = iter.page.NextWithContext(ctx)
	if err != nil {
		iter.i--
		return err
	}
	iter.i = 0
	return nil
}

// Next advances to the next value.  If there was an error making
// the request the iterator does not advance and the error is returned.
// Deprecated: Use NextWithContext() instead.
func (iter *ManagedClusterListResultIterator) Next() error {
	return iter.NextWithContext(context.Background())
}

// NotDone returns true if the enumeration should be started or is not yet complete.
func (iter ManagedClusterListResultIterator) NotDone() bool {
	return iter.page.NotDone() && iter.i < len(iter.page.Values())
}

// Response returns the raw server response from the last page request.
func (iter ManagedClusterListResultIterator) Response() ManagedClusterListResult {
	return iter.page.Response()
}

// Value returns the current value or a zero-initialized value if the
// iterator has advanced beyond the end of the collection.
func (iter ManagedClusterListResultIterator) Value() ManagedCluster {
	if !iter.page.NotDone() {
		return ManagedCluster{}
	}
	return iter.page.Values()[iter.i]
}

// Creates a new instance of the ManagedClusterListResultIterator type.
func NewManagedClusterListResultIterator(page ManagedClusterListResultPage) ManagedClusterListResultIterator {
	return ManagedClusterListResultIterator{page: page}
}

// IsEmpty returns true if the ListResult contains no values.
func (mclr ManagedClusterListResult) IsEmpty() bool {
	return mclr.Value == nil || len(*mclr.Value) == 0
}

// hasNextLink returns true if the NextLink is not empty.
func (mclr ManagedClusterListResult) hasNextLink() bool {
	return mclr.NextLink != nil && len(*mclr.NextLink) != 0
}

// managedClusterListResultPreparer prepares a request to retrieve the next set of results.
// It returns nil if no more results exist.
func (mclr ManagedClusterListResult) managedClusterListResultPreparer(ctx context.Context) (*http.Request, error) {
	if !mclr.hasNextLink() {
		return nil, nil
	}
	return autorest.Prepare((&http.Request{}).WithContext(ctx),
		autorest.AsJSON(),
		autorest.AsGet(),
		autorest.WithBaseURL(to.String(mclr.NextLink)))
}

// ManagedClusterListResultPage contains a page of ManagedCluster values.
type ManagedClusterListResultPage struct {
	fn   func(context.Context, ManagedClusterListResult) (ManagedClusterListResult, error)
	mclr ManagedClusterListResult
}

// NextWithContext advances to the next page of values.  If there was an error making
// the request the page does not advance and the error is returned.
func (page *ManagedClusterListResultPage) NextWithContext(ctx context.Context) (err error) {
	if tracing.IsEnabled() {
		ctx = tracing.StartSpan(ctx, fqdn+"/ManagedClusterListResultPage.NextWithContext")
		defer func() {
			sc := -1
			if page.Response().Response.Response != nil {
				sc = page.Response().Response.Response.StatusCode
			}
			tracing.EndSpan(ctx, sc, err)
		}()
	}
	for {
		next, err := page.fn(ctx, page.mclr)
		if err != nil {
			return err
		}
		page.mclr = next
		if !next.hasNextLink() || !next.IsEmpty() {
			break
		}
	}
	return nil
}

// Next advances to the next page of values.  If there was an error making
// the request the page does not advance and the error is returned.
// Deprecated: Use NextWithContext() instead.
func (page *ManagedClusterListResultPage) Next() error {
	return page.NextWithContext(context.Background())
}

// NotDone returns true if the page enumeration should be started or is not yet complete.
func (page ManagedClusterListResultPage) NotDone() bool {
	return !page.mclr.IsEmpty()
}

// Response returns the raw server response from the last page request.
func (page ManagedClusterListResultPage) Response() ManagedClusterListResult {
	return page.mclr
}

// Values returns the slice of values for the current page or nil if there are no values.
func (page ManagedClusterListResultPage) Values() []ManagedCluster {
	if page.mclr.IsEmpty() {
		return nil
	}
	return *page.mclr.Value
}

// Creates a new instance of the ManagedClusterListResultPage type.
func NewManagedClusterListResultPage(cur ManagedClusterListResult, getNextPage func(context.Context, ManagedClusterListResult) (ManagedClusterListResult, error)) ManagedClusterListResultPage {
	return ManagedClusterListResultPage{
		fn:   getNextPage,
		mclr: cur,
	}
}

// ManagedClusterPoolUpgradeProfile the list of available upgrade versions.
type ManagedClusterPoolUpgradeProfile struct {
	// KubernetesVersion - Kubernetes version (major, minor, patch).
	KubernetesVersion *string `json:"kubernetesVersion,omitempty"`
	// Name - Pool name.
	Name *string `json:"name,omitempty"`
	// OsType - OsType to be used to specify os type. Choose from Linux and Windows. Default to Linux. Possible values include: 'Linux', 'Windows'
	OsType OSType `json:"osType,omitempty"`
	// Upgrades - List of orchestrator types and versions available for upgrade.
	Upgrades *[]string `json:"upgrades,omitempty"`
}

// ManagedClusterProperties properties of the managed cluster.
type ManagedClusterProperties struct {
	// ProvisioningState - READ-ONLY; The current deployment or provisioning state, which only appears in the response.
	ProvisioningState *string `json:"provisioningState,omitempty"`
	// KubernetesVersion - Version of Kubernetes specified when creating the managed cluster.
	KubernetesVersion *string `json:"kubernetesVersion,omitempty"`
	// DNSPrefix - DNS prefix specified when creating the managed cluster.
	DNSPrefix *string `json:"dnsPrefix,omitempty"`
	// Fqdn - READ-ONLY; FQDN for the master pool.
	Fqdn *string `json:"fqdn,omitempty"`
	// AgentPoolProfiles - Properties of the agent pool. Currently only one agent pool can exist.
	AgentPoolProfiles *[]ManagedClusterAgentPoolProfile `json:"agentPoolProfiles,omitempty"`
	// LinuxProfile - Profile for Linux VMs in the container service cluster.
	LinuxProfile *LinuxProfile `json:"linuxProfile,omitempty"`
	// ServicePrincipalProfile - Information about a service principal identity for the cluster to use for manipulating Azure APIs.
	ServicePrincipalProfile *ManagedClusterServicePrincipalProfile `json:"servicePrincipalProfile,omitempty"`
	// AddonProfiles - Profile of managed cluster add-on.
	AddonProfiles map[string]*ManagedClusterAddonProfile `json:"addonProfiles"`
	// NodeResourceGroup - READ-ONLY; Name of the resource group containing agent pool nodes.
	NodeResourceGroup *string `json:"nodeResourceGroup,omitempty"`
	// EnableRBAC - Whether to enable Kubernetes Role-Based Access Control.
	EnableRBAC *bool `json:"enableRBAC,omitempty"`
	// NetworkProfile - Profile of network configuration.
	NetworkProfile *NetworkProfile `json:"networkProfile,omitempty"`
	// AadProfile - Profile of Azure Active Directory configuration.
	AadProfile *ManagedClusterAADProfile `json:"aadProfile,omitempty"`
}

// MarshalJSON is the custom marshaler for ManagedClusterProperties.
func (mcp ManagedClusterProperties) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mcp.KubernetesVersion != nil {
		objectMap["kubernetesVersion"] = mcp.KubernetesVersion
	}
	if mcp.DNSPrefix != nil {
		objectMap["dnsPrefix"] = mcp.DNSPrefix
	}
	if mcp.AgentPoolProfiles != nil {
		objectMap["agentPoolProfiles"] = mcp.AgentPoolProfiles
	}
	if mcp.LinuxProfile != nil {
		objectMap["linuxProfile"] = mcp.LinuxProfile
	}
	if mcp.ServicePrincipalProfile != nil {
		objectMap["servicePrincipalProfile"] = mcp.ServicePrincipalProfile
	}
	if mcp.AddonProfiles != nil {
		objectMap["addonProfiles"] = mcp.AddonProfiles
	}
	if mcp.EnableRBAC != nil {
		objectMap["enableRBAC"] = mcp.EnableRBAC
	}
	if mcp.NetworkProfile != nil {
		objectMap["networkProfile"] = mcp.NetworkProfile
	}
	if mcp.AadProfile != nil {
		objectMap["aadProfile"] = mcp.AadProfile
	}
	return json.Marshal(objectMap)
}

// ManagedClustersCreateOrUpdateFuture an abstraction for monitoring and retrieving the results of a
// long-running operation.
type ManagedClustersCreateOrUpdateFuture struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ManagedClustersClient) (ManagedCluster, error)
}

// ManagedClustersDeleteFuture an abstraction for monitoring and retrieving the results of a long-running
// operation.
type ManagedClustersDeleteFuture struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ManagedClustersClient) (autorest.Response, error)
}

// ManagedClusterServicePrincipalProfile information about a service principal identity for the cluster to
// use for manipulating Azure APIs.
type ManagedClusterServicePrincipalProfile struct {
	// ClientID - The ID for the service principal.
	ClientID *string `json:"clientId,omitempty"`
	// Secret - The secret password associated with the service principal in plain text.
	Secret *string `json:"secret,omitempty"`
}

// ManagedClustersResetAADProfileFuture an abstraction for monitoring and retrieving the results of a
// long-running operation.
type ManagedClustersResetAADProfileFuture struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ManagedClustersClient) (autorest.Response, error)
}

// ManagedClustersResetServicePrincipalProfileFuture an abstraction for monitoring and retrieving the
// results of a long-running operation.
type ManagedClustersResetServicePrincipalProfileFuture struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ManagedClustersClient) (autorest.Response, error)
}

// ManagedClustersUpdateTagsFuture an abstraction for monitoring and retrieving the results of a
// long-running operation.
type ManagedClustersUpdateTagsFuture struct {
	azure.FutureAPI
	// Result returns the result of the asynchronous operation.
	// If the operation has not completed it will return an error.
	Result func(ManagedClustersClient) (ManagedCluster, error)
}

// ManagedClusterUpgradeProfile the list of available upgrades for compute pools.
type ManagedClusterUpgradeProfile struct {
	autorest.Response `json:"-"`
	// ID - READ-ONLY; Id of upgrade profile.
	ID *string `json:"id,omitempty"`
	// Name - READ-ONLY; Name of upgrade profile.
	Name *string `json:"name,omitempty"`
	// Type - READ-ONLY; Type of upgrade profile.
	Type *string `json:"type,omitempty"`
	// ManagedClusterUpgradeProfileProperties - Properties of upgrade profile.
	*ManagedClusterUpgradeProfileProperties `json:"properties,omitempty"`
}

// MarshalJSON is the custom marshaler for ManagedClusterUpgradeProfile.
func (mcup ManagedClusterUpgradeProfile) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mcup.ManagedClusterUpgradeProfileProperties != nil {
		objectMap["properties"] = mcup.ManagedClusterUpgradeProfileProperties
	}
	return json.Marshal(objectMap)
}

// UnmarshalJSON is the custom unmarshaler for ManagedClusterUpgradeProfile struct.
func (mcup *ManagedClusterUpgradeProfile) UnmarshalJSON(body []byte) error {
	var m map[string]*json.RawMessage
	err := json.Unmarshal(body, &m)
	if err != nil {
		return err
	}
	for k, v := range m {
		switch k {
		case "id":
			if v != nil {
				var ID string
				err = json.Unmarshal(*v, &ID)
				if err != nil {
					return err
				}
				mcup.ID = &ID
			}
		case "name":
			if v != nil {
				var name string
				err = json.Unmarshal(*v, &name)
				if err != nil {
					return err
				}
				mcup.Name = &name
			}
		case "type":
			if v != nil {
				var typeVar string
				err = json.Unmarshal(*v, &typeVar)
				if err != nil {
					return err
				}
				mcup.Type = &typeVar
			}
		case "properties":
			if v != nil {
				var managedClusterUpgradeProfileProperties ManagedClusterUpgradeProfileProperties
				err = json.Unmarshal(*v, &managedClusterUpgradeProfileProperties)
				if err != nil {
					return err
				}
				mcup.ManagedClusterUpgradeProfileProperties = &managedClusterUpgradeProfileProperties
			}
		}
	}

	return nil
}

// ManagedClusterUpgradeProfileProperties control plane and agent pool upgrade profiles.
type ManagedClusterUpgradeProfileProperties struct {
	// ControlPlaneProfile - The list of available upgrade versions for the control plane.
	ControlPlaneProfile *ManagedClusterPoolUpgradeProfile `json:"controlPlaneProfile,omitempty"`
	// AgentPoolProfiles - The list of available upgrade versions for agent pools.
	AgentPoolProfiles *[]ManagedClusterPoolUpgradeProfile `json:"agentPoolProfiles,omitempty"`
}

// MasterProfile profile for the container service master.
type MasterProfile struct {
	// Count - Number of masters (VMs) in the container service cluster. Allowed values are 1, 3, and 5. The default value is 1.
	Count *int32 `json:"count,omitempty"`
	// DNSPrefix - DNS prefix to be used to create the FQDN for the master pool.
	DNSPrefix *string `json:"dnsPrefix,omitempty"`
	// VMSize - Size of agent VMs. Possible values include: 'StandardA1', 'StandardA10', 'StandardA11', 'StandardA1V2', 'StandardA2', 'StandardA2V2', 'StandardA2mV2', 'StandardA3', 'StandardA4', 'StandardA4V2', 'StandardA4mV2', 'StandardA5', 'StandardA6', 'StandardA7', 'StandardA8', 'StandardA8V2', 'StandardA8mV2', 'StandardA9', 'StandardB2ms', 'StandardB2s', 'StandardB4ms', 'StandardB8ms', 'StandardD1', 'StandardD11', 'StandardD11V2', 'StandardD11V2Promo', 'StandardD12', 'StandardD12V2', 'StandardD12V2Promo', 'StandardD13', 'StandardD13V2', 'StandardD13V2Promo', 'StandardD14', 'StandardD14V2', 'StandardD14V2Promo', 'StandardD15V2', 'StandardD16V3', 'StandardD16sV3', 'StandardD1V2', 'StandardD2', 'StandardD2V2', 'StandardD2V2Promo', 'StandardD2V3', 'StandardD2sV3', 'StandardD3', 'StandardD32V3', 'StandardD32sV3', 'StandardD3V2', 'StandardD3V2Promo', 'StandardD4', 'StandardD4V2', 'StandardD4V2Promo', 'StandardD4V3', 'StandardD4sV3', 'StandardD5V2', 'StandardD5V2Promo', 'StandardD64V3', 'StandardD64sV3', 'StandardD8V3', 'StandardD8sV3', 'StandardDS1', 'StandardDS11', 'StandardDS11V2', 'StandardDS11V2Promo', 'StandardDS12', 'StandardDS12V2', 'StandardDS12V2Promo', 'StandardDS13', 'StandardDS132V2', 'StandardDS134V2', 'StandardDS13V2', 'StandardDS13V2Promo', 'StandardDS14', 'StandardDS144V2', 'StandardDS148V2', 'StandardDS14V2', 'StandardDS14V2Promo', 'StandardDS15V2', 'StandardDS1V2', 'StandardDS2', 'StandardDS2V2', 'StandardDS2V2Promo', 'StandardDS3', 'StandardDS3V2', 'StandardDS3V2Promo', 'StandardDS4', 'StandardDS4V2', 'StandardDS4V2Promo', 'StandardDS5V2', 'StandardDS5V2Promo', 'StandardE16V3', 'StandardE16sV3', 'StandardE2V3', 'StandardE2sV3', 'StandardE3216sV3', 'StandardE328sV3', 'StandardE32V3', 'StandardE32sV3', 'StandardE4V3', 'StandardE4sV3', 'StandardE6416sV3', 'StandardE6432sV3', 'StandardE64V3', 'StandardE64sV3', 'StandardE8V3', 'StandardE8sV3', 'StandardF1', 'StandardF16', 'StandardF16s', 'StandardF16sV2', 'StandardF1s', 'StandardF2', 'StandardF2s', 'StandardF2sV2', 'StandardF32sV2', 'StandardF4', 'StandardF4s', 'StandardF4sV2', 'StandardF64sV2', 'StandardF72sV2', 'StandardF8', 'StandardF8s', 'StandardF8sV2', 'StandardG1', 'StandardG2', 'StandardG3', 'StandardG4', 'StandardG5', 'StandardGS1', 'StandardGS2', 'StandardGS3', 'StandardGS4', 'StandardGS44', 'StandardGS48', 'StandardGS5', 'StandardGS516', 'StandardGS58', 'StandardH16', 'StandardH16m', 'StandardH16mr', 'StandardH16r', 'StandardH8', 'StandardH8m', 'StandardL16s', 'StandardL32s', 'StandardL4s', 'StandardL8s', 'StandardM12832ms', 'StandardM12864ms', 'StandardM128ms', 'StandardM128s', 'StandardM6416ms', 'StandardM6432ms', 'StandardM64ms', 'StandardM64s', 'StandardNC12', 'StandardNC12sV2', 'StandardNC12sV3', 'StandardNC24', 'StandardNC24r', 'StandardNC24rsV2', 'StandardNC24rsV3', 'StandardNC24sV2', 'StandardNC24sV3', 'StandardNC6', 'StandardNC6sV2', 'StandardNC6sV3', 'StandardND12s', 'StandardND24rs', 'StandardND24s', 'StandardND6s', 'StandardNV12', 'StandardNV24', 'StandardNV6'
	VMSize VMSizeTypes `json:"vmSize,omitempty"`
	// OsDiskSizeGB - OS Disk Size in GB to be used to specify the disk size for every machine in this master/agent pool. If you specify 0, it will apply the default osDisk size according to the vmSize specified.
	OsDiskSizeGB *int32 `json:"osDiskSizeGB,omitempty"`
	// VnetSubnetID - VNet SubnetID specifies the VNet's subnet identifier.
	VnetSubnetID *string `json:"vnetSubnetID,omitempty"`
	// FirstConsecutiveStaticIP - FirstConsecutiveStaticIP used to specify the first static ip of masters.
	FirstConsecutiveStaticIP *string `json:"firstConsecutiveStaticIP,omitempty"`
	// StorageProfile - Storage profile specifies what kind of storage used. Choose from StorageAccount and ManagedDisks. Leave it empty, we will choose for you based on the orchestrator choice. Possible values include: 'StorageAccount', 'ManagedDisks'
	StorageProfile StorageProfileTypes `json:"storageProfile,omitempty"`
	// Fqdn - READ-ONLY; FQDN for the master pool.
	Fqdn *string `json:"fqdn,omitempty"`
}

// MarshalJSON is the custom marshaler for MasterProfile.
func (mp MasterProfile) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if mp.Count != nil {
		objectMap["count"] = mp.Count
	}
	if mp.DNSPrefix != nil {
		objectMap["dnsPrefix"] = mp.DNSPrefix
	}
	if mp.VMSize != "" {
		objectMap["vmSize"] = mp.VMSize
	}
	if mp.OsDiskSizeGB != nil {
		objectMap["osDiskSizeGB"] = mp.OsDiskSizeGB
	}
	if mp.VnetSubnetID != nil {
		objectMap["vnetSubnetID"] = mp.VnetSubnetID
	}
	if mp.FirstConsecutiveStaticIP != nil {
		objectMap["firstConsecutiveStaticIP"] = mp.FirstConsecutiveStaticIP
	}
	if mp.StorageProfile != "" {
		objectMap["storageProfile"] = mp.StorageProfile
	}
	return json.Marshal(objectMap)
}

// NetworkProfile profile of network configuration.
type NetworkProfile struct {
	// NetworkPlugin - Network plugin used for building Kubernetes network. Possible values include: 'Azure', 'Kubenet'
	NetworkPlugin NetworkPlugin `json:"networkPlugin,omitempty"`
	// NetworkPolicy - Network policy used for building Kubernetes network. Possible values include: 'Calico'
	NetworkPolicy NetworkPolicy `json:"networkPolicy,omitempty"`
	// PodCidr - A CIDR notation IP range from which to assign pod IPs when kubenet is used.
	PodCidr *string `json:"podCidr,omitempty"`
	// ServiceCidr - A CIDR notation IP range from which to assign service cluster IPs. It must not overlap with any Subnet IP ranges.
	ServiceCidr *string `json:"serviceCidr,omitempty"`
	// DNSServiceIP - An IP address assigned to the Kubernetes DNS service. It must be within the Kubernetes service address range specified in serviceCidr.
	DNSServiceIP *string `json:"dnsServiceIP,omitempty"`
	// DockerBridgeCidr - A CIDR notation IP range assigned to the Docker bridge network. It must not overlap with any Subnet IP ranges or the Kubernetes service address range.
	DockerBridgeCidr *string `json:"dockerBridgeCidr,omitempty"`
}

// OperationListResult the List Compute Operation operation response.
type OperationListResult struct {
	autorest.Response `json:"-"`
	// Value - READ-ONLY; The list of compute operations
	Value *[]OperationValue `json:"value,omitempty"`
}

// OperationValue describes the properties of a Compute Operation value.
type OperationValue struct {
	// Origin - READ-ONLY; The origin of the compute operation.
	Origin *string `json:"origin,omitempty"`
	// Name - READ-ONLY; The name of the compute operation.
	Name *string `json:"name,omitempty"`
	// OperationValueDisplay - Describes the properties of a Compute Operation Value Display.
	*OperationValueDisplay `json:"display,omitempty"`
}

// MarshalJSON is the custom marshaler for OperationValue.
func (ov OperationValue) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if ov.OperationValueDisplay != nil {
		objectMap["display"] = ov.OperationValueDisplay
	}
	return json.Marshal(objectMap)
}

// UnmarshalJSON is the custom unmarshaler for OperationValue struct.
func (ov *OperationValue) UnmarshalJSON(body []byte) error {
	var m map[string]*json.RawMessage
	err := json.Unmarshal(body, &m)
	if err != nil {
		return err
	}
	for k, v := range m {
		switch k {
		case "origin":
			if v != nil {
				var origin string
				err = json.Unmarshal(*v, &origin)
				if err != nil {
					return err
				}
				ov.Origin = &origin
			}
		case "name":
			if v != nil {
				var name string
				err = json.Unmarshal(*v, &name)
				if err != nil {
					return err
				}
				ov.Name = &name
			}
		case "display":
			if v != nil {
				var operationValueDisplay OperationValueDisplay
				err = json.Unmarshal(*v, &operationValueDisplay)
				if err != nil {
					return err
				}
				ov.OperationValueDisplay = &operationValueDisplay
			}
		}
	}

	return nil
}

// OperationValueDisplay describes the properties of a Compute Operation Value Display.
type OperationValueDisplay struct {
	// Operation - READ-ONLY; The display name of the compute operation.
	Operation *string `json:"operation,omitempty"`
	// Resource - READ-ONLY; The display name of the resource the operation applies to.
	Resource *string `json:"resource,omitempty"`
	// Description - READ-ONLY; The description of the operation.
	Description *string `json:"description,omitempty"`
	// Provider - READ-ONLY; The resource provider for the operation.
	Provider *string `json:"provider,omitempty"`
}

// OrchestratorProfile contains information about orchestrator.
type OrchestratorProfile struct {
	// OrchestratorType - Orchestrator type.
	OrchestratorType *string `json:"orchestratorType,omitempty"`
	// OrchestratorVersion - Orchestrator version (major, minor, patch).
	OrchestratorVersion *string `json:"orchestratorVersion,omitempty"`
}

// OrchestratorProfileType profile for the container service orchestrator.
type OrchestratorProfileType struct {
	// OrchestratorType - The orchestrator to use to manage container service cluster resources. Valid values are Kubernetes, Swarm, DCOS, DockerCE and Custom. Possible values include: 'Kubernetes', 'Swarm', 'DCOS', 'DockerCE', 'Custom'
	OrchestratorType OrchestratorTypes `json:"orchestratorType,omitempty"`
	// OrchestratorVersion - The version of the orchestrator to use. You can specify the major.minor.patch part of the actual version.For example, you can specify version as "1.6.11".
	OrchestratorVersion *string `json:"orchestratorVersion,omitempty"`
}

// OrchestratorVersionProfile the profile of an orchestrator and its available versions.
type OrchestratorVersionProfile struct {
	// OrchestratorType - Orchestrator type.
	OrchestratorType *string `json:"orchestratorType,omitempty"`
	// OrchestratorVersion - Orchestrator version (major, minor, patch).
	OrchestratorVersion *string `json:"orchestratorVersion,omitempty"`
	// Default - Installed by default if version is not specified.
	Default *bool `json:"default,omitempty"`
	// Upgrades - The list of available upgrade versions.
	Upgrades *[]OrchestratorProfile `json:"upgrades,omitempty"`
}

// OrchestratorVersionProfileListResult the list of versions for supported orchestrators.
type OrchestratorVersionProfileListResult struct {
	autorest.Response `json:"-"`
	// ID - READ-ONLY; Id of the orchestrator version profile list result.
	ID *string `json:"id,omitempty"`
	// Name - READ-ONLY; Name of the orchestrator version profile list result.
	Name *string `json:"name,omitempty"`
	// Type - READ-ONLY; Type of the orchestrator version profile list result.
	Type *string `json:"type,omitempty"`
	// OrchestratorVersionProfileProperties - The properties of an orchestrator version profile.
	*OrchestratorVersionProfileProperties `json:"properties,omitempty"`
}

// MarshalJSON is the custom marshaler for OrchestratorVersionProfileListResult.
func (ovplr OrchestratorVersionProfileListResult) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if ovplr.OrchestratorVersionProfileProperties != nil {
		objectMap["properties"] = ovplr.OrchestratorVersionProfileProperties
	}
	return json.Marshal(objectMap)
}

// UnmarshalJSON is the custom unmarshaler for OrchestratorVersionProfileListResult struct.
func (ovplr *OrchestratorVersionProfileListResult) UnmarshalJSON(body []byte) error {
	var m map[string]*json.RawMessage
	err := json.Unmarshal(body, &m)
	if err != nil {
		return err
	}
	for k, v := range m {
		switch k {
		case "id":
			if v != nil {
				var ID string
				err = json.Unmarshal(*v, &ID)
				if err != nil {
					return err
				}
				ovplr.ID = &ID
			}
		case "name":
			if v != nil {
				var name string
				err = json.Unmarshal(*v, &name)
				if err != nil {
					return err
				}
				ovplr.Name = &name
			}
		case "type":
			if v != nil {
				var typeVar string
				err = json.Unmarshal(*v, &typeVar)
				if err != nil {
					return err
				}
				ovplr.Type = &typeVar
			}
		case "properties":
			if v != nil {
				var orchestratorVersionProfileProperties OrchestratorVersionProfileProperties
				err = json.Unmarshal(*v, &orchestratorVersionProfileProperties)
				if err != nil {
					return err
				}
				ovplr.OrchestratorVersionProfileProperties = &orchestratorVersionProfileProperties
			}
		}
	}

	return nil
}

// OrchestratorVersionProfileProperties the properties of an orchestrator version profile.
type OrchestratorVersionProfileProperties struct {
	// Orchestrators - List of orchestrator version profiles.
	Orchestrators *[]OrchestratorVersionProfile `json:"orchestrators,omitempty"`
}

// Properties properties of the container service.
type Properties struct {
	// ProvisioningState - READ-ONLY; The current deployment or provisioning state, which only appears in the response.
	ProvisioningState *string `json:"provisioningState,omitempty"`
	// OrchestratorProfile - Profile for the container service orchestrator.
	OrchestratorProfile *OrchestratorProfileType `json:"orchestratorProfile,omitempty"`
	// CustomProfile - Properties to configure a custom container service cluster.
	CustomProfile *CustomProfile `json:"customProfile,omitempty"`
	// ServicePrincipalProfile - Information about a service principal identity for the cluster to use for manipulating Azure APIs. Exact one of secret or keyVaultSecretRef need to be specified.
	ServicePrincipalProfile *ServicePrincipalProfile `json:"servicePrincipalProfile,omitempty"`
	// MasterProfile - Profile for the container service master.
	MasterProfile *MasterProfile `json:"masterProfile,omitempty"`
	// AgentPoolProfiles - Properties of the agent pool.
	AgentPoolProfiles *[]AgentPoolProfile `json:"agentPoolProfiles,omitempty"`
	// WindowsProfile - Profile for Windows VMs in the container service cluster.
	WindowsProfile *WindowsProfile `json:"windowsProfile,omitempty"`
	// LinuxProfile - Profile for Linux VMs in the container service cluster.
	LinuxProfile *LinuxProfile `json:"linuxProfile,omitempty"`
	// DiagnosticsProfile - Profile for diagnostics in the container service cluster.
	DiagnosticsProfile *DiagnosticsProfile `json:"diagnosticsProfile,omitempty"`
}

// MarshalJSON is the custom marshaler for Properties.
func (p Properties) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if p.OrchestratorProfile != nil {
		objectMap["orchestratorProfile"] = p.OrchestratorProfile
	}
	if p.CustomProfile != nil {
		objectMap["customProfile"] = p.CustomProfile
	}
	if p.ServicePrincipalProfile != nil {
		objectMap["servicePrincipalProfile"] = p.ServicePrincipalProfile
	}
	if p.MasterProfile != nil {
		objectMap["masterProfile"] = p.MasterProfile
	}
	if p.AgentPoolProfiles != nil {
		objectMap["agentPoolProfiles"] = p.AgentPoolProfiles
	}
	if p.WindowsProfile != nil {
		objectMap["windowsProfile"] = p.WindowsProfile
	}
	if p.LinuxProfile != nil {
		objectMap["linuxProfile"] = p.LinuxProfile
	}
	if p.DiagnosticsProfile != nil {
		objectMap["diagnosticsProfile"] = p.DiagnosticsProfile
	}
	return json.Marshal(objectMap)
}

// Resource the Resource model definition.
type Resource struct {
	// ID - READ-ONLY; Resource Id
	ID *string `json:"id,omitempty"`
	// Name - READ-ONLY; Resource name
	Name *string `json:"name,omitempty"`
	// Type - READ-ONLY; Resource type
	Type *string `json:"type,omitempty"`
	// Location - Resource location
	Location *string `json:"location,omitempty"`
	// Tags - Resource tags
	Tags map[string]*string `json:"tags"`
}

// MarshalJSON is the custom marshaler for Resource.
func (r Resource) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if r.Location != nil {
		objectMap["location"] = r.Location
	}
	if r.Tags != nil {
		objectMap["tags"] = r.Tags
	}
	return json.Marshal(objectMap)
}

// ServicePrincipalProfile information about a service principal identity for the cluster to use for
// manipulating Azure APIs. Either secret or keyVaultSecretRef must be specified.
type ServicePrincipalProfile struct {
	// ClientID - The ID for the service principal.
	ClientID *string `json:"clientId,omitempty"`
	// Secret - The secret password associated with the service principal in plain text.
	Secret *string `json:"secret,omitempty"`
	// KeyVaultSecretRef - Reference to a secret stored in Azure Key Vault.
	KeyVaultSecretRef *KeyVaultSecretRef `json:"keyVaultSecretRef,omitempty"`
}

// SSHConfiguration SSH configuration for Linux-based VMs running on Azure.
type SSHConfiguration struct {
	// PublicKeys - The list of SSH public keys used to authenticate with Linux-based VMs. Only expect one key specified.
	PublicKeys *[]SSHPublicKey `json:"publicKeys,omitempty"`
}

// SSHPublicKey contains information about SSH certificate public key data.
type SSHPublicKey struct {
	// KeyData - Certificate public key used to authenticate with VMs through SSH. The certificate must be in PEM format with or without headers.
	KeyData *string `json:"keyData,omitempty"`
}

// TagsObject tags object for patch operations.
type TagsObject struct {
	// Tags - Resource tags.
	Tags map[string]*string `json:"tags"`
}

// MarshalJSON is the custom marshaler for TagsObject.
func (toVar TagsObject) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if toVar.Tags != nil {
		objectMap["tags"] = toVar.Tags
	}
	return json.Marshal(objectMap)
}

// VMDiagnostics profile for diagnostics on the container service VMs.
type VMDiagnostics struct {
	// Enabled - Whether the VM diagnostic agent is provisioned on the VM.
	Enabled *bool `json:"enabled,omitempty"`
	// StorageURI - READ-ONLY; The URI of the storage account where diagnostics are stored.
	StorageURI *string `json:"storageUri,omitempty"`
}

// MarshalJSON is the custom marshaler for VMDiagnostics.
func (vd VMDiagnostics) MarshalJSON() ([]byte, error) {
	objectMap := make(map[string]interface{})
	if vd.Enabled != nil {
		objectMap["enabled"] = vd.Enabled
	}
	return json.Marshal(objectMap)
}

// WindowsProfile profile for Windows VMs in the container service cluster.
type WindowsProfile struct {
	// AdminUsername - The administrator username to use for Windows VMs.
	AdminUsername *string `json:"adminUsername,omitempty"`
	// AdminPassword - The administrator password to use for Windows VMs.
	AdminPassword *string `json:"adminPassword,omitempty"`
}
