Skip to content

machineid is a lightweight Go library that generates a unique, stable, and anonymized identifier for the machine it is running on.

License

Notifications You must be signed in to change notification settings

banditmoscow1337/machineid

Repository files navigation

machineid

machineid is a lightweight Go library that generates a unique, stable, and anonymized identifier for the machine it is running on. It creates a robust ID by querying OS-specific native constructs (SMBIOS, systemd, IORegistry) and falls back to hardware MAC addresses if necessary.

Additionally, machineid detects the environment type (Physical, Virtual Machine, or Container) and prefixes the ID accordingly.

Features

  • Cross-Platform: Support for Windows, Linux, and macOS.

  • Environment Aware: Detects if the application is running in a Docker container, a VM (VMware, VirtualBox, KVM, Hyper-V), or on Physical hardware.

  • Stable & Robust:

  • Windows: Prioritizes the immutable Motherboard UUID (SMBIOS) via native API, falling back to Disk Serial and then Registry UUID.

  • Linux: Uses /etc/machine-id.

  • macOS: Uses IOPlatformUUID.

  • Fallback: Generates a reproducible ID based on physical network interface MAC addresses if OS-specific IDs are unavailable.

  • Privacy Focused: The raw machine ID is hashed (SHA256) before being returned.

  • App Specific: Can generate scoped IDs for specific applications to prevent cross-app tracking.

Installation

go get github.com/banditmoscow1337/machineid

Usage

Get a Machine ID

The ID() function returns the unique ID prefixed with the detected environment type (e.g., physical: or vm:).

package  main

import (
	"log"
	"github.com/banditmoscow1337/machineid"
)

func main() {
	id, err := machineid.ID()
	if  err != nil {
		log.Fatal(err)
	}

	log.Println("Machine ID:", id)
	// Output Example: physical:9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08
}

Get an App-Specific Protected ID

To ensure privacy or separate identities between different applications on the same machine, use ProtectedID. This salts the machine ID with your application's unique string.

func main() {
	appID := "my-awesome-app"
	id, err := machineid.ProtectedID(appID)
	if err != nil {
		log.Fatal(err)
	}

	fmt.Printf("Protected ID for %s: %s\n", appID, id)
}

How it Works

The library attempts to resolve a unique ID using the following priority order per platform:

Windows

SMBIOS UUID: Reads the System Information (Type 1) table from the firmware via the Windows API. This persists even if Windows is re-installed.

Disk Serial: Reads the serial number of the primary disk drive.

Registry: Falls back to HKLM\SOFTWARE\Microsoft\Cryptography\MachineGuid.

Linux

Machine ID: Reads /etc/machine-id (generated by systemd at installation).

Environment Checks: Checks /.dockerenv and cgroups to detect Container/Docker environments.

macOS

IOPlatformUUID: Queries the IOPlatformExpertDevice registry entry.

Fallback (All Platforms)

If the OS-specific method fails (e.g., missing permissions or stripped OS), the library generates a consistent ID by hashing the MAC addresses of all valid physical network interfaces. It automatically ignores loopback adapters and virtual interfaces (Docker, VPNs) to ensure stability.

License

MIT

About

machineid is a lightweight Go library that generates a unique, stable, and anonymized identifier for the machine it is running on.

Topics

Resources

License

Stars

Watchers

Forks

Packages

No packages published

Languages