craft-native 0.0.91 → 0.0.94

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/dist/index.js CHANGED
@@ -17,7 +17,7 @@ var __require = import.meta.require;
17
17
 
18
18
  // src/index.ts
19
19
  import { execFile as execFile2, spawn as spawn4 } from "child_process";
20
- import { mkdtempSync as mkdtempSync3, readFileSync as readFileSync3, writeFileSync as writeFileSync3 } from "fs";
20
+ import { mkdtempSync as mkdtempSync3, writeFileSync as writeFileSync3 } from "fs";
21
21
  import { tmpdir as tmpdir4 } from "os";
22
22
  import { join as join4 } from "path";
23
23
  import { promisify as promisify2 } from "util";
@@ -40,6 +40,7 @@ function resolveCraftBinary(explicit) {
40
40
  }
41
41
  return "craft";
42
42
  }
43
+ var CRAFT_CLI_SPAWN_MARKER = "CRAFT_CLI_SPAWNED_FROM";
43
44
  function craftBinaryNotFoundMessage(triedPath) {
44
45
  return [
45
46
  `Craft native binary not found (tried "${triedPath}").`,
@@ -56,6 +57,11 @@ function craftBinaryNotFoundMessage(triedPath) {
56
57
  ].join(`
57
58
  `);
58
59
  }
60
+ // package.json
61
+ var version = "0.0.94";
62
+
63
+ // src/sdk-version.ts
64
+ var SDK_VERSION = version;
59
65
 
60
66
  // src/package.ts
61
67
  import { spawn } from "child_process";
@@ -183,13 +189,13 @@ async function packageApp(config) {
183
189
  }
184
190
  async function packageMacOS(config, outDir) {
185
191
  const results = [];
186
- const { name, version, bundleId = `com.myapp.${name.toLowerCase()}` } = config;
192
+ const { name, version: version2, bundleId = `com.myapp.${name.toLowerCase()}` } = config;
187
193
  const opts = config.macos || {};
188
194
  const hardenedRuntime = !opts.appStore;
189
195
  const appBundlePath = join(outDir, `${name}.app`);
190
196
  const appBundle = createMacOSAppBundle({
191
197
  name,
192
- version,
198
+ version: version2,
193
199
  bundleId,
194
200
  buildNumber: opts.buildNumber,
195
201
  category: opts.category,
@@ -233,7 +239,7 @@ async function packageMacOS(config, outDir) {
233
239
  }
234
240
  results.push({ success: true, platform: "macos", format: "app", outputPath: appBundlePath });
235
241
  if (opts.dmg !== false) {
236
- const outputPath = join(outDir, `${name}-${version}.dmg`);
242
+ const outputPath = join(outDir, `${name}-${version2}.dmg`);
237
243
  const dmgResult = await createDMG({ appBundlePath, outputPath, volumeName: name });
238
244
  results.push({
239
245
  success: dmgResult.success,
@@ -246,12 +252,12 @@ async function packageMacOS(config, outDir) {
246
252
  results.push(...await notarizeIfRequested(opts, outputPath, "dmg"));
247
253
  }
248
254
  if (opts.pkg || opts.appStore) {
249
- const outputPath = join(outDir, `${name}-${version}.pkg`);
255
+ const outputPath = join(outDir, `${name}-${version2}.pkg`);
250
256
  const pkgResult = await createPKG({
251
257
  appBundlePath,
252
258
  outputPath,
253
259
  identifier: bundleId,
254
- version,
260
+ version: version2,
255
261
  appStore: opts.appStore === true,
256
262
  installerIdentity: opts.installerIdentity
257
263
  });
@@ -297,14 +303,14 @@ async function notarizeIfRequested(opts, artifactPath, format) {
297
303
  }
298
304
  async function packageWindows(config, outDir) {
299
305
  const results = [];
300
- const { name, version } = config;
306
+ const { name, version: version2 } = config;
301
307
  const opts = config.windows || {};
302
308
  if (opts.msi !== false) {
303
309
  const msiResult = await createMSI({
304
310
  name,
305
- version,
311
+ version: version2,
306
312
  binaryPath: config.binaryPath,
307
- outputPath: join(outDir, `${name}-${version}.msi`),
313
+ outputPath: join(outDir, `${name}-${version2}.msi`),
308
314
  manufacturer: config.author || "Unknown",
309
315
  architecture: opts.architecture || windowsArchitecture(process.arch),
310
316
  certificatePath: opts.certificatePath,
@@ -321,9 +327,9 @@ async function packageWindows(config, outDir) {
321
327
  if (opts.zip || opts.msi === false) {
322
328
  const zipResult = await createZIP({
323
329
  name,
324
- version,
330
+ version: version2,
325
331
  binaryPath: config.binaryPath,
326
- outputPath: join(outDir, `${name}-${version}-windows.zip`)
332
+ outputPath: join(outDir, `${name}-${version2}-windows.zip`)
327
333
  });
328
334
  results.push({
329
335
  success: zipResult.success,
@@ -337,14 +343,14 @@ async function packageWindows(config, outDir) {
337
343
  }
338
344
  async function packageLinux(config, outDir) {
339
345
  const results = [];
340
- const { name, version } = config;
346
+ const { name, version: version2 } = config;
341
347
  const opts = config.linux || {};
342
348
  if (opts.deb !== false) {
343
349
  const debResult = await createDEB({
344
350
  name,
345
- version,
351
+ version: version2,
346
352
  binaryPath: config.binaryPath,
347
- outputPath: join(outDir, `${name}_${version}_amd64.deb`),
353
+ outputPath: join(outDir, `${name}_${version2}_amd64.deb`),
348
354
  description: config.description || "",
349
355
  maintainer: config.author || "Unknown",
350
356
  dependencies: opts.debDependencies || ["libgtk-3-0", "libwebkit2gtk-4.1-37"]
@@ -360,9 +366,9 @@ async function packageLinux(config, outDir) {
360
366
  if (opts.rpm) {
361
367
  const rpmResult = await createRPM({
362
368
  name,
363
- version,
369
+ version: version2,
364
370
  binaryPath: config.binaryPath,
365
- outputPath: join(outDir, `${name}-${version}-1.x86_64.rpm`),
371
+ outputPath: join(outDir, `${name}-${version2}-1.x86_64.rpm`),
366
372
  description: config.description || "",
367
373
  requires: opts.rpmDependencies || ["gtk3", "webkit2gtk3"]
368
374
  });
@@ -377,9 +383,9 @@ async function packageLinux(config, outDir) {
377
383
  if (opts.appImage) {
378
384
  const appImageResult = await createAppImage({
379
385
  name,
380
- version,
386
+ version: version2,
381
387
  binaryPath: config.binaryPath,
382
- outputPath: join(outDir, `${name}-${version}-x86_64.AppImage`),
388
+ outputPath: join(outDir, `${name}-${version2}-x86_64.AppImage`),
383
389
  iconPath: config.iconPath
384
390
  });
385
391
  results.push({
@@ -2570,7 +2576,7 @@ class SystemTray {
2570
2576
  }
2571
2577
  async setIcon(icon) {
2572
2578
  this._options.icon = icon;
2573
- await this._call("setIcon", icon);
2579
+ await this._call("setIcon", JSON.stringify({ icon }));
2574
2580
  }
2575
2581
  async setTooltip(tooltip) {
2576
2582
  this._options.tooltip = tooltip;
@@ -2584,6 +2590,9 @@ class SystemTray {
2584
2590
  if (!processedItem.id && processedItem.label) {
2585
2591
  processedItem.id = `menu_${index}_${Date.now()}`;
2586
2592
  }
2593
+ if (!processedItem.action && processedItem.id && processedItem.type !== "separator") {
2594
+ processedItem.action = processedItem.id;
2595
+ }
2587
2596
  if (processedItem.submenu) {
2588
2597
  processedItem.submenu = processItems(processedItem.submenu);
2589
2598
  }
@@ -2646,9 +2655,9 @@ class SystemTray {
2646
2655
  return new Promise((resolve, reject) => {
2647
2656
  try {
2648
2657
  window.webkit.messageHandlers.craft.postMessage({
2649
- type: "tray",
2650
- action,
2651
- data: typeof data === "string" ? data : JSON.stringify(data)
2658
+ t: "tray",
2659
+ a: action,
2660
+ d: typeof data === "string" ? data : JSON.stringify(data)
2652
2661
  });
2653
2662
  resolve(undefined);
2654
2663
  } catch (error) {
@@ -3928,8 +3937,8 @@ var crypto = {
3928
3937
  if (combined.length < 1 + SALT_LEN + IV_LEN + TAG_LEN) {
3929
3938
  throw new CraftCryptoError("Ciphertext too short to be valid");
3930
3939
  }
3931
- const version = combined[0];
3932
- if (version !== FORMAT_VERSION) {
3940
+ const version2 = combined[0];
3941
+ if (version2 !== FORMAT_VERSION) {
3933
3942
  throw new LegacyCiphertextError;
3934
3943
  }
3935
3944
  const salt = combined.slice(1, 1 + SALT_LEN);
@@ -4850,11 +4859,18 @@ var share = {
4850
4859
  return craft.share.share(options);
4851
4860
  }
4852
4861
  if (navigator.share) {
4853
- await navigator.share({
4854
- title: options.title,
4855
- text: options.text,
4856
- url: options.url
4857
- });
4862
+ try {
4863
+ await navigator.share({
4864
+ title: options.title,
4865
+ text: options.text,
4866
+ url: options.url
4867
+ });
4868
+ return true;
4869
+ } catch (error) {
4870
+ if (error instanceof DOMException && error.name === "AbortError")
4871
+ return false;
4872
+ throw error;
4873
+ }
4858
4874
  } else {
4859
4875
  throw new Error("Share API not available");
4860
4876
  }
@@ -4887,6 +4903,13 @@ var lifecycle = {
4887
4903
  return () => document.removeEventListener("visibilitychange", handler);
4888
4904
  }
4889
4905
  };
4906
+ function bridgeNotification(options, now = Date.now()) {
4907
+ const { scheduleAt, ...rest } = options;
4908
+ if (scheduleAt === undefined)
4909
+ return rest;
4910
+ const wait = Math.ceil(scheduleAt - now);
4911
+ return wait > 0 ? { ...rest, delay: wait } : rest;
4912
+ }
4890
4913
  var notifications = {
4891
4914
  async show(options) {
4892
4915
  const craft = getCraftMobile();
@@ -4900,7 +4923,7 @@ var notifications = {
4900
4923
  async schedule(options) {
4901
4924
  const craft = getCraftMobile();
4902
4925
  if (typeof window !== "undefined" && craft?.notifications) {
4903
- return craft.notifications.schedule(options);
4926
+ return craft.notifications.schedule(bridgeNotification(options));
4904
4927
  }
4905
4928
  throw new Error("Scheduled notifications not available in web");
4906
4929
  },
@@ -10576,14 +10599,14 @@ async function updaterCommand(args) {
10576
10599
  switch (subcommand) {
10577
10600
  case "check": {
10578
10601
  const url = rest[0];
10579
- const version = rest[1] || "0.0.0";
10602
+ const version2 = rest[1] || "0.0.0";
10580
10603
  if (!url) {
10581
10604
  console.error("Usage: craft updater check <update-url> [current-version]");
10582
10605
  process.exit(1);
10583
10606
  }
10584
10607
  const updater = new AutoUpdater({
10585
10608
  updateUrl: url,
10586
- currentVersion: version,
10609
+ currentVersion: version2,
10587
10610
  appPath: process.cwd(),
10588
10611
  autoDownload: false
10589
10612
  });
@@ -10617,14 +10640,14 @@ ${update.releaseNotes}`);
10617
10640
  break;
10618
10641
  }
10619
10642
  case "generate-manifest": {
10620
- const version = rest[0];
10643
+ const version2 = rest[0];
10621
10644
  const outputPath = rest[1] || "update.json";
10622
- if (!version) {
10645
+ if (!version2) {
10623
10646
  console.error("Usage: craft updater generate-manifest <version> [output]");
10624
10647
  process.exit(1);
10625
10648
  }
10626
10649
  const manifest = {
10627
- version,
10650
+ version: version2,
10628
10651
  releaseDate: new Date().toISOString(),
10629
10652
  platforms: {}
10630
10653
  };
@@ -10656,21 +10679,13 @@ var updater_default = AutoUpdater;
10656
10679
  // src/index.ts
10657
10680
  var execFileAsync2 = promisify2(execFile2);
10658
10681
  var versionMismatchWarned = false;
10659
- function getSdkVersion() {
10660
- try {
10661
- const pkgPath = join4(import.meta.dir, "..", "package.json");
10662
- return JSON.parse(readFileSync3(pkgPath, "utf-8")).version ?? "unknown";
10663
- } catch {
10664
- return "unknown";
10665
- }
10666
- }
10667
10682
  async function probeBinaryVersion(craftPath) {
10668
10683
  if (versionMismatchWarned)
10669
10684
  return;
10670
10685
  try {
10671
10686
  const { stdout } = await execFileAsync2(craftPath, ["--version"], { timeout: 2000 });
10672
10687
  const nativeVersion = parseCraftVersionOutput(stdout);
10673
- const sdkVersion = getSdkVersion();
10688
+ const sdkVersion = SDK_VERSION;
10674
10689
  if (sdkVersion !== "unknown" && nativeVersion && nativeVersion !== sdkVersion) {
10675
10690
  versionMismatchWarned = true;
10676
10691
  console.warn(`\u26A0\uFE0F Craft binary/SDK version mismatch: SDK=${sdkVersion}, native=${nativeVersion}.
@@ -10680,7 +10695,27 @@ async function probeBinaryVersion(craftPath) {
10680
10695
  }
10681
10696
  function parseCraftVersionOutput(output) {
10682
10697
  const firstLine = output.trim().split(/\r?\n/, 1)[0] ?? "";
10683
- return firstLine.replace(/^craft version\s+/i, "").replace(/^v/, "").trim();
10698
+ const withoutName = firstLine.replace(/^craft(?:\s+version)?[\s/]+/i, "").trim();
10699
+ const firstToken = withoutName.split(/\s+/, 1)[0] ?? "";
10700
+ return firstToken.replace(/^v/, "").trim();
10701
+ }
10702
+ var STDERR_TAIL_LIMIT = 4000;
10703
+ function craftProcessFailedMessage(code, stderr, quiet) {
10704
+ const said = stderr.trim();
10705
+ const header = `\u274C Craft process exited with code ${code}`;
10706
+ if (said)
10707
+ return `${header}
10708
+
10709
+ ${said}`;
10710
+ const where = quiet ? "It wrote nothing to stderr. Re-run without `quiet` to see its full output." : "Check the console output above for more details.";
10711
+ return `${header}
10712
+
10713
+ ` + `This may indicate:
10714
+ ` + ` \u2022 Invalid window configuration
10715
+ ` + ` \u2022 Malformed HTML content
10716
+ ` + ` \u2022 System resource constraints
10717
+
10718
+ ` + where;
10684
10719
  }
10685
10720
  function detectDevMode() {
10686
10721
  if (typeof process === "undefined")
@@ -10743,8 +10778,14 @@ class CraftApp {
10743
10778
  const args = this.buildArgs();
10744
10779
  const craftPath = await this.findCraftBinary();
10745
10780
  probeBinaryVersion(craftPath);
10781
+ const quiet = this.config.quiet === true;
10746
10782
  this.process = spawn4(craftPath, args, {
10747
- stdio: this.config.quiet ? "ignore" : "inherit"
10783
+ stdio: quiet ? ["ignore", "ignore", "pipe"] : "inherit",
10784
+ env: { ...process.env, [CRAFT_CLI_SPAWN_MARKER]: craftPath }
10785
+ });
10786
+ let stderrTail = "";
10787
+ this.process.stderr?.on("data", (chunk) => {
10788
+ stderrTail = (stderrTail + chunk.toString()).slice(-STDERR_TAIL_LIMIT);
10748
10789
  });
10749
10790
  return new Promise((resolve, reject) => {
10750
10791
  this.process?.on("error", (error) => {
@@ -10764,18 +10805,11 @@ class CraftApp {
10764
10805
  ` + `For troubleshooting, visit:
10765
10806
  ` + " https://github.com/home-lang/craft/issues"));
10766
10807
  });
10767
- this.process?.on("exit", (code) => {
10808
+ this.process?.on("close", (code) => {
10768
10809
  if (code === 0 || code === null) {
10769
10810
  resolve();
10770
10811
  } else {
10771
- reject(new Error(`\u274C Craft process exited with code ${code}
10772
-
10773
- ` + `This may indicate:
10774
- ` + ` \u2022 Invalid window configuration
10775
- ` + ` \u2022 Malformed HTML content
10776
- ` + ` \u2022 System resource constraints
10777
-
10778
- ` + "Check the console output above for more details."));
10812
+ reject(new Error(craftProcessFailedMessage(code, stderrTail, quiet)));
10779
10813
  }
10780
10814
  });
10781
10815
  });
@@ -11091,6 +11125,7 @@ export {
11091
11125
  createArcSidebar,
11092
11126
  createApp,
11093
11127
  craftUnavailableMessage,
11128
+ craftProcessFailedMessage,
11094
11129
  craftBinaryNotFoundMessage,
11095
11130
  copy,
11096
11131
  exports_components as components,
@@ -201,7 +201,7 @@ export interface SimulatorDevice {
201
201
  runtime: string;
202
202
  }
203
203
  /**
204
- * Every available simulator, newest runtime first, iPhones before iPads.
204
+ * Every available *iOS* simulator, newest runtime first, iPhones before iPads.
205
205
  *
206
206
  * Exported because the choice is worth testing without a simulator present -
207
207
  * `pickSimulator` is the policy and this is the data it reads.
@@ -559,7 +559,7 @@ async function open(options) {
559
559
  await $`open ${projectPath}`;
560
560
  }
561
561
  function orderSimulators(devices) {
562
- return [...devices].sort((left, right) => {
562
+ return devices.filter((device) => device.runtime.startsWith("iOS")).sort((left, right) => {
563
563
  const booted = Number(right.state === "Booted") - Number(left.state === "Booted");
564
564
  if (booted !== 0)
565
565
  return booted;