import React from 'react';
import PropTypes from 'prop-types';
import { allSupportedPostcodeExamples } from '../helpers/supportedPostcodeExamples';
import { getCountries } from '../utils/countries';

export function Debug({
	isTest = false,
	showHelpers = false,
	links = {},
	countries = [],
}) {
	// Strings are used rather than JSX as this component is injected into HTML
	// along with onclick handlers, styles and javascript. JSX will escape and
	// modify the HTML which we do not want. Once our applications are on JSX
	// entirely this component should be rethought.
	const testEnvironment = `
		<span class="ncf__debug-environment">
			<a class="ncf__button ncf__button--debug o3-button o3-button--secondary ncf__debug-button--test"   data-o3-theme="inverse"onclick="setTestEnvironment('off');"><strong>TEST</strong> relax you are using the test API</a>
		</span>
	`;
	const productionEnvironment = `
		<span class="ncf__debug-environment">
			<a class="ncf__button ncf__button--debug o3-button o3-button--secondary ncf__debug-button--production" data-o3-theme="inverse" onclick="setTestEnvironment('on');"><strong>PRODUCTION</strong> careful you are using the production API</a>
		</span>
	`;
	const testCards = `
		<button id="ncf-copy-visa-checkout-card" class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="copyToClipboard('checkoutVisa');" title="Copy Checkout Visa test card number to clipboard">EU Visa (cvv:100)</button>
		<button id="ncf-copy-visa-checkout-3ds" class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="copyToClipboard('checkout3dsChallenge');" title="Copy Checkout challenge code -Checkout1!- to clipboard">EU 3ds challenge</button>
		<button id="ncf-copy-visa-chase-card" class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="copyToClipboard('chaseVisa');" title="Copy Chase card number to clipboard">US Visa (exp:1230,cvv:111)</button>
		<button id="ncf-link-checkout-cards" class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="window.open('https://www.checkout.com/docs/testing/test-card-numbers#Credit_cards', '_blank');" title="Checkout test cards documentation">Doc:Checkout</button>
	`;
	const linksString = Object.keys(links).map(
		(link) =>
			`<a key=${link} class="ncf__button o3-button o3-button--secondary" data-o3-theme="inverse" href="${links[link]}">${link}</a>`
	);

	// Builds a Country dropdown component to allow the user to select a country and reload the page with the selected country
	// This is useful for testing the form with different countries without having to change the URL manually
	// The dropdown is built using the getCountries function which groups countries into frequently used and alphabetical
	const filteredCountries = getCountries({ filter: countries });

	const createOption = (country) =>
		`<option key="${country.code}" value="${country.code}">${country.name}</option>`;

	const createOptGroup = (countryGroup) =>
		`<optgroup key="${countryGroup.label}" label="${countryGroup.label}">
			${countryGroup.countries.reduce(
				(options, country) => `${options} ${createOption(country)}`
			)}
		</optgroup>`;

	const optionsToRender = filteredCountries.reduce(
		(options, country) =>
			`${options} ${
				country.label ? createOptGroup(country) : createOption(country)
			}`,
		''
	);
	const countriesDropDown = `
		<select class="ncf__button ncf__button--debug o3-button o3-button--secondary ncf__button--max-width" data-o3-theme="inverse" id="ncf-country" onchange="reloadWithSelectedCountry();">
			<option value="">Change country</option>
			<hr />
			${optionsToRender}
		</select>
	`;

	const helpers = `
		<span class="ncf__debug-helpers o3-type-body-base">
			<button class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="logout();" title="Logout and refresh">Logout</button>
			<button class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="fillForm();" title="Fill form with debug data">Fill</button>
			<button class="ncf__button ncf__button--debug o3-button o3-button--secondary" data-o3-theme="inverse" onclick="fillForm(); submitForm();" title="Fill form with debug data and submit">Fill &amp; Submit</button>
			${countriesDropDown}
			${isTest ? testCards : ''}
			${links.length ? linksString : ''}
		</span>
	`;
	const html = {
		__html: `${isTest ? testEnvironment : productionEnvironment}${
			showHelpers ? helpers : ''
		}`,
	};
	const javascript = {
		__html: `
	var FORM_SELECTOR = 'form.ncf';
	var INPUT_SELECTOR = FORM_SELECTOR + ' input:not([type="checkbox"]):not([type="radio"])';
	var SELECT_SELECTOR = FORM_SELECTOR + ' select';
	var CHECKBOX_SELECTOR = FORM_SELECTOR + ' input[type="checkbox"]';
	var RADIO_SELECTOR = FORM_SELECTOR + ' input[type="radio"]';
	// This env var gets set in production. We use this when creating email addresses in case any
	// get into production so Membership know who to come to about deleting them.
	var SYSTEM_CODE = document.documentElement.getAttribute('data-next-app') || 'n-conversion-forms';
	var COUNTRY_CODE = window.FT && window.FT.country || 'GBR';

	var postcodeByCountry = ${JSON.stringify(allSupportedPostcodeExamples)};

	var debugData = {
		billingCity: 'London',
		billingCountry: COUNTRY_CODE,
		billingPostcode: postcodeByCountry[COUNTRY_CODE],
		country: COUNTRY_CODE,
		deliveryAddressLine1: 'delivery test1',
		deliveryAddressLine2: 'delivery test2',
		deliveryAddressLine3: 'APT 2C',
		deliveryCity: 'delivery city',
		deliveryCounty: 'delivery county',
		deliveryPostcode: postcodeByCountry[COUNTRY_CODE],
		email: SYSTEM_CODE + '-' + Date.now() + '@ftqa.org',
		firstName: 'Test',
		industry: 'DEF',
		lastName: 'Test',
		jobTitle: 'CEO',
		organisation: 'ft-org',
		password: 'testpassword123',
		position: 'AS',
		postCode: postcodeByCountry[COUNTRY_CODE],
		primaryTelephone: '0987654321',
		responsibility: 'ADL',
		ukVisaWorldpay: '4111111111111111',
		usAmex: '378282246310005',
		usVisaWorldpay: '4112344112344113',
		checkoutVisa: '4242424242424242',
		checkout3dsChallenge: 'Checkout1!',
		chaseVisa: '4011361100000010',
		verificationEmail: SYSTEM_CODE + '-' + Date.now() + '@ftqa.org',
		yearOfBirth: 1999
	};

	function logout () {
		const options = {
			mode: 'no-cors',
			credentials: 'include'
		};
		fetch('https://www.ft.com/logout', options).then(function () {
			window.location.reload();
		});
	}

	function fillForm () {
		var changeEvent = document.createEvent('HTMLEvents');
		changeEvent.initEvent('change', false, true);

		var inputs = document.querySelectorAll(INPUT_SELECTOR + ', ' + SELECT_SELECTOR);
		inputs.forEach(function (input) {
			if (!/hidden/i.test(input.type) && input.disabled === false) {
				var value = debugData[input.name];
				input.value = value;
				input.dispatchEvent(changeEvent);
			}
		});
		var checkboxes = document.querySelectorAll(CHECKBOX_SELECTOR + ', ' + RADIO_SELECTOR);
		checkboxes.forEach(function (checkbox) {
			checkbox.checked = true;
			checkbox.dispatchEvent(changeEvent);
		});
	}

	function submitForm () {
		document.querySelector(FORM_SELECTOR).submit();
	}

	function copyToClipboard (name) {
		var string = debugData[name];
		var textarea = document.createElement('textarea');
		textarea.value = string;
		document.body.appendChild(textarea);
		textarea.select();
		document.execCommand('copy');
		document.body.removeChild(textarea);
	}

	function setTestEnvironment (state) {
		var flags = document.cookie.match('(^|[^;]+)\\\\s*next-flags\\\\s*=\\\\s*([^;]+)').pop();
		var flag = 'conversionSandbox%3A';
		flags = flags.replace(flag + 'on', '');
		flags = flags.replace(flag + 'off', '');
		document.cookie = 'next-flags=' + flags + '%2C' + flag + state + '; path=/; domain=.ft.com;';
		window.location.reload();
	}
	
	function reloadWithSelectedCountry () {
		var countryBox = document.getElementById("ncf-country");
		var selectedValue = countryBox.options[countryBox.selectedIndex].value;
		if (selectedValue) {
			const url = new URL(window.location);
			url.searchParams.set("countryCode", selectedValue);
			history.pushState({}, "", url);
			window.location.reload();
		}
	}
	`,
	};
	const style = {
		__html: `
	.ncf__debug-panel {
		position: absolute;
		background-color: #262a33;
		color: #ffffff;
		bottom: 0;
		left: 0;
		width: 100%;
		padding: 10px;
		position: fixed;
		z-index: 1000;
		opacity: 0.8;
	}
	.o3-button--secondary.o3-button.ncf__debug-button--test {
		background-color: #008040;
	}
	.o3-button--secondary.o3-button.ncf__debug-button--production {
		background-color: #990000;
	}
	.ncf__button--debug {
		padding: 0px 5px;
	}
	`,
	};

	return (
		(isTest || showHelpers) && (
			<React.Fragment>
				{/* Debug Panel for working with Conversion Forms */}
				{/* Style and scripts are inline to reduce the impact on production files */}
				<div className="ncf__debug-panel" dangerouslySetInnerHTML={html}></div>
				<script dangerouslySetInnerHTML={javascript}></script>
				<style dangerouslySetInnerHTML={style}></style>
			</React.Fragment>
		)
	);
}

Debug.propTypes = {
	isTest: PropTypes.bool,
	showHelpers: PropTypes.bool,
	links: PropTypes.object,
	countries: PropTypes.array,
};
