OverviewFilesCommitsIssuesDocsReleasesPeers

mirall-cli / node_modules / hyper-svc / lib / uds-backend.js

43 lines · javascript ref:
/**
 * UDS backend selection.
 *
 * A socket "path" beginning with '@' names a Linux ABSTRACT-namespace socket
 * (no filesystem entry) instead of a pathname socket. Abstract sockets are the
 * only UNIX-socket option when SELinux denies the shell domain from creating
 * pathname sockets — e.g. an unrooted Android phone (celltron) running the
 * daemon under proot, where bind(AF_UNIX, "/path.sock") returns EACCES.
 *
 * For every non-'@' path we use #node:net exactly as before — byte-for-byte
 * unchanged behavior. bare-abstract-socket is imported LAZILY (dynamic import,
 * only at the async call sites below) so pathname deployments never load the
 * native addon.
 */

import net from '#node:net'

let _abstract = null

async function loadAbstract () {
  if (_abstract === null) {
    const m = await import('bare-abstract-socket')
    _abstract = m.default || m
  }
  return _abstract
}

// True if `path` names an abstract-namespace socket (leading '@').
export function isAbstract (path) {
  return typeof path === 'string' && path.length > 1 && path[0] === '@'
}

// Resolve the transport backend + the name to bind/connect. The returned
// `backend` exposes net-compatible createServer(opts, onConnection) and
// createConnection(name). For abstract paths the leading '@' is stripped
// (bare-abstract-socket adds the actual leading NUL).
export async function udsBackend (path) {
  if (isAbstract(path)) {
    return { backend: await loadAbstract(), name: path.slice(1), abstract: true }
  }
  return { backend: net, name: path, abstract: false }
}