GithubHelp home page GithubHelp logo

aftman's Introduction

Aftman

Aftman is a toolchain manager. It enables installing project-specific command line tools and switching between them seamlessly.

$ rojo --version
Rojo 6.2.0

$ cat ~/.aftman/aftman.toml
[tools]
rojo = "rojo-rbx/[email protected]"

$ cd uses-rojo-7
$ rojo --version
Rojo 7.1.0

$ cat aftman.toml
[tools]
rojo = "rojo-rbx/[email protected]" 

Supported Platforms

Aftman supports:

  • Windows (x86, x86-64)
  • macOS (x86-64, AArch64)
  • Linux (x86, x86-64, AArch64)

Installation

You can install Aftman by downloading a pre-built binary for your platform from Aftman's GitHub Releases Page.

Once you have the release unzipped, run:

./aftman self-install

This will install Aftman to its own bin directory and update your system's PATH environment variable for you.

Getting Started

To create a new aftman.toml file in your current directory, run

aftman init

To add a new tool, you can follow the instructions in the file, or run

aftman add rojo-rbx/rojo

# install a specific version
aftman add rojo-rbx/[email protected]

# install with a different binary name
aftman add BurntSushi/ripgrep rg

If your PATH is configured correctly (see Installation), you will now be able to run that tool from your project.

To install a tool system-wide so that it can be used anywhere, edit ~/.aftman/aftman.toml or run

aftman add --global rojo-rbx/rojo

To install all tools listed by your aftman.toml files, run

aftman install

Authenticating with GitHub (Aftman 0.2.7+)

If you're running into GitHub rate limits or want to manage private tools hosted on GitHub, you can give Aftman a Personal Access Token.

Generate a Personal Access Token, then edit ~/.aftman/auth.toml to add it:

github = "pat goes here"

Aftman will use this token to authenticate all requests to GitHub.

Subcommands

For detailed help information, run aftman --help.

aftman init

Usage:

aftman init [path]

Creates a new aftman.toml file in the given directory. Defaults to the current directory.

aftman add

Usage:

aftman add [--global] <tool-spec> [tool-alias]

Installs a new tool with the given tool spec and optional alias to use for installing the tool.

Examples:

# Install the latest version of Rojo in the nearest aftman.toml file
aftman add rojo-rbx/rojo

# Install the latest version of Rojo globally
aftman add --global rojo-rbx/rojo

# Install a specific version of Rojo locally
aftman add rojo-rbx/[email protected]

# Install Rojo with a different binary name
aftman add rojo-rbx/[email protected] rojo6

aftman install

Usage:

aftman install [--no-trust-check] [--skip-untrusted]

Install all tools listed in aftman.toml files based on your current directory.

If --no-trust-check is given, all tools will be installed, regardless of whether they are known. This should generally only be used in CI environments. To trust a specific tool before running aftman install, use aftman trust <tool> instead.

If --skip-untrusted is given, only already trusted tools will be installed, others will be skipped and not emit any errors.

aftman self-install

Usage:

aftman self-install

Installs Aftman, upgrades any references to Aftman, and adds aftman to your system PATH if supported.

Whenever you upgrade Aftman, run this command. Aftman makes copies of itself to mimic the tools it installs, and this command will ensure those copies get updated as well.

aftman trust

Usage:

aftman trust <tool-name>

Adds a tool to the list of trusted tools.

Aftman prompts the user before installing new tools. Running aftman trust beforehand skips this prompt. This is useful when running automation that depends on a tool from a known location.

aftman list

Added in Aftman 0.2.6.

Usage:

aftman list

Lists all tools currently managed by Aftman.

aftman update

This subcommand is not yet implemented.

Differences from Foreman

Aftman is spiritually very similar to Foreman, a project I created at Roblox.

I'm hoping to fix some of the core design mistakes I made in Foreman and also take a little more care with the codebase. Roughly:

  • Exact version dependencies. Using a range here has tripped up lots of users, so Aftman uses exact versions in all configuration files.
  • Commands to install, uninstall, and upgrade tools. Editing a global, tucked-away toml file by hand is rough.
  • Change model to no longer trust-by-default. Aftman prompts before downloading new tools. (Roblox/foreman#16).
  • Better strategy for storing executables. (Roblox/foreman#11)
  • Better heuristics for picking the right artifacts for your platform. Aftman uses your Compiler, OS, architecture, and will eventually support custom patterns. (Roblox/foreman#18)
  • Proper error handling. Unlike Foreman, which uses Result::unwrap liberally, Aftman has good error hygiene with helpful context attached.
  • Less Roblox-angled. Aftman does not market itself as being for Roblox development. It is a generally useful tool that can install all sorts of CLI tools.

License

Aftman is available under the terms of the MIT license. See https://opensource.org/licenses/MIT or LICENSE for details.

aftman's People

Contributors

bloeo avatar dervexdev avatar filiptibell avatar jacksonwelsh avatar johnnymorganz avatar lasttalon avatar lpghatguy avatar nezuo avatar sasial-dev avatar sur4y avatar yumacide avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

aftman's Issues

How do we uninstall tools?

The readme states you could uninstall tools, yet there is no option to do so? Is it done implicitly? Has the explicit command not been implemented yet?

Ability to keep descendant processes running after aftman closes

The way Aftman puts processes into a job on Windows disallows all descendant processes from running after Aftman closes unless you do some really hacky stuff.

It is possible to allow job processes to break away from jobs without hacks: set the JOB_OBJECT_LIMIT_BREAKAWAY_OK limit on the job, then the child processes can break away if spawned with CREATE_BREAKAWAY_FROM_JOB.

This is almost straightforward: Rust already has a mechanism for setting creation flags like CREATE_BREAKAWAY_FROM_JOB. There's no existing API for setting job limits like JOB_OBJECT_LIMIT_BREAKAWAY_OK though, even in the command_group crate. The correct sequence for setting this limit looks like: create the job, set the limit, spawn the descendant processes. I feel like this would be a simple change to the command_group crate to support (or alternatively, a simple change to run the same code in Aftman instead).


I particularly need this for spawning Roblox Studio. Without this (or workarounds), Studio is closed as soon as the spawner is done. We are using this for a tool that downloads a copy of production and opens it as a local file to avoid mistakes that can happen when production is actually open.

This would also be applicable for any other launching-of-a-gui utility command.


As a workaround, the WMI Win32_Process.Create method just so happens to ignore jobs. I was having a lot of trouble calling this from Rust, so I ended up having Rust run a powershell snippet which spawns the process. How hacky!

To open a rbxl file, we do the following:

    powershell_script::run(&format!(
        r#"([WMICLASS]"win32_process").Create('explorer "{}"')"#,
        path.as_os_str().to_string_lossy()
    ))

`aftman install --skip-untrusted`

It would be useful for automated workflows to be able to install only previously trusted tools, so that a new tool being added to a checked-in aftman.toml doesn't break any existing tooling.

Add `aftman add --local`

We should add a flag to automatically create an aftman.toml file and add a tool to it in one step.

Auth for private repositories

We currently maintain an internal CLI and are blocked from adopting Aftman until it supports authenticating with GitHub PATs. Are you open to a PR for this?

Supporting adding to PATH on non-Windows platforms

We can follow what Cargo does here.

They append to ~/.zshenv and/or ~/.profile the following:

. "$HOME/.cargo/env"

and then include this script, ~/.cargo/env:

#!/bin/sh
# rustup shell setup
# affix colons on either side of $PATH to simplify matching
case ":${PATH}:" in
    *:"$HOME/.cargo/bin":*)
        ;;
    *)
        # Prepending path in case a system-installed rustc needs to be overridden
        export PATH="$HOME/.cargo/bin:$PATH"
        ;;
esac

This seems reasonable to me.

Aftman does not pass-through the tool's exit code

When using a tool managed using aftman, the exit code of the tool is not passed through (which causes problems such as rojo-rbx/rojo#651)
It is however correctly handled in foreman

PS C:\Users\Development\Documents\rojo> C:\Users\Development\.aftman\bin\rojo.exe sourcemap
[ERROR rojo] Rojo project referred to a file using $path that could not be turned into a Roblox Instance by Rojo.
        Check that the file exists and is a file type known by Rojo.

        Project path: C:\Users\Development\Documents\rojo\default.project.json
        File $path: src/shared
PS C:\Users\Development\Documents\rojo> $LASTEXITCODE
0
PS C:\Users\Development\Documents\rojo> C:\Users\Development\.foreman\bin\rojo.exe sourcemap
[ERROR rojo] Rojo project referred to a file using $path that could not be turned into a Roblox Instance by Rojo.
        Check that the file exists and is a file type known by Rojo.

        Project path: C:\Users\Development\Documents\rojo\default.project.json
        File $path: src/shared
PS C:\Users\Development\Documents\rojo> $LASTEXITCODE
1

Download & install already trusted tools in parallel

The majority of the time spent in some of our CI jobs (~5 seconds or sometimes more) is spent downloading and installing tools managed by aftman, and I suspect this will grow slightly over time.

It would be great if aftman could download & install tools in parallel similar to what cargo does for tools that are already trusted or when using --no-trust-check. Maybe install could even be split into two phases, where the first is accepting trust for any new tools and the second is the download & install process.

Support for bare executables & more formats in releases

I've encountered a few tools that do not have executables zipped in their releases, one of them being sentry-cli:

https://github.com/getsentry/sentry-cli/releases

It would be cool if we had support for this! It also seems like aftman already sets the proper executable flags on unix, so I guess it may just be a minor matching fix. Right now we work around this by maintaining a fork with the only purpose of mirroring releases that zip up the executables.

What features will Aftman have over Foreman?

Other than the obvious benefit of not being owned by Roblox (who seem to have no interest in maintaining Foreman), what will Aftman have over Foreman?

I believe you answered this on Discord already but for posterity it should be recorded on GitHub too.

`aftman self-install` fails when libssl/libcrypto is not present on Linux

Expected Behavior

aftman self-install should either install or prompt the user to install missing dependencies.

Actual Behavior

aftman self-install fails to install unless a very specific build of libssl and libcrypto are present in /usr/lib/.

Without openssl installed:

> ./aftman self-install
./aftman: error while loading shared libraries: libssl.so.1.1: cannot open shared object file: No such file or directory

With apt (or other incompatible) build of openssl installed and manually moved to /usr/lib/:

./aftman self-install
./aftman: symbol lookup error: /lib/libssl.so.1.1: undefined symbol: EVP_idea_cbc, version OPENSSL_1_1_0

With "correct" build of openssl installed

I found that the build of libssl and libcrpyo used by Steam were what aftman was expecting. Here's the steps to find and move these into the appropriate directory:

  1. Ensure you have Steam installed (proton may also be required, I haven't checked)
  2. Run find / -type f -name "libcrypto.so.1.1" 2>/dev/null (/dev/null simply removes error logs) for libcrypto and libssl respectively. Make sure the path contains something along the lines of SteamLinuxRuntime_soldier!
  3. Once you've located the path to one of the libcrypto or libssl builds on your system, e.g. ~/.steam/debian-installation/steamapps/common/SteamLinuxRuntime_soldier/var/tmp-M2O211/usr/lib/x86_64-linux-gnu/libcrypto.so.1.1, use sudo cp <steam_libssl_dir> /usr/lib/ to copy the libssl and libcrypto build to your system library.
  4. Run sudo ldconfig to refresh libraries, though this isn't strictly necessary
  5. Run aftman self-install normally, and it should work!

Steps to reproduce

I've only confirmed this to affect debian/ubuntu, however neither libssl nor libcrypto are installed by default, and aftman does not appear to use the openssl package without modification, so the steps to reproduce are simply:

  1. Boot up any modern version of Ubuntu
  2. Try to use aftman self-install

It should also be noted that this will affect aftman's ability to install packages as well, even if manually installed. Building manually will work, however the package binaries aftman installs (e.g. rojo) will also fail to run with similar errors.

Add option to treat tool names as case-insensitive

This issue builds onto #41

Was trying to install wally earlier, followed the guide and aftman was saying it's not in my aftman.toml when it is. After I changed the name from "wally" (lowercase w) to "Wally" (uppercase W, the same name as in the aftman bin) it worked fine. Why is this the case when the official wally docs use it in lowercase?

Aftman error: Incorrect function. (os error 1)

Trying to follow instuctions on readme.
When I try to use aftman to add a tool I get error messages like so:
$ aftman.exe add rojo-rbx/rojo
Tool rojo-rbx/rojo has never been installed before. Install it? [y/n] Aftman error: Incorrect function. (os error 1)

$ aftman install
Tool rojo-rbx/rojo has never been installed before. Install it? [y/n] Aftman error: Incorrect function. (os error 1)

dougb@DougPC MINGW64 ~

On Windows using GitBash shell.

Cannot use tools with Aftman when Foreman is already managing them

I have some projects that use Foreman, and when trying to install the same tools via Aftman I run into issues where Foreman is still trying to invoke those tools.

Here's my aftman.toml:

# This file lists tools managed by Aftman, a cross-platform toolchain manager.
# For more information, see https://github.com/LPGhatguy/aftman

# To add a new tool, add an entry to this table.
[tools]
luau-lsp = "JohnnyMorganz/[email protected]"
rojo = "rojo-rbx/[email protected]"
selene = "kampfkarren/[email protected]"
stylua = "JohnnyMorganz/[email protected]"
wally = "UpliftGames/[email protected]"

And after running aftman install, attempting to run wally init results in the following:

➜  camera-shaker git:(wally) wally init
'wally' is not a known Foreman tool, but Foreman was invoked with its name.

To use this tool from /Users/marin/Code/camera-shaker, declare it in a 'foreman.toml' file in the current directory or a parent directory.

Available Tools:

➜  camera-shaker git:(wally) 

Is this something that Aftman could provide support for? Or is this ultimately an issue with Foreman that would need to be patched? I'm hoping for the former, because I don't expect Foreman to receive any special support to not conflict with Aftman.

I'm currently torn on switching to Aftman because I have several projects still using Foreman, and there will continue to be projects owned by Roblox and other authors that won't be ported to Aftman.

`aftman self-install` fails when /tmp is on a seperate filesystem

When installing aftman on a unix-like operating system, aftman self-install will fail if /tmp is on a seperate filesystem (i.e. tmpfs)

[INFO  aftman::tool_storage] Updating all Aftman binaries...
Aftman error: failed to rename file from /home/josh/.aftman/bin/rojo to /tmp/.tmpaVMK5X/rojo

Caused by:
    Invalid cross-device link (os error 18)

Weird behaviour depending on the capitalisation of executable suffix

On Windows, sometimes the path to an aftman managed executable is returned by tools (such as node-which) with a capitalised suffix .EXE, e.g.: C:\Users\Development\.aftman\bin\stylua.EXE

I'm not sure exactly why its returned like this sometimes, but I've seen it often occur for users, and myself.

When attempting to run this executable directly using the path, there can be odd behaviour.
For example, in cmd:

C:\Users\Development\Downloads\project>C:\Users\Development\.aftman\bin\stylua.EXE --version
stylua 0.18.1

But in powershell:

PS C:\Users\Development\Downloads\project> C:\Users\Development\.aftman\bin\stylua.EXE --version
Aftman error: Tried to run an Aftman-managed version of stylua.EXE, but no aftman.toml files list this tool.
To run stylua.EXE from this directory, add it to one of these files:
- C:\Users\Development\Downloads\project\aftman.toml
- C:\Users\Development\.aftman\aftman.toml

But C:\Users\Development\Downloads\project\aftman.toml contains the contents:

# This file lists tools managed by Aftman, a cross-platform toolchain manager.
# For more information, see https://github.com/LPGhatguy/aftman

# To add a new tool, add an entry to this table.
[tools]
rojo = "rojo-rbx/[email protected]"
selene = "Kampfkarren/[email protected]"
wally = "UpliftGames/[email protected]"
luau-lsp = "JohnnyMorganz/[email protected]"
stylua = "JohnnyMorganz/[email protected]"
wally-package-types = "JohnnyMorganz/[email protected]"

I would expect the tool to always run fine, even with .EXE as a suffix.

Looking at the code, the offending issue seems to be current_exe_name() not stripping the .EXE suffix like it does for .exe, meaning aftman doesn't find it in manfiest.tools vector

https://github.com/LPGhatguy/aftman/blob/412d5b5a54971a881bfd99ebd7976b48cf5dedfe/src/main.rs#L73C1-L83C2

Aftman does not install correctly if ~/.zshenv file does not exist (MacOS).

Currently aftman will say that it has successfully installed, but if the ~/.zshenv is not present already then it will silently fail without warning as it cannot add it to the system path.

Preferably it should aggressively create this file that is required if it is needed, but at the very least should prompt the user if the file doesn't exist, that they should create it.

Add `--fallible` flag to `aftman install`

I use a private command line tool hosted on GitHub and would like to install it using aftman. This breaks my CI however, since it cannot install the tool. If there were a way to ignore installation errors or ignore specific tools it would solve my issue. The title API is just an example.

GitLab support

Foreman now supports installing tools from GitLab. We should support installing tools from GitLab too!

Arm64/aarch64 binaries don't get prioritized over x86

Just noticed that aftman chose the wrong binary when installing one of our internal tools:

CleanShot 2022-09-13 at 18 29 28@2x

In the screenshot you can see that the files downloaded are definitely x86 while the architecture I'm using is arm.
If I delete the x86_64 binary from the release aftman correctly picks the aarch64 one.

I'm thinking something might be going wrong during artifact selection / ordering

Improved error messages when Rosetta is not installed

When running an executable built for x86 on an M1/M2 mac you will get this confusing error message if Rosetta is not installed:
Bad CPU type in executable
Since aftman will always pull x86 executables if a native one is not found for these machines (https://github.com/LPGhatguy/aftman/blob/main/src/tool_source/mod.rs#L36) it might be good for aftman to also be aware of rosetta and point users in the right direction if they don't have it installed.

Aftman GitHub Action

Foreman has a GitHub Action that automates downloading and installing Foreman. I think we should create an action for Aftman, too.

Getting "...Error while loading shared libraries: libssl.so.1.1..." on WSL Ubuntu

I've been trying to use install aftman on my ubuntu WSL system using the provided binary for linux. I unzip the linux file and attempt to run ./aftman self-install, and soon after I am unfortunately greeted with the error:

./aftman: error while loading shared libraries: libssl.so.1.1: cannot open shared object file: No such file or directory

Any ideas on how to fix this?

How do I uninstall Aftman?

I'm probably stupid but I can't figure out how to install Aftman as I prefer Foreman, but I don't know how to just get rid of it off my computer and all projects. It's not like Aftman is installing Rojo anyway so I might as well use Foreman. Anyone that can help?

aftman self-install fails on zsh environment

Following from the discussion on #28:

On Ubuntu 22.04, I also had issues running aftman self-install without sudo. Without running as sudo I get this error:

./aftman self-install
[INFO  aftman::tool_storage] Updating all Aftman binaries...
[INFO  aftman::tool_storage] Updated Aftman binaries successfully!
[ERROR aftman::system_path::unix] Error trying to write /home/overhash/.zshenv: failed to open file `/home/overhash/.zshenv`

What's more interesting is that when I do use sudo ./aftman self-install, it still won't update the zshenv. I had to manually move my .zshenv to a new file and then run aftman self-install (which created a fresh ~/.zshenv) before I merged my old changes in.

Most interestingly, all files are chmod 644. Running aftman self-install again after installing still causes the issue. I'm suspecting there's something funny going on here when actually reading the file.

Running off 652c4df.

aftman does not mark binaries in tool-storage as executable on Unix systems

image

I'm able to consistently reproduce this issue on Ubuntu WSL in Windows 11.

Text version
~/playgrounds/rbxts > rm -rf ~/.aftman/
~/playgrounds/rbxts > aftman init
~/playgrounds/rbxts > aftman add rojo-rbx/rojo
Tool rojo-rbx/rojo has never been installed before. Install it? yes
[INFO  aftman::tool_storage] Installing tool: rojo-rbx/rojo
[INFO  aftman::tool_storage] Downloading rojo-rbx/rojo v7.1.0 (rojo-7.1.0-linux.zip)...
[INFO  aftman::tool_storage] rojo-rbx/rojo v7.1.0 installed successfully.
[INFO  aftman::manifest] Tool rojo = rojo-rbx/[email protected] has been added to /home/osyris/playgrounds/rbxts/aftman.toml
~/playgrounds/rbxts > rojo -V
thread 'main' panicked at 'called `Result::unwrap()` on an `Err` value: Os { code: 13, kind: PermissionDenied, message: "Permission denied" }', src/tool_storage.rs:77:71
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace
~/playgrounds/rbxts > chmod +x ~/.aftman/tool-storage/rojo-rbx/rojo/7.1.0/rojo 
~/playgrounds/rbxts > rojo -V
Rojo 7.1.0
~/playgrounds/rbxts >

Aftman fails to update cross-volume (Rojo extension)

The rojo extension tries to install aftman itself. However, this has aftman wanting to update, and it's failing. I believe this is because my /home and /tmp directories are not under the same volumes, my /home volume is isolated from my root volume, for taking snapshots and backups. Aftman is the only program I've experienced having this problem before so I assume there's a solution to this.

image

P.s. this makes the Rojo extension unusable for me unfortunately 😎

Respect XDG environment variables for .aftman folder

Rather than placing the .aftman folder directly into HOME, I'd much prefer if it tried out the XDG_DATA_HOME environment variable first, then fall back to HOME.

It may also be a little better to separate aftman.toml into XDG_CONFIG_HOME which would make backups easier.

Additionally, perhaps make use of an environment variable named AFTMAN_HOME, much like RUSTUP_HOME and CARGO_HOME are (although this may pollute the env, it is still better than not having an option where .aftman is found at all)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.