Release!
This commit is contained in:
@@ -1,7 +1,123 @@
|
||||
# Tauri + Vanilla
|
||||
# WVU Medicine Help Alert Web Client
|
||||
|
||||
This template should help get you started developing with Tauri in vanilla HTML, CSS and Javascript.
|
||||
A lightweight Tauri-based desktop wrapper for the WVU Medicine PinPoint HelpAlert duress alarm system. Built to replace the vendor's crashing desktop client with a stable, tray-resident application that brings alerts to the foreground automatically.
|
||||
|
||||
## Recommended IDE Setup
|
||||
## Why This Exists
|
||||
|
||||
- [VS Code](https://code.visualstudio.com/) + [Tauri](https://marketplace.visualstudio.com/items?itemName=tauri-apps.tauri-vscode) + [rust-analyzer](https://marketplace.visualstudio.com/items?itemName=rust-lang.rust-analyzer)
|
||||
The vendor's native desktop client crashes hospital workstations. The web version works but has two problems: users get logged out due to inactivity, and browser notifications don't reliably surface when the tab is backgrounded. This app solves both by wrapping the web client in a persistent Tauri window with native alert detection.
|
||||
|
||||
## How It Works
|
||||
|
||||
1. The app loads PinPoint's web login page in a native webview
|
||||
2. After login, the user clicks "Alerts" to navigate to the HelpAlert GWT page
|
||||
3. Injected JavaScript monitors the DOM every 2 seconds for new alerts (identified by "Claim" buttons and "Elapsed Time" markers)
|
||||
4. When a new alert is detected, the app calls into the Rust backend which unminimizes, focuses, and temporarily pins the window on top
|
||||
5. Closing the window minimizes to the system tray instead of exiting — the app stays running and monitoring
|
||||
|
||||
## Architecture
|
||||
|
||||
- **Frontend:** Vendor's HelpAlert web app loaded directly in the Tauri webview, no custom UI
|
||||
- **Injection:** `src/inject.js` handles `window.open()` interception (alerts page opens in same window instead of a new tab) and DOM-based alert detection
|
||||
- **Backend:** Rust/Tauri handles system tray, window management, and the `alert_detected` command that brings the window to the foreground
|
||||
- **IPC:** JavaScript detects alerts → invokes Tauri command → Rust brings window to front
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- Rust toolchain (`rustup`)
|
||||
- Tauri CLI: `cargo install tauri-cli --version "^2"`
|
||||
- For Windows cross-compilation from Linux: `x86_64-pc-windows-gnu` target
|
||||
- WiX Toolset (for MSI installer generation)
|
||||
|
||||
## WRY Fork Requirement
|
||||
|
||||
This project requires a forked version of [wry](https://github.com/tauri-apps/wry) (Tauri's WebView library). The vendor's HelpAlert page uses GWT (Google Web Toolkit), which declares a global `ipc` variable. WRY also declares `window.ipc` for its IPC bridge, causing a collision that crashes the GWT page.
|
||||
|
||||
The fork renames WRY's `ipc` to `__wry_ipc` in `src/webview2/mod.rs` (line 897), resolving the collision.
|
||||
|
||||
The fork is referenced in `src-tauri/Cargo.toml`:
|
||||
|
||||
```toml
|
||||
[patch.crates-io]
|
||||
wry = { path = "../../wry" }
|
||||
```
|
||||
|
||||
Adjust the path to match your local wry fork location.
|
||||
|
||||
## Building
|
||||
|
||||
### Development
|
||||
|
||||
```bash
|
||||
cargo tauri dev
|
||||
```
|
||||
|
||||
### Release (Windows cross-compile from Linux)
|
||||
|
||||
```bash
|
||||
cargo tauri build -- --target x86_64-pc-windows-gnu
|
||||
```
|
||||
|
||||
The MSI installer will be in `src-tauri/target/x86_64-pc-windows-gnu/release/bundle/msi/`.
|
||||
|
||||
The installer bundles the WebView2 runtime offline, so target machines don't need internet access.
|
||||
|
||||
### Standalone EXE
|
||||
|
||||
The raw `.exe` is also available at `src-tauri/target/x86_64-pc-windows-gnu/release/` but requires WebView2 to already be installed on the target machine.
|
||||
|
||||
## Project Structure
|
||||
|
||||
```
|
||||
duress/
|
||||
├── src/
|
||||
│ ├── index.html # Fallback loading page (shown briefly during startup)
|
||||
│ └── inject.js # Injected JS: window.open intercept + alert detection
|
||||
├── src-tauri/
|
||||
│ ├── Cargo.toml # Rust dependencies (includes wry fork patch)
|
||||
│ ├── tauri.conf.json # App config: name, version, bundling, security
|
||||
│ ├── capabilities/
|
||||
│ │ └── default.json # Tauri v2 permissions and remote domain IPC access
|
||||
│ ├── permissions/
|
||||
│ │ └── alert-detected.toml # Custom command permission
|
||||
│ ├── src/
|
||||
│ │ ├── main.rs # Windows entrypoint
|
||||
│ │ └── lib.rs # App logic: tray, window management, alert_detected command
|
||||
│ └── icons/ # App icons (generated via cargo tauri icon)
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Configuration
|
||||
|
||||
### Adding the vendor URL
|
||||
|
||||
The vendor URL is set in `lib.rs`:
|
||||
|
||||
```rust
|
||||
let url = WebviewUrl::External("https://helpalert.wvumedicine.org".parse().unwrap());
|
||||
```
|
||||
|
||||
### Alert detection tuning
|
||||
|
||||
Alert detection in `inject.js` looks for lines preceding "Geo:" in the page text. If the vendor changes their alert format, update the detection logic in the `setInterval` callback.
|
||||
|
||||
### Polling interval
|
||||
|
||||
The DOM is checked every 2000ms (2 seconds). Adjust the `setInterval` delay in `inject.js` if needed.
|
||||
|
||||
## Deployment Notes
|
||||
|
||||
- Target machines need Windows 10 or 11
|
||||
- The MSI installer includes WebView2 runtime (offline) — no internet required
|
||||
- The app installs per-machine by default
|
||||
- Users should be instructed that closing the window minimizes to tray, and "Quit" in the tray menu is the actual exit
|
||||
|
||||
## Known Limitations
|
||||
|
||||
- Alert detection relies on DOM text parsing ("Geo:" pattern preceding alert names). If the vendor updates their GWT UI significantly, detection may need adjustment.
|
||||
- GWT class names are obfuscated and change between builds, so selectors are text-based rather than class-based.
|
||||
- Session keepalive has not been implemented yet — if the session times out, the user must re-authenticate manually. Testing suggests the session may persist indefinitely while the app is running.
|
||||
- The wry fork must be kept in sync with upstream when updating Tauri.
|
||||
|
||||
## License
|
||||
|
||||
Internal use — WVU Medicine / Racoon City Technologies.
|
||||
Reference in New Issue
Block a user