@absolutejs/absolute 0.20.0-beta.41 → 0.20.0-beta.42

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.
@@ -6090,6 +6090,57 @@ var expoAppConfig = (config) => ({
6090
6090
  version: config.iosVersion ?? "0.1.0"
6091
6091
  }
6092
6092
  });
6093
+ var expoDynamicAppConfig = `${EXPO_GENERATED_HEADER}const config = require('./app.json');
6094
+
6095
+ if (process.env.ABSOLUTE_EXPO_DEVELOPMENT === '1' && process.env.ABSOLUTE_EXPO_DEVELOPMENT_CA_PATH) {
6096
+ config.expo.plugins = [
6097
+ ...config.expo.plugins,
6098
+ './plugins/withAbsoluteDevelopmentCa'
6099
+ ];
6100
+ }
6101
+
6102
+ module.exports = config;
6103
+ `;
6104
+ var expoDevelopmentCaPlugin = `${EXPO_GENERATED_HEADER}const { AndroidConfig, withAndroidManifest, withDangerousMod } = require('expo/config-plugins');
6105
+ const { copyFile, mkdir } = require('node:fs/promises');
6106
+ const path = require('node:path');
6107
+
6108
+ const NETWORK_CONFIG = [
6109
+ '<?xml version="1.0" encoding="utf-8"?>',
6110
+ '<network-security-config>',
6111
+ ' <debug-overrides>',
6112
+ ' <trust-anchors>',
6113
+ ' <certificates src="@raw/absolutejs_dev_ca" />',
6114
+ ' </trust-anchors>',
6115
+ ' </debug-overrides>',
6116
+ '</network-security-config>',
6117
+ ''
6118
+ ].join('\\n');
6119
+
6120
+ const withAbsoluteDevelopmentCa = config => {
6121
+ config = withAndroidManifest(config, value => {
6122
+ const application = AndroidConfig.Manifest.getMainApplicationOrThrow(value.modResults);
6123
+ application.$['android:networkSecurityConfig'] = '@xml/absolutejs_dev_network_security';
6124
+ return value;
6125
+ });
6126
+ return withDangerousMod(config, ['android', async value => {
6127
+ const certificate = process.env.ABSOLUTE_EXPO_DEVELOPMENT_CA_PATH;
6128
+ if (!certificate) throw new Error('AbsoluteJS Expo HTTPS development requires its development CA path.');
6129
+ const resources = path.join(value.modRequest.platformProjectRoot, 'app', 'src', 'main', 'res');
6130
+ await Promise.all([
6131
+ mkdir(path.join(resources, 'raw'), { recursive: true }),
6132
+ mkdir(path.join(resources, 'xml'), { recursive: true })
6133
+ ]);
6134
+ await Promise.all([
6135
+ copyFile(certificate, path.join(resources, 'raw', 'absolutejs_dev_ca.pem')),
6136
+ require('node:fs/promises').writeFile(path.join(resources, 'xml', 'absolutejs_dev_network_security.xml'), NETWORK_CONFIG)
6137
+ ]);
6138
+ return value;
6139
+ }]);
6140
+ };
6141
+
6142
+ module.exports = withAbsoluteDevelopmentCa;
6143
+ `;
6093
6144
  var metroConfig = (projectRoot) => `${EXPO_GENERATED_HEADER}const { getDefaultConfig } = require('expo/metro-config');
6094
6145
  const path = require('node:path');
6095
6146
 
@@ -6433,8 +6484,13 @@ node_modules/
6433
6484
  `
6434
6485
  ],
6435
6486
  [join14(project, "app.json"), jsonSource(expoAppConfig(config))],
6487
+ [join14(project, "app.config.js"), expoDynamicAppConfig],
6436
6488
  [join14(project, "package.json"), jsonSource(expoPackage())],
6437
6489
  [join14(project, "metro.config.js"), metroConfig(projectRoot)],
6490
+ [
6491
+ join14(project, "plugins", "withAbsoluteDevelopmentCa.js"),
6492
+ expoDevelopmentCaPlugin
6493
+ ],
6438
6494
  [
6439
6495
  join14(project, "tsconfig.json"),
6440
6496
  jsonSource(expoTsConfig(projectRoot, project))
@@ -6960,6 +7016,9 @@ var METRO_READY_TIMEOUT_MS = 60000;
6960
7016
  var PROCESS_CLOSE_TIMEOUT_MS = 2000;
6961
7017
  var commandEnvironment = (options) => ({
6962
7018
  ABSOLUTE_EXPO_DEVELOPMENT: "1",
7019
+ ...options.certificateAuthorityPath ? {
7020
+ ABSOLUTE_EXPO_DEVELOPMENT_CA_PATH: options.certificateAuthorityPath
7021
+ } : {},
6963
7022
  ...options.androidOrigin ? { EXPO_PUBLIC_ABSOLUTE_DEV_ANDROID_ORIGIN: options.androidOrigin } : {},
6964
7023
  ...options.iosOrigin ? { EXPO_PUBLIC_ABSOLUTE_DEV_IOS_ORIGIN: options.iosOrigin } : {}
6965
7024
  });
@@ -6977,6 +7036,9 @@ var planAbsoluteExpoDevSession = (config, options) => {
6977
7036
  throw new TypeError("The Expo development controller requires Expo.");
6978
7037
  if (options.platforms.length === 0)
6979
7038
  throw new TypeError("Expo development requires a local target platform.");
7039
+ const secureOrigin = [options.androidOrigin, options.iosOrigin].some((origin) => origin && new URL(origin).protocol === "https:");
7040
+ if (secureOrigin && !options.certificateAuthorityPath)
7041
+ throw new TypeError("Expo HTTPS development requires the AbsoluteJS development CA certificate.");
6980
7042
  const env = commandEnvironment(options);
6981
7043
  const metro = {
6982
7044
  args: [
@@ -7066,6 +7128,21 @@ var waitForExit = (process2) => new Promise((resolve14) => {
7066
7128
  }
7067
7129
  process2.once("exit", (code) => resolve14(code ?? 1));
7068
7130
  });
7131
+ var runUtilityCommand = async (run, command, args, options) => {
7132
+ const child = run(command, args, {
7133
+ cwd: options.cwd,
7134
+ env: process.env,
7135
+ stdio: ["ignore", "pipe", "pipe"]
7136
+ });
7137
+ forwardLines(child, options.log);
7138
+ const abort = () => void stopProcess(child);
7139
+ options.signal?.addEventListener("abort", abort, { once: true });
7140
+ const exitCode = await waitForExit(child);
7141
+ options.signal?.removeEventListener("abort", abort);
7142
+ if (options.signal?.aborted)
7143
+ throw abortError();
7144
+ return exitCode;
7145
+ };
7069
7146
  var startAbsoluteExpoDevSession = async (options) => {
7070
7147
  const plan = planAbsoluteExpoDevSession(options.config, options);
7071
7148
  const executable = options.executable ?? await absoluteExpoExecutable(plan.project);
@@ -7074,6 +7151,16 @@ var startAbsoluteExpoDevSession = async (options) => {
7074
7151
  return;
7075
7152
  });
7076
7153
  const timings = {};
7154
+ let caEnrollmentServer = null;
7155
+ const closeEnrollmentServer = async () => {
7156
+ const server = caEnrollmentServer;
7157
+ caEnrollmentServer = null;
7158
+ await server?.close();
7159
+ };
7160
+ const publishTiming = (phase, durationMs) => {
7161
+ timings[phase] = (timings[phase] ?? 0) + durationMs;
7162
+ options.onPhaseTiming?.({ durationMs, phase });
7163
+ };
7077
7164
  const setState = (state) => {
7078
7165
  options.onStateChange?.(state);
7079
7166
  };
@@ -7174,6 +7261,30 @@ var startAbsoluteExpoDevSession = async (options) => {
7174
7261
  if (exitCode !== 0) {
7175
7262
  throw new Error(`Expo ${platform} development build exited with status ${exitCode}.`);
7176
7263
  }
7264
+ if (platform === "ios" && options.certificateAuthorityPath && options.iosOrigin && new URL(options.iosOrigin).protocol === "https:" && !options.iosDevice) {
7265
+ setState("enrolling-trust");
7266
+ const trustStarted = performance.now();
7267
+ const utilityOptions = {
7268
+ cwd: plan.project,
7269
+ signal: options.signal,
7270
+ log: (line) => line && log(`[ios-trust] ${line}`)
7271
+ };
7272
+ const trustExit = await runUtilityCommand(run, "xcrun", [
7273
+ "simctl",
7274
+ "keychain",
7275
+ "booted",
7276
+ "add-root-cert",
7277
+ options.certificateAuthorityPath
7278
+ ], utilityOptions);
7279
+ if (trustExit !== 0)
7280
+ throw new Error(`Expo iOS Simulator development CA trust exited with status ${trustExit}.`);
7281
+ await runUtilityCommand(run, "xcrun", ["simctl", "terminate", "booted", options.config.appId], utilityOptions);
7282
+ const launchExit = await runUtilityCommand(run, "xcrun", ["simctl", "launch", "booted", options.config.appId], utilityOptions);
7283
+ if (launchExit !== 0)
7284
+ throw new Error(`Expo iOS Simulator relaunch exited with status ${launchExit}.`);
7285
+ log("Installed the AbsoluteJS development CA into the Expo iOS Simulator and relaunched the app.");
7286
+ publishTiming("enrolling-trust", performance.now() - trustStarted);
7287
+ }
7177
7288
  const durationMs = performance.now() - started;
7178
7289
  timings[state] = durationMs;
7179
7290
  options.onPhaseTiming?.({ durationMs, phase: state });
@@ -7185,7 +7296,22 @@ var startAbsoluteExpoDevSession = async (options) => {
7185
7296
  await runNativeCommand(command);
7186
7297
  await runNativeCommands(remaining);
7187
7298
  };
7299
+ const startPhysicalIosEnrollment = async () => {
7300
+ if (!options.iosDevice || !options.certificateAuthorityPath || !options.iosOrigin || new URL(options.iosOrigin).protocol !== "https:") {
7301
+ return;
7302
+ }
7303
+ setState("enrolling-trust");
7304
+ const trustStarted = performance.now();
7305
+ const startEnrollment = options.startCaEnrollmentServer ?? startAbsoluteIosCaEnrollmentServer;
7306
+ caEnrollmentServer = await startEnrollment({
7307
+ certificateAuthorityPath: options.certificateAuthorityPath,
7308
+ displayHost: new URL(options.iosOrigin).hostname
7309
+ });
7310
+ log(`On the iOS device, open ${caEnrollmentServer.url}, install the AbsoluteJS development CA profile, then enable it under Settings > General > About > Certificate Trust Settings. This public CA endpoint exists only for this dev session.`);
7311
+ publishTiming("enrolling-trust", performance.now() - trustStarted);
7312
+ };
7188
7313
  try {
7314
+ await startPhysicalIosEnrollment();
7189
7315
  await metroPromise;
7190
7316
  const metroMs = performance.now() - metroStarted;
7191
7317
  timings["starting-metro"] = metroMs;
@@ -7202,12 +7328,14 @@ var startAbsoluteExpoDevSession = async (options) => {
7202
7328
  close: async () => {
7203
7329
  options.signal?.removeEventListener("abort", abort);
7204
7330
  await stopProcess(metro);
7331
+ await closeEnrollmentServer();
7205
7332
  setState("closed");
7206
7333
  }
7207
7334
  };
7208
7335
  } catch (error) {
7209
7336
  options.signal?.removeEventListener("abort", abort);
7210
7337
  await stopProcess(metro);
7338
+ await closeEnrollmentServer();
7211
7339
  setState("failed");
7212
7340
  throw error;
7213
7341
  }
@@ -9417,5 +9545,5 @@ export {
9417
9545
  ABSOLUTE_ANDROID_RELEASE_FORMAT
9418
9546
  };
9419
9547
 
9420
- //# debugId=DD3370D585C0D59B64756E2164756E21
9548
+ //# debugId=711828E2D236C77164756E2164756E21
9421
9549
  //# sourceMappingURL=index.js.map