Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
"eslint-plugin-lint": "^1.0.0",
"eslint-plugin-react": "^7.30.1",
"eslint-plugin-relay": "^1.8.3",
"flow-api-translator": "0.30.0",
"flow-bin": "^0.279.0",
"glob": "^7.1.1",
"hermes-eslint": "0.31.2",
Expand All @@ -47,6 +48,7 @@
"scripts": {
"build-clean": "rm -rf ./packages/*/build",
"build": "node ./scripts/build.js",
"build-ts-experimental": "node -r @babel/register ./scripts/generateTypeScriptDefinitions.js",
"clean-all": "rm -rf ./node_modules && rm -rf ./packages/*/node_modules && yarn run build-clean",
"lint-fix": "eslint . --fix --cache && prettier --write .",
"lint": "eslint . --cache && prettier --check .",
Expand Down
46 changes: 46 additions & 0 deletions packages/metro-config/src/__flowtests__/types-flowtest.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
/**
* Copyright (c) Meta Platforms, Inc. and affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @flow strict-local
* @format
* @oncall react_native
*/

import type {ConfigT, InputConfigT} from 'metro-config';

declare var config: ConfigT;
declare var inputConfig: InputConfigT;

declare function isMutableArray<T: $ReadOnlyArray<mixed>>(
arr: T,
): T extends Array<mixed> ? true : false;

// Ensure ConfigT satisfies InputConfigT
(config: InputConfigT);

// Ensure empty config satisfies InputConfigT
({}: InputConfigT);
// And it may be partial
({
resolver: {},
transformer: {},
serializer: {},
server: {},
symbolicator: {},
}: InputConfigT);

// Both are deep read-only
(isMutableArray(config.cacheStores): false);
if (
inputConfig.cacheStores != null &&
typeof inputConfig.cacheStores !== 'function'
) {
(isMutableArray(inputConfig.cacheStores): false);
}

// ConfigT is completely hydrated (no errors accessing deep props)
config.resolver.unstable_conditionsByPlatform['foo'];
config.transformer.assetPlugins[0];
12 changes: 6 additions & 6 deletions packages/metro-config/src/defaults/defaults.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@

import type {PerfLogger, RootPerfLogger} from '../types';

export {default as defaultCreateModuleIdFactory} from 'metro/private/lib/createModuleIdFactory';
export {default as defaultCreateModuleIdFactory} from './createModuleIdFactory';

export const assetExts = [
export const assetExts: Array<string> = [
// Image formats
'bmp',
'gif',
Expand Down Expand Up @@ -50,17 +50,17 @@ export const assetExts = [
'zip',
];

export const assetResolutions = ['1', '1.5', '2', '3', '4'];
export const assetResolutions: Array<string> = ['1', '1.5', '2', '3', '4'];

export const sourceExts = ['js', 'jsx', 'json', 'ts', 'tsx'];
export const sourceExts: Array<string> = ['js', 'jsx', 'json', 'ts', 'tsx'];

export const additionalExts = ['cjs', 'mjs'];
export const additionalExts: Array<string> = ['cjs', 'mjs'];

export const moduleSystem = (require.resolve(
'metro-runtime/src/polyfills/require.js',
): string);

export const platforms = ['ios', 'android', 'windows', 'web'];
export const platforms: Array<string> = ['ios', 'android', 'windows', 'web'];

export const DEFAULT_METRO_MINIFIER_PATH = 'metro-minify-terser';

Expand Down
11 changes: 7 additions & 4 deletions packages/metro-config/src/defaults/exclusionList.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,17 @@
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @flow strict-local
* @format
* @oncall react_native
*/

import path from 'path';

var list = [/\/__tests__\/.*/];
const list = [/\/__tests__\/.*/];

function escapeRegExp(pattern) {
if (Object.prototype.toString.call(pattern) === '[object RegExp]') {
function escapeRegExp(pattern: RegExp | string) {
if (pattern instanceof RegExp) {
// the forward slash may or may not be escaped in regular expression depends
// on if it's in brackets. See this post for details
// https://github.com/nodejs/help/issues/3039. The or condition in string
Expand All @@ -34,7 +35,9 @@ function escapeRegExp(pattern) {
}
}

export default function exclusionList(additionalExclusions) {
export default function exclusionList(
additionalExclusions?: $ReadOnlyArray<RegExp | string>,
): RegExp {
return new RegExp(
'(' +
(additionalExclusions || []).concat(list).map(escapeRegExp).join('|') +
Expand Down
8 changes: 6 additions & 2 deletions packages/metro-config/src/defaults/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,9 @@ import {
sourceExts,
} from './defaults';
import exclusionList from './exclusionList';
import getMaxWorkers from './getMaxWorkers';
import {FileStore} from 'metro-cache';
import {Terminal} from 'metro-core';
import getMaxWorkers from 'metro/private/lib/getMaxWorkers';
import TerminalReporter from 'metro/private/lib/TerminalReporter';
import os from 'os';
import path from 'path';
Expand Down Expand Up @@ -180,4 +180,8 @@ async function getDefaultConfig(rootPath: ?string): Promise<ConfigT> {
}

getDefaultConfig.getDefaultValues = getDefaultValues;
export default getDefaultConfig;

export default getDefaultConfig as interface {
(rootPath?: string): Promise<ConfigT>,
getDefaultValues: (rootPath?: string) => ConfigT,
};
20 changes: 12 additions & 8 deletions packages/metro-config/src/defaults/validConfig.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,17 +9,17 @@
* @oncall react_native
*/

/* eslint-disable import/no-commonjs */
import type {InputConfigT} from '../types';

'use strict';

module.exports = (async () => {
export default (async () => {
const defaultConfig = await require('./index').default('/path/to/project');
const validConfig = {
...defaultConfig,
resolver: {
...defaultConfig.resolver,
resolveRequest: function CustomResolver() {},
resolveRequest: function CustomResolver() {
throw new Error('Not implemented');
},
hasteImplModulePath: './path',
},
server: {
Expand All @@ -28,13 +28,17 @@ module.exports = (async () => {
},
transformer: {
...defaultConfig.transformer,
getTransformOptions: function getTransformOptions() {},
getTransformOptions: function getTransformOptions() {
throw new Error('Not implemented');
},
},
serializer: {
...defaultConfig.serializer,
customSerializer: function customSerializer() {},
customSerializer: function customSerializer() {
throw new Error('Not implemented');
},
},
};

return validConfig;
}: () => any);
}: () => Promise<InputConfigT>);
66 changes: 29 additions & 37 deletions packages/metro-config/src/types.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,9 @@
*
* @format
* @flow strict-local
* @oncall react_native
*/

import type {IntermediateStackFrame} from '../../metro/src/Server/symbolicate';
import type {HandleFunction, Server} from 'connect';
import type {CacheStore} from 'metro-cache';
import typeof * as MetroCache from 'metro-cache';
Expand All @@ -24,6 +24,7 @@ import type {
} from 'metro/private/DeltaBundler/types';
import type {Reporter} from 'metro/private/lib/reporting';
import type MetroServer from 'metro/private/Server';
import type {IntermediateStackFrame} from 'metro/private/Server/symbolicate';

export type ExtraTransformOptions = $ReadOnly<{
preloadedModules?: $ReadOnly<{[path: string]: true, ...}> | false,
Expand Down Expand Up @@ -143,13 +144,12 @@ type TransformerConfigT = {
...JsTransformerConfig,
getTransformOptions: GetTransformOptions,
// TODO(moti): Remove this Meta-internal option from Metro's public config
transformVariants: {+[name: string]: {...}},
transformVariants: {+[name: string]: Partial<ExtraTransformOptions>},
publicPath: string,
unstable_workerThreads: boolean,
};

type MetalConfigT = {
cacheStores: $ReadOnlyArray<CacheStore<TransformResult<>>>,
cacheVersion: string,
fileMapCacheDirectory?: string,
hasteMapCacheDirectory?: string, // Deprecated, alias of fileMapCacheDirectory
Expand All @@ -164,6 +164,8 @@ type MetalConfigT = {
watchFolders: $ReadOnlyArray<string>,
};

type CacheStoresConfigT = $ReadOnlyArray<CacheStore<TransformResult<>>>;

type ServerConfigT = {
/** @deprecated */
enhanceMiddleware: (Middleware, MetroServer) => Middleware | Server,
Expand Down Expand Up @@ -208,56 +210,46 @@ type WatcherConfigT = {
}>,
};

export type InputConfigT = $ReadOnly<
Partial<{
...MetalConfigT,
...$ReadOnly<{
cacheStores:
| $ReadOnlyArray<CacheStore<TransformResult<>>>
| (MetroCache => $ReadOnlyArray<CacheStore<TransformResult<>>>),
export type InputConfigT = Partial<
$ReadOnly<
MetalConfigT & {
cacheStores: CacheStoresConfigT | (MetroCache => CacheStoresConfigT),
resolver: $ReadOnly<Partial<ResolverConfigT>>,
server: $ReadOnly<Partial<ServerConfigT>>,
serializer: $ReadOnly<Partial<SerializerConfigT>>,
symbolicator: $ReadOnly<Partial<SymbolicatorConfigT>>,
transformer: $ReadOnly<Partial<TransformerConfigT>>,
watcher: $ReadOnly<
Partial<{
...WatcherConfigT,
healthCheck?: $ReadOnly<Partial<WatcherConfigT['healthCheck']>>,
unstable_autoSaveCache?: $ReadOnly<
Partial<WatcherConfigT['unstable_autoSaveCache']>,
>,
}>,
watcher: Partial<
$ReadOnly<
Omit<
WatcherConfigT,
'healthCheck' | 'unstable_autoSaveCache' | 'watchman',
> & {
healthCheck: Partial<$ReadOnly<WatcherConfigT['healthCheck']>>,
unstable_autoSaveCache: Partial<
$ReadOnly<WatcherConfigT['unstable_autoSaveCache']>,
>,
watchman: Partial<$ReadOnly<WatcherConfigT['watchman']>>,
},
>,
>,
}>,
}>,
},
>,
>;

export type MetroConfig = InputConfigT;

export type IntermediateConfigT = {
...MetalConfigT,
...{
resolver: ResolverConfigT,
server: ServerConfigT,
serializer: SerializerConfigT,
symbolicator: SymbolicatorConfigT,
transformer: TransformerConfigT,
watcher: WatcherConfigT,
},
};

export type ConfigT = $ReadOnly<{
...$ReadOnly<MetalConfigT>,
...$ReadOnly<{
export type ConfigT = $ReadOnly<
MetalConfigT & {
cacheStores: CacheStoresConfigT,
resolver: $ReadOnly<ResolverConfigT>,
server: $ReadOnly<ServerConfigT>,
serializer: $ReadOnly<SerializerConfigT>,
symbolicator: $ReadOnly<SymbolicatorConfigT>,
transformer: $ReadOnly<TransformerConfigT>,
watcher: $ReadOnly<WatcherConfigT>,
}>,
}>;
},
>;

export type YargArguments = $ReadOnly<{
config?: string,
Expand Down
16 changes: 3 additions & 13 deletions packages/metro-config/types/types.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -140,12 +140,11 @@ export interface SerializerConfigT {

export interface TransformerConfigT extends JsTransformerConfig {
getTransformOptions: GetTransformOptions;
transformVariants: Readonly<{[name: string]: unknown}>;
transformVariants: Readonly<{[name: string]: Partial<ExtraTransformOptions>}>;
publicPath: string;
}

export interface MetalConfigT {
cacheStores: ReadonlyArray<CacheStore<TransformResult>>;
cacheVersion: string;
fileMapCacheDirectory?: string;
/** Deprecated, alias of fileMapCacheDirectory */
Expand Down Expand Up @@ -212,8 +211,7 @@ export interface WatcherInputConfigT
unstable_autoSaveCache?: Partial<WatcherConfigT['unstable_autoSaveCache']>;
}

export interface InputConfigT
extends Partial<Omit<MetalConfigT, 'cacheStores'>> {
export interface InputConfigT extends Partial<MetalConfigT> {
readonly cacheStores?:
| ReadonlyArray<CacheStore<TransformResult>>
| ((metroCache: MetroCache) => ReadonlyArray<CacheStore<TransformResult>>);
Expand All @@ -227,16 +225,8 @@ export interface InputConfigT

export type MetroConfig = InputConfigT;

export interface IntermediateConfigT extends MetalConfigT {
resolver: ResolverConfigT;
server: ServerConfigT;
serializer: SerializerConfigT;
symbolicator: SymbolicatorConfigT;
transformer: TransformerConfigT;
watcher: WatcherConfigT;
}

export interface ConfigT extends Readonly<MetalConfigT> {
readonly cacheStores: ReadonlyArray<CacheStore<TransformResult>>;
readonly resolver: Readonly<ResolverConfigT>;
readonly server: Readonly<ServerConfigT>;
readonly serializer: Readonly<SerializerConfigT>;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@
import type {Module, TransformInputOptions} from '../../types';

import CountingSet from '../../../lib/CountingSet';
import createModuleIdFactory from '../../../lib/createModuleIdFactory';
import baseJSBundle from '../baseJSBundle';
import createModuleIdFactory from 'metro-config/private/defaults/createModuleIdFactory';

const path = require('path');

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,9 @@
import type {Dependency} from '../../../types';

import CountingSet from '../../../../lib/CountingSet';
import createModuleIdFactory from '../../../../lib/createModuleIdFactory';
import {wrapModule} from '../js';
import {wrap as raw} from 'jest-snapshot-serializer-raw';
import createModuleIdFactory from 'metro-config/private/defaults/createModuleIdFactory';
import nullthrows from 'nullthrows';

let myModule;
Expand Down
5 changes: 1 addition & 4 deletions packages/metro/src/Server/symbolicate.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,7 @@ export type IntermediateStackFrame = {
collapse?: boolean,
...
};
export type StackFrameOutput = $ReadOnly<{
...IntermediateStackFrame,
...
}>;
export type StackFrameOutput = $ReadOnly<IntermediateStackFrame>;
type ExplodedSourceMapModule = ExplodedSourceMap[number];
type Position = {+line1Based: number, column0Based: number};

Expand Down
Loading
Loading