Skip to content

Commit

Permalink
add local-install/li option
Browse files Browse the repository at this point in the history
  • Loading branch information
jhheider committed Feb 20, 2025
1 parent eed178e commit 1073c32
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 14 deletions.
3 changes: 3 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,9 @@ jobs:
- run: ./pkgm.ts i pkgx.sh/brewkit
- run: /usr/local/bin/bk --help

- run: ./pkgm.ts li pkgx.sh/brewkit
- run: ~/.local/bin/bk --help

- run: |
if [[ "$(/usr/local/bin/pkgx --version)" != "pkgx 2"* ]]; then
exit 1
Expand Down
35 changes: 21 additions & 14 deletions pkgm.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
#!/usr/bin/env -S pkgx --quiet deno^2.1 run --ext=ts --allow-sys=uid --allow-run --allow-env=PKGX_DIR,HOMEBREW_PREFIX,HOME --allow-read=/usr/local/pkgs
#!/usr/bin/env -S pkgx --quiet deno^2.1 run --ext=ts --allow-sys=uid --allow-run --allow-env=PKGX_DIR,HOMEBREW_PREFIX,HOME --allow-read=/usr/local/pkgs,$HOME/.local/pkgs
import { dirname, fromFileUrl, join } from "jsr:@std/path@^1";
import { ensureDir, existsSync } from "jsr:@std/fs@^1";
import { parse as parse_args } from "jsr:@std/[email protected]";
Expand Down Expand Up @@ -34,7 +34,11 @@ if (parsedArgs.help) {
switch (parsedArgs._[0]) {
case "install":
case "i":
await install(args);
await install(args, '/usr/local');
break;
case "local-install":
case "li":
await install(args, `${Deno.env.get("HOME")!}/.local`);
break;
case "uninstall":
case "rm":
Expand All @@ -49,12 +53,12 @@ if (parsedArgs.help) {
Deno.exit(1);
break;
case "sudo-install": {
const [pkgx_dir, runtime_env, ...paths] = args;
const [pkgx_dir, runtime_env, basePath, ...paths] = args;
const parsed_runtime_env = JSON.parse(runtime_env) as Record<
string,
Record<string, string>
>;
await sudo_install(pkgx_dir, paths, parsed_runtime_env);
await sudo_install(pkgx_dir, paths, parsed_runtime_env, basePath);
break;
}
default:
Expand All @@ -67,7 +71,7 @@ if (parsedArgs.help) {
}
}

async function install(args: string[]) {
async function install(args: string[], basePath: string) {
if (args.length === 0) {
console.error("no packages specified");
Deno.exit(1);
Expand Down Expand Up @@ -106,7 +110,7 @@ async function install(args: string[]) {

const to_install = [];
for (const prefix of pkg_prefixes) {
if (!existsSync(join("/usr/local/pkgs", prefix))) {
if (!existsSync(join(`${basePath}/pkgs`, prefix))) {
to_install.push(prefix);
}
}
Expand All @@ -118,9 +122,9 @@ async function install(args: string[]) {

const self = fromFileUrl(import.meta.url);
const pkgx_dir = Deno.env.get("PKGX_DIR") || `${Deno.env.get("HOME")}/.pkgx`;
const needs_sudo = Deno.uid() != 0;
const needs_sudo = Deno.uid() != 0 && basePath === "/usr/local";

const runtime_env = expand_runtime_env(json.runtime_env);
const runtime_env = expand_runtime_env(json.runtime_env, basePath);

args = [
"pkgx",
Expand All @@ -133,6 +137,7 @@ async function install(args: string[]) {
"sudo-install",
pkgx_dir,
runtime_env,
basePath,
...to_install,
];
const cmd = needs_sudo ? "/usr/bin/sudo" : args.shift()!;
Expand All @@ -145,12 +150,13 @@ async function sudo_install(
pkgx_dir: string,
pkg_prefixes: string[],
runtime_env: Record<string, Record<string, string>>,
basePath: string,
) {
const dst = "/usr/local";
const dst = basePath;
for (const pkg_prefix of pkg_prefixes) {
// create /usr/local/pkgs/${prefix}
// create ${dst}/pkgs/${prefix}
await mirror_directory(join(dst, "pkgs"), pkgx_dir, pkg_prefix);
// symlink /usr/local/pkgs/${prefix} to /usr/local
// symlink ${dst}/pkgs/${prefix} to ${dst}
if (!pkg_prefix.startsWith("pkgx.sh/v")) {
// ^^ don’t overwrite ourselves
// ^^ * https://github.com/pkgxdev/pkgm/issues/14
Expand All @@ -169,14 +175,14 @@ async function sudo_install(
if (!pkg_prefix) continue; //FIXME wtf?

for (const bin of ["bin", "sbin"]) {
const bin_prefix = join("/usr/local/pkgs", pkg_prefix, bin);
const bin_prefix = join(`${dst}/pkgs`, pkg_prefix, bin);

if (!existsSync(bin_prefix)) continue;

for await (const entry of Deno.readDir(bin_prefix)) {
if (!entry.isFile) continue;

const to_stub = join("/usr/local", bin, entry.name);
const to_stub = join(dst, bin, entry.name);

let sh = `#!/bin/sh\n`;
for (const [key, value] of Object.entries(env)) {
Expand Down Expand Up @@ -288,12 +294,13 @@ async function create_v_symlinks(prefix: string) {

function expand_runtime_env(
runtime_env: Record<string, Record<string, string>>,
basePath: string,
) {
const expanded: Record<string, Record<string, string>> = {};
for (const [project, env] of Object.entries(runtime_env)) {
const expanded_env: Record<string, string> = {};
for (const [key, value] of Object.entries(env)) {
const new_value = value.replaceAll(/\$?{{.*prefix}}/g, "/usr/local");
const new_value = value.replaceAll(/\$?{{.*prefix}}/g, basePath);
expanded_env[key] = new_value;
}
expanded[project] = expanded_env;
Expand Down

0 comments on commit 1073c32

Please sign in to comment.