UNPKG

@tywalk/pcf-helper

Version:

Command line helper for building and publishing PCF controls to Dataverse.

127 lines (126 loc) 6.16 kB
"use strict"; var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.defaultPrompt = void 0; exports.buildProfileFromOptions = buildProfileFromOptions; exports.runProfileInit = runProfileInit; const readline_1 = __importDefault(require("readline")); const color_logger_1 = __importDefault(require("@tywalk/color-logger")); const configUtil_1 = require("./configUtil"); /** Default prompt implementation using Node's built-in readline. */ const defaultPrompt = (question, currentValue) => new Promise((resolve) => { const rl = readline_1.default.createInterface({ input: process.stdin, output: process.stdout, }); const displayDefault = currentValue ? ` [${currentValue}]` : ''; rl.question(`${question}${displayDefault}: `, (answer) => { rl.close(); const trimmed = answer.trim(); resolve(trimmed || currentValue || ''); }); }); exports.defaultPrompt = defaultPrompt; /** * Builds a Profile from the options, prompting for each field when interactive. * * Returns only the fields the user actually supplied — empty answers are not * written to disk, so a skipped prompt produces no key in the profile. */ function buildProfileFromOptions(options_1) { return __awaiter(this, arguments, void 0, function* (options, prompt = exports.defaultPrompt) { const interactive = !options.nonInteractive; const ask = (question, current) => __awaiter(this, void 0, void 0, function* () { if (!interactive) return current; const answer = yield prompt(question, current); return answer || undefined; }); const environment = yield ask('Dataverse environment name', options.environment); const publisherName = yield ask('Publisher display name', options.publisherName); const publisherPrefix = yield ask('Publisher prefix (2-8 chars, e.g. "tyw")', options.publisherPrefix); const profilePath = yield ask('Path to PCF solution folder (blank to skip)', options.path); const template = yield ask('Control template (field|dataset; blank to skip)', options.template); const framework = yield ask('Rendering framework (none|react; blank to skip)', options.framework); // Session fields are only prompted when the user passed at least one, // to keep the common path short. const anySessionFlag = options.sessionUrl || options.sessionScript || options.sessionBundle; let session; if (anySessionFlag && interactive) { const url = yield ask('Session: remote environment URL', options.sessionUrl); const script = yield ask('Session: remote script to intercept', options.sessionScript); const bundle = yield ask('Session: local bundle path', options.sessionBundle); session = {}; if (url) session.remoteEnvironmentUrl = url; if (script) session.remoteScriptToIntercept = script; if (bundle) session.localBundlePath = bundle; if (Object.keys(session).length === 0) session = undefined; } else if (anySessionFlag) { // Non-interactive + some session flags passed — just use what was given. session = {}; if (options.sessionUrl) session.remoteEnvironmentUrl = options.sessionUrl; if (options.sessionScript) session.remoteScriptToIntercept = options.sessionScript; if (options.sessionBundle) session.localBundlePath = options.sessionBundle; if (Object.keys(session).length === 0) session = undefined; } const profile = {}; if (environment) profile.environment = environment; if (profilePath) profile.path = profilePath; if (publisherName) profile.publisherName = publisherName; if (publisherPrefix) profile.publisherPrefix = publisherPrefix; if (template) profile.template = template; if (framework) profile.framework = framework; if (session) profile.session = session; return profile; }); } /** * Orchestrates the full `profile init` flow: collect fields (prompting when * interactive), then write the profile to the target config file. */ function runProfileInit(options_1) { return __awaiter(this, arguments, void 0, function* (options, prompt = exports.defaultPrompt) { if (!options.name || !options.name.trim()) { throw new Error('Profile name is required. Usage: profile init <name>'); } const profile = yield buildProfileFromOptions(options, prompt); const result = (0, configUtil_1.writeProfile)(options.name, profile, { global: options.global, setDefault: options.setDefault, force: options.force, }); const verb = result.replacedProfile ? 'Updated' : 'Created'; color_logger_1.default.log(`${verb} profile "${options.name}" in ${result.filePath}`); if (options.setDefault) { color_logger_1.default.log(`Set "${options.name}" as the default profile.`); } return result; }); }