Skip to main content

Overview

The @unhook/cli package has been enhanced to work seamlessly across all major platforms (macOS, Windows, Linux, ARM/x64) using a hybrid approach that downloads platform-specific binaries during installation.

Architecture

Build System

  • GitHub Actions: Builds binaries for all supported platforms
  • Release Assets: Uploads binaries to GitHub releases with standardized naming
  • Platforms Supported:
    • linux-x64 (glibc)
    • linux-arm64 (glibc)
    • linux-x64-musl (Alpine Linux)
    • linux-arm64-musl (Alpine Linux ARM64)
    • darwin-x64 (macOS Intel)
    • darwin-arm64 (macOS Apple Silicon)
    • win32-x64 (Windows 64-bit)

Installation Flow

1

Package Installation

User runs npm install @unhook/cli
2

Postinstall Hook

scripts/install.cjs executes automatically
3

Platform Detection

Detects OS, architecture, and libc variant (musl vs glibc)
4

Binary Download

Downloads appropriate binary from GitHub releases
5

Installation

Stores binary in ~/.unhook/bin/{version}/ with proper permissions

Runtime Flow

1

Command Execution

User runs unhook [command]
2

Wrapper Execution

bin/cli.cjs wrapper script executes
3

Binary Location

Wrapper detects platform and locates downloaded binary
4

Transparent Execution

Spawns platform-specific binary with user arguments
5

Result Return

Returns binary exit code transparently to user

File Structure

Implementation Details

Platform Detection

The CLI intelligently detects the target platform and architecture:

Binary Naming Convention

Binaries follow this pattern: unhook-{platform}-{arch}[.exe]

macOS Examples

  • unhook-darwin-arm64 (Apple Silicon)
  • unhook-darwin-x64 (Intel)

Linux Examples

  • unhook-linux-x64 (glibc)
  • unhook-linux-x64-musl (Alpine)
  • unhook-linux-arm64 (ARM64 glibc)
  • unhook-linux-arm64-musl (ARM64 Alpine)

Windows Examples

  • unhook-win32-x64.exe (64-bit)

Version Management

  • Binaries are stored in versioned directories: ~/.unhook/bin/{version}/
  • Old versions are automatically cleaned up during installation
  • Multiple versions can coexist temporarily during upgrades

Edge Cases & Robustness

Network Issues

Problem: Users behind corporate firewalls or with poor connectivitySolution:
  • Respect HTTP_PROXY, HTTPS_PROXY environment variables
  • 30-second timeout with clear error messages
  • Graceful fallback with manual install instructions
Problem: Users without write permissions to home directorySolution:
  • Clear error messages with specific instructions
  • Platform-specific guidance (sudo on Linux/macOS, admin on Windows)
  • Alternative installation paths suggested

Platform-Specific Handling

Security (Gatekeeper):
Code Signing: macOS binaries are signed and notarized during CI

CI/CD Environments

Problem: CI systems shouldn’t download binaries during installation Solution:

Testing Strategy

Integration Tests

Comprehensive test suite covering:
  1. Platform Detection: Verify correct platform/arch identification
  2. URL Construction: Ensure proper download URLs
  3. Error Handling: Test failure scenarios
  4. Package Configuration: Validate package.json settings
  5. Platform-Specific Behavior: Test OS-specific features

Test Execution

Troubleshooting

Performance Considerations

One-time Download

Binaries are cached locally after first install

Version Management

Only current version kept, old versions cleaned up

Efficient Detection

Fast platform/arch detection using Node.js APIs

Minimal Overhead

CLI wrapper adds ~10ms startup time

Security Considerations

All security measures are implemented to ensure safe binary distribution:
  • Verified Downloads: Binaries downloaded from official GitHub releases only
  • Code Signing: macOS binaries are signed and notarized
  • No Build Tools Required: Users don’t need compilers or build chains
  • Quarantine Removal: Automatic handling of macOS security restrictions

Future Enhancements

  1. Checksum Verification: Verify binary integrity using SHA checksums
  2. Delta Updates: Only download changed parts of binaries
  3. Mirror Support: Allow alternative download sources
  4. Offline Mode: Bundle common binaries with the package
  5. Auto-updates: Automatic binary updates when package is updated

Contributing

When adding support for new platforms:
1

Update CI

Update the GitHub Actions workflow (.github/workflows/cli-github-release.yml)
2

Add Platform Mapping

Add platform mapping in both install.cjs and cli.cjs
3

Update Documentation

Update documentation and tests
4

Test on Platform

Test on the target platform before releasing

References