All files / src/components ShowApiKeyModal.vue

97.05% Statements 33/34
85.71% Branches 12/14
80% Functions 4/5
97.05% Lines 33/34

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140    17x           2x 2x 2x 2x                     2x   2x 2x       2x       2x   2x       2x 2x 2x                                     2x   2x         2x   2x 6x                   2x                                               14x       14x   14x 14x     14x 5x       2x 2x 2x 2x 2x 1x                   14x          
<template>
  <div
    v-if="isOpen && apiKey && apiKeyValue"
    class="modal fade show d-block"
    tabindex="-1"
    style="background-color: rgba(0, 0, 0, 0.5)"
    @click.self="close"
  >
    <div class="modal-dialog modal-dialog-centered modal-lg">
      <div class="modal-content">
        <div class="modal-header bg-success text-white">
          <h5 class="modal-title">
            <font-awesome-icon icon="fa-solid fa-check-circle" class="me-2" />
            {{ t('apiKeys.keyCreated') }}
          </h5>
          <button
            type="button"
            class="btn-close btn-close-white"
            aria-label="Close"
            @click="close"
          ></button>
        </div>
        <div class="modal-body">
          <!-- Warning -->
          <div class="alert alert-warning">
            <h5 class="alert-heading">
              <font-awesome-icon icon="fa-solid fa-exclamation-triangle" class="me-2" />
              {{ t('apiKeys.importantWarning') }}
            </h5>
            <p class="mb-0">{{ t('apiKeys.saveKeyWarning') }}</p>
          </div>
 
          <!-- API Key Info -->
          <div class="mb-3">
            <h6>{{ t('apiKeys.keyName') }}</h6>
            <p class="text-muted">{{ apiKey.name }}</p>
          </div>
 
          <!-- The Key Itself -->
          <div class="mb-3">
            <label class="form-label fw-bold">{{ t('apiKeys.yourApiKey') }}</label>
            <div class="input-group">
              <input
                ref="keyInput"
                :value="apiKeyValue"
                type="text"
                class="form-control font-monospace"
                readonly
              />
              <button class="btn btn-outline-secondary" type="button" @click="copyKey">
                <font-awesome-icon
                  :icon="copied ? 'fa-solid fa-check' : 'fa-solid fa-copy'"
                  :class="copied ? 'text-success' : ''"
                />
                {{ copied ? t('common.copied') : t('common.copy') }}
              </button>
            </div>
          </div>
 
          <!-- Usage Example -->
          <div class="mb-3">
            <h6>{{ t('apiKeys.usageExample') }}</h6>
            <pre class="bg-light p-3 rounded"><code>curl -H "X-API-Key: {{ apiKeyValue }}" \
  {{ apiBaseUrl }}/v1/entities/ENTITY_ID</code></pre>
          </div>
 
          <!-- Permissions -->
          <div class="mb-3">
            <h6>{{ t('apiKeys.permissions') }}</h6>
            <div class="d-flex flex-wrap gap-2">
              <code
                v-for="permission in apiKey.permissions"
                :key="permission"
                class="bg-light p-2 rounded"
              >
                {{ permission }}
              </code>
            </div>
          </div>
        </div>
        <div class="modal-footer">
          <button type="button" class="btn btn-primary" @click="close">
            <font-awesome-icon icon="fa-solid fa-check" class="me-2" />
            {{ t('common.done') }}
          </button>
        </div>
      </div>
    </div>
  </div>
</template>
 
<script setup lang="ts">
import { ref, computed } from 'vue'
import { useUILanguage } from '@/composables/useUILanguage'
import type { ApiKey } from '@/stores/apiKeys'
 
interface Props {
  isOpen: boolean
  apiKey: ApiKey | null
  apiKeyValue: string
}
 
defineProps<Props>()
 
const emit = defineEmits<{
  close: []
}>()
 
const { t } = useUILanguage()
 
const keyInput = ref<HTMLInputElement | null>(null)
const copied = ref(false)
 
// Get API base URL from environment
const apiBaseUrl = computed(() => {
  return import.meta.env.VITE_API_URL || 'https://api.flows.browsway.com'
})
 
function copyKey() {
  Eif (keyInput.value) {
    keyInput.value.select()
    document.execCommand('copy')
    copied.value = true
    setTimeout(() => {
      copied.value = false
    }, 2000)
  }
}
 
function close() {
  emit('close')
}
 
// Expose internal methods for testing
defineExpose({
  copyKey,
  copied
})
</script>