<template>
  <v-card class="span-12 panel-pad">
    <h2 class="section-title mb-1">ServiceNow integration</h2>
    <p class="quiet text-body-2 mb-3">
      Submit alerts as ServiceNow incidents (Table API) and pull asset data from the CMDB. Uses basic auth over HTTPS.
      Leave the password blank to keep the stored value.
    </p>

    <h3 class="section-title text-body-1 mb-2">Connection</h3>
    <div class="form-grid">
      <v-text-field v-model="form.servicenow_instance_url" class="full" label="Instance URL" placeholder="https://dev12345.service-now.com" />
      <v-text-field v-model="form.servicenow_username" label="Username (integration user)" autocomplete="off" />
      <v-text-field
        v-model="form.servicenow_password"
        type="password"
        :label="settings.servicenow_password_set ? 'Password (unchanged)' : 'Password'"
        autocomplete="new-password"
      />
      <div class="d-flex align-center">
        <v-btn v-if="settings.servicenow_password_set" variant="text" size="small" color="error" prepend-icon="mdi-key-remove" @click="clearPassword">Clear password</v-btn>
      </div>
    </div>

    <v-divider class="my-4" />
    <h3 class="section-title text-body-1 mb-2">Incident creation (push)</h3>
    <div class="form-grid">
      <v-switch v-model="form.servicenow_ticket_enabled" label="Allow submitting alerts as incidents" color="primary" density="compact" hide-details />
      <v-switch v-model="form.servicenow_auto_ticket" label="Auto-create incidents for new critical alerts" color="primary" density="compact" hide-details />
      <v-text-field v-model="form.servicenow_incident_table" label="Incident table" placeholder="incident" />
      <v-text-field v-model="form.servicenow_assignment_group" label="Assignment group (sys_id or name, optional)" />
      <v-text-field v-model="form.servicenow_caller_id" class="full" label="Caller / requested-for (sys_id, optional)" />
    </div>

    <v-divider class="my-4" />
    <h3 class="section-title text-body-1 mb-2">CMDB asset sync (pull)</h3>
    <div class="form-grid">
      <v-text-field v-model="form.servicenow_cmdb_table" label="CMDB CI table" placeholder="cmdb_ci_hardware" />
      <v-text-field v-model.number="form.servicenow_cmdb_limit" type="number" label="Max records per sync" />
      <v-text-field v-model="form.servicenow_cmdb_query" class="full" label="Filter (sysparm_query, optional)" placeholder="install_status=1^operational_status=1" />
    </div>
    <v-textarea
      v-model="cmdbMapText"
      class="mt-2"
      label="Field mapping (asset field → CMDB column, JSON)"
      :rows="6"
      hint="Maps DepreCore asset fields to ServiceNow CI columns. Leave default to use the built-in hardware mapping."
      persistent-hint
      :error-messages="mapError"
    />
    <div class="toolbar-row mt-3">
      <v-btn variant="tonal" prepend-icon="mdi-database-sync" :loading="syncing" :disabled="!settings.configured" @click="syncCmdb">Sync CMDB now</v-btn>
      <div class="quiet text-body-2 ml-2">Last sync: {{ settings.servicenow_last_sync_at ? shortDate(settings.servicenow_last_sync_at) : 'Never' }}</div>
    </div>
    <v-alert v-if="settings.servicenow_last_sync_status" class="mt-2" density="compact" type="info">{{ settings.servicenow_last_sync_status }}</v-alert>

    <v-divider class="my-4" />
    <div class="toolbar-row">
      <v-btn variant="tonal" prepend-icon="mdi-connection" :loading="testing" :disabled="!form.servicenow_instance_url" @click="test">Test connection</v-btn>
      <v-spacer />
      <v-btn color="primary" prepend-icon="mdi-content-save" :loading="saving" @click="save">Save ServiceNow settings</v-btn>
    </div>
    <v-alert v-if="status" class="mt-3" density="compact" :type="statusType">{{ status }}</v-alert>
  </v-card>
</template>

<script>
import { apiRequest } from '../services/api';
import { shortDate } from '../utils/format';

function blankForm() {
  return {
    servicenow_instance_url: '',
    servicenow_username: '',
    servicenow_password: '',
    servicenow_incident_table: 'incident',
    servicenow_assignment_group: '',
    servicenow_caller_id: '',
    servicenow_ticket_enabled: false,
    servicenow_auto_ticket: false,
    servicenow_cmdb_table: 'cmdb_ci_hardware',
    servicenow_cmdb_query: '',
    servicenow_cmdb_limit: 200
  };
}

export default {
  props: {
    token: { type: String, required: true }
  },
  data() {
    return {
      settings: {},
      form: blankForm(),
      cmdbMapText: '',
      mapError: '',
      saving: false,
      testing: false,
      syncing: false,
      status: '',
      statusType: 'success'
    };
  },
  mounted() {
    this.load();
  },
  methods: {
    shortDate,
    async api(path, options = {}) {
      return apiRequest(path, this.token, options);
    },
    apply(settings) {
      this.settings = settings;
      this.form = {
        servicenow_instance_url: settings.servicenow_instance_url || '',
        servicenow_username: settings.servicenow_username || '',
        servicenow_password: '',
        servicenow_incident_table: settings.servicenow_incident_table || 'incident',
        servicenow_assignment_group: settings.servicenow_assignment_group || '',
        servicenow_caller_id: settings.servicenow_caller_id || '',
        servicenow_ticket_enabled: settings.servicenow_ticket_enabled || false,
        servicenow_auto_ticket: settings.servicenow_auto_ticket || false,
        servicenow_cmdb_table: settings.servicenow_cmdb_table || 'cmdb_ci_hardware',
        servicenow_cmdb_query: settings.servicenow_cmdb_query || '',
        servicenow_cmdb_limit: settings.servicenow_cmdb_limit || 200
      };
      this.cmdbMapText = JSON.stringify(settings.servicenow_cmdb_map || {}, null, 2);
    },
    async load() {
      const data = await (await this.api('/api/servicenow/settings')).json();
      this.apply(data.settings);
    },
    buildPayload() {
      this.mapError = '';
      const payload = { ...this.form };
      if (!payload.servicenow_password) delete payload.servicenow_password;
      const text = this.cmdbMapText.trim();
      if (text) {
        try {
          payload.servicenow_cmdb_map = JSON.parse(text);
        } catch {
          this.mapError = 'Field mapping must be valid JSON.';
          return null;
        }
      } else {
        payload.servicenow_cmdb_map = '';
      }
      return payload;
    },
    async save() {
      const payload = this.buildPayload();
      if (!payload) return;
      this.saving = true;
      this.status = '';
      try {
        const data = await (await this.api('/api/servicenow/settings', { method: 'PUT', body: JSON.stringify(payload) })).json();
        this.apply(data.settings);
        this.statusType = 'success';
        this.status = 'ServiceNow settings saved.';
      } catch (error) {
        this.statusType = 'error';
        this.status = error.message;
      } finally {
        this.saving = false;
      }
    },
    async clearPassword() {
      this.status = '';
      try {
        const data = await (await this.api('/api/servicenow/settings', { method: 'PUT', body: JSON.stringify({ servicenow_password_clear: true }) })).json();
        this.apply(data.settings);
        this.statusType = 'success';
        this.status = 'Password cleared.';
      } catch (error) {
        this.statusType = 'error';
        this.status = error.message;
      }
    },
    async test() {
      this.testing = true;
      this.status = '';
      try {
        await this.save();
        const result = await (await this.api('/api/servicenow/test', { method: 'POST', body: JSON.stringify({}) })).json();
        this.statusType = 'success';
        this.status = `Connected to ${result.instance}.`;
      } catch (error) {
        this.statusType = 'error';
        this.status = `Connection failed: ${error.message}`;
      } finally {
        this.testing = false;
      }
    },
    async syncCmdb() {
      const payload = this.buildPayload();
      if (!payload) return;
      this.syncing = true;
      this.status = '';
      try {
        await this.save();
        const result = await (await this.api('/api/servicenow/cmdb-sync', { method: 'POST', body: JSON.stringify({}) })).json();
        this.statusType = 'success';
        this.status = result.status || `Synced ${result.total} CI(s).`;
        await this.load();
      } catch (error) {
        this.statusType = 'error';
        this.status = `Sync failed: ${error.message}`;
      } finally {
        this.syncing = false;
      }
    }
  }
};
</script>
