Skip to content

Commit ba84396

Browse files
authored
fix(create-twilio-function): place runtime-handler in dependencies (#331)
1 parent bbd78cf commit ba84396

File tree

5 files changed

+62
-33
lines changed

5 files changed

+62
-33
lines changed

packages/create-twilio-function/src/create-twilio-function/create-files.js

+5-5
Original file line numberDiff line numberDiff line change
@@ -22,15 +22,15 @@ async function createFile(fullPath, content) {
2222
return writeFile(fullPath, content, { flag: 'wx' });
2323
}
2424

25-
const javaScriptDeps = { twilio: versions.twilio };
25+
const javaScriptDeps = {
26+
twilio: versions.twilio,
27+
'@twilio/runtime-handler': versions.twilioRuntimeHandler,
28+
};
2629
const typescriptDeps = {
2730
'@twilio-labs/serverless-runtime-types': versions.serverlessRuntimeTypes,
2831
...javaScriptDeps,
2932
};
30-
const javaScriptDevDeps = {
31-
'@twilio/runtime-handler': versions.twilioRuntimeHandler,
32-
'twilio-run': versions.twilioRun,
33-
};
33+
const javaScriptDevDeps = { 'twilio-run': versions.twilioRun };
3434
const typescriptDevDeps = {
3535
...javaScriptDevDeps,
3636
typescript: versions.typescript,

packages/create-twilio-function/tests/create-files.test.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ describe('create-files', () => {
7979
expect(packageJSON.devDependencies['twilio-run']).toEqual(
8080
versions.twilioRun
8181
);
82-
expect(packageJSON.devDependencies['@twilio/runtime-handler']).toEqual(
82+
expect(packageJSON.dependencies['@twilio/runtime-handler']).toEqual(
8383
versions.twilioRuntimeHandler
8484
);
8585
expect(packageJSON.dependencies['twilio']).toEqual(versions.twilio);
@@ -105,7 +105,7 @@ describe('create-files', () => {
105105
expect(packageJSON.devDependencies.typescript).toEqual(
106106
versions.typescript
107107
);
108-
expect(packageJSON.devDependencies['@twilio/runtime-handler']).toEqual(
108+
expect(packageJSON.dependencies['@twilio/runtime-handler']).toEqual(
109109
versions.twilioRuntimeHandler
110110
);
111111
expect(

packages/twilio-run/src/commands/start.ts

+6
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import { Server } from 'http';
22
import inquirer from 'inquirer';
33
import { Argv } from 'yargs';
4+
import { checkForValidRuntimeHandlerVersion } from '../checks/check-runtime-handler';
45
import checkLegacyConfig from '../checks/legacy-config';
56
import checkNodejsVersion from '../checks/nodejs-version';
67
import checkProjectStructure from '../checks/project-structure';
@@ -48,6 +49,11 @@ export async function handler(
4849

4950
const config = await getConfigFromCli(argv, cliInfo, externalCliOptions);
5051

52+
if (!checkForValidRuntimeHandlerVersion(config.pkgJson)) {
53+
process.exitCode = 1;
54+
return;
55+
}
56+
5157
const command = getFullCommand(argv);
5258
const directories = {
5359
assetsDirectories: config.assetsFolderName

packages/twilio-run/src/config/start.ts

+12-9
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,10 @@ import { AllAvailableFlagTypes, SharedFlagNames } from '../flags';
99
import { EnvironmentVariablesWithAuth } from '../types/generic';
1010
import { fileExists } from '../utils/fs';
1111
import { getDebugFunction, logger } from '../utils/logger';
12+
import { readPackageJsonContent } from './utils';
1213
import { readSpecializedConfig } from './global';
1314
import { mergeFlagsAndConfig } from './utils/mergeFlagsAndConfig';
15+
import { PackageJson } from 'type-fest';
1416

1517
const debug = getDebugFunction('twilio-run:cli:config');
1618

@@ -38,6 +40,7 @@ export type StartCliConfig = {
3840
assetsFolderName?: string;
3941
functionsFolderName?: string;
4042
forkProcess: boolean;
43+
pkgJson: PackageJson;
4144
};
4245

4346
export type ConfigurableStartCliFlags = Pick<
@@ -160,18 +163,17 @@ export async function getConfigFromCli(
160163
cliInfo: CliInfo = { options: {} },
161164
externalCliOptions?: ExternalCliOptions
162165
): Promise<StartCliConfig> {
163-
const configFlags = readSpecializedConfig(
164-
flags.cwd || process.cwd(),
165-
flags.config,
166-
'start',
167-
{
168-
username:
169-
(externalCliOptions && externalCliOptions.accountSid) || undefined,
170-
}
171-
) as StartCliFlags;
166+
let cwd = flags.cwd ? path.resolve(flags.cwd) : process.cwd();
167+
flags.cwd = cwd;
168+
const configFlags = readSpecializedConfig(cwd, flags.config, 'start', {
169+
username:
170+
(externalCliOptions && externalCliOptions.accountSid) || undefined,
171+
}) as StartCliFlags;
172172
const cli = mergeFlagsAndConfig<StartCliFlags>(configFlags, flags, cliInfo);
173173
const config = {} as StartCliConfig;
174174

175+
const pkgJson = await readPackageJsonContent(cli);
176+
175177
config.inspect = getInspectInfo(cli);
176178
config.baseDir = getBaseDirectory(cli);
177179
config.env = await getEnvironment(cli, config.baseDir);
@@ -184,6 +186,7 @@ export async function getConfigFromCli(
184186
config.assetsFolderName = cli.assetsFolder;
185187
config.functionsFolderName = cli.functionsFolder;
186188
config.forkProcess = cli.forkProcess;
189+
config.pkgJson = pkgJson;
187190

188191
return config;
189192
}

packages/twilio-run/src/printers/start.ts

+37-17
Original file line numberDiff line numberDiff line change
@@ -4,43 +4,44 @@ import boxen from 'boxen';
44
import chalk from 'chalk';
55
import logSymbols from 'log-symbols';
66
import wrapAnsi from 'wrap-ansi';
7+
import { ServerConfig } from '../../../runtime-handler/dist/dev-runtime/types';
78
import { StartCliConfig } from '../config/start';
89
import { getFunctionsAndAssets } from '../runtime/internal/runtime-paths';
910
import { logger } from '../utils/logger';
1011
import { shouldPrettyPrint, terminalLink, windowSize } from './utils';
1112

1213
function printAsset(
1314
asset: ServerlessResourceConfig,
14-
config: StartCliConfig
15+
config: StartCliConfig | ServerConfig
1516
): string {
1617
const prefix = config.legacyMode ? '/asset' : '';
1718
return chalk`{dim ${config.url}${prefix}}${asset.path}`;
1819
}
1920

2021
function printFunction(
2122
fn: ServerlessResourceConfig,
22-
config: StartCliConfig
23+
config: StartCliConfig | ServerConfig
2324
): string {
2425
return chalk`{dim ${config.url}}${fn.path}`;
2526
}
2627

2728
function printPlainRouteInfo(
2829
functions: ServerlessResourceConfig[],
2930
assets: ServerlessResourceConfig[],
30-
config: StartCliConfig
31+
config: StartCliConfig | ServerConfig
3132
): string {
3233
const functionHeading = 'Functions';
3334
let functionInfo;
3435
if (functions.length > 0) {
35-
functionInfo = functions.map(fn => printFunction(fn, config)).join('\n');
36+
functionInfo = functions.map((fn) => printFunction(fn, config)).join('\n');
3637
} else {
3738
functionInfo = 'No functions found';
3839
}
3940

4041
const assetHeading = 'Assets';
4142
let assetInfo;
4243
if (assets.length > 0) {
43-
assetInfo = assets.map(asset => printAsset(asset, config)).join('\n');
44+
assetInfo = assets.map((asset) => printAsset(asset, config)).join('\n');
4445
} else {
4546
assetInfo = 'No assets found';
4647
}
@@ -67,7 +68,7 @@ function printPlainRouteInfo(
6768

6869
function prettyPrintAsset(
6970
asset: ServerlessResourceConfig,
70-
config: StartCliConfig
71+
config: StartCliConfig | ServerConfig
7172
): string {
7273
const prefix = config.legacyMode ? '/asset' : '';
7374
const assetPath = prefix + asset.path;
@@ -83,7 +84,7 @@ function prettyPrintAsset(
8384

8485
function prettyPrintFunction(
8586
fn: ServerlessResourceConfig,
86-
config: StartCliConfig
87+
config: StartCliConfig | ServerConfig
8788
) {
8889
const accessPrefix =
8990
fn.access === 'protected' ? chalk.cyan.bold('[protected] ') : '';
@@ -94,7 +95,7 @@ function prettyPrintFunction(
9495
function printPrettyRouteInfo(
9596
functions: ServerlessResourceConfig[],
9697
assets: ServerlessResourceConfig[],
97-
config: StartCliConfig
98+
config: StartCliConfig | ServerConfig
9899
): string {
99100
const functionHeading = chalk`{green.bold Twilio functions available:}`;
100101
let functionInfo;
@@ -146,15 +147,34 @@ function printPrettyRouteInfo(
146147
return boxen(wrappedOutput, { padding: 1 });
147148
}
148149

149-
export async function printRouteInfo(config: StartCliConfig): Promise<void> {
150-
const searchConfig: SearchConfig = {
151-
functionsFolderNames: config.functionsFolderName
152-
? [config.functionsFolderName]
153-
: undefined,
154-
assetsFolderNames: config.assetsFolderName
155-
? [config.assetsFolderName]
156-
: undefined,
157-
};
150+
// A magic function from https://fettblog.eu/typescript-hasownproperty/
151+
// This narrows down a type based on the property that an object has. It is used
152+
// below to distinguish between `StartCliConfig` and `ServerConfig` as the
153+
// `ServerConfig` does not have functionsFolderName or assetsFolderName
154+
// properties.
155+
function hasOwnProperty<X extends {}, Y extends PropertyKey>(
156+
obj: X,
157+
prop: Y
158+
): obj is X & Record<Y, unknown> {
159+
return obj.hasOwnProperty(prop);
160+
}
161+
162+
export async function printRouteInfo(
163+
config: StartCliConfig | ServerConfig
164+
): Promise<void> {
165+
const searchConfig: SearchConfig = {};
166+
if (
167+
hasOwnProperty(config, 'functionsFolderName') &&
168+
typeof config.functionsFolderName === 'string'
169+
) {
170+
searchConfig.functionsFolderNames = [config.functionsFolderName];
171+
}
172+
if (
173+
hasOwnProperty(config, 'assetsFolderName') &&
174+
typeof config.assetsFolderName === 'string'
175+
) {
176+
searchConfig.assetsFolderNames = [config.assetsFolderName];
177+
}
158178

159179
const { functions, assets } = await getFunctionsAndAssets(
160180
config.baseDir,

0 commit comments

Comments
 (0)