text: "use strict";
  var __assign = (this && this.__assign) || function () {
      __assign = Object.assign || function(t) {
          for (var s, i = 1, n = arguments.length; i < n; i++) {
              s = arguments[i];
              for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
                  t[p] = s[p];
          }
          return t;
      };
      return __assign.apply(this, arguments);
  };
  var __importDefault = (this && this.__importDefault) || function (mod) {
      return (mod && mod.__esModule) ? mod : { "default": mod };
  };
  Object.defineProperty(exports, "__esModule", { value: true });
  exports.setup = exports.userConfigPath = void 0;
  var chalk_1 = __importDefault(require("chalk"));
  var fs_1 = __importDefault(require("fs"));
  var glob_1 = __importDefault(require("glob"));
  var path_1 = __importDefault(require("path"));
  var readline_sync_1 = __importDefault(require("readline-sync"));
  var url_join_1 = __importDefault(require("url-join"));
  var find_app_name_1 = require("./find-app-name");
  var secret_patch_1 = require("./secret-patch");
  var userConfigFileName = 'scjssconfig.json';
  exports.userConfigPath = path_1.default.resolve(process.cwd(), userConfigFileName);
  /**
   * @param {string | undefined} initialData
   * @param {boolean} allowInteraction
   * @param {string} paramName
   * @param {string} prompt
   * @param {string} examplePrompt
   * @param {RegExp} [validation]
   * @param {string} [validationMessage]
   * @param {boolean} skipValidationIfNonInteractive
   */
  function getInteractiveData(initialData, allowInteraction, paramName, prompt, examplePrompt, validation, validationMessage, skipValidationIfNonInteractive) {
      if (skipValidationIfNonInteractive === void 0) { skipValidationIfNonInteractive = false; }
      if (!allowInteraction && !initialData && !skipValidationIfNonInteractive) {
          throw new Error("Non interactive mode specified and " + paramName + " not provided.");
      }
      if (allowInteraction) {
          var finalPrompt = initialData
              ? prompt + " [" + initialData + "]: "
              : prompt + " " + examplePrompt + ": ";
          return readline_sync_1.default.question(finalPrompt, {
              defaultInput: initialData,
              limit: validation,
              limitMessage: validationMessage,
          });
      }
      var result = initialData;
      if (validation && validationMessage && !validation.test(result)) {
          if (skipValidationIfNonInteractive) {
              console.error(chalk_1.default.yellow(validationMessage));
          }
          else {
              throw new Error(validationMessage);
          }
      }
      return result;
  }
  /**
   * @param {boolean} interactive
   * @param {string} outputFile
   * @param {JssConfiguration} [initialData]
   * @param {string} [configName]
   */
  function setup(interactive, outputFile, initialData, configName) {
      if (configName === void 0) { configName = 'sitecore'; }
      var getValidation = function (regexp) { return ((initialData === null || initialData === void 0 ? void 0 : initialData.skipValidation) ? undefined : regexp); };
      var config = {
          sitecore: {
              instancePath: '',
          },
      };
      if (!outputFile) {
          outputFile = exports.userConfigPath;
      }
      // read in any existing config file so that we can keep its values
      if (outputFile && fs_1.default.existsSync(outputFile)) {
          try {
              var existingFile = fs_1.default.readFileSync(outputFile, 'utf8');
              var existingJson = JSON.parse(existingFile);
              console.log(chalk_1.default.green("Found existing " + outputFile + ". The existing config will become defaults in this setup session."));
              config = existingJson;
          }
          catch (e) {
              console.warn(chalk_1.default.yellow("Found existing " + outputFile + " but error reading it. Existing values will be ignored."), e);
          }
      }
      var existingConfigObject = config[configName] || {};
      // merge existing values with any CLI arguments (which should override any preexisting values)
      if (initialData) {
          config[configName] = __assign(__assign({}, config[configName]), { instancePath: initialData.instancePath || existingConfigObject.instancePath, apiKey: initialData.apiKey || existingConfigObject.apiKey, deploySecret: initialData.deploySecret || existingConfigObject.deploySecret, deployUrl: initialData.deployUrl || existingConfigObject.deployUrl, layoutServiceHost: initialData.layoutServiceHost || existingConfigObject.layoutServiceHost });
      }
      var configObject = config[configName];
      // INSTANCE PATH
      var getInstancePath = function (initialPath) {
          configObject.instancePath = getInteractiveData(initialPath, interactive, 'instancePath', 'Path to the Sitecore folder', '(e.g. c:\\inetpub\\wwwroot\\my.siteco.re)', getValidation(/[A-z]/), 'Invalid input.', true);
          if (configObject.instancePath) {
              if (!fs_1.default.existsSync(configObject.instancePath)) {
                  console.log(chalk_1.default.red(configObject.instancePath + " did not exist!"));
                  if (interactive) {
                      getInstancePath();
                  }
                  else {
                      process.exit(1);
                  }
              }
          }
          else {
              console.warn(chalk_1.default.yellow('Non-interactive mode specified and no instancePath given. File/config deployment will not be available.'));
          }
      };
      // if you are setting up for the first time, we don't need an instance path for a remote Sitecore instance
      if (interactive) {
          if (!configObject.instancePath &&
              readline_sync_1.default.keyInYN('Is your Sitecore instance on this machine or accessible via network share?')) {
              getInstancePath(configObject.instancePath);
          }
          else if (configObject.instancePath) {
              getInstancePath(configObject.instancePath);
          }
      }
      // DEPLOY URL/LS HOST
      var defaultDeployUrl = '/sitecore/api/jss/import';
      if (!interactive && !configObject.layoutServiceHost) {
          throw 'Non interactive mode specified and layoutServiceHost not provided.';
      }
      if (interactive) {
          configObject.layoutServiceHost = getInteractiveData(configObject.layoutServiceHost, interactive, 'host', 'Sitecore hostname', '(e.g. http://myapp.local.siteco.re; see /sitecore/config; ensure added to hosts)', getValidation(/^https?:\/\/(.*)/), 'Invalid input. Must start with http(s)');
      }
      if (interactive) {
          configObject.deployUrl = getInteractiveData(configObject.deployUrl || url_join_1.default(configObject.layoutServiceHost, defaultDeployUrl), interactive, 'host', 'Sitecore import service URL', '(usually same as hostname)', getValidation(/^https?:\/\/(.*)/), 'Invalid input. Must start with http(s)');
      }
      // API KEY
      configObject.apiKey = getInteractiveData(configObject.apiKey, interactive, 'apiKey', 'Sitecore API Key', '(ID of API key item)', getValidation(/^{?[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}}?$/i), 'Invalid API Key. Should be a GUID / Sitecore Item ID.');
      // DEPLOY SECRET
      configObject.deploySecret = getInteractiveData(configObject.deploySecret, interactive, 'deploySecret', 'Please enter your deployment secret', '(32+ random chars; or press enter to generate one)', getValidation(/^(.{32,}|)$/), 'Invalid secret. Should be blank or at least 32 random characters.', true);
      if (!configObject.deploySecret && interactive) {
          configObject.deploySecret =
              Math.random()
                  .toString(36)
                  .substring(2, 15) +
                  Math.random()
                      .toString(36)
                      .substring(2, 15) +
                  Math.random()
                      .toString(36)
                      .substring(2, 15) +
                  Math.random()
                      .toString(36)
                      .substring(2, 15);
          console.log('Deployment secret has been generated. Ensure the JSS app config on the Sitecore end has the same secret set.');
      }
      if (configObject.deploySecret) {
          var appConfig = glob_1.default
              .sync('./sitecore/config/*.config')
              .find(function (file) { return !file.match(/deploysecret/); });
          if (appConfig) {
              var appName = find_app_name_1.findAppNameInConfig(appConfig);
              if (appName) {
                  var patchFile = path_1.default.resolve("./sitecore/config/" + appName + ".deploysecret.config");
                  secret_patch_1.writeSecretPatchFile(patchFile, appName, configObject.deploySecret);
                  console.log("Deploy secret Sitecore config written to " + chalk_1.default.green(patchFile));
                  console.log('Ensure this configuration is deployed to Sitecore.');
              }
              else {
                  console.log(chalk_1.default.yellow("Unable to resolve JSS app name in " + appConfig));
                  console.log(chalk_1.default.yellow(
                  // eslint-disable-next-line prettier/prettier
                  'For deployment to succeed the app\'s \'deploySecret\' must be set in a Sitecore config patch similar to:'));
                  console.log(secret_patch_1.createSecretPatchContents('YOUR-JSS-APP-NAME-HERE', configObject.deploySecret));
                  console.log('');
              }
          }
          else {
              console.log(chalk_1.default.yellow('No JSS config patches were in ./sitecore/config to get the JSS app name from.'));
              console.log(chalk_1.default.yellow(
              // eslint-disable-next-line prettier/prettier
              'For deployment to succeed the app\'s \'deploySecret\' must be set in a Sitecore config patch similar to:'));
              console.log(secret_patch_1.createSecretPatchContents('YOUR-JSS-APP-NAME-HERE', configObject.deploySecret));
              console.log('');
          }
      }
      fs_1.default.writeFileSync(outputFile, JSON.stringify(config, null, 2));
      var hostName = 'undefined';
      if (configObject.layoutServiceHost) {
          hostName = configObject.layoutServiceHost.replace(/https?:\/\//, '');
      }
      console.log("JSS connection settings saved to " + chalk_1.default.green(outputFile));
      console.log();
      console.log(chalk_1.default.green('NEXT STEPS'));
      console.log("* Ensure the " + chalk_1.default.green('hostName') + " in /sitecore/config/*.config is configured as " + chalk_1.default.green(hostName) + ", and in hosts file if needed.");
      if (configObject.instancePath) {
          console.log("* Deploy your configuration (i.e. '" + chalk_1.default.green('jss deploy config') + "')");
          console.log("* Deploy your app (i.e. '" + chalk_1.default.green('jss deploy app -c -d') + "')");
      }
      else {
          console.log("* Deploy the app's items (i.e. " + chalk_1.default.green('jss deploy items -c -d') + ")");
          console.log("* Create a production build (i.e. " + chalk_1.default.green('jss build') + ")");
          console.log("* Copy the build artifacts to the Sitecore instance in the " + chalk_1.default.green('sitecoreDistPath') + " set in package.json.");
          console.warn(chalk_1.default.yellow('  > Note:') + " " + chalk_1.default.red('jss deploy config') + ", " + chalk_1.default.red('jss deploy files') + ", and " + chalk_1.default.red('jss deploy app') + " cannot be used with remote Sitecore.");
      }
      console.log("* Test your app in integrated mode by visiting " + chalk_1.default.green(configObject.layoutServiceHost));
  }
  exports.setup = setup;
  