"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.command = void 0; const clc = require("colorette"); const fs = require("fs"); const os = require("os"); const path = require("path"); const command_1 = require("../command"); const config_1 = require("../config"); const auth_1 = require("../auth"); const init_1 = require("../init"); const logger_1 = require("../logger"); const prompt_1 = require("../prompt"); const requireAuth_1 = require("../requireAuth"); const fsutils = require("../fsutils"); const utils = require("../utils"); const homeDir = os.homedir(); const TEMPLATE_ROOT = path.resolve(__dirname, "../../templates/"); const BANNER_TEXT = fs.readFileSync(path.join(TEMPLATE_ROOT, "banner.txt"), "utf8"); const GITIGNORE_TEMPLATE = fs.readFileSync(path.join(TEMPLATE_ROOT, "_gitignore"), "utf8"); function isOutside(from, to) { return !!/^\.\./.exec(path.relative(from, to)); } const choices = [ { value: "database", name: "Realtime Database: Configure a security rules file for Realtime Database and (optionally) provision default instance", checked: false, }, { value: "firestore", name: "Firestore: Configure security rules and indexes files for Firestore", checked: false, }, { value: "functions", name: "Functions: Configure a Cloud Functions directory and its files", checked: false, }, { value: "hosting", name: "Hosting: Configure files for Firebase Hosting and (optionally) set up GitHub Action deploys", checked: false, }, { value: "hosting:github", name: "Hosting: Set up GitHub Action deploys", checked: false, }, { value: "storage", name: "Storage: Configure a security rules file for Cloud Storage", checked: false, }, { value: "emulators", name: "Emulators: Set up local emulators for Firebase products", checked: false, }, { value: "remoteconfig", name: "Remote Config: Configure a template file for Remote Config", checked: false, }, ]; const featureNames = choices.map((choice) => choice.value); const DESCRIPTION = `Interactively configure the current directory as a Firebase project or initialize new features in an already configured Firebase project directory. This command will create or update 'firebase.json' and '.firebaserc' configuration files in the current directory. To initialize a specific Firebase feature, run 'firebase init [feature]'. Valid features are: ${[...featureNames] .sort() .map((n) => `\n - ${n}`) .join("")}`; exports.command = new command_1.Command("init [feature]") .description(DESCRIPTION) .before(requireAuth_1.requireAuth) .action((feature, options) => { if (feature && !featureNames.includes(feature)) { return utils.reject(clc.bold(feature) + " is not a supported feature; must be one of " + featureNames.join(", ") + "."); } const cwd = options.cwd || process.cwd(); const warnings = []; let warningText = ""; if (isOutside(homeDir, cwd)) { warnings.push("You are currently outside your home directory"); } if (cwd === homeDir) { warnings.push("You are initializing your home directory as a Firebase project directory"); } const existingConfig = config_1.Config.load(options, true); if (existingConfig) { warnings.push("You are initializing within an existing Firebase project directory"); } const config = existingConfig !== null ? existingConfig : new config_1.Config({}, { projectDir: cwd, cwd: cwd }); if (warnings.length) { warningText = "\nBefore we get started, keep in mind:\n\n " + clc.yellow(clc.bold("* ")) + warnings.join("\n " + clc.yellow(clc.bold("* "))) + "\n"; } logger_1.logger.info(clc.yellow(clc.bold(BANNER_TEXT)) + "\nYou're about to initialize a Firebase project in this directory:\n\n " + clc.bold(config.projectDir) + "\n" + warningText); const setup = { config: config.src, rcfile: config.readProjectFile(".firebaserc", { json: true, fallback: {}, }), }; let next; if (process.platform === "win32") { next = (0, prompt_1.promptOnce)({ type: "confirm", message: "Are you ready to proceed?", }); } else { next = Promise.resolve(true); } return next .then((proceed) => { if (!proceed) { return utils.reject("Aborted by user.", { exit: 1 }); } if (feature) { setup.featureArg = true; setup.features = [feature]; return undefined; } return (0, prompt_1.prompt)(setup, [ { type: "checkbox", name: "features", message: "Which Firebase features do you want to set up for this directory? " + "Press Space to select features, then Enter to confirm your choices.", choices: choices, }, ]); }) .then(() => { var _a; if (!setup.features || ((_a = setup.features) === null || _a === void 0 ? void 0 : _a.length) === 0) { return utils.reject("Must select at least one feature. Use " + clc.bold(clc.underline("SPACEBAR")) + " to select features, or specify a feature by running " + clc.bold("firebase init [feature_name]")); } setup.features.unshift("project"); const allAccounts = (0, auth_1.getAllAccounts)(); if (allAccounts.length > 1) { setup.features.unshift("account"); } if (setup.features.includes("hosting") && setup.features.includes("hosting:github")) { setup.features = setup.features.filter((f) => f !== "hosting:github"); } return (0, init_1.init)(setup, config, options); }) .then(() => { logger_1.logger.info(); utils.logBullet("Writing configuration info to " + clc.bold("firebase.json") + "..."); config.writeProjectFile("firebase.json", setup.config); utils.logBullet("Writing project information to " + clc.bold(".firebaserc") + "..."); config.writeProjectFile(".firebaserc", setup.rcfile); if (!fsutils.fileExistsSync(config.path(".gitignore"))) { utils.logBullet("Writing gitignore file to " + clc.bold(".gitignore") + "..."); config.writeProjectFile(".gitignore", GITIGNORE_TEMPLATE); } logger_1.logger.info(); utils.logSuccess("Firebase initialization complete!"); }); });