import React, { useEffect, useMemo, useState } from 'react';
import { Alert, Badge, Button, Divider, Group, Paper, PasswordInput, Select, Stack, Switch, Text, TextInput } from '@mantine/core';
import { IconAlertTriangle, IconCheck, IconExternalLink, IconPlugConnected, IconX } from '@tabler/icons-react';
import { __, sprintf } from '@wordpress/i18n';

const apiFetch = window.wp.apiFetch;
const emptySettings = {
	testMode: true,
	merchantAccount: '',
	apiKey: '',
	clientKey: '',
	liveUrlPrefix: '',
	captureMode: 'automatic',
	debugLogging: false,
};


function normalizeSettings(data, testMode = Boolean(data?.testMode)) {
	const profile = data?.environments?.[ testMode ? 'test' : 'live' ] || data || {};
	return {
		...emptySettings,
		testMode,
		merchantAccount: profile.merchantAccount || '',
		apiKey: '',
		clientKey: profile.clientKey || '',
		liveUrlPrefix: profile.liveUrlPrefix || '',
		captureMode: data?.captureMode || 'automatic',
		debugLogging: Boolean(data?.debugLogging),
	};
}

function comparable(settings) {
	return JSON.stringify({ ...settings, apiKey: '' });
}

export default function ConfigTab({ settingsData, loading, onSettingsChanged }) {
	const [settings, setSettings] = useState(emptySettings);
	const [initialSettings, setInitialSettings] = useState(comparable(emptySettings));
	const [saving, setSaving] = useState(false);
	const [verifying, setVerifying] = useState(false);
	const [success, setSuccess] = useState(null);
	const [error, setError] = useState(null);
	const [connectionResult, setConnectionResult] = useState(null);

	useEffect(() => {
		if (!settingsData) {
			return;
		}
		const normalized = normalizeSettings(settingsData);
		setSettings(normalized);
		setInitialSettings(comparable(normalized));
	}, [settingsData]);

	const errors = useMemo(() => {
		const next = {};
		const merchant = settings.merchantAccount.trim();
		if (!merchant) {
			next.merchantAccount = __('Merchant account is required.', 'digital-apps-payments-for-adyen');
		} else if (merchant.includes('@') || merchant.toLowerCase().startsWith('ws_')) {
			next.merchantAccount = __('Use the merchant account, for example DigitalAppsECOM, not the ws_ API credential username.', 'digital-apps-payments-for-adyen');
		} else if (!/^[A-Za-z0-9][A-Za-z0-9._-]{1,127}$/.test(merchant)) {
			next.merchantAccount = __('Enter a valid merchant account.', 'digital-apps-payments-for-adyen');
		}

		const selectedProfile = settingsData?.environments?.[ settings.testMode ? 'test' : 'live' ];
		if (!selectedProfile?.apiKeyConfigured && !settings.apiKey.trim()) {
			next.apiKey = __('API key is required.', 'digital-apps-payments-for-adyen');
		}

		const requiredPrefix = settings.testMode ? 'test_' : 'live_';
		if (!settings.clientKey.trim().startsWith(requiredPrefix) || settings.clientKey.trim().length <= requiredPrefix.length) {
			next.clientKey = sprintf(
				/* translators: %s: Required Adyen client key prefix. */
				__('Client key must begin with %s for this environment.', 'digital-apps-payments-for-adyen'),
				requiredPrefix
			);
		}
		if (!settings.testMode && !/^[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$/.test(settings.liveUrlPrefix.trim())) {
			next.liveUrlPrefix = __('Enter the live URL prefix from Adyen Customer Area, without a protocol or domain.', 'digital-apps-payments-for-adyen');
		}
		return next;
	}, [settings, settingsData]);

	const dirty = comparable(settings) !== initialSettings || settings.apiKey.trim() !== '';
	const valid = Object.keys(errors).length === 0;
	const gatewayEnabled = settingsData?.readiness?.environments?.test?.items?.gateway === true;

	const update = (key, value) => {
		setSettings((current) => ({ ...current, [key]: value }));
		setSuccess(null);
		setConnectionResult(null);
	};

	const changeEnvironment = (testMode) => {
		const profile = normalizeSettings(settingsData, testMode);
		setSettings((current) => ({
			...current,
			testMode,
			merchantAccount: profile.merchantAccount,
			apiKey: '',
			clientKey: profile.clientKey,
			liveUrlPrefix: profile.liveUrlPrefix,
		}));
		setSuccess(null);
		setConnectionResult(null);
	};

	const save = (event) => {
		event.preventDefault();
		if (!valid) {
			setError(__('Correct the highlighted fields before saving.', 'digital-apps-payments-for-adyen'));
			return;
		}

		setSaving(true);
		setError(null);
		setSuccess(null);
		apiFetch({
			path: '/digitalapps-payments-for-adyen/v1/settings',
			method: 'POST',
			headers: { 'X-WP-Nonce': DigitalAppsPaymentsForAdyenSettings.nonce },
			data: settings,
		})
			.then((result) => {
				if (!result.success) {
					throw new Error(result.message || __('Settings could not be saved.', 'digital-apps-payments-for-adyen'));
				}
				onSettingsChanged(result.settings);
				setSuccess(__('Your Adyen settings have been saved.', 'digital-apps-payments-for-adyen'));
			})
			.catch((requestError) => setError(requestError.message || __('Settings could not be saved.', 'digital-apps-payments-for-adyen')))
			.finally(() => setSaving(false));
	};

	const verifyConnection = () => {
		setVerifying(true);
		setError(null);
		setConnectionResult(null);
		apiFetch({
			path: '/digitalapps-payments-for-adyen/v1/connection-test',
			method: 'POST',
			headers: { 'X-WP-Nonce': DigitalAppsPaymentsForAdyenSettings.nonce },
		})
			.then(setConnectionResult)
			.catch((requestError) => setError(requestError.message || __('The connection could not be verified.', 'digital-apps-payments-for-adyen')))
			.finally(() => setVerifying(false));
	};

	return (
		<Stack gap="md">
			{success && <Alert icon={<IconCheck size={16} />} title={__('Settings saved', 'digital-apps-payments-for-adyen')} color="green">{success}</Alert>}
			{error && <Alert icon={<IconX size={16} />} title={__('Check your settings', 'digital-apps-payments-for-adyen')} color="red">{error}</Alert>}
			{connectionResult && (
				<Alert
					icon={connectionResult.success ? <IconCheck size={16} /> : <IconX size={16} />}
					title={connectionResult.success ? __('Connection verified', 'digital-apps-payments-for-adyen') : __('Connection failed', 'digital-apps-payments-for-adyen')}
					color={connectionResult.success ? (connectionResult.cardEnabled ? 'green' : 'orange') : 'red'}
				>
					{connectionResult.message}
				</Alert>
			)}
			{settingsData && (
				<Alert
					icon={gatewayEnabled ? <IconCheck size={18} /> : <IconAlertTriangle size={18} />}
					title={gatewayEnabled
						? __('Adyen Card is active in WooCommerce', 'digital-apps-payments-for-adyen')
						: __('Activate Adyen Card in WooCommerce', 'digital-apps-payments-for-adyen')}
					color={gatewayEnabled ? 'green' : 'orange'}
				>
					<Stack gap="sm" align="flex-start">
						<Text size="sm">
							{gatewayEnabled
								? __('Customers can use Adyen Card at checkout. Manage its activation, and any additional Adyen payment methods, under WooCommerce > Settings > Payments.', 'digital-apps-payments-for-adyen')
								: __('Saving your Adyen configuration does not activate it at checkout. Open WooCommerce Payments and enable Adyen Card, plus any additional Adyen payment methods you want to offer.', 'digital-apps-payments-for-adyen')}
						</Text>
						<Button
							component="a"
							href={DigitalAppsPaymentsForAdyenSettings.paymentsUrl}
							target="_blank"
							rel="noreferrer"
							aria-label={__('Open WooCommerce Payments in a new tab', 'digital-apps-payments-for-adyen')}
							variant={gatewayEnabled ? 'light' : 'filled'}
							color={gatewayEnabled ? 'green' : 'orange'}
							leftSection={<IconExternalLink size={16} />}
						>
							{__('Open WooCommerce Payments', 'digital-apps-payments-for-adyen')}
						</Button>
					</Stack>
				</Alert>
			)}

			<Paper component="form" onSubmit={save} p="md" withBorder noValidate>
				<Stack gap="md">
					<Group justify="space-between">
						<Text size="lg" fw={500}>{__('Adyen API configuration', 'digital-apps-payments-for-adyen')}</Text>
						<Badge color={settings.testMode ? 'yellow' : 'blue'} variant="light">
							{settings.testMode ? __('Test environment', 'digital-apps-payments-for-adyen') : __('Live environment', 'digital-apps-payments-for-adyen')}
						</Badge>
					</Group>

					<Switch
						label={__('Test mode', 'digital-apps-payments-for-adyen')}
						description={__('Use Adyen test endpoints and test credentials.', 'digital-apps-payments-for-adyen')}
						checked={settings.testMode}
						onChange={(event) => changeEnvironment(event.currentTarget.checked)}
						disabled={loading || saving}
					/>

					<Divider label={__('API credentials', 'digital-apps-payments-for-adyen')} labelPosition="center" />
					<TextInput
						label={__('Merchant account', 'digital-apps-payments-for-adyen')}
						description={__('This is the merchant account shown under Adyen Payments, not the API credential username.', 'digital-apps-payments-for-adyen')}
						placeholder={__('For example, DigitalAppsECOM', 'digital-apps-payments-for-adyen')}
						value={settings.merchantAccount}
						onChange={(event) => update('merchantAccount', event.currentTarget.value)}
						error={settings.merchantAccount !== '' ? errors.merchantAccount : null}
						disabled={loading || saving}
						required
					/>
					<PasswordInput
						label={__('API key', 'digital-apps-payments-for-adyen')}
						placeholder={settingsData?.environments?.[ settings.testMode ? 'test' : 'live' ]?.apiKeyConfigured ? __('API key configured - leave blank to keep it', 'digital-apps-payments-for-adyen') : __('Enter API key', 'digital-apps-payments-for-adyen')}
						value={settings.apiKey}
						onChange={(event) => update('apiKey', event.currentTarget.value)}
						error={errors.apiKey}
						disabled={loading || saving}
						required={!settingsData?.environments?.[ settings.testMode ? 'test' : 'live' ]?.apiKeyConfigured}
						visibilityToggleButtonProps={{ 'aria-label': __('Toggle API key visibility', 'digital-apps-payments-for-adyen') }}
					/>
					<TextInput
						label={__('Client key', 'digital-apps-payments-for-adyen')}
						description={__('The client-side key used by the Adyen checkout component.', 'digital-apps-payments-for-adyen')}
						placeholder={settings.testMode ? 'test_…' : 'live_…'}
						value={settings.clientKey}
						onChange={(event) => update('clientKey', event.currentTarget.value)}
						error={settings.clientKey !== '' ? errors.clientKey : null}
						disabled={loading || saving}
						required
					/>
					{!settings.testMode && (
						<TextInput
							label={__('Live URL prefix', 'digital-apps-payments-for-adyen')}
							description={__('Enter only the prefix assigned under API URLs in Adyen Customer Area.', 'digital-apps-payments-for-adyen')}
							placeholder="1797a841fbb37ca7-digitalapps"
							value={settings.liveUrlPrefix}
							onChange={(event) => update('liveUrlPrefix', event.currentTarget.value.toLowerCase())}
							error={settings.liveUrlPrefix !== '' ? errors.liveUrlPrefix : null}
							disabled={loading || saving}
							required
						/>
					)}

					<Divider label={__('Payment settings', 'digital-apps-payments-for-adyen')} labelPosition="center" />
					<Select
						label={__('Payment capture mode', 'digital-apps-payments-for-adyen')}
						description={__('Automatic capture processes payments immediately. Manual capture authorizes first and captures later.', 'digital-apps-payments-for-adyen')}
						data={[
							{ value: 'automatic', label: __('Automatic capture', 'digital-apps-payments-for-adyen') },
							{ value: 'manual', label: __('Manual capture', 'digital-apps-payments-for-adyen') },
						]}
						value={settings.captureMode}
						onChange={(value) => update('captureMode', value)}
						disabled={loading || saving}
					/>

					<Divider label={__('Diagnostics', 'digital-apps-payments-for-adyen')} labelPosition="center" />
					<Switch
						label={__('Verbose debug logging', 'digital-apps-payments-for-adyen')}
						description={__('Record debug-level events in WooCommerce logs. Warnings and errors are always recorded.', 'digital-apps-payments-for-adyen')}
						checked={settings.debugLogging}
						onChange={(event) => update('debugLogging', event.currentTarget.checked)}
						disabled={loading || saving}
					/>

					<Group justify="space-between" mt="md">
						<Button
							variant="light"
							leftSection={<IconPlugConnected size={16} />}
							onClick={verifyConnection}
							loading={verifying}
							disabled={loading || saving || dirty || !valid}
						>
							{__('Verify connection', 'digital-apps-payments-for-adyen')}
						</Button>
						<Button type="submit" loading={saving} disabled={loading || !dirty || !valid}>
							{__('Save settings', 'digital-apps-payments-for-adyen')}
						</Button>
					</Group>
					{dirty && (
						<Text size="xs" c="dimmed" ta="right">
							{__('Save changes before verifying the connection.', 'digital-apps-payments-for-adyen')}
						</Text>
					)}
				</Stack>
			</Paper>
		</Stack>
	);
}
