expo-module-scripts 5.1.0-canary-20251120-e46b3cc → 5.1.0-canary-20251205-756eb7a
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintrc.js +1 -1
- package/CHANGELOG.md +7 -0
- package/babel.config.base.js +1 -1
- package/babel.config.cli.js +6 -6
- package/babel.config.plugin.js +1 -1
- package/babel.config.scripts.js +1 -1
- package/babel.config.utils.js +1 -1
- package/bin/expo-module-babel +3 -5
- package/bin/expo-module-build +24 -28
- package/bin/expo-module-clean +30 -13
- package/bin/expo-module-configure +83 -62
- package/bin/expo-module-eslint +3 -5
- package/bin/expo-module-jest +3 -5
- package/bin/expo-module-lint +16 -27
- package/bin/expo-module-prepare +30 -17
- package/bin/expo-module-prepublishOnly +4 -6
- package/bin/expo-module-readme +16 -13
- package/bin/expo-module-test +28 -27
- package/bin/expo-module-tsc +4 -4
- package/bin/expo-module-typecheck +8 -8
- package/bin/expo-module.js +2 -3
- package/{createJestPreset.js → createJestPreset.cjs} +2 -2
- package/ios/{jest-preset.js → jest-preset.cjs} +1 -1
- package/jest-preset-scripts.cjs +2 -0
- package/{jest-preset.js → jest-preset.cjs} +1 -1
- package/package.json +51 -5
- package/universal/{jest-preset.js → jest-preset.cjs} +1 -1
- package/utils/commandUtils.js +55 -0
- package/utils/fileUtils.js +11 -0
- package/bin/npx +0 -13
- package/jest-preset-scripts.js +0 -2
- /package/{eslint.config.base.js → eslint.config.base.cjs} +0 -0
- /package/{eslintrc.base.js → eslintrc.base.cjs} +0 -0
- /package/{jest-preset-cli.js → jest-preset-cli.cjs} +0 -0
- /package/{jest-preset-plugin.js → jest-preset-plugin.cjs} +0 -0
- /package/{jest-preset-utils.js → jest-preset-utils.cjs} +0 -0
- /package/{jest-setup-react-19.js → jest-setup-react-19.cjs} +0 -0
package/.eslintrc.js
CHANGED
package/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
### 🎉 New features
|
|
8
8
|
|
|
9
9
|
- Ensure `loader()` functions are stripped from client bundles ([#40670](https://github.com/expo/expo/pull/40670) by [@hassankhan](https://github.com/hassankhan))
|
|
10
|
+
- Rewrite using Node.js to add Windows support. ([#36296](https://github.com/expo/expo/pull/36296) by [@Simek](https://github.com/Simek) and [@kudo](https://github.com/kudo))
|
|
10
11
|
|
|
11
12
|
### 🐛 Bug fixes
|
|
12
13
|
|
|
@@ -14,6 +15,12 @@
|
|
|
14
15
|
|
|
15
16
|
- Add more tests related files to the `.npmignore` template. ([#39551](https://github.com/expo/expo/pull/39551) by [@Simek](https://github.com/Simek))
|
|
16
17
|
|
|
18
|
+
## 5.0.8 - 2025-12-04
|
|
19
|
+
|
|
20
|
+
### 💡 Others
|
|
21
|
+
|
|
22
|
+
- Update to `glob@^13.0.0` ([#41079](https://github.com/expo/expo/pull/41079) by [@kitten](https://github.com/kitten))
|
|
23
|
+
|
|
17
24
|
## 5.0.7 — 2025-09-10
|
|
18
25
|
|
|
19
26
|
_This version does not introduce any user-facing changes._
|
package/babel.config.base.js
CHANGED
package/babel.config.cli.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
|
|
1
|
+
export default function (api) {
|
|
2
2
|
api.cache(true);
|
|
3
3
|
return {
|
|
4
4
|
presets: [
|
|
5
5
|
[
|
|
6
|
-
|
|
6
|
+
'@babel/preset-env',
|
|
7
7
|
{
|
|
8
8
|
modules: false, // Disable the default `modules-commonjs`, to enable lazy evaluation
|
|
9
9
|
targets: {
|
|
@@ -11,13 +11,13 @@ module.exports = function (api) {
|
|
|
11
11
|
},
|
|
12
12
|
},
|
|
13
13
|
],
|
|
14
|
-
|
|
14
|
+
'@babel/preset-typescript',
|
|
15
15
|
],
|
|
16
16
|
plugins: [
|
|
17
|
-
|
|
18
|
-
|
|
17
|
+
'babel-plugin-dynamic-import-node',
|
|
18
|
+
'@babel/plugin-transform-export-namespace-from',
|
|
19
19
|
[
|
|
20
|
-
|
|
20
|
+
'@babel/plugin-transform-modules-commonjs',
|
|
21
21
|
{
|
|
22
22
|
lazy: () => true,
|
|
23
23
|
},
|
package/babel.config.plugin.js
CHANGED
package/babel.config.scripts.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
export * from './babel.config.cli';
|
package/babel.config.utils.js
CHANGED
package/bin/expo-module-babel
CHANGED
|
@@ -1,7 +1,5 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import { getArgs, packageManagerExecAsync } from '../utils/commandUtils.js';
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
"$script_dir/npx" babel "$@"
|
|
5
|
+
await packageManagerExecAsync(['babel', ...getArgs()]);
|
package/bin/expo-module-build
CHANGED
|
@@ -1,34 +1,30 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import fs from 'node:fs';
|
|
4
|
+
import path from 'node:path';
|
|
5
|
+
import { fileURLToPath } from 'node:url';
|
|
4
6
|
|
|
5
|
-
|
|
7
|
+
import { commandRunner, getArgs, addWatchFlagIfNeeded } from '../utils/commandUtils.js';
|
|
6
8
|
|
|
7
|
-
|
|
9
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
8
10
|
|
|
9
|
-
|
|
10
|
-
# plugin/tsconfig.json
|
|
11
|
-
extra_module_build_types=("plugin" "cli" "utils" "scripts")
|
|
12
|
-
for i in "${extra_module_build_types[@]}"
|
|
13
|
-
do
|
|
14
|
-
if [ "$1" == "$i" ]; then
|
|
15
|
-
# Check if tsconfig.json exists in the directory
|
|
16
|
-
if [ -f "$(pwd)/$i/tsconfig.json" ]; then
|
|
17
|
-
# `--build` must be the first argument, so reset the array
|
|
18
|
-
args=()
|
|
19
|
-
args+=("--build")
|
|
20
|
-
args+=("$(pwd)/$i")
|
|
21
|
-
# Push the rest of the arguments minus the `plugin` arg
|
|
22
|
-
args+=("${@:2}")
|
|
23
|
-
else
|
|
24
|
-
echo "tsconfig.json not found in $@, skipping build for $@/"
|
|
25
|
-
exit
|
|
26
|
-
fi
|
|
27
|
-
fi
|
|
28
|
-
done
|
|
11
|
+
const EXTRA_MODULE_BUILD_TARGETS = ['plugin', 'cli', 'utils', 'scripts'];
|
|
29
12
|
|
|
30
|
-
|
|
31
|
-
args+=("--watch")
|
|
32
|
-
fi
|
|
13
|
+
let args = getArgs();
|
|
33
14
|
|
|
34
|
-
|
|
15
|
+
// If the command is used like `yarn build plugin`, set the --build option to point to plugin/tsconfig.json
|
|
16
|
+
if (EXTRA_MODULE_BUILD_TARGETS.includes(args[0])) {
|
|
17
|
+
const target = args[0];
|
|
18
|
+
const targetDir = path.join(process.cwd(), args[0]);
|
|
19
|
+
if (fs.existsSync(path.join(targetDir, 'tsconfig.json'))) {
|
|
20
|
+
// Push the rest of the arguments minus the `plugin` arg
|
|
21
|
+
const restArgs = args.slice(1);
|
|
22
|
+
args = ['--build', targetDir, ...restArgs];
|
|
23
|
+
} else {
|
|
24
|
+
console.log(`tsconfig.json not found in ${target}, skipping build for ${target}`);
|
|
25
|
+
process.exit(0);
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
args = addWatchFlagIfNeeded(args);
|
|
30
|
+
await commandRunner(path.join(dirname, 'expo-module-tsc'), args);
|
package/bin/expo-module-clean
CHANGED
|
@@ -1,16 +1,33 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import fs from 'node:fs';
|
|
4
|
+
import path from 'node:path';
|
|
4
5
|
|
|
5
|
-
|
|
6
|
-
echo "The current working directory is not a package's root directory"
|
|
7
|
-
exit 1
|
|
8
|
-
fi
|
|
6
|
+
import { directoryExistsAsync } from '../utils/fileUtils.js';
|
|
9
7
|
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
8
|
+
async function runAsync() {
|
|
9
|
+
if (!fs.existsSync(path.join(process.cwd(), 'package.json'))) {
|
|
10
|
+
console.error("The current working directory is not a package's root directory");
|
|
11
|
+
process.exit(1);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
// Support `yarn clean plugin` to delete ./plugin/build/
|
|
15
|
+
const directory = process.argv[2];
|
|
16
|
+
if (directory && (await directoryExistsAsync(path.join(process.cwd(), directory)))) {
|
|
17
|
+
await fs.promises.rm(path.join(process.cwd(), directory, 'build'), {
|
|
18
|
+
recursive: true,
|
|
19
|
+
force: true,
|
|
20
|
+
});
|
|
21
|
+
} else {
|
|
22
|
+
await fs.promises.rm(path.join(process.cwd(), 'build'), { recursive: true, force: true });
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
(async () => {
|
|
27
|
+
try {
|
|
28
|
+
await runAsync();
|
|
29
|
+
} catch (error) {
|
|
30
|
+
console.error(error);
|
|
31
|
+
process.exit(error.status || error.code || 1);
|
|
32
|
+
}
|
|
33
|
+
})();
|
|
@@ -1,77 +1,98 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import { glob } from 'glob';
|
|
4
|
+
import crypto from 'node:crypto';
|
|
5
|
+
import fs from 'node:fs';
|
|
6
|
+
import path from 'node:path';
|
|
7
|
+
import { fileURLToPath } from 'node:url';
|
|
4
8
|
|
|
5
|
-
|
|
9
|
+
import { commandRunner } from '../utils/commandUtils.js';
|
|
10
|
+
import { toPosixPath } from '../utils/fileUtils.js';
|
|
6
11
|
|
|
7
|
-
|
|
12
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
8
13
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
OPTIONAL_TEMPLATE_FILES=
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
14
|
+
// an optional template file will be synced only if the target file is present in the file system,
|
|
15
|
+
// and its content contains the string `@generated`.
|
|
16
|
+
const OPTIONAL_TEMPLATE_FILES = [
|
|
17
|
+
// add a relative file path from `templates/` for each new optional file
|
|
18
|
+
'eslint.config.js',
|
|
19
|
+
path.join('scripts', 'with-node.sh'),
|
|
20
|
+
];
|
|
16
21
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
get_relative_files() {
|
|
20
|
-
pushd "$1" > /dev/null
|
|
21
|
-
local files=$(find . -type f | cut -c 3-)
|
|
22
|
-
popd > /dev/null
|
|
23
|
-
echo "$files"
|
|
24
|
-
}
|
|
22
|
+
async function runAsync() {
|
|
23
|
+
await commandRunner(path.join(dirname, 'expo-module-readme'));
|
|
25
24
|
|
|
25
|
+
const templatesDir = path.join(dirname, '..', 'templates');
|
|
26
|
+
const templateDirents = await glob('**/*', {
|
|
27
|
+
cwd: templatesDir,
|
|
28
|
+
withFileTypes: true,
|
|
29
|
+
});
|
|
30
|
+
const templateFiles = templateDirents
|
|
31
|
+
.filter((dirent) => dirent.isFile())
|
|
32
|
+
.map((dirent) => path.relative(templatesDir, path.join(dirent.parentPath, dirent.name)));
|
|
26
33
|
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
34
|
+
await Promise.all(
|
|
35
|
+
templateFiles.map(async (templateFile) => {
|
|
36
|
+
if (OPTIONAL_TEMPLATE_FILES.includes(toPosixPath(templateFile))) {
|
|
37
|
+
await syncFileIfPresentAsync(
|
|
38
|
+
path.join(templatesDir, templateFile),
|
|
39
|
+
path.join(process.cwd(), templateFile)
|
|
40
|
+
);
|
|
41
|
+
} else {
|
|
42
|
+
await syncFileIfMissingAsync(
|
|
43
|
+
path.join(templatesDir, templateFile),
|
|
44
|
+
path.join(process.cwd(), templateFile)
|
|
45
|
+
);
|
|
46
|
+
}
|
|
47
|
+
})
|
|
48
|
+
);
|
|
36
49
|
}
|
|
37
50
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
fi
|
|
47
|
-
}
|
|
51
|
+
(async () => {
|
|
52
|
+
try {
|
|
53
|
+
await runAsync();
|
|
54
|
+
} catch (error) {
|
|
55
|
+
console.error(error);
|
|
56
|
+
process.exit(error.status || error.code || 1);
|
|
57
|
+
}
|
|
58
|
+
})();
|
|
48
59
|
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
done
|
|
60
|
+
/**
|
|
61
|
+
* syncs the source file if the target file is missing or the existing file contains `@generated`.
|
|
62
|
+
*/
|
|
63
|
+
async function syncFileIfMissingAsync(sourcePath, targetPath) {
|
|
64
|
+
const shouldSync = !fs.existsSync(targetPath) || (await hasGeneratedMarkerAsync(targetPath));
|
|
65
|
+
if (shouldSync) {
|
|
66
|
+
await syncFileAsync(sourcePath, targetPath);
|
|
67
|
+
}
|
|
68
|
+
}
|
|
59
69
|
|
|
60
|
-
|
|
61
|
-
|
|
70
|
+
/**
|
|
71
|
+
* syncs the source file if the target file is present in the file system and its content contains `@generated`.
|
|
72
|
+
*/
|
|
73
|
+
async function syncFileIfPresentAsync(sourcePath, targetPath) {
|
|
74
|
+
const shouldSync = fs.existsSync(targetPath) && (await hasGeneratedMarkerAsync(targetPath));
|
|
75
|
+
if (shouldSync) {
|
|
76
|
+
await syncFileAsync(sourcePath, targetPath);
|
|
77
|
+
}
|
|
62
78
|
}
|
|
63
79
|
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
80
|
+
async function syncFileAsync(sourcePath, targetPath) {
|
|
81
|
+
// NOTE(kudo): the performance is definitely not as good as rsync, not sure if we should just copy the file anyway.
|
|
82
|
+
const sourceData = await fs.promises.readFile(sourcePath);
|
|
83
|
+
const sourceChecksum = crypto.createHash('md5').update(sourceData).digest('hex');
|
|
84
|
+
let targetChecksum = '';
|
|
85
|
+
if (fs.existsSync(targetPath)) {
|
|
86
|
+
const targetData = await fs.promises.readFile(targetPath);
|
|
87
|
+
targetChecksum = crypto.createHash('md5').update(targetData).digest('hex');
|
|
88
|
+
}
|
|
67
89
|
|
|
68
|
-
|
|
90
|
+
if (sourceChecksum !== targetChecksum) {
|
|
91
|
+
await fs.promises.cp(sourcePath, targetPath, { recursive: true, force: true });
|
|
92
|
+
}
|
|
93
|
+
}
|
|
69
94
|
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
else
|
|
75
|
-
sync_file_if_missing "$script_dir/../templates/$template_relative_file" "$template_relative_file"
|
|
76
|
-
fi
|
|
77
|
-
done
|
|
95
|
+
async function hasGeneratedMarkerAsync(filePath) {
|
|
96
|
+
const data = await fs.promises.readFile(filePath, 'utf8');
|
|
97
|
+
return data.includes('@generated');
|
|
98
|
+
}
|
package/bin/expo-module-eslint
CHANGED
|
@@ -1,7 +1,5 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import { getArgs, packageManagerExecAsync } from '../utils/commandUtils.js';
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
"$script_dir/npx" eslint "$@"
|
|
5
|
+
await packageManagerExecAsync(['eslint', ...getArgs()]);
|
package/bin/expo-module-jest
CHANGED
|
@@ -1,7 +1,5 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import { getArgs, packageManagerExecAsync } from '../utils/commandUtils.js';
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
"$script_dir/npx" jest "$@"
|
|
5
|
+
await packageManagerExecAsync(['jest', ...getArgs()]);
|
package/bin/expo-module-lint
CHANGED
|
@@ -1,33 +1,22 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import path from 'node:path';
|
|
4
|
+
import { commandRunner, getArgs } from '../utils/commandUtils.js';
|
|
5
|
+
import { fileURLToPath } from 'node:url';
|
|
4
6
|
|
|
5
|
-
|
|
7
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
6
8
|
|
|
7
|
-
|
|
9
|
+
const EXTRA_MODULE_BUILD_TARGETS = ['plugin', 'cli', 'utils', 'scripts'];
|
|
8
10
|
|
|
9
|
-
|
|
10
|
-
extra_module_build_types=("plugin" "cli" "utils" "scripts")
|
|
11
|
-
found_target=""
|
|
12
|
-
for i in "${extra_module_build_types[@]}"
|
|
13
|
-
do
|
|
14
|
-
if [ "$1" == "$i" ]; then
|
|
15
|
-
found_target=$i
|
|
16
|
-
fi
|
|
17
|
-
done
|
|
11
|
+
let args = getArgs();
|
|
18
12
|
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
args
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
fi
|
|
28
|
-
else
|
|
29
|
-
args+=("$@")
|
|
30
|
-
args+=("src")
|
|
31
|
-
fi
|
|
13
|
+
// If the command is used like `yarn lint plugin` then set the target to `plugin/src`
|
|
14
|
+
if (EXTRA_MODULE_BUILD_TARGETS.includes(args[0])) {
|
|
15
|
+
// Push the rest of the arguments minus the `plugin` arg
|
|
16
|
+
const target = args[0];
|
|
17
|
+
args = [...args.slice(1), `${target}/src`];
|
|
18
|
+
} else {
|
|
19
|
+
args = [...args, 'src'];
|
|
20
|
+
}
|
|
32
21
|
|
|
33
|
-
|
|
22
|
+
await commandRunner(path.join(dirname, 'expo-module-eslint'), args);
|
package/bin/expo-module-prepare
CHANGED
|
@@ -1,22 +1,35 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import path from 'node:path';
|
|
4
|
+
import { fileURLToPath } from 'node:url';
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
import { commandRunner } from '../utils/commandUtils.js';
|
|
7
|
+
import { directoryExistsAsync } from '../utils/fileUtils.js';
|
|
6
8
|
|
|
7
|
-
|
|
9
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
8
10
|
|
|
9
|
-
|
|
10
|
-
"$script_dir/expo-module-clean"
|
|
11
|
-
"$script_dir/expo-module-configure"
|
|
12
|
-
"$script_dir/expo-module-build"
|
|
11
|
+
process.env.EXPO_NONINTERACTIVE = 1;
|
|
13
12
|
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
13
|
+
async function runAsync() {
|
|
14
|
+
console.log('Configuring module');
|
|
15
|
+
await commandRunner(path.join(dirname, 'expo-module-clean'));
|
|
16
|
+
await commandRunner(path.join(dirname, 'expo-module-configure'));
|
|
17
|
+
await commandRunner(path.join(dirname, 'expo-module-build'));
|
|
18
|
+
|
|
19
|
+
for (const target of ['plugin', 'cli', 'utils', 'scripts']) {
|
|
20
|
+
if (await directoryExistsAsync(path.join(process.cwd(), target))) {
|
|
21
|
+
console.log(`Configuring ${target}`);
|
|
22
|
+
await commandRunner(path.join(dirname, 'expo-module-clean'), [target]);
|
|
23
|
+
await commandRunner(path.join(dirname, 'expo-module-build'), [target]);
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
(async () => {
|
|
29
|
+
try {
|
|
30
|
+
await runAsync();
|
|
31
|
+
} catch (error) {
|
|
32
|
+
console.error(error);
|
|
33
|
+
process.exit(error.status || error.code || 1);
|
|
34
|
+
}
|
|
35
|
+
})();
|
|
@@ -1,9 +1,7 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import { packageManagerExecAsync } from '../utils/commandUtils.js';
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
process.env.EXPO_NONINTERACTIVE = 1;
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
"$script_dir/npx" proofread
|
|
7
|
+
await packageManagerExecAsync(['proofread']);
|
package/bin/expo-module-readme
CHANGED
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
'use strict';
|
|
3
2
|
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
3
|
+
import { globSync } from 'glob';
|
|
4
|
+
import fs from 'node:fs';
|
|
5
|
+
import path from 'node:path';
|
|
6
|
+
import { fileURLToPath } from 'node:url';
|
|
7
|
+
|
|
8
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
7
9
|
|
|
8
10
|
function replaceAll(current, replacement, content) {
|
|
9
11
|
const regexp = new RegExp(escapeRegExp('${' + current + '}'), 'g');
|
|
@@ -14,7 +16,7 @@ function escapeRegExp(string) {
|
|
|
14
16
|
return string.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
|
|
15
17
|
}
|
|
16
18
|
|
|
17
|
-
function
|
|
19
|
+
function removeInapplicableSections(name, content) {
|
|
18
20
|
const opener = `<!--- remove for ${name} --->`;
|
|
19
21
|
const closer = `<!--- end remove for ${name} --->`;
|
|
20
22
|
let nextContent = content;
|
|
@@ -40,7 +42,7 @@ function removeOptionals(content) {
|
|
|
40
42
|
const DEFAULT_HOMEPAGE = 'https://docs.expo.dev/versions/latest/';
|
|
41
43
|
|
|
42
44
|
function generateREADME() {
|
|
43
|
-
const template = path.join(
|
|
45
|
+
const template = path.join(dirname, '..', 'templates', 'README.md');
|
|
44
46
|
let readme = fs.readFileSync(template, 'utf8');
|
|
45
47
|
const pkg = JSON.parse(fs.readFileSync(path.join(process.cwd(), 'package.json'), 'utf8'));
|
|
46
48
|
const packageName = pkg.name;
|
|
@@ -59,9 +61,10 @@ function generateREADME() {
|
|
|
59
61
|
|
|
60
62
|
if (isIOS) {
|
|
61
63
|
const podspecs = globSync('{ios/**/,}*.podspec');
|
|
62
|
-
if (!podspecs[0])
|
|
63
|
-
|
|
64
|
-
|
|
64
|
+
if (!podspecs[0])
|
|
65
|
+
throw new Error(
|
|
66
|
+
`The Expo module named "${packageName}" contains an "ios" directory but does not define a Podspec, which is required for modules with iOS implementations.`
|
|
67
|
+
);
|
|
65
68
|
const podspecPath = podspecs[0];
|
|
66
69
|
const podName = (() => {
|
|
67
70
|
const parts = podspecPath.split('/');
|
|
@@ -70,11 +73,11 @@ function generateREADME() {
|
|
|
70
73
|
|
|
71
74
|
readme = replaceAll('podName', podName, readme);
|
|
72
75
|
} else {
|
|
73
|
-
readme =
|
|
76
|
+
readme = removeInapplicableSections('no-ios', readme);
|
|
74
77
|
}
|
|
75
78
|
|
|
76
79
|
if (isInterface) {
|
|
77
|
-
readme =
|
|
80
|
+
readme = removeInapplicableSections('interfaces', readme);
|
|
78
81
|
} else {
|
|
79
82
|
let docName;
|
|
80
83
|
if (homepage === DEFAULT_HOMEPAGE || homepage.startsWith('https://github.com')) {
|
|
@@ -124,13 +127,13 @@ function generateREADME() {
|
|
|
124
127
|
|
|
125
128
|
readme = replaceAll('androidPackageName', androidPackageName, readme);
|
|
126
129
|
} else {
|
|
127
|
-
readme =
|
|
130
|
+
readme = removeInapplicableSections('no-package', readme);
|
|
128
131
|
}
|
|
129
132
|
}
|
|
130
133
|
|
|
131
134
|
readme = replaceAll('androidPackagePath', androidPackagePath, readme);
|
|
132
135
|
} else {
|
|
133
|
-
readme =
|
|
136
|
+
readme = removeInapplicableSections('no-android', readme);
|
|
134
137
|
}
|
|
135
138
|
}
|
|
136
139
|
return removeOptionals(readme);
|
package/bin/expo-module-test
CHANGED
|
@@ -1,35 +1,36 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import fs from 'node:fs';
|
|
4
|
+
import { createRequire } from 'node:module';
|
|
5
|
+
import path from 'node:path';
|
|
6
|
+
import { fileURLToPath } from 'node:url';
|
|
4
7
|
|
|
5
|
-
|
|
8
|
+
import { commandRunner, getArgs, addWatchFlagIfNeeded } from '../utils/commandUtils.js';
|
|
6
9
|
|
|
7
|
-
|
|
10
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
11
|
+
const require = createRequire(import.meta.url);
|
|
8
12
|
|
|
9
|
-
|
|
10
|
-
extra_module_build_types=("plugin" "cli" "utils" "scripts")
|
|
11
|
-
for i in "${extra_module_build_types[@]}"
|
|
12
|
-
do
|
|
13
|
-
if [ "$1" == "$i" ]; then
|
|
14
|
-
args=()
|
|
15
|
-
args+=("--rootDir")
|
|
16
|
-
args+=("$i")
|
|
13
|
+
const EXTRA_MODULE_BUILD_TARGETS = ['plugin', 'cli', 'utils', 'scripts'];
|
|
17
14
|
|
|
18
|
-
|
|
19
|
-
args+=("--config")
|
|
20
|
-
args+=("$i/jest.config.js")
|
|
21
|
-
else
|
|
22
|
-
args+=("--config")
|
|
23
|
-
args+=("$(node --print "require.resolve('expo-module-scripts/jest-preset-$i.js')")")
|
|
24
|
-
fi
|
|
15
|
+
let args = getArgs();
|
|
25
16
|
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
17
|
+
// If the command is used like `yarn test plugin`, set the --rootDir option to the `plugin` directory
|
|
18
|
+
if (EXTRA_MODULE_BUILD_TARGETS.includes(args[0])) {
|
|
19
|
+
const target = args[0];
|
|
20
|
+
const targetDir = path.join(process.cwd(), target);
|
|
21
|
+
const restArgs = args.slice(1);
|
|
22
|
+
args = ['--rootDir', target];
|
|
30
23
|
|
|
31
|
-
if
|
|
32
|
-
|
|
33
|
-
|
|
24
|
+
if (fs.existsSync(path.join(targetDir, 'jest.config.js'))) {
|
|
25
|
+
args.push('--config', `${target}/jest.config.js`);
|
|
26
|
+
} else {
|
|
27
|
+
const jestConfigPath = require.resolve(`expo-module-scripts/jest-preset-${target}.js`);
|
|
28
|
+
args.push('--config', jestConfigPath);
|
|
29
|
+
}
|
|
30
|
+
// Push the rest of the arguments minus the `plugin` arg
|
|
31
|
+
args.push(...restArgs);
|
|
32
|
+
}
|
|
34
33
|
|
|
35
|
-
|
|
34
|
+
args = addWatchFlagIfNeeded(args);
|
|
35
|
+
|
|
36
|
+
await commandRunner(path.join(dirname, 'expo-module-jest'), args);
|
package/bin/expo-module-tsc
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import { getArgs, packageManagerExecAsync } from '../utils/commandUtils.js';
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
const args = getArgs();
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
await packageManagerExecAsync(['tsc', ...args]);
|
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
#!/usr/bin/env
|
|
1
|
+
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
import path from 'node:path';
|
|
4
|
+
import { fileURLToPath } from 'node:url';
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
import { commandRunner, getArgs } from '../utils/commandUtils.js';
|
|
6
7
|
|
|
7
|
-
|
|
8
|
-
if [[ -t 1 && (-z "$CI" && -z "$EXPO_NONINTERACTIVE") ]]; then
|
|
9
|
-
args+=("--watch")
|
|
10
|
-
fi
|
|
8
|
+
const dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
11
9
|
|
|
12
|
-
|
|
10
|
+
const args = getArgs({ maybeAddWatchFlag: true });
|
|
11
|
+
|
|
12
|
+
await commandRunner(path.join(dirname, 'expo-module-tsc'), ['--noEmit', ...args]);
|
package/bin/expo-module.js
CHANGED
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
'use strict';
|
|
3
2
|
|
|
4
|
-
|
|
5
|
-
const process = require('process');
|
|
3
|
+
import { program } from 'commander';
|
|
6
4
|
|
|
5
|
+
// Common scripts
|
|
7
6
|
program.command('configure', `Generate common configuration files`);
|
|
8
7
|
program.command('readme', `Generate README`);
|
|
9
8
|
program.command(
|
|
@@ -4,7 +4,7 @@ const fs = require('fs');
|
|
|
4
4
|
const path = require('path');
|
|
5
5
|
const { resolveWorkspaceRoot } = require('resolve-workspace-root');
|
|
6
6
|
|
|
7
|
-
module.exports = function (basePreset) {
|
|
7
|
+
module.exports = function createJestPreset(basePreset) {
|
|
8
8
|
// Explicitly catch and log errors since Jest sometimes suppresses error messages
|
|
9
9
|
try {
|
|
10
10
|
return _createJestPreset(basePreset);
|
|
@@ -73,7 +73,7 @@ function _createJestPreset(basePreset) {
|
|
|
73
73
|
...basePreset.transform,
|
|
74
74
|
},
|
|
75
75
|
// Add the React 19 workaround
|
|
76
|
-
setupFiles: [...basePreset.setupFiles, require.resolve('./jest-setup-react-19.
|
|
76
|
+
setupFiles: [...basePreset.setupFiles, require.resolve('./jest-setup-react-19.cjs')],
|
|
77
77
|
};
|
|
78
78
|
}
|
|
79
79
|
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const createJestPreset = require('../createJestPreset');
|
|
1
|
+
const createJestPreset = require('../createJestPreset.cjs');
|
|
2
2
|
|
|
3
3
|
console.warn(
|
|
4
4
|
'The Jest preset "expo-module-scripts/ios" is deprecated, please convert your tests to universal tests and use "expo-module-scripts" instead'
|
package/package.json
CHANGED
|
@@ -1,11 +1,56 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "expo-module-scripts",
|
|
3
|
-
"version": "5.1.0-canary-
|
|
3
|
+
"version": "5.1.0-canary-20251205-756eb7a",
|
|
4
4
|
"description": "A private package for various tasks for Expo module packages like compiling and testing",
|
|
5
5
|
"main": "index.js",
|
|
6
|
+
"type": "module",
|
|
6
7
|
"bin": {
|
|
7
8
|
"expo-module": "bin/expo-module.js"
|
|
8
9
|
},
|
|
10
|
+
"exports": {
|
|
11
|
+
"./package.json": "./package.json",
|
|
12
|
+
"./babel.config.*": {
|
|
13
|
+
"require": "./babel.config.*.js"
|
|
14
|
+
},
|
|
15
|
+
"./babel.config.*.js": {
|
|
16
|
+
"require": "./babel.config.*.js"
|
|
17
|
+
},
|
|
18
|
+
"./eslintrc.base.js": {
|
|
19
|
+
"require": "./eslintrc.base.cjs"
|
|
20
|
+
},
|
|
21
|
+
"./eslint.config.base": {
|
|
22
|
+
"require": "./eslint.config.base.cjs"
|
|
23
|
+
},
|
|
24
|
+
"./jest-preset-*": {
|
|
25
|
+
"import": "./jest-preset-*.cjs",
|
|
26
|
+
"require": "./jest-preset-*.cjs"
|
|
27
|
+
},
|
|
28
|
+
"./jest-preset-*.js": {
|
|
29
|
+
"import": "./jest-preset-*.cjs",
|
|
30
|
+
"require": "./jest-preset-*.cjs"
|
|
31
|
+
},
|
|
32
|
+
"./jest-preset": {
|
|
33
|
+
"import": "./jest-preset.cjs",
|
|
34
|
+
"require": "./jest-preset.cjs"
|
|
35
|
+
},
|
|
36
|
+
"./jest-preset.js": {
|
|
37
|
+
"import": "./jest-preset.cjs",
|
|
38
|
+
"require": "./jest-preset.cjs"
|
|
39
|
+
},
|
|
40
|
+
"./*/jest-preset": {
|
|
41
|
+
"import": "./*/jest-preset.cjs",
|
|
42
|
+
"require": "./*/jest-preset.cjs"
|
|
43
|
+
},
|
|
44
|
+
"./*/jest-preset.js": {
|
|
45
|
+
"import": "./*/jest-preset.cjs",
|
|
46
|
+
"require": "./*/jest-preset.cjs"
|
|
47
|
+
},
|
|
48
|
+
"./tsconfig.*": "./tsconfig.*.json",
|
|
49
|
+
"./tsconfig": "./tsconfig.json",
|
|
50
|
+
"./types/*.d.ts": {
|
|
51
|
+
"types": "./types/*.d.ts"
|
|
52
|
+
}
|
|
53
|
+
},
|
|
9
54
|
"scripts": {
|
|
10
55
|
"lint": "expo-module eslint ."
|
|
11
56
|
},
|
|
@@ -31,15 +76,16 @@
|
|
|
31
76
|
"@babel/preset-env": "^7.23.8",
|
|
32
77
|
"@babel/preset-typescript": "^7.23.3",
|
|
33
78
|
"@expo/npm-proofread": "^1.0.1",
|
|
79
|
+
"@expo/spawn-async": "^1.7.2",
|
|
34
80
|
"@testing-library/react-native": "^13.2.0",
|
|
35
81
|
"@tsconfig/node18": "^18.2.2",
|
|
36
82
|
"@types/jest": "^29.2.1",
|
|
37
83
|
"babel-plugin-dynamic-import-node": "^2.3.3",
|
|
38
|
-
"babel-preset-expo": "54.1.0-canary-
|
|
84
|
+
"babel-preset-expo": "54.1.0-canary-20251205-756eb7a",
|
|
39
85
|
"commander": "^12.1.0",
|
|
40
|
-
"eslint-config-universe": "15.0.4-canary-
|
|
41
|
-
"glob": "^
|
|
42
|
-
"jest-expo": "55.0.0-canary-
|
|
86
|
+
"eslint-config-universe": "15.0.4-canary-20251205-756eb7a",
|
|
87
|
+
"glob": "^13.0.0",
|
|
88
|
+
"jest-expo": "55.0.0-canary-20251205-756eb7a",
|
|
43
89
|
"jest-snapshot-prettier": "npm:prettier@^2",
|
|
44
90
|
"jest-watch-typeahead": "2.2.1",
|
|
45
91
|
"resolve-workspace-root": "^2.0.0",
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
const { withWatchPlugins } = require('jest-expo/config');
|
|
2
2
|
|
|
3
|
-
const createJestPreset = require('../createJestPreset');
|
|
3
|
+
const createJestPreset = require('../createJestPreset.cjs');
|
|
4
4
|
|
|
5
5
|
console.warn(
|
|
6
6
|
'The Jest preset "expo-module-scripts/universal" is deprecated; please use the alias "expo-module-scripts" instead'
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import spawnAsync from '@expo/spawn-async';
|
|
2
|
+
|
|
3
|
+
export async function commandRunner(command, params = [], { cwd } = {}) {
|
|
4
|
+
return await spawnAsync(command, params, {
|
|
5
|
+
stdio: 'inherit',
|
|
6
|
+
cwd: cwd ?? process.cwd(),
|
|
7
|
+
}).catch((error) => {
|
|
8
|
+
console.error(`Command failed: ${command} ${params.join(' ')}`);
|
|
9
|
+
if (error.message) {
|
|
10
|
+
console.error(error.message);
|
|
11
|
+
}
|
|
12
|
+
process.exit(error.status || error.code || 1);
|
|
13
|
+
});
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export async function packageManagerExecAsync(params, { cwd } = {}) {
|
|
17
|
+
let command = '';
|
|
18
|
+
const args = [];
|
|
19
|
+
|
|
20
|
+
const npmConfigUserAgent = process.env.npm_config_user_agent;
|
|
21
|
+
if (npmConfigUserAgent?.includes('yarn')) {
|
|
22
|
+
command = 'yarn';
|
|
23
|
+
args.push(...params);
|
|
24
|
+
} else if (npmConfigUserAgent?.includes('pnpm')) {
|
|
25
|
+
command = 'pnpm';
|
|
26
|
+
args.push('exec', ...params);
|
|
27
|
+
} else if (npmConfigUserAgent?.includes('bun')) {
|
|
28
|
+
command = 'bunx';
|
|
29
|
+
args.push(...params);
|
|
30
|
+
} else {
|
|
31
|
+
command = 'npx';
|
|
32
|
+
args.push(...params);
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
return commandRunner(command, args, { cwd });
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
export function getArgs({ maybeAddWatchFlag = false } = {}) {
|
|
39
|
+
let args = process.argv.slice(2);
|
|
40
|
+
if (maybeAddWatchFlag) {
|
|
41
|
+
args = addWatchFlagIfNeeded(args);
|
|
42
|
+
}
|
|
43
|
+
return args;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
function shouldAddWatchFlag() {
|
|
47
|
+
return process.stdout.isTTY && !process.env.CI && !process.env.EXPO_NONINTERACTIVE;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
export function addWatchFlagIfNeeded(args) {
|
|
51
|
+
if (shouldAddWatchFlag() && !args.includes('--watch')) {
|
|
52
|
+
args.push('--watch');
|
|
53
|
+
}
|
|
54
|
+
return args;
|
|
55
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import fs from 'node:fs';
|
|
2
|
+
|
|
3
|
+
const REGEXP_REPLACE_SLASHES = /\\/g;
|
|
4
|
+
|
|
5
|
+
export async function directoryExistsAsync(file) {
|
|
6
|
+
return (await fs.promises.stat(file).catch(() => null))?.isDirectory() ?? false;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
export function toPosixPath(filePath) {
|
|
10
|
+
return filePath.replace(REGEXP_REPLACE_SLASHES, '/');
|
|
11
|
+
}
|
package/bin/npx
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env bash
|
|
2
|
-
|
|
3
|
-
# Runs `npx` through Yarn or pnpm if necessary so that the environment variables are set up similarly across
|
|
4
|
-
# Yarn, pnpm and npm.
|
|
5
|
-
|
|
6
|
-
# shellcheck disable=SC2154
|
|
7
|
-
if [[ "$npm_config_user_agent" =~ yarn ]] && [ -x "$(command -v yarn)" ]; then
|
|
8
|
-
yarn exec -- npx "$@"
|
|
9
|
-
elif [[ "$npm_config_user_agent" =~ pnpm ]] && [ -x "$(command -v pnpm)" ]; then
|
|
10
|
-
pnpm exec -- npx "$@"
|
|
11
|
-
else
|
|
12
|
-
npx "$@"
|
|
13
|
-
fi
|
package/jest-preset-scripts.js
DELETED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|