// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  The ASF licenses this file
// to you 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.

<template>
  <div>
    <a-spin :spinning="loading" v-ctrl-enter="handleSubmit">
      <a-row :gutter="12">
        <a-col :md="24" :lg="7" v-if="!isDiskImport">
          <info-card
            class="vm-info-card"
            :isStatic="true"
            :resource="resource"
            :title="$t('label.unmanaged.instance')" />
        </a-col>
        <a-col :md="24" :lg="17">
          <a-card :bordered="true">
            <a-form
              :ref="formRef"
              :model="form"
              :rules="rules"
              @finish="handleSubmit"
              layout="vertical">
              <a-alert
                v-if="selectedVmwareVcenter && isVmRunning"
                type="warning"
                :showIcon="true"
                :message="$t('message.import.running.instance.warning')"
              />
              <a-form-item name="displayname" ref="displayname">
                <template #label>
                  <tooltip-label :title="$t('label.displayname')" :tooltip="apiParams.displayname.description"/>
                </template>
                <a-input
                  v-model:value="form.displayname"
                  :placeholder="apiParams.displayname.description"
                  ref="displayname"
                  v-focus="true" />
              </a-form-item>
              <a-form-item name="hostname" ref="hostname">
                <template #label>
                  <tooltip-label :title="$t('label.hostnamelabel')" :tooltip="apiParams.hostname.description"/>
                </template>
                <a-input
                  v-model:value="form.hostname"
                  :placeholder="apiParams.hostname.description" />
              </a-form-item>
              <a-form-item name="domainid" ref="domainid">
                <template #label>
                  <tooltip-label :title="$t('label.domainid')" :tooltip="apiParams.domainid.description"/>
                </template>
                <a-select
                  v-model:value="form.domainid"
                  showSearch
                  optionFilterProp="label"
                  :filterOption="(input, option) => {
                    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                  }"
                  :loading="optionsLoading.domains"
                  :placeholder="apiParams.domainid.description"
                  @change="val => { this.selectedDomainId = val }">
                  <a-select-option v-for="dom in domainSelectOptions" :key="dom.value" :label="dom.label">
                    <span>
                      <resource-icon v-if="dom.icon" :image="dom.icon" size="1x" style="margin-right: 5px"/>
                      <block-outlined v-else-if="dom.value !== null" style="margin-right: 5px" />
                      {{ dom.label }}
                    </span>
                  </a-select-option>
                </a-select>
              </a-form-item>
              <a-form-item name="account" ref="account" v-if="selectedDomainId">
                <template #label>
                  <tooltip-label :title="$t('label.account')" :tooltip="apiParams.account.description"/>
                </template>
                <a-input
                  v-model:value="form.account"
                  :placeholder="apiParams.account.description"/>
              </a-form-item>
              <a-form-item name="projectid" ref="projectid">
                <template #label>
                  <tooltip-label :title="$t('label.project')" :tooltip="apiParams.projectid.description"/>
                </template>
                <a-select
                  v-model:value="form.projectid"
                  showSearch
                  optionFilterProp="label"
                  :filterOption="(input, option) => {
                    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                  }"
                  :loading="optionsLoading.projects"
                  :placeholder="apiParams.projectid.description">
                  <a-select-option v-for="proj in projectSelectOptions" :key="proj.value" :label="proj.label">
                    <span>
                      <resource-icon v-if="proj.icon" :image="proj.icon" size="1x" style="margin-right: 5px"/>
                      <project-outlined  v-else-if="proj.value !== null" style="margin-right: 5px" />
                      {{ proj.label }}
                    </span>
                  </a-select-option>
                </a-select>
              </a-form-item>
              <a-form-item name="templateid" ref="templateid" v-if="cluster.hypervisortype === 'VMware' || (cluster.hypervisortype === 'KVM' && !selectedVmwareVcenter && !isDiskImport && !isExternalImport)">
                <template #label>
                  <tooltip-label :title="$t('label.templatename')" :tooltip="apiParams.templateid.description + '. ' + $t('message.template.import.vm.temporary')"/>
                </template>
                <a-radio-group
                  style="width:100%"
                  :value="templateType"
                  @change="changeTemplateType">
                  <a-row :gutter="12">
                    <a-col :md="24" :lg="12" v-if="this.cluster.hypervisortype === 'VMware'">
                      <a-radio value="auto">
                        {{ $t('label.template.temporary.import') }}
                      </a-radio>
                    </a-col>
                    <a-col :md="24" :lg="12">
                      <a-radio value="custom">
                        {{ $t('label.template.select.existing') }}
                      </a-radio>
                      <a-select
                        :disabled="templateType === 'auto'"
                        style="margin-top:10px"
                        v-model:value="form.templateid"
                        showSearch
                        optionFilterProp="label"
                        :filterOption="(input, option) => {
                          return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                        }"
                        :loading="optionsLoading.templates"
                        :placeholder="apiParams.templateid.description">
                        <a-select-option v-for="temp in templateSelectOptions" :key="temp.value" :label="temp.label">
                          <span>
                            <resource-icon v-if="temp.icon" :image="temp.icon" size="1x" style="margin-right: 5px"/>
                            <os-logo v-else-if="temp.value !== null" :osId="temp.ostypeid" :osName="temp.ostypename" size="lg" style="margin-left: -1px" />
                            {{ temp.label }}
                          </span>
                        </a-select-option>
                      </a-select>
                    </a-col>
                  </a-row>
                </a-radio-group>
              </a-form-item>
              <a-form-item name="converthostid" ref="converthostid">
                <check-box-select-pair
                  layout="vertical"
                  v-if="cluster.hypervisortype === 'KVM' && selectedVmwareVcenter"
                  :resourceKey="cluster.id"
                  :selectOptions="kvmHostsForConversion"
                  :checkBoxLabel="'(Optional) Select a KVM host in the cluster to perform the instance conversion through virt-v2v'"
                  :defaultCheckBoxValue="false"
                  :reversed="false"
                  @handle-checkselectpair-change="updateSelectedKvmHostForConversion"
                />
              </a-form-item>
              <a-form-item name="convertstorageoption" ref="convertstorageoption">
                <check-box-select-pair
                  layout="vertical"
                  style="margin-bottom: 20px"
                  v-if="cluster.hypervisortype === 'KVM' && selectedVmwareVcenter"
                  :resourceKey="cluster.id"
                  :selectOptions="storageOptionsForConversion"
                  :checkBoxLabel="'(Optional) Select a Storage temporary destination for the converted disks through virt-v2v'"
                  :defaultCheckBoxValue="false"
                  :reversed="false"
                  @handle-checkselectpair-change="updateSelectedStorageOptionForConversion"
                />
              </a-form-item>
              <a-form-item v-if="showStoragePoolsForConversion" name="convertstoragepool" ref="convertstoragepool" :label="$t('label.storagepool')">
                <a-select
                  v-model:value="form.convertstoragepoolid"
                  defaultActiveFirstOption
                  showSearch
                  optionFilterProp="label"
                  :filterOption="(input, option) => {
                    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                  }"
                  @change="val => { selectedStoragePoolForConversion = val }">
                  <a-select-option v-for="(pool) in storagePoolsForConversion" :key="pool.id" :label="pool.name">
                    {{ pool.name }}
                  </a-select-option>
                </a-select>
              </a-form-item>
              <a-form-item name="serviceofferingid" ref="serviceofferingid">
                <template #label>
                  <tooltip-label :title="$t('label.serviceofferingid')" :tooltip="apiParams.serviceofferingid.description"/>
                </template>
                <compute-offering-selection
                  :compute-items="computeOfferings"
                  :loading="computeOfferingLoading"
                  :rowCount="totalComputeOfferings"
                  :value="computeOffering ? computeOffering.id : ''"
                  :minimumCpunumber="isVmRunning ? resource.cpunumber : null"
                  :minimumCpuspeed="isVmRunning ? resource.cpuspeed : null"
                  :minimumMemory="isVmRunning ? resource.memory : null"
                  :allowAllOfferings="selectedVmwareVcenter ? true : false"
                  size="small"
                  @select-compute-item="($event) => updateComputeOffering($event)"
                  @handle-search-filter="($event) => fetchComputeOfferings($event)" />
                <compute-selection
                  class="row-element"
                  v-if="computeOffering && (computeOffering.iscustomized || computeOffering.iscustomizediops)"
                  :isCustomized="computeOffering.iscustomized"
                  :isCustomizedIOps="'iscustomizediops' in computeOffering && computeOffering.iscustomizediops"
                  :cpuNumberInputDecorator="cpuNumberKey"
                  :cpuSpeedInputDecorator="cpuSpeedKey"
                  :memoryInputDecorator="memoryKey"
                  :computeOfferingId="computeOffering.id"
                  :preFillContent="resource"
                  :isConstrained="'serviceofferingdetails' in computeOffering"
                  :minCpu="getMinCpu()"
                  :maxCpu="getMaxCpu()"
                  :minMemory="getMinMemory()"
                  :maxMemory="getMaxMemory()"
                  :cpuSpeed="getCPUSpeed()"
                  @update-iops-value="updateFieldValue"
                  @update-compute-cpunumber="updateFieldValue"
                  @update-compute-cpuspeed="updateCpuSpeed"
                  @update-compute-memory="updateFieldValue" />
              </a-form-item>
              <div v-if="resource.disk && resource.disk.length > 1">
                <a-form-item name="selection" ref="selection">
                  <template #label>
                    <tooltip-label :title="$t('label.disk.selection')" :tooltip="apiParams.datadiskofferinglist.description"/>
                  </template>
                </a-form-item>
                <a-form-item name="rootdiskid" ref="rootdiskid" :label="$t('label.select.root.disk')">
                  <a-select
                    v-model:value="form.rootdiskid"
                    defaultActiveFirstOption
                    showSearch
                    optionFilterProp="label"
                    :filterOption="(input, option) => {
                      return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                    }"
                    @change="onSelectRootDisk">
                    <a-select-option v-for="(opt, optIndex) in resource.disk" :key="optIndex" :label="opt.label || opt.id">
                      {{ opt.label || opt.id }}
                    </a-select-option>
                  </a-select>
                  <a-table
                    :columns="selectedRootDiskColumns"
                    :dataSource="selectedRootDiskSources"
                    :pagination="false">
                    <template #bodyCell="{ column, record }">
                      <template v-if="column.key === 'name'">
                        <span>{{ record.displaytext || record.name }}</span>
                        <div v-if="record.meta">
                          <div v-for="meta in record.meta" :key="meta.key">
                            <a-tag style="margin-top: 5px" :key="meta.key">{{ meta.key + ': ' + meta.value }}</a-tag>
                          </div>
                        </div>
                      </template>
                    </template>
                  </a-table>
                </a-form-item>
                <multi-disk-selection
                  :items="dataDisks"
                  :zoneId="cluster.zoneid"
                  :selectionEnabled="false"
                  :customOfferingsAllowed="true"
                  :autoSelectCustomOffering="true"
                  :isKVMUnmanage="isKVMUnmanage"
                  :autoSelectLabel="$t('label.auto.assign.diskoffering.disk.size')"
                  @select-multi-disk-offering="updateMultiDiskOffering" />
              </div>
              <div v-if="resource.nic && resource.nic.length > 0">
                <a-form-item name="networkselection" ref="networkselection">
                  <template #label>
                    <tooltip-label :title="$t('label.network.selection')" :tooltip="apiParams.nicnetworklist.description"/>
                  </template>
                  <span>{{ $t('message.ip.address.changes.effect.after.vm.restart') }}</span>
                </a-form-item>
                <a-row v-if="selectedVmwareVcenter" :gutter="12" justify="end">
                  <a-col style="text-align: right">
                    <a-form-item name="forced" ref="forced">
                      <template #label>
                        <tooltip-label
                          :title="$t('label.allow.duplicate.macaddresses')"
                          :tooltip="apiParams.forced.description"/>
                      </template>
                      <a-switch v-model:checked="form.forced" @change="val => { switches.forced = val }" />
                    </a-form-item>
                  </a-col>
                </a-row>
                <multi-network-selection
                  :items="nics"
                  :zoneId="cluster.zoneid"
                  :domainid="form.domainid"
                  :account="form.account"
                  :selectionEnabled="false"
                  :filterUnimplementedNetworks="true"
                  :hypervisor="this.cluster.hypervisortype"
                  :filterMatchKey="isKVMUnmanage ? undefined : 'broadcasturi'"
                  @select-multi-network="updateMultiNetworkOffering" />
              </div>
              <a-row v-else style="margin: 12px 0" >
                <div v-if="!isExternalImport && !isDiskImport">
                  <a-alert type="warning">
                    <template #message>
                      <div v-html="$t('message.warn.importing.instance.without.nic')"></div>
                    </template>
                  </a-alert>
                </div>
              </a-row>
              <div v-if="isDiskImport">
                <a-form-item name="networkid" ref="networkid">
                  <template #label>
                    <tooltip-label :title="$t('label.network')"/>
                  </template>
                  <a-select
                    v-model:value="form.networkid"
                    showSearch
                    optionFilterProp="label"
                    :filterOption="(input, option) => {
                      return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0
                    }"
                    :loading="optionsLoading.networks">
                    <a-select-option v-for="network in networkSelectOptions" :key="network.value" :label="network.label">
                      <span>
                        {{ network.label }}
                      </span>
                    </a-select-option>
                  </a-select>
                </a-form-item>
              </div>
              <a-row v-if="!selectedVmwareVcenter" :gutter="12">
                <a-col :md="24" :lg="12">
                  <a-form-item name="migrateallowed" ref="migrateallowed">
                    <template #label>
                      <tooltip-label :title="$t('label.migrate.allowed')" :tooltip="apiParams.migrateallowed.description"/>
                    </template>
                    <a-switch v-model:checked="form.migrateallowed" @change="val => { switches.migrateAllowed = val }" />
                  </a-form-item>
                </a-col>
                <a-col>
                  <a-form-item name="forced" ref="forced">
                    <template #label>
                      <tooltip-label
                        :title="$t('label.forced')"
                        :tooltip="apiParams.forced.description"/>
                    </template>
                    <a-switch v-model:checked="form.forced" @change="val => { switches.forced = val }" />
                  </a-form-item>
                </a-col>
              </a-row>
              <div :span="24" class="action-button">
                <a-button @click="closeAction">{{ $t('label.cancel') }}</a-button>
                <a-button :loading="loading" type="primary" @click="handleSubmit">{{ $t('label.ok') }}</a-button>
              </div>
            </a-form>
          </a-card>
        </a-col>
      </a-row>
    </a-spin>
  </div>
</template>

<script>
import { ref, reactive, toRaw } from 'vue'
import { api } from '@/api'
import _ from 'lodash'
import InfoCard from '@/components/view/InfoCard'
import TooltipLabel from '@/components/widgets/TooltipLabel'
import ComputeOfferingSelection from '@views/compute/wizard/ComputeOfferingSelection'
import ComputeSelection from '@views/compute/wizard/ComputeSelection'
import MultiDiskSelection from '@views/compute/wizard/MultiDiskSelection'
import MultiNetworkSelection from '@views/compute/wizard/MultiNetworkSelection'
import OsLogo from '@/components/widgets/OsLogo'
import ResourceIcon from '@/components/view/ResourceIcon'
import CheckBoxSelectPair from '@/components/CheckBoxSelectPair'

export default {
  name: 'ImportUnmanagedInstances',
  components: {
    InfoCard,
    TooltipLabel,
    ComputeOfferingSelection,
    ComputeSelection,
    MultiDiskSelection,
    MultiNetworkSelection,
    OsLogo,
    ResourceIcon,
    CheckBoxSelectPair
  },
  props: {
    cluster: {
      type: Object,
      required: true
    },
    host: {
      type: Object,
      required: true
    },
    pool: {
      type: Object,
      required: true
    },
    resource: {
      type: Object,
      required: true
    },
    isOpen: {
      type: Boolean,
      required: false
    },
    zoneid: {
      type: String,
      required: false
    },
    importsource: {
      type: String,
      required: false
    },
    hypervisor: {
      type: String,
      required: false
    },
    exthost: {
      type: String,
      required: false
    },
    username: {
      type: String,
      required: false
    },
    password: {
      type: String,
      required: false
    },
    tmppath: {
      type: String,
      required: false
    },
    diskpath: {
      type: String,
      required: false
    },
    selectedVmwareVcenter: {
      type: Array,
      required: false
    }
  },
  data () {
    return {
      options: {
        domains: [],
        projects: [],
        networks: [],
        templates: []
      },
      rowCount: {},
      optionsLoading: {
        domains: false,
        projects: false,
        networks: false,
        templates: false
      },
      domains: [],
      domainLoading: false,
      selectedDomainId: null,
      templates: [],
      templateLoading: false,
      templateType: this.defaultTemplateType(),
      totalComputeOfferings: 0,
      computeOfferings: [],
      computeOfferingLoading: false,
      computeOffering: {},
      selectedRootDiskIndex: 0,
      dataDisksOfferingsMapping: {},
      nicsNetworksMapping: {},
      cpuNumberKey: 'cpuNumber',
      cpuSpeedKey: 'cpuSpeed',
      memoryKey: 'memory',
      minIopsKey: 'minIops',
      maxIopsKey: 'maxIops',
      switches: {},
      loading: false,
      kvmHostsForConversion: [],
      selectedKvmHostForConversion: null,
      storageOptionsForConversion: [
        {
          id: 'secondary',
          name: 'Secondary Storage'
        }, {
          id: 'primary',
          name: 'Primary Storage'
        }
      ],
      storagePoolsForConversion: [],
      selectedStorageOptionForConversion: null,
      selectedStoragePoolForConversion: null,
      showStoragePoolsForConversion: false,
      selectedRootDiskColumns: [
        {
          key: 'name',
          dataIndex: 'name',
          title: this.$t('label.rootdisk')
        }
      ],
      selectedRootDiskSources: []
    }
  },
  beforeCreate () {
    this.apiConfig = this.$store.getters.apis.importUnmanagedInstance || {}
    this.apiParams = {}
    this.apiConfig.params.forEach(param => {
      this.apiParams[param.name] = param
    })
  },
  created () {
    this.initForm()
    this.fetchData()
  },
  computed: {
    params () {
      return {
        domains: {
          list: 'listDomains',
          isLoad: true,
          field: 'domainid',
          options: {
            details: 'min',
            showicon: true
          }
        },
        projects: {
          list: 'listProjects',
          isLoad: true,
          field: 'projectid',
          options: {
            details: 'min',
            showicon: true
          }
        },
        networks: {
          list: 'listNetworks',
          isLoad: true,
          field: 'networkid',
          options: {
            zoneid: this.zoneid,
            details: 'min'
          }
        },
        templates: {
          list: 'listTemplates',
          isLoad: true,
          options: {
            templatefilter: 'all',
            hypervisor: this.cluster.hypervisortype,
            showicon: true
          },
          field: 'templateid'
        }
      }
    },
    isVmRunning () {
      if (this.resource && this.resource.powerstate === 'PowerOn') {
        return true
      }
      return false
    },
    isDiskImport () {
      if (this.importsource === 'local' || this.importsource === 'shared') {
        return true
      }
      return false
    },
    isExternalImport () {
      if (this.importsource === 'external') {
        return true
      }
      return false
    },
    isKVMUnmanage () {
      return this.hypervisor && this.hypervisor === 'kvm' && (this.importsource === 'unmanaged' || this.importsource === 'external')
    },
    domainSelectOptions () {
      var domains = this.options.domains.map((domain) => {
        return {
          label: domain.path || domain.name,
          value: domain.id,
          icon: domain?.icon?.base64image || ''
        }
      })
      domains.unshift({
        label: '',
        value: null
      })
      return domains
    },
    projectSelectOptions () {
      var projects = this.options.projects.map((project) => {
        return {
          label: project.name,
          value: project.id,
          icon: project?.icon?.base64image || ''
        }
      })
      projects.unshift({
        label: '',
        value: null
      })
      return projects
    },
    networkSelectOptions () {
      var networks = this.options.networks.map((network) => {
        return {
          label: network.name + ' (' + network.displaytext + ')',
          value: network.id
        }
      })
      networks.unshift({
        label: '',
        value: null
      })
      return networks
    },
    templateSelectOptions () {
      return this.options.templates.map((template) => {
        return {
          label: template.name,
          value: template.id,
          icon: template?.icon?.base64image || '',
          ostypeid: template.ostypeid,
          ostypename: template.ostypename
        }
      })
    },
    dataDisks () {
      var disks = []
      if (this.resource.disk && this.resource.disk.length > 1) {
        for (var index = 0; index < this.resource.disk.length; ++index) {
          if (index !== this.selectedRootDiskIndex) {
            var disk = { ...this.resource.disk[index] }
            disk.size = disk.capacity / (1024 * 1024 * 1024)
            disk.name = disk.label
            disk.meta = this.getMeta(disk, { controller: 'controller', datastorename: 'datastore', position: 'position' })
            disks.push(disk)
          }
        }
      }
      return disks
    },
    nics () {
      var nics = []
      if (this.resource.nic && this.resource.nic.length > 0) {
        for (var nicEntry of this.resource.nic) {
          var nic = { ...nicEntry }
          nic.name = nic.name || nic.id
          nic.displaytext = nic.name
          if (this.isExternalImport && nic.vlanid === -1) {
            delete nic.vlanid
          }
          if (nic.vlanid) {
            nic.broadcasturi = 'vlan://' + nic.vlanid
            if (nic.isolatedpvlan) {
              nic.broadcasturi = 'pvlan://' + nic.vlanid + '-i' + nic.isolatedpvlan
            }
          }
          if (this.cluster.hypervisortype === 'VMware') {
            nic.meta = this.getMeta(nic, { macaddress: 'mac', vlanid: 'vlan', networkname: 'network' })
          } else {
            nic.meta = this.getMeta(nic, { macaddress: 'mac', vlanid: 'vlan' })
          }
          nics.push(nic)
        }
      }
      return nics
    }
  },
  watch: {
    isOpen (newValue) {
      if (newValue) {
        this.resetForm()
        this.$refs.displayname.focus()
        this.selectMatchingComputeOffering()
      }
    }
  },
  methods: {
    initForm () {
      this.formRef = ref()
      this.form = reactive({
        rootdiskid: 0,
        migrateallowed: this.switches.migrateAllowed,
        forced: this.switches.forced,
        domainid: null,
        account: null
      })
      this.rules = reactive({
        displayname: [{ required: true, message: this.$t('message.error.input.value') }],
        templateid: [{ required: this.templateType !== 'auto', message: this.$t('message.error.input.value') }],
        rootdiskid: [{ required: this.templateType !== 'auto', message: this.$t('message.error.input.value') }]
      })
    },
    fetchData () {
      _.each(this.params, (param, name) => {
        if (param.isLoad) {
          this.fetchOptions(param, name)
        }
      })
      this.fetchComputeOfferings({
        keyword: '',
        pageSize: 10,
        page: 1
      })
      this.fetchKvmHostsForConversion()
      if (this.resource?.disk?.length > 1) {
        this.updateSelectedRootDisk()
      }
    },
    getMeta (obj, metaKeys) {
      var meta = []
      for (var key in metaKeys) {
        if (key in obj) {
          meta.push({ key: metaKeys[key], value: obj[key] })
        }
      }
      return meta
    },
    getMinCpu () {
      if (this.isVmRunning) {
        return this.resource.cpunumber
      }
      return 'serviceofferingdetails' in this.computeOffering ? this.computeOffering.serviceofferingdetails.mincpunumber * 1 : 1
    },
    getMinMemory () {
      if (this.isVmRunning) {
        return this.resource.memory
      }
      return 'serviceofferingdetails' in this.computeOffering ? this.computeOffering.serviceofferingdetails.minmemory * 1 : 32
    },
    getMaxCpu () {
      if (this.isVmRunning) {
        return this.resource.cpunumber
      }
      return 'serviceofferingdetails' in this.computeOffering ? this.computeOffering.serviceofferingdetails.maxcpunumber * 1 : Number.MAX_SAFE_INTEGER
    },
    getMaxMemory () {
      if (this.isVmRunning) {
        return this.resource.memory
      }
      return 'serviceofferingdetails' in this.computeOffering ? this.computeOffering.serviceofferingdetails.maxmemory * 1 : Number.MAX_SAFE_INTEGER
    },
    getCPUSpeed () {
      if (!this.computeOffering) {
        return 0
      }
      if (this.computeOffering.cpuspeed) {
        return this.computeOffering.cpuspeed * 1
      }
      return this.resource.cpuspeed * 1 || 0
    },
    fetchOptions (param, name, exclude) {
      if (exclude && exclude.length > 0) {
        if (exclude.includes(name)) {
          return
        }
      }
      this.optionsLoading[name] = true
      param.loading = true
      param.opts = []
      const options = param.options || {}
      if (!('listall' in options)) {
        options.listall = true
      }
      api(param.list, options).then((response) => {
        param.loading = false
        _.map(response, (responseItem, responseKey) => {
          if (Object.keys(responseItem).length === 0) {
            this.rowCount[name] = 0
            this.options[name] = []
            return
          }
          if (!responseKey.includes('response')) {
            return
          }
          _.map(responseItem, (response, key) => {
            if (key === 'count') {
              this.rowCount[name] = response
              return
            }
            param.opts = response
            this.options[name] = response
          })
        })
      }).catch(function (error) {
        console.log(error.stack)
        param.loading = false
      }).finally(() => {
        this.optionsLoading[name] = false
      })
    },
    fetchComputeOfferings (options) {
      this.computeOfferingLoading = true
      this.totalComputeOfferings = 0
      this.computeOfferings = []
      this.offeringsMap = []
      api('listServiceOfferings', {
        keyword: options.keyword,
        page: options.page,
        pageSize: options.pageSize,
        details: 'min',
        response: 'json'
      }).then(response => {
        this.totalComputeOfferings = response.listserviceofferingsresponse.count
        if (this.totalComputeOfferings === 0) {
          return
        }
        this.computeOfferings = response.listserviceofferingsresponse.serviceoffering
        this.computeOfferings.map(i => { this.offeringsMap[i.id] = i })
      }).finally(() => {
        this.computeOfferingLoading = false
        this.selectMatchingComputeOffering()
      })
    },
    updateCpuSpeed (name, value) {
      if (this.computeOffering.iscustomized) {
        if (this.computeOffering.serviceofferingdetails) {
          this.updateFieldValue(this.cpuSpeedKey, this.computeOffering.cpuspeed)
        } else {
          this.updateFieldValue(this.cpuSpeedKey, value)
        }
      }
    },
    updateFieldValue (name, value) {
      this.form[name] = value
    },
    updateComputeOffering (id) {
      this.updateFieldValue('computeofferingid', id)
      this.computeOffering = this.computeOfferings.filter(x => x.id === id)[0]
      if (this.computeOffering && !this.computeOffering.iscustomizediops) {
        this.updateFieldValue(this.minIopsKey, undefined)
        this.updateFieldValue(this.maxIopsKey, undefined)
      }
    },
    updateMultiDiskOffering (data) {
      this.dataDisksOfferingsMapping = data
    },
    updateMultiNetworkOffering (data) {
      this.nicsNetworksMapping = data
    },
    defaultTemplateType () {
      if (this.cluster.hypervisortype === 'VMware') {
        return 'auto'
      }
      return 'custom'
    },
    changeTemplateType (e) {
      this.templateType = e.target.value
      if (this.templateType === 'auto') {
        this.updateFieldValue('templateid', undefined)
      }
      this.rules = reactive({
        displayname: [{ required: true, message: this.$t('message.error.input.value') }],
        templateid: [{ required: this.templateType !== 'auto', message: this.$t('message.error.input.value') }],
        rootdiskid: [{ required: this.templateType !== 'auto', message: this.$t('message.error.input.value') }]
      })
    },
    selectMatchingComputeOffering () {
      var offerings = [...this.computeOfferings]
      offerings.sort(function (a, b) {
        return a.cpunumber - b.cpunumber
      })
      for (var offering of offerings) {
        var cpuNumberMatches = false
        var cpuSpeedMatches = false
        var memoryMatches = false
        if (!offering.iscustomized) {
          cpuNumberMatches = offering.cpunumber === this.resource.cpunumber
          cpuSpeedMatches = !this.resource.cpuspeed || offering.cpuspeed === this.resource.cpuspeed
          memoryMatches = offering.memory === this.resource.memory
        } else {
          cpuNumberMatches = cpuSpeedMatches = memoryMatches = true
          if (offering.serviceofferingdetails) {
            cpuNumberMatches = (this.resource.cpunumber >= offering.serviceofferingdetails.mincpunumber &&
              this.resource.cpunumber <= offering.serviceofferingdetails.maxcpunumber)
            memoryMatches = (this.resource.memory >= offering.serviceofferingdetails.minmemory &&
              this.resource.memory <= offering.serviceofferingdetails.maxmemory)
            cpuSpeedMatches = !this.resource.cpuspeed || offering.cpuspeed === this.resource.cpuspeed
          }
        }
        if (cpuNumberMatches && cpuSpeedMatches && memoryMatches) {
          setTimeout(() => {
            this.updateComputeOffering(offering.id)
          }, 250)
          break
        }
      }
    },
    fetchKvmHostsForConversion () {
      api('listHosts', {
        clusterid: this.cluster.id,
        hypervisor: this.cluster.hypervisortype,
        type: 'Routing',
        state: 'Up',
        resourcestate: 'Enabled'
      }).then(json => {
        this.kvmHostsForConversion = json.listhostsresponse.host || []
      })
    },
    fetchStoragePoolsForConversion () {
      if (this.selectedStorageOptionForConversion === 'primary') {
        api('listStoragePools', {
          zoneid: this.cluster.zoneid,
          state: 'Up'
        }).then(json => {
          this.storagePoolsForConversion = json.liststoragepoolsresponse.storagepool || []
        })
      } else if (this.selectedStorageOptionForConversion === 'local') {
        const kvmHost = this.kvmHostsForConversion.filter(x => x.id === this.selectedKvmHostForConversion)[0]
        api('listStoragePools', {
          scope: 'HOST',
          ipaddress: kvmHost.ipaddress,
          state: 'Up'
        }).then(json => {
          this.storagePoolsForConversion = json.liststoragepoolsresponse.storagepool || []
        })
      }
    },
    updateSelectedKvmHostForConversion (clusterid, checked, value) {
      if (checked) {
        this.selectedKvmHostForConversion = value
        const kvmHost = this.kvmHostsForConversion.filter(x => x.id === this.selectedKvmHostForConversion)[0]
        if (kvmHost.islocalstorageactive) {
          this.storageOptionsForConversion.push({
            id: 'local',
            name: 'Host Local Storage'
          })
        } else {
          this.resetStorageOptionsForConversion()
        }
      } else {
        this.selectedKvmHostForConversion = null
        this.resetStorageOptionsForConversion()
      }
    },
    updateSelectedStorageOptionForConversion (clusterid, checked, value) {
      if (checked) {
        this.selectedStorageOptionForConversion = value
        this.fetchStoragePoolsForConversion()
        this.showStoragePoolsForConversion = value !== 'secondary'
      } else {
        this.showStoragePoolsForConversion = false
        this.selectedStoragePoolForConversion = null
      }
    },
    resetStorageOptionsForConversion () {
      this.storageOptionsForConversion = [
        {
          id: 'secondary',
          name: 'Secondary Storage'
        }, {
          id: 'primary',
          name: 'Primary Storage'
        }
      ]
    },
    onSelectRootDisk (val) {
      this.selectedRootDiskIndex = val
      this.updateSelectedRootDisk()
    },
    updateSelectedRootDisk () {
      var rootDisk = this.resource.disk[this.selectedRootDiskIndex]
      rootDisk.size = rootDisk.capacity / (1024 * 1024 * 1024)
      rootDisk.name = `${rootDisk.label} (${rootDisk.size} GB)`
      rootDisk.meta = this.getMeta(rootDisk, { controller: 'controller', datastorename: 'datastore', position: 'position' })
      this.selectedRootDiskSources = [rootDisk]
    },
    handleSubmit (e) {
      e.preventDefault()
      if (this.loading) return
      this.formRef.value.validate().then(() => {
        const values = toRaw(this.form)
        const params = {
          name: this.resource.name,
          clusterid: this.cluster.id,
          displayname: values.displayname,
          zoneid: this.zoneid,
          importsource: this.importsource,
          hypervisor: this.hypervisor,
          host: this.exthost,
          hostname: values.hostname,
          username: this.username,
          password: this.password,
          hostid: this.host.id,
          storageid: this.pool.id,
          diskpath: this.diskpath,
          temppath: this.tmppath
        }
        var importapi = 'importUnmanagedInstance'
        if (this.isExternalImport || this.isDiskImport || this.selectedVmwareVcenter) {
          importapi = 'importVm'
          if (this.isDiskImport) {
            if (!values.networkid) {
              this.$notification.error({
                message: this.$t('message.request.failed'),
                description: this.$t('message.please.enter.valid.value') + ': ' + this.$t('label.network')
              })
              return
            }
            params.name = values.displayname
            params.networkid = values.networkid
          }
        }
        if (!this.computeOffering || !this.computeOffering.id) {
          this.$notification.error({
            message: this.$t('message.request.failed'),
            description: this.$t('message.step.2.continue')
          })
          return
        }
        params.serviceofferingid = values.computeofferingid
        if (this.computeOffering.iscustomized) {
          var details = [this.cpuNumberKey, this.cpuSpeedKey, this.memoryKey]
          for (var detail of details) {
            if (!(values[detail] || this.computeOffering[detail])) {
              this.$notification.error({
                message: this.$t('message.request.failed'),
                description: this.$t('message.please.enter.valid.value') + ': ' + this.$t('label.' + detail.toLowerCase())
              })
              return
            }
            if (values[detail]) {
              params['details[0].' + detail] = values[detail]
            }
          }
        }
        if (this.computeOffering.iscustomizediops) {
          var iopsDetails = [this.minIopsKey, this.maxIopsKey]
          for (var iopsDetail of iopsDetails) {
            if (!values[iopsDetail] || values[iopsDetail] < 0) {
              this.$notification.error({
                message: this.$t('message.request.failed'),
                description: this.$t('message.please.enter.valid.value') + ': ' + this.$t('label.' + iopsDetail.toLowerCase())
              })
              return
            }
            params['details[0].' + iopsDetail] = values[iopsDetail]
          }
          if (values[this.minIopsKey] > values[this.maxIopsKey]) {
            this.$notification.error({
              message: this.$t('message.request.failed'),
              description: this.$t('error.form.message')
            })
          }
        }
        if (this.isDiskImport) {
          var storageType = this.computeOffering.storagetype
          if (this.importsource !== storageType) {
            this.$notification.error({
              message: this.$t('message.request.failed'),
              description: 'Incompatible Storage. Import Source is: ' + this.importsource + '. Storage Type in service offering is: ' + storageType
            })
            return
          }
        }
        if (this.selectedVmwareVcenter) {
          if (this.selectedVmwareVcenter.existingvcenterid) {
            params.existingvcenterid = this.selectedVmwareVcenter.existingvcenterid
          } else {
            params.vcenter = this.selectedVmwareVcenter.vcenter
            params.datacentername = this.selectedVmwareVcenter.datacentername
            params.username = this.selectedVmwareVcenter.username
            params.password = this.selectedVmwareVcenter.password
          }
          params.hostip = this.resource.hostname
          params.clustername = this.resource.clustername
          if (this.selectedKvmHostForConversion) {
            params.convertinstancehostid = this.selectedKvmHostForConversion
          }
          if (this.selectedStoragePoolForConversion) {
            params.convertinstancepoolid = this.selectedStoragePoolForConversion
          }
        }
        var keys = ['hostname', 'domainid', 'projectid', 'account', 'migrateallowed', 'forced']
        if (this.templateType !== 'auto') {
          keys.push('templateid')
        }
        for (var key of keys) {
          if (values[key]) {
            params[key] = values[key]
          }
        }
        var diskOfferingIndex = 0
        for (var diskId in this.dataDisksOfferingsMapping) {
          if (!this.dataDisksOfferingsMapping[diskId]) {
            this.$notification.error({
              message: this.$t('message.request.failed'),
              description: this.$t('message.select.disk.offering') + ': ' + diskId
            })
            return
          }
          params['datadiskofferinglist[' + diskOfferingIndex + '].disk'] = diskId
          params['datadiskofferinglist[' + diskOfferingIndex + '].diskOffering'] = this.dataDisksOfferingsMapping[diskId]
          diskOfferingIndex++
        }
        var nicNetworkIndex = 0
        var nicIpIndex = 0
        var networkcheck = new Set()
        for (var nicId in this.nicsNetworksMapping) {
          if (!this.nicsNetworksMapping[nicId].network) {
            this.$notification.error({
              message: this.$t('message.request.failed'),
              description: this.$t('message.select.nic.network') + ': ' + nicId
            })
            return
          }
          params['nicnetworklist[' + nicNetworkIndex + '].nic'] = nicId
          params['nicnetworklist[' + nicNetworkIndex + '].network'] = this.nicsNetworksMapping[nicId].network
          var netId = this.nicsNetworksMapping[nicId].network
          if (!networkcheck.has(netId)) {
            networkcheck.add(netId)
          } else {
            this.$notification.error({
              message: this.$t('message.request.failed'),
              description: 'Same network cannot be assigned to multiple Nics'
            })
            return
          }
          nicNetworkIndex++
          if ('ipAddress' in this.nicsNetworksMapping[nicId]) {
            if (!this.nicsNetworksMapping[nicId].ipAddress) {
              this.$notification.error({
                message: this.$t('message.request.failed'),
                description: this.$t('message.enter.valid.nic.ip') + ': ' + nicId
              })
              return
            }
            params['nicipaddresslist[' + nicIpIndex + '].nic'] = nicId
            params['nicipaddresslist[' + nicIpIndex + '].ip4Address'] = this.nicsNetworksMapping[nicId].ipAddress
            nicIpIndex++
          }
        }
        this.updateLoading(true)
        const name = params.name
        return new Promise((resolve, reject) => {
          api(importapi, params).then(response => {
            var jobId
            if (this.isDiskImport || this.isExternalImport || this.selectedVmwareVcenter) {
              jobId = response.importvmresponse.jobid
            } else {
              jobId = response.importunmanagedinstanceresponse.jobid
            }
            let msgLoading = this.$t('label.import.instance') + ' ' + name + ' ' + this.$t('label.in.progress')
            if (this.selectedKvmHostForConversion) {
              const kvmHost = this.kvmHostsForConversion.filter(x => x.id === this.selectedKvmHostForConversion)[0]
              msgLoading += ' on host ' + kvmHost.name
            }
            this.$pollJob({
              jobId,
              title: this.$t('label.import.instance'),
              description: name,
              loadingMessage: msgLoading,
              catchMessage: this.$t('error.fetching.async.job.result'),
              successMessage: this.$t('message.success.import.instance') + ' ' + name,
              successMethod: result => {
                this.$emit('refresh-data')
                resolve(result)
              },
              errorMethod: (result) => {
                this.updateLoading(false)
                reject(result.jobresult.errortext)
              }
            })
          }).catch(error => {
            this.updateLoading(false)
            this.$notifyError(error)
          }).finally(() => {
            this.closeAction()
            this.updateLoading(false)
          })
        })
      }).catch(() => {
        this.$emit('loading-changed', false)
      })
    },
    updateLoading (value) {
      this.loading = value
      this.$emit('loading-changed', value)
    },
    resetForm () {
      var fields = ['displayname', 'hostname', 'domainid', 'account', 'projectid', 'computeofferingid']
      for (var field of fields) {
        this.updateFieldValue(field, undefined)
      }
      this.templateType = this.defaultTemplateType()
      this.updateComputeOffering(undefined)
      this.switches = {}
    },
    closeAction () {
      this.$emit('close-action')
    }
  }
}
</script>

<style lang="less">
@import url('../../style/index');
.ant-table-selection-column {
  // Fix for the table header if the row selection use radio buttons instead of checkboxes
  > div:empty {
    width: 16px;
  }
}

.ant-collapse-borderless > .ant-collapse-item {
  border: 1px solid @border-color-split;
  border-radius: @border-radius-base !important;
  margin: 0 0 1.2rem;
}

.form-layout {
  width: 120vw;

  @media (min-width: 1000px) {
    width: 550px;
  }
}

.action-button {
  text-align: right;

  button {
    margin-right: 5px;
  }
}
</style>
