UNPKG

@twilio/plugin-microvisor

Version:

Interact with your Twilio Microvisor devices

133 lines (132 loc) 6.03 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.TwilioClientCommand = void 0; const tslib_1 = require("tslib"); const { TwilioClientCommand } = require('@twilio/cli-core').baseCommands; exports.TwilioClientCommand = TwilioClientCommand; const device_log_client_1 = tslib_1.__importDefault(require("../../../lib/logs/device-log-client")); const core_1 = require("@oclif/core"); const node_url_1 = require("node:url"); const node_process_1 = tslib_1.__importDefault(require("node:process")); const { TwilioCliError } = require('@twilio/cli-core').services.error; class MicrovisorLogsStream extends TwilioClientCommand { async run() { await super.run(); if (!/^UV[\da-z]{32}$/.test(this.args.deviceSid)) { throw new TwilioCliError('DEVICESID must be a sid starting with UV'); } const apiBaseUrlString = this.flags['microvisor-api-url']; // defaults to 'https://microvisor.twilio.com/' const logEnableUrl = new node_url_1.URL(`v1/Devices/${this.args.deviceSid}`, apiBaseUrlString); const tokenUrl = new node_url_1.URL(`v1/Devices/${this.args.deviceSid}/LoggingToken`, apiBaseUrlString); const baseWsUrlString = this.flags['microvisor-debug-url']; let baseWsUrl = new node_url_1.URL(baseWsUrlString); // Check configured tunnel domain ends in twilio.com. If it does, perform the same mangling as the http // client. If not, leave things alone (this is probably a Twilion trying to hit a test endpoint) if (/^[^:]+:\/\/[^/]+\.twilio\.com/.test(baseWsUrlString)) { baseWsUrl.hostname = this.twilioClient.getHostname(baseWsUrl.hostname, this.twilioClient.edge, this.twilioClient.region); } const websocketUrl = new node_url_1.URL('logging', baseWsUrl); // If the configured logging token domain ends in twilio.com, use the twilio client, // otherwise use a simpler http client which doesn't mangle the domain let apiClient = null; let tokenRequestOpts = { method: 'POST', uri: tokenUrl.toString() }; let enableLoggingRequestOpts = { method: 'POST', uri: logEnableUrl.toString(), data: { LoggingEnabled: true } }; if (/^[^:]+:\/\/[^/]+\.twilio\.com/.test(apiBaseUrlString)) { apiClient = this.twilioClient; } else { apiClient = this.httpClient; tokenRequestOpts.username = this.currentProfile.apiKey; enableLoggingRequestOpts.username = this.currentProfile.apiKey; tokenRequestOpts.password = this.currentProfile.apiSecret; enableLoggingRequestOpts.password = this.currentProfile.apiSecret; } const streamOptions = { twilioClient: apiClient, tokenRequestOpts: tokenRequestOpts, enableLoggingRequestOpts: enableLoggingRequestOpts, websocketUrl: websocketUrl }; this.stream = new device_log_client_1.default(streamOptions); this.stream.on('open', () => { this.logger.debug('Websocket connected'); }); this.stream.on('connectFailed', (message) => { this.logger.error(message); }); this.stream.on('log', (logLine) => { const output = formatLogMessage(logLine, this.flags['cli-output-format']); console.log('%s', output); }); this.stream.on('error', (error) => this.logger.error(error.message)); process.on('SIGINT', async () => { this.logger.debug('Shutting down...'); setTimeout(node_process_1.default.exit, 1000); this.stream.close(); }); } async runCommand() { return this.run(); } } exports.default = MicrovisorLogsStream; MicrovisorLogsStream.args = [ { name: 'deviceSid', required: true, description: 'The Sid of the device you wish to stream logging from' } ]; function formatLogMessage(jsonLog, format) { var logLine; switch (format) { case 'json': logLine = `${jsonLog}`; break; default: logLine = formatForTextOutput(jsonLog); } return logLine; } function formatForTextOutput(jsonLog) { var logData = JSON.parse(jsonLog); // the longest category we publish is "[app_logging]" so 13 chars is the optimal padding var paddedCategory = `[${logData.category}]`.padEnd(13, ' '); // special case app crash lines, they arrive as json, add a header and pretty print switch (logData.category) { case 'app_crash': // parse the embedded json, and pretty print var crashStructured = JSON.parse(logData.message); return `${logData.timestamp} ${paddedCategory} Crash Report:\n${JSON.stringify(crashStructured, null, 2)}`; default: // strip trailing newlines off, unlikely to be intentional when used in text mode return `${logData.timestamp} ${paddedCategory} ${logData.message.trim()}`; } } // remove some of the base output implementations delete MicrovisorLogsStream.flags['cli-output-format']; delete MicrovisorLogsStream.flags.silent; MicrovisorLogsStream.flags = Object.assign({ // replace the base output flag format, we only support json or text (text) 'cli-output-format': core_1.Flags.string({ char: 'o', helpLabel: '-o', default: 'text', options: ['json', 'text'], description: 'Format of command output.' }), 'microvisor-debug-url': core_1.Flags.string({ description: 'First part of the url for the microvisor-debug endpoint', default: 'wss://microvisor-debug.us1.twilio.com', hidden: true }), 'microvisor-api-url': core_1.Flags.string({ description: 'First part of the url for microvisor api', default: 'https://microvisor.twilio.com/', hidden: true }) }, TwilioClientCommand.flags);