@bobfrankston/msger 0.1.325 → 0.1.327
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/index.d.ts +1 -1
- package/index.js +1 -1
- package/msger-native/builder/postinstall.js +14 -0
- package/package.json +1 -1
- package/shower.d.ts +3 -0
- package/shower.js +15 -3
package/index.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export { showMessageBox, showService, ServiceHandle, MessageBoxOptions, MessageBoxResult } from "./shower.js";
|
|
1
|
+
export { showMessageBox, showService, ServiceHandle, MessageBoxOptions, MessageBoxResult, setAppName } from "./shower.js";
|
package/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// Export showMessageBox and types for use as a library
|
|
2
|
-
export { showMessageBox, showService, ServiceHandle } from "./shower.js";
|
|
2
|
+
export { showMessageBox, showService, ServiceHandle, setAppName } from "./shower.js";
|
|
3
3
|
// If run directly (e.g., `node .` or `node index.js`), run the CLI
|
|
4
4
|
// @ts-ignore - import.meta.main is available in Node.js 20+
|
|
5
5
|
if (import.meta.main) {
|
|
@@ -76,6 +76,20 @@ if (fs.existsSync(srcBinary)) {
|
|
|
76
76
|
}
|
|
77
77
|
}
|
|
78
78
|
|
|
79
|
+
// Step 2b: Create/update a stable-name hardlink so the launcher always uses
|
|
80
|
+
// the same path. Taskbar pins and AUMID grouping depend on a fixed exe path.
|
|
81
|
+
// Hardlink shares inode with the timestamped copy — deleting the old link
|
|
82
|
+
// doesn't affect a running process (it holds its own file handle).
|
|
83
|
+
const stableLink = path.join(userBinDir, `${baseName}${ext}`);
|
|
84
|
+
try {
|
|
85
|
+
// Remove old link (may point to previous version)
|
|
86
|
+
try { fs.unlinkSync(stableLink); } catch { /* didn't exist */ }
|
|
87
|
+
fs.linkSync(versionedBinary, stableLink);
|
|
88
|
+
} catch (e) {
|
|
89
|
+
// Hardlink failed (cross-device, locked, etc.) — copy as fallback
|
|
90
|
+
try { fs.copyFileSync(versionedBinary, stableLink); } catch { /* */ }
|
|
91
|
+
}
|
|
92
|
+
|
|
79
93
|
// Step 3a: Clean up old timestamped copies in the user bin dir (keep the one
|
|
80
94
|
// we just created). Locked copies are silently skipped — they get cleaned up
|
|
81
95
|
// on the next install once their owning process has exited.
|
package/package.json
CHANGED
package/shower.d.ts
CHANGED
|
@@ -61,6 +61,9 @@ export interface MessageBoxResult {
|
|
|
61
61
|
autoSize: boolean;
|
|
62
62
|
};
|
|
63
63
|
}
|
|
64
|
+
/** Set the app name used for the per-user binary directory.
|
|
65
|
+
* Call before showService/showMessageBox — e.g. `setAppName("mailx")`. */
|
|
66
|
+
export declare function setAppName(name: string): void;
|
|
64
67
|
/**
|
|
65
68
|
* Show a message box dialog using native Rust implementation (extended version)
|
|
66
69
|
* @param options Message box configuration
|
package/shower.js
CHANGED
|
@@ -53,15 +53,22 @@ export function closeMessageBox(pid) {
|
|
|
53
53
|
* exe inside it is locked. Keeping timestamped copies here means npm only
|
|
54
54
|
* manages the stable `msgernative.exe` (which isn't the one being executed),
|
|
55
55
|
* so it's never locked. */
|
|
56
|
+
/** App name for per-user bin dir. Set via `setAppName()` so each app using
|
|
57
|
+
* msger gets its own binary path (%LOCALAPPDATA%\<appName>\bin\) and thus
|
|
58
|
+
* its own taskbar identity. Defaults to "msger" for standalone use. */
|
|
59
|
+
let _appName = "msger";
|
|
60
|
+
/** Set the app name used for the per-user binary directory.
|
|
61
|
+
* Call before showService/showMessageBox — e.g. `setAppName("mailx")`. */
|
|
62
|
+
export function setAppName(name) { _appName = name; }
|
|
56
63
|
function getUserBinDir() {
|
|
57
64
|
const isWindows = platform() === 'win32';
|
|
58
65
|
if (isWindows) {
|
|
59
66
|
const base = process.env.LOCALAPPDATA || path.join(process.env.USERPROFILE || '.', 'AppData', 'Local');
|
|
60
|
-
return path.join(base,
|
|
67
|
+
return path.join(base, _appName, 'bin');
|
|
61
68
|
}
|
|
62
69
|
const xdg = process.env.XDG_DATA_HOME;
|
|
63
70
|
const base = xdg || path.join(process.env.HOME || '.', '.local', 'share');
|
|
64
|
-
return path.join(base,
|
|
71
|
+
return path.join(base, _appName, 'bin');
|
|
65
72
|
}
|
|
66
73
|
/** Resolve the native binary path. Prefers a timestamped copy in the per-user
|
|
67
74
|
* bin dir (immune to npm-upgrade locks). Falls back to the package's bundled
|
|
@@ -86,8 +93,13 @@ function resolveBinaryPath() {
|
|
|
86
93
|
baseName = 'msgernative';
|
|
87
94
|
ext = '';
|
|
88
95
|
}
|
|
96
|
+
// Prefer the stable-name hardlink in the user dir — same path every time,
|
|
97
|
+
// so taskbar pins and AUMID grouping don't break on updates.
|
|
98
|
+
const stableLink = path.join(userBinDir, `${baseName}${ext}`);
|
|
99
|
+
if (fs.existsSync(stableLink))
|
|
100
|
+
return stableLink;
|
|
89
101
|
const pattern = new RegExp(`^${baseName.replace(/[.*+?^${}()|[\]\\]/g, '\\$&')}-(\\d+)${ext.replace('.', '\\.')}$`);
|
|
90
|
-
//
|
|
102
|
+
// Fallback: per-user timestamped copy (pre-hardlink installs)
|
|
91
103
|
try {
|
|
92
104
|
const matches = fs.readdirSync(userBinDir)
|
|
93
105
|
.filter(f => pattern.test(f))
|