var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
    function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
    var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
    var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
    var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
    var _, done = false;
    for (var i = decorators.length - 1; i >= 0; i--) {
        var context = {};
        for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
        for (var p in contextIn.access) context.access[p] = contextIn.access[p];
        context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
        var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
        if (kind === "accessor") {
            if (result === void 0) continue;
            if (result === null || typeof result !== "object") throw new TypeError("Object expected");
            if (_ = accept(result.get)) descriptor.get = _;
            if (_ = accept(result.set)) descriptor.set = _;
            if (_ = accept(result.init)) initializers.unshift(_);
        }
        else if (_ = accept(result)) {
            if (kind === "field") initializers.unshift(_);
            else descriptor[key] = _;
        }
    }
    if (target) Object.defineProperty(target, contextIn.name, descriptor);
    done = true;
};
var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
    var useValue = arguments.length > 2;
    for (var i = 0; i < initializers.length; i++) {
        value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
    }
    return useValue ? value : void 0;
};
import { DeesElement, html, customElement, css, state, cssManager, } from '@design.estate/dees-element';
import * as appstate from '../../appstate.js';
import * as interfaces from '../../../dist_ts_interfaces/index.js';
import { viewHostCss } from '../shared/css.js';
import './dns-provider-form.js';
let OpsViewProviders = (() => {
    let _classDecorators = [customElement('ops-view-providers')];
    let _classDescriptor;
    let _classExtraInitializers = [];
    let _classThis;
    let _classSuper = DeesElement;
    let _domainsState_decorators;
    let _domainsState_initializers = [];
    let _domainsState_extraInitializers = [];
    var OpsViewProviders = class extends _classSuper {
        static { _classThis = this; }
        static {
            const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
            _domainsState_decorators = [state()];
            __esDecorate(this, null, _domainsState_decorators, { kind: "accessor", name: "domainsState", static: false, private: false, access: { has: obj => "domainsState" in obj, get: obj => obj.domainsState, set: (obj, value) => { obj.domainsState = value; } }, metadata: _metadata }, _domainsState_initializers, _domainsState_extraInitializers);
            __esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
            OpsViewProviders = _classThis = _classDescriptor.value;
            if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
        }
        #domainsState_accessor_storage = __runInitializers(this, _domainsState_initializers, appstate.domainsStatePart.getState());
        get domainsState() { return this.#domainsState_accessor_storage; }
        set domainsState(value) { this.#domainsState_accessor_storage = value; }
        constructor() {
            super();
            __runInitializers(this, _domainsState_extraInitializers);
            const sub = appstate.domainsStatePart.select().subscribe((newState) => {
                this.domainsState = newState;
            });
            this.rxSubscriptions.push(sub);
        }
        async connectedCallback() {
            await super.connectedCallback();
            await appstate.domainsStatePart.dispatchAction(appstate.fetchDomainsAndProvidersAction, null);
        }
        static styles = [
            cssManager.defaultStyles,
            viewHostCss,
            css `
      .providersContainer {
        display: flex;
        flex-direction: column;
        gap: 24px;
      }

      .statusBadge {
        display: inline-flex;
        align-items: center;
        padding: 3px 10px;
        border-radius: 12px;
        font-size: 12px;
        font-weight: 600;
        text-transform: uppercase;
      }

      .statusBadge.ok {
        background: ${cssManager.bdTheme('#dcfce7', '#14532d')};
        color: ${cssManager.bdTheme('#166534', '#4ade80')};
      }

      .statusBadge.error {
        background: ${cssManager.bdTheme('#fef2f2', '#450a0a')};
        color: ${cssManager.bdTheme('#991b1b', '#f87171')};
      }

      .statusBadge.untested {
        background: ${cssManager.bdTheme('#f3f4f6', '#1f2937')};
        color: ${cssManager.bdTheme('#4b5563', '#9ca3af')};
      }

      .statusBadge.builtin {
        background: ${cssManager.bdTheme('#e0e7ff', '#1e1b4b')};
        color: ${cssManager.bdTheme('#3730a3', '#a5b4fc')};
      }
    `,
        ];
        render() {
            const providers = this.domainsState.providers;
            return html `
      <dees-heading level="3">DNS Providers</dees-heading>
      <div class="providersContainer">
        <dees-table
          .heading1=${'Providers'}
          .heading2=${'Built-in dcrouter + external DNS provider accounts'}
          .data=${providers}
          .showColumnFilters=${true}
          .displayFunction=${(p) => ({
                Name: p.name,
                Type: this.providerTypeLabel(p.type),
                Status: p.builtIn
                    ? html `<span class="statusBadge builtin">built-in</span>`
                    : this.renderStatusBadge(p.status),
                'Last Tested': p.builtIn
                    ? '—'
                    : p.lastTestedAt
                        ? new Date(p.lastTestedAt).toLocaleString()
                        : 'never',
                Error: p.builtIn ? '—' : p.lastError || '-',
            })}
          .dataActions=${[
                {
                    name: 'Add Provider',
                    iconName: 'lucide:plus',
                    type: ['header'],
                    actionFunc: async () => {
                        await this.showCreateDialog();
                    },
                },
                {
                    name: 'Refresh',
                    iconName: 'lucide:rotateCw',
                    type: ['header'],
                    actionFunc: async () => {
                        await appstate.domainsStatePart.dispatchAction(appstate.fetchDomainsAndProvidersAction, null);
                    },
                },
                {
                    name: 'Test Connection',
                    iconName: 'lucide:plug',
                    type: ['inRow', 'contextmenu'],
                    actionRelevancyCheckFunc: (p) => !p.builtIn,
                    actionFunc: async (actionData) => {
                        const provider = actionData.item;
                        await this.testProvider(provider);
                    },
                },
                {
                    name: 'Edit',
                    iconName: 'lucide:pencil',
                    type: ['inRow', 'contextmenu'],
                    actionRelevancyCheckFunc: (p) => !p.builtIn,
                    actionFunc: async (actionData) => {
                        const provider = actionData.item;
                        await this.showEditDialog(provider);
                    },
                },
                {
                    name: 'Delete',
                    iconName: 'lucide:trash2',
                    type: ['inRow', 'contextmenu'],
                    actionRelevancyCheckFunc: (p) => !p.builtIn,
                    actionFunc: async (actionData) => {
                        const provider = actionData.item;
                        await this.deleteProvider(provider);
                    },
                },
            ]}
        ></dees-table>
      </div>
    `;
        }
        renderStatusBadge(status) {
            return html `<span class="statusBadge ${status}">${status}</span>`;
        }
        providerTypeLabel(type) {
            return interfaces.data.getDnsProviderTypeDescriptor(type)?.displayName ?? type;
        }
        async showCreateDialog() {
            const { DeesModal, DeesToast } = await import('@design.estate/dees-catalog');
            const formEl = document.createElement('dns-provider-form');
            DeesModal.createAndShow({
                heading: 'Add DNS Provider',
                content: html `${formEl}`,
                menuOptions: [
                    { name: 'Cancel', action: async (modalArg) => modalArg.destroy() },
                    {
                        name: 'Create',
                        action: async (modalArg) => {
                            const data = await formEl.collectData();
                            if (!data)
                                return;
                            if (!data.name) {
                                DeesToast.show({ message: 'Name is required', type: 'warning', duration: 2500 });
                                return;
                            }
                            if (!data.credentialsTouched) {
                                DeesToast.show({
                                    message: 'Fill in the provider credentials',
                                    type: 'warning',
                                    duration: 2500,
                                });
                                return;
                            }
                            await appstate.domainsStatePart.dispatchAction(appstate.createDnsProviderAction, {
                                name: data.name,
                                type: data.type,
                                credentials: data.credentials,
                            });
                            modalArg.destroy();
                        },
                    },
                ],
            });
        }
        async showEditDialog(provider) {
            const { DeesModal } = await import('@design.estate/dees-catalog');
            const formEl = document.createElement('dns-provider-form');
            formEl.providerName = provider.name;
            formEl.selectedType = provider.type;
            formEl.lockType = true;
            formEl.credentialsHint =
                'Leave credential fields blank to keep the current values. Fill them to rotate.';
            DeesModal.createAndShow({
                heading: `Edit Provider: ${provider.name}`,
                content: html `${formEl}`,
                menuOptions: [
                    { name: 'Cancel', action: async (modalArg) => modalArg.destroy() },
                    {
                        name: 'Save',
                        action: async (modalArg) => {
                            const data = await formEl.collectData();
                            if (!data)
                                return;
                            await appstate.domainsStatePart.dispatchAction(appstate.updateDnsProviderAction, {
                                id: provider.id,
                                name: data.name || provider.name,
                                // Only send credentials if the user actually entered something —
                                // otherwise we keep the current secret untouched.
                                credentials: data.credentialsTouched ? data.credentials : undefined,
                            });
                            modalArg.destroy();
                        },
                    },
                ],
            });
        }
        async testProvider(provider) {
            const { DeesToast } = await import('@design.estate/dees-catalog');
            await appstate.domainsStatePart.dispatchAction(appstate.testDnsProviderAction, {
                id: provider.id,
            });
            const updated = appstate.domainsStatePart
                .getState()
                .providers.find((p) => p.id === provider.id);
            if (updated?.status === 'ok') {
                DeesToast.show({
                    message: `${provider.name}: connection OK`,
                    type: 'success',
                    duration: 3000,
                });
            }
            else {
                DeesToast.show({
                    message: `${provider.name}: ${updated?.lastError || 'connection failed'}`,
                    type: 'error',
                    duration: 4000,
                });
            }
        }
        async deleteProvider(provider) {
            const linkedDomains = this.domainsState.domains.filter((d) => d.providerId === provider.id);
            const { DeesModal } = await import('@design.estate/dees-catalog');
            const doDelete = async (force) => {
                await appstate.domainsStatePart.dispatchAction(appstate.deleteDnsProviderAction, {
                    id: provider.id,
                    force,
                });
            };
            if (linkedDomains.length > 0) {
                DeesModal.createAndShow({
                    heading: `Provider in use`,
                    content: html `
          <p>
            Provider <strong>${provider.name}</strong> is referenced by ${linkedDomains.length}
            domain(s). Deleting will also remove the imported domain(s) and their cached
            records (the records at ${provider.type} are NOT touched).
          </p>
        `,
                    menuOptions: [
                        { name: 'Cancel', action: async (modalArg) => modalArg.destroy() },
                        {
                            name: 'Force Delete',
                            action: async (modalArg) => {
                                await doDelete(true);
                                modalArg.destroy();
                            },
                        },
                    ],
                });
            }
            else {
                await doDelete(false);
            }
        }
        static {
            __runInitializers(_classThis, _classExtraInitializers);
        }
    };
    return OpsViewProviders = _classThis;
})();
export { OpsViewProviders };
//# sourceMappingURL=data:application/json;base64, 