import { HostProcessHostname, HostProcessPlatform } from "@t3tools/shared/hostProcess"; import * as Effect from "effect/Effect"; import * as FileSystem from "effect/FileSystem"; import * as Option from "effect/Option"; import * as Schema from "effect/Schema"; import * as ProcessRunner from "../processRunner.ts"; interface ResolveServerEnvironmentLabelInput { readonly cwdBaseName: string; } const ServerEnvironmentLabelCommandProbe = Schema.Literals([ "macos-computer-name", "linux-pretty-hostname", ]); type ServerEnvironmentLabelCommandProbe = typeof ServerEnvironmentLabelCommandProbe.Type; export class ServerEnvironmentLabelFileError extends Schema.TaggedError()( "ServerEnvironmentLabelFileError", { operation: Schema.Literals(["inspect", "read"]), path: Schema.String, cause: Schema.Defect(), }, ) { override get message(): string { return `Failed to ${this.operation} environment-label file at ${this.path}.`; } } export class ServerEnvironmentLabelCommandError extends Schema.TaggedError()( "ServerEnvironmentLabelCommandError", { probe: ServerEnvironmentLabelCommandProbe, executable: Schema.String, argumentCount: Schema.Number, cause: Schema.Defect(), }, ) { override get message(): string { return `Failed to run environment-label probe '${this.probe}' with ${this.executable}.`; } } function normalizeLabel(value: string | null | undefined): string | null { const trimmed = value?.trim(); return trimmed && trimmed.length > 0 ? trimmed : null; } function parseMachineInfoValue(raw: string, key: string): string | null { for (const line of raw.split(/\r?\n/g)) { const trimmed = line.trim(); if (trimmed.length === 0 || trimmed.startsWith("#") || !trimmed.startsWith(`${key}=`)) { continue; } const value = trimmed.slice(key.length + 1).trim(); if ( (value.startsWith('"') && value.endsWith('"')) || (value.startsWith("'") && value.endsWith("'")) ) { return normalizeLabel(value.slice(1, -1)); } return normalizeLabel(value); } return null; } const readLinuxMachineInfo = Effect.fn("readLinuxMachineInfo")(function* () { const fileSystem = yield* FileSystem.FileSystem; const machineInfoPath = "/etc/machine-info"; return yield* fileSystem.exists(machineInfoPath).pipe( Effect.mapError( (cause) => new ServerEnvironmentLabelFileError({ operation: "inspect", path: machineInfoPath, cause, }), ), Effect.flatMap((exists) => exists ? fileSystem.readFileString(machineInfoPath).pipe( Effect.mapError( (cause) => new ServerEnvironmentLabelFileError({ operation: "read", path: machineInfoPath, cause, }), ), ) : Effect.succeed(null), ), Effect.catchTags({ ServerEnvironmentLabelFileError: (error) => Effect.logDebug(error.message).pipe( Effect.annotateLogs({ operation: error.operation, path: error.path, cause: error, }), Effect.as(null), ), }), ); }); const runFriendlyLabelCommand = Effect.fn("runFriendlyLabelCommand")(function* (input: { readonly probe: ServerEnvironmentLabelCommandProbe; readonly command: string; readonly args: readonly string[]; }) { const processRunner = yield* ProcessRunner.ProcessRunner; const result = yield* processRunner .run({ command: input.command, args: input.args, timeoutBehavior: "timedOutResult", }) .pipe( Effect.mapError( (cause) => new ServerEnvironmentLabelCommandError({ probe: input.probe, executable: input.command, argumentCount: input.args.length, cause, }), ), Effect.map(Option.some), Effect.catchTags({ ServerEnvironmentLabelCommandError: (error) => Effect.logDebug(error.message).pipe( Effect.annotateLogs({ probe: error.probe, executable: error.executable, argumentCount: error.argumentCount, cause: error, }), Effect.as(Option.none()), ), }), ); if (Option.isNone(result) || result.value.code !== 0) { return null; } return normalizeLabel(result.value.stdout); }); const resolveFriendlyHostLabel = Effect.fn("resolveFriendlyHostLabel")(function* () { const platform = yield* HostProcessPlatform; if (platform === "darwin") { return yield* runFriendlyLabelCommand({ probe: "macos-computer-name", command: "scutil", args: ["--get", "ComputerName"], }); } if (platform === "linux") { const machineInfo = normalizeLabel(yield* readLinuxMachineInfo()); if (machineInfo) { const prettyHostname = parseMachineInfoValue(machineInfo, "PRETTY_HOSTNAME"); if (prettyHostname) { return prettyHostname; } } return yield* runFriendlyLabelCommand({ probe: "linux-pretty-hostname", command: "hostnamectl", args: ["--pretty"], }); } return null; }); export const resolveServerEnvironmentLabel = Effect.fn("resolveServerEnvironmentLabel")(function* ( input: ResolveServerEnvironmentLabelInput, ) { const friendlyHostLabel = yield* resolveFriendlyHostLabel(); if (friendlyHostLabel) { return friendlyHostLabel; } const hostname = normalizeLabel(yield* HostProcessHostname); if (hostname) { return hostname; } return normalizeLabel(input.cwdBaseName) ?? "T3 environment"; });