pake-cli 3.2.15 → 3.2.16
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/README.md +321 -307
- package/dist/cli.js +200 -21
- package/package.json +1 -1
- package/src-tauri/capabilities/default.json +2 -1
- package/src-tauri/src/app/invoke.rs +27 -7
- package/src-tauri/src/inject/event.js +524 -20
- package/src-tauri/src/util.rs +35 -18
- package/src-tauri/tauri.macos.conf.json +0 -1
package/dist/cli.js
CHANGED
|
@@ -22,7 +22,7 @@ import sharp from 'sharp';
|
|
|
22
22
|
import * as psl from 'psl';
|
|
23
23
|
|
|
24
24
|
var name = "pake-cli";
|
|
25
|
-
var version = "3.2.
|
|
25
|
+
var version = "3.2.16";
|
|
26
26
|
var description = "🤱🏻 Turn any webpage into a desktop app with Rust. 🤱🏻 利用 Rust 轻松构建轻量级多端桌面应用。";
|
|
27
27
|
var engines = {
|
|
28
28
|
node: ">=16.0.0"
|
|
@@ -435,9 +435,19 @@ StartupNotify=true
|
|
|
435
435
|
tauriConf.bundle.linux.deb.files = {
|
|
436
436
|
[`/usr/share/applications/${desktopFileName}`]: `assets/${desktopFileName}`,
|
|
437
437
|
};
|
|
438
|
-
const validTargets = [
|
|
438
|
+
const validTargets = [
|
|
439
|
+
'deb',
|
|
440
|
+
'appimage',
|
|
441
|
+
'rpm',
|
|
442
|
+
'deb-arm64',
|
|
443
|
+
'appimage-arm64',
|
|
444
|
+
'rpm-arm64',
|
|
445
|
+
];
|
|
446
|
+
const baseTarget = options.targets.includes('-arm64')
|
|
447
|
+
? options.targets.replace('-arm64', '')
|
|
448
|
+
: options.targets;
|
|
439
449
|
if (validTargets.includes(options.targets)) {
|
|
440
|
-
tauriConf.bundle.targets = [
|
|
450
|
+
tauriConf.bundle.targets = [baseTarget];
|
|
441
451
|
}
|
|
442
452
|
else {
|
|
443
453
|
logger.warn(`✼ The target must be one of ${validTargets.join(', ')}, the default 'deb' will be used.`);
|
|
@@ -709,33 +719,46 @@ class BaseBuilder {
|
|
|
709
719
|
class MacBuilder extends BaseBuilder {
|
|
710
720
|
constructor(options) {
|
|
711
721
|
super(options);
|
|
722
|
+
// Store the original targets value for architecture selection
|
|
723
|
+
this.buildArch = options.targets || 'auto';
|
|
712
724
|
// Use DMG by default for distribution
|
|
713
725
|
// Only create app bundles for testing to avoid user interaction
|
|
714
726
|
if (process.env.PAKE_CREATE_APP === '1') {
|
|
715
|
-
this.
|
|
727
|
+
this.buildFormat = 'app';
|
|
716
728
|
}
|
|
717
729
|
else {
|
|
718
|
-
this.
|
|
730
|
+
this.buildFormat = 'dmg';
|
|
719
731
|
}
|
|
732
|
+
// Set targets to format for Tauri
|
|
733
|
+
this.options.targets = this.buildFormat;
|
|
720
734
|
}
|
|
721
735
|
getFileName() {
|
|
722
736
|
const { name } = this.options;
|
|
723
737
|
// For app bundles, use simple name without version/arch
|
|
724
|
-
if (this.
|
|
738
|
+
if (this.buildFormat === 'app') {
|
|
725
739
|
return name;
|
|
726
740
|
}
|
|
727
741
|
// For DMG files, use versioned filename
|
|
728
742
|
let arch;
|
|
729
|
-
if (this.options.multiArch) {
|
|
743
|
+
if (this.buildArch === 'universal' || this.options.multiArch) {
|
|
730
744
|
arch = 'universal';
|
|
731
745
|
}
|
|
746
|
+
else if (this.buildArch === 'apple') {
|
|
747
|
+
arch = 'aarch64';
|
|
748
|
+
}
|
|
749
|
+
else if (this.buildArch === 'intel') {
|
|
750
|
+
arch = 'x64';
|
|
751
|
+
}
|
|
732
752
|
else {
|
|
753
|
+
// Auto-detect based on current architecture
|
|
733
754
|
arch = process.arch === 'arm64' ? 'aarch64' : process.arch;
|
|
734
755
|
}
|
|
735
756
|
return `${name}_${tauriConfig.version}_${arch}`;
|
|
736
757
|
}
|
|
737
758
|
getBuildCommand() {
|
|
738
|
-
if
|
|
759
|
+
// Determine if we need universal build
|
|
760
|
+
const needsUniversal = this.buildArch === 'universal' || this.options.multiArch;
|
|
761
|
+
if (needsUniversal) {
|
|
739
762
|
const baseCommand = this.options.debug
|
|
740
763
|
? 'npm run tauri build -- --debug'
|
|
741
764
|
: 'npm run tauri build --';
|
|
@@ -754,38 +777,171 @@ class MacBuilder extends BaseBuilder {
|
|
|
754
777
|
}
|
|
755
778
|
return fullCommand;
|
|
756
779
|
}
|
|
780
|
+
else if (this.buildArch === 'apple') {
|
|
781
|
+
// Build for Apple Silicon only
|
|
782
|
+
const baseCommand = this.options.debug
|
|
783
|
+
? 'npm run tauri build -- --debug'
|
|
784
|
+
: 'npm run tauri build --';
|
|
785
|
+
const configPath = path.join('src-tauri', '.pake', 'tauri.conf.json');
|
|
786
|
+
let fullCommand = `${baseCommand} --target aarch64-apple-darwin -c "${configPath}"`;
|
|
787
|
+
// Add features
|
|
788
|
+
const features = ['cli-build'];
|
|
789
|
+
const macOSVersion = this.getMacOSMajorVersion();
|
|
790
|
+
if (macOSVersion >= 23) {
|
|
791
|
+
features.push('macos-proxy');
|
|
792
|
+
}
|
|
793
|
+
if (features.length > 0) {
|
|
794
|
+
fullCommand += ` --features ${features.join(',')}`;
|
|
795
|
+
}
|
|
796
|
+
return fullCommand;
|
|
797
|
+
}
|
|
798
|
+
else if (this.buildArch === 'intel') {
|
|
799
|
+
// Build for Intel only
|
|
800
|
+
const baseCommand = this.options.debug
|
|
801
|
+
? 'npm run tauri build -- --debug'
|
|
802
|
+
: 'npm run tauri build --';
|
|
803
|
+
const configPath = path.join('src-tauri', '.pake', 'tauri.conf.json');
|
|
804
|
+
let fullCommand = `${baseCommand} --target x86_64-apple-darwin -c "${configPath}"`;
|
|
805
|
+
// Add features
|
|
806
|
+
const features = ['cli-build'];
|
|
807
|
+
const macOSVersion = this.getMacOSMajorVersion();
|
|
808
|
+
if (macOSVersion >= 23) {
|
|
809
|
+
features.push('macos-proxy');
|
|
810
|
+
}
|
|
811
|
+
if (features.length > 0) {
|
|
812
|
+
fullCommand += ` --features ${features.join(',')}`;
|
|
813
|
+
}
|
|
814
|
+
return fullCommand;
|
|
815
|
+
}
|
|
757
816
|
return super.getBuildCommand();
|
|
758
817
|
}
|
|
759
818
|
getBasePath() {
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
819
|
+
const needsUniversal = this.buildArch === 'universal' || this.options.multiArch;
|
|
820
|
+
const basePath = this.options.debug ? 'debug' : 'release';
|
|
821
|
+
if (needsUniversal) {
|
|
822
|
+
return `src-tauri/target/universal-apple-darwin/${basePath}/bundle`;
|
|
823
|
+
}
|
|
824
|
+
else if (this.buildArch === 'apple') {
|
|
825
|
+
return `src-tauri/target/aarch64-apple-darwin/${basePath}/bundle`;
|
|
826
|
+
}
|
|
827
|
+
else if (this.buildArch === 'intel') {
|
|
828
|
+
return `src-tauri/target/x86_64-apple-darwin/${basePath}/bundle`;
|
|
829
|
+
}
|
|
830
|
+
return super.getBasePath();
|
|
763
831
|
}
|
|
764
832
|
}
|
|
765
833
|
|
|
766
834
|
class WinBuilder extends BaseBuilder {
|
|
767
835
|
constructor(options) {
|
|
768
836
|
super(options);
|
|
769
|
-
this.
|
|
837
|
+
this.buildFormat = 'msi';
|
|
838
|
+
// Store the original targets value for architecture selection
|
|
839
|
+
this.buildArch = options.targets || 'auto';
|
|
840
|
+
// Set targets to msi format for Tauri
|
|
841
|
+
this.options.targets = this.buildFormat;
|
|
770
842
|
}
|
|
771
843
|
getFileName() {
|
|
772
844
|
const { name } = this.options;
|
|
773
|
-
const { arch } = process;
|
|
774
845
|
const language = tauriConfig.bundle.windows.wix.language[0];
|
|
775
|
-
|
|
846
|
+
// Determine architecture name based on explicit targets option or auto-detect
|
|
847
|
+
let targetArch;
|
|
848
|
+
if (this.buildArch === 'arm64') {
|
|
849
|
+
targetArch = 'aarch64';
|
|
850
|
+
}
|
|
851
|
+
else if (this.buildArch === 'x64') {
|
|
852
|
+
targetArch = 'x64';
|
|
853
|
+
}
|
|
854
|
+
else {
|
|
855
|
+
// Auto-detect based on current architecture if no explicit target
|
|
856
|
+
const archMap = {
|
|
857
|
+
x64: 'x64',
|
|
858
|
+
arm64: 'aarch64',
|
|
859
|
+
};
|
|
860
|
+
targetArch = archMap[process.arch] || process.arch;
|
|
861
|
+
}
|
|
862
|
+
return `${name}_${tauriConfig.version}_${targetArch}_${language}`;
|
|
863
|
+
}
|
|
864
|
+
getBuildCommand() {
|
|
865
|
+
const baseCommand = this.options.debug
|
|
866
|
+
? 'npm run build:debug'
|
|
867
|
+
: 'npm run build';
|
|
868
|
+
// Use temporary config directory to avoid modifying source files
|
|
869
|
+
const configPath = path.join('src-tauri', '.pake', 'tauri.conf.json');
|
|
870
|
+
let fullCommand = `${baseCommand} -- -c "${configPath}"`;
|
|
871
|
+
// Determine build target based on explicit targets option or auto-detect
|
|
872
|
+
let buildTarget;
|
|
873
|
+
if (this.buildArch === 'arm64') {
|
|
874
|
+
buildTarget = 'aarch64-pc-windows-msvc';
|
|
875
|
+
}
|
|
876
|
+
else if (this.buildArch === 'x64') {
|
|
877
|
+
buildTarget = 'x86_64-pc-windows-msvc';
|
|
878
|
+
}
|
|
879
|
+
else {
|
|
880
|
+
// Auto-detect based on current architecture if no explicit target
|
|
881
|
+
buildTarget =
|
|
882
|
+
process.arch === 'arm64'
|
|
883
|
+
? 'aarch64-pc-windows-msvc'
|
|
884
|
+
: 'x86_64-pc-windows-msvc';
|
|
885
|
+
}
|
|
886
|
+
fullCommand += ` --target ${buildTarget}`;
|
|
887
|
+
// Add features
|
|
888
|
+
const features = ['cli-build'];
|
|
889
|
+
if (features.length > 0) {
|
|
890
|
+
fullCommand += ` --features ${features.join(',')}`;
|
|
891
|
+
}
|
|
892
|
+
return fullCommand;
|
|
893
|
+
}
|
|
894
|
+
getBasePath() {
|
|
895
|
+
const basePath = this.options.debug ? 'debug' : 'release';
|
|
896
|
+
// Determine target based on explicit targets option or auto-detect
|
|
897
|
+
let target;
|
|
898
|
+
if (this.buildArch === 'arm64') {
|
|
899
|
+
target = 'aarch64-pc-windows-msvc';
|
|
900
|
+
}
|
|
901
|
+
else if (this.buildArch === 'x64') {
|
|
902
|
+
target = 'x86_64-pc-windows-msvc';
|
|
903
|
+
}
|
|
904
|
+
else {
|
|
905
|
+
// Auto-detect based on current architecture if no explicit target
|
|
906
|
+
target =
|
|
907
|
+
process.arch === 'arm64'
|
|
908
|
+
? 'aarch64-pc-windows-msvc'
|
|
909
|
+
: 'x86_64-pc-windows-msvc';
|
|
910
|
+
}
|
|
911
|
+
return `src-tauri/target/${target}/${basePath}/bundle/`;
|
|
776
912
|
}
|
|
777
913
|
}
|
|
778
914
|
|
|
779
915
|
class LinuxBuilder extends BaseBuilder {
|
|
780
916
|
constructor(options) {
|
|
781
917
|
super(options);
|
|
918
|
+
// Parse target format and architecture
|
|
919
|
+
const target = options.targets || 'deb';
|
|
920
|
+
if (target.includes('-arm64')) {
|
|
921
|
+
this.buildFormat = target.replace('-arm64', '');
|
|
922
|
+
this.buildArch = 'arm64';
|
|
923
|
+
}
|
|
924
|
+
else {
|
|
925
|
+
this.buildFormat = target;
|
|
926
|
+
this.buildArch = 'auto';
|
|
927
|
+
}
|
|
928
|
+
// Set targets to format for Tauri
|
|
929
|
+
this.options.targets = this.buildFormat;
|
|
782
930
|
}
|
|
783
931
|
getFileName() {
|
|
784
932
|
const { name, targets } = this.options;
|
|
785
933
|
const version = tauriConfig.version;
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
|
|
934
|
+
// Determine architecture based on explicit target or auto-detect
|
|
935
|
+
let arch;
|
|
936
|
+
if (this.buildArch === 'arm64') {
|
|
937
|
+
arch = targets === 'rpm' || targets === 'appimage' ? 'aarch64' : 'arm64';
|
|
938
|
+
}
|
|
939
|
+
else {
|
|
940
|
+
// Auto-detect or default to current architecture
|
|
941
|
+
arch = process.arch === 'x64' ? 'amd64' : process.arch;
|
|
942
|
+
if (arch === 'arm64' && (targets === 'rpm' || targets === 'appimage')) {
|
|
943
|
+
arch = 'aarch64';
|
|
944
|
+
}
|
|
789
945
|
}
|
|
790
946
|
// The RPM format uses different separators and version number formats
|
|
791
947
|
if (targets === 'rpm') {
|
|
@@ -802,6 +958,31 @@ class LinuxBuilder extends BaseBuilder {
|
|
|
802
958
|
}
|
|
803
959
|
}
|
|
804
960
|
}
|
|
961
|
+
getBuildCommand() {
|
|
962
|
+
const baseCommand = this.options.debug
|
|
963
|
+
? 'npm run build:debug'
|
|
964
|
+
: 'npm run build';
|
|
965
|
+
// Use temporary config directory to avoid modifying source files
|
|
966
|
+
const configPath = path.join('src-tauri', '.pake', 'tauri.conf.json');
|
|
967
|
+
let fullCommand = `${baseCommand} -- -c "${configPath}"`;
|
|
968
|
+
// Add ARM64 target if explicitly specified
|
|
969
|
+
if (this.buildArch === 'arm64') {
|
|
970
|
+
fullCommand += ' --target aarch64-unknown-linux-gnu';
|
|
971
|
+
}
|
|
972
|
+
// Add features
|
|
973
|
+
const features = ['cli-build'];
|
|
974
|
+
if (features.length > 0) {
|
|
975
|
+
fullCommand += ` --features ${features.join(',')}`;
|
|
976
|
+
}
|
|
977
|
+
return fullCommand;
|
|
978
|
+
}
|
|
979
|
+
getBasePath() {
|
|
980
|
+
const basePath = this.options.debug ? 'debug' : 'release';
|
|
981
|
+
if (this.buildArch === 'arm64') {
|
|
982
|
+
return `src-tauri/target/aarch64-unknown-linux-gnu/${basePath}/bundle/`;
|
|
983
|
+
}
|
|
984
|
+
return super.getBasePath();
|
|
985
|
+
}
|
|
805
986
|
getFileType(target) {
|
|
806
987
|
if (target === 'appimage') {
|
|
807
988
|
return 'AppImage';
|
|
@@ -1068,7 +1249,7 @@ async function tryGetFavicon(url, appName) {
|
|
|
1068
1249
|
continue;
|
|
1069
1250
|
}
|
|
1070
1251
|
}
|
|
1071
|
-
spinner.warn(
|
|
1252
|
+
spinner.warn(`No favicon found for ${domain}. Using default.`);
|
|
1072
1253
|
return null;
|
|
1073
1254
|
}
|
|
1074
1255
|
catch (error) {
|
|
@@ -1271,9 +1452,7 @@ program
|
|
|
1271
1452
|
.addOption(new Option('--user-agent <string>', 'Custom user agent')
|
|
1272
1453
|
.default(DEFAULT_PAKE_OPTIONS.userAgent)
|
|
1273
1454
|
.hideHelp())
|
|
1274
|
-
.addOption(new Option('--targets <string>', '
|
|
1275
|
-
.default(DEFAULT_PAKE_OPTIONS.targets)
|
|
1276
|
-
.hideHelp())
|
|
1455
|
+
.addOption(new Option('--targets <string>', 'Build target: Linux: "deb", "rpm", "appimage", "deb-arm64", "rpm-arm64", "appimage-arm64"; Windows: "x64", "arm64"; macOS: "intel", "apple", "universal"').default(DEFAULT_PAKE_OPTIONS.targets))
|
|
1277
1456
|
.addOption(new Option('--app-version <string>', 'App version, the same as package.json version')
|
|
1278
1457
|
.default(DEFAULT_PAKE_OPTIONS.appVersion)
|
|
1279
1458
|
.hideHelp())
|
package/package.json
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
use crate::util::{check_file_or_append,
|
|
1
|
+
use crate::util::{check_file_or_append, get_download_message_with_lang, show_toast, MessageType};
|
|
2
2
|
use std::fs::{self, File};
|
|
3
3
|
use std::io::Write;
|
|
4
4
|
use std::str::FromStr;
|
|
@@ -10,12 +10,14 @@ use tauri_plugin_http::reqwest::{ClientBuilder, Request};
|
|
|
10
10
|
pub struct DownloadFileParams {
|
|
11
11
|
url: String,
|
|
12
12
|
filename: String,
|
|
13
|
+
language: Option<String>,
|
|
13
14
|
}
|
|
14
15
|
|
|
15
16
|
#[derive(serde::Deserialize)]
|
|
16
17
|
pub struct BinaryDownloadParams {
|
|
17
18
|
filename: String,
|
|
18
19
|
binary: Vec<u8>,
|
|
20
|
+
language: Option<String>,
|
|
19
21
|
}
|
|
20
22
|
|
|
21
23
|
#[derive(serde::Deserialize)]
|
|
@@ -28,7 +30,10 @@ pub struct NotificationParams {
|
|
|
28
30
|
#[command]
|
|
29
31
|
pub async fn download_file(app: AppHandle, params: DownloadFileParams) -> Result<(), String> {
|
|
30
32
|
let window: WebviewWindow = app.get_webview_window("pake").unwrap();
|
|
31
|
-
show_toast(
|
|
33
|
+
show_toast(
|
|
34
|
+
&window,
|
|
35
|
+
&get_download_message_with_lang(MessageType::Start, params.language.clone()),
|
|
36
|
+
);
|
|
32
37
|
|
|
33
38
|
let output_path = app.path().download_dir().unwrap().join(params.filename);
|
|
34
39
|
let file_path = check_file_or_append(output_path.to_str().unwrap());
|
|
@@ -47,11 +52,17 @@ pub async fn download_file(app: AppHandle, params: DownloadFileParams) -> Result
|
|
|
47
52
|
|
|
48
53
|
let mut file = File::create(file_path).unwrap();
|
|
49
54
|
file.write_all(&bytes).unwrap();
|
|
50
|
-
show_toast(
|
|
55
|
+
show_toast(
|
|
56
|
+
&window,
|
|
57
|
+
&get_download_message_with_lang(MessageType::Success, params.language.clone()),
|
|
58
|
+
);
|
|
51
59
|
Ok(())
|
|
52
60
|
}
|
|
53
61
|
Err(e) => {
|
|
54
|
-
show_toast(
|
|
62
|
+
show_toast(
|
|
63
|
+
&window,
|
|
64
|
+
&get_download_message_with_lang(MessageType::Failure, params.language),
|
|
65
|
+
);
|
|
55
66
|
Err(e.to_string())
|
|
56
67
|
}
|
|
57
68
|
}
|
|
@@ -63,17 +74,26 @@ pub async fn download_file_by_binary(
|
|
|
63
74
|
params: BinaryDownloadParams,
|
|
64
75
|
) -> Result<(), String> {
|
|
65
76
|
let window: WebviewWindow = app.get_webview_window("pake").unwrap();
|
|
66
|
-
show_toast(
|
|
77
|
+
show_toast(
|
|
78
|
+
&window,
|
|
79
|
+
&get_download_message_with_lang(MessageType::Start, params.language.clone()),
|
|
80
|
+
);
|
|
67
81
|
let output_path = app.path().download_dir().unwrap().join(params.filename);
|
|
68
82
|
let file_path = check_file_or_append(output_path.to_str().unwrap());
|
|
69
83
|
let download_file_result = fs::write(file_path, ¶ms.binary);
|
|
70
84
|
match download_file_result {
|
|
71
85
|
Ok(_) => {
|
|
72
|
-
show_toast(
|
|
86
|
+
show_toast(
|
|
87
|
+
&window,
|
|
88
|
+
&get_download_message_with_lang(MessageType::Success, params.language.clone()),
|
|
89
|
+
);
|
|
73
90
|
Ok(())
|
|
74
91
|
}
|
|
75
92
|
Err(e) => {
|
|
76
|
-
show_toast(
|
|
93
|
+
show_toast(
|
|
94
|
+
&window,
|
|
95
|
+
&get_download_message_with_lang(MessageType::Failure, params.language),
|
|
96
|
+
);
|
|
77
97
|
Err(e.to_string())
|
|
78
98
|
}
|
|
79
99
|
}
|