Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Should be easier to use, with dependencies from Homebrew and mimic build conf. Documentation enabled by default. #190

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
162 changes: 88 additions & 74 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,49 +1,42 @@
# asdf-erlang

Erlang plugin for [asdf](https://github.com/asdf-vm/asdf) version manager that relies on [kerl](https://github.com/kerl/kerl) for builds.
## About

This plugin aims to combine the best of both worlds by using kerl.

kerl's compatibility and build scripts, together with asdf's easy version switching and support for the .tool-versions file. You do not need to have kerl already installed to use this. The plugin will install it's own version of kerl automatically.
Under the hood, asdf-erlang will use existing [kerl](https://github.com/kerl/kerl) or install it if it's missing.

## Install

```
asdf plugin add erlang https://github.com/asdf-vm/asdf-erlang.git
```

Important: Make sure to read the "Before asdf install" section below to install dependencies!

## Use
## Requirements

Check [asdf](https://github.com/asdf-vm/asdf) readme for instructions on how to install & manage versions of Erlang. To specify custom options you [can set environment variables just as you would when using kerl](https://github.com/kerl/kerl#kerl_base_dir). For example, to skip the java dependency during installation use:
### macOS
* Homebrew
* Xcode CLI tools
* openssl
* wxmac

```
$ export KERL_CONFIGURE_OPTIONS="--disable-debug --without-javac"
$ asdf install erlang <version>
```
`brew install openssl wxmac`

You can also install Erlang from git, or provide the url to a fork and build from git.
Addtional dependencies if building from source:
`brew install autoconf libtool `

```
$ asdf install erlang ref:master
macOS will by default try to fetch and use prebuilt.

$ export OTP_GITHUB_URL="https://github.com/basho/otp"
$ asdf install erlang ref:basho
```
Note, for macOS 10.15.4 and newer, 22.3.1 is the earliest version that can be built from source. Earlier versions will fail to compile. See [this issue](https://github.com/kerl/kerl/issues/335#issuecomment-605487028) for details.

See [kerl](https://github.com/kerl/kerl) for the complete list of customization options. Note that the `KERL_BASE_DIR` and `KERL_CONFIG` environment variables are set by the plugin when it runs kerl so it will not be possible to customize them.

## Before `asdf install`

## Ubuntu and Debian
### Ubuntu and Debian

Note that if you are using a previous version of Linux, you may need a different version of one of the below
libraries.

### Ubuntu 16.04 LTS "Xenial Xerus"

Install the build tools (dpkg-dev g++ gcc libc6-dev make debianutils m4 perl)
#### Ubuntu 16.04 LTS "Xenial Xerus"

Install the build tools (dpkg-dev g++ gcc libc6-dev make debianutils m4 perl)
`apt-get -y install build-essential autoconf`

Needed for HiPE (native code) support, but already installed by autoconf
Expand All @@ -64,15 +57,15 @@ ODBC support (libltdl3-dev odbcinst1debian2 unixodbc)
For building documentation:
`apt-get install xsltproc fop`

If you want to install all the above:
If you want to install all the above:
`apt-get -y install build-essential autoconf m4 libncurses5-dev libwxgtk3.0-dev libgl1-mesa-dev libglu1-mesa-dev libpng-dev libssh-dev unixodbc-dev xsltproc fop`

### Ubuntu 20.04 LTS
#### Ubuntu 20.04 LTS

If you want to install all the above:
If you want to install all the above:
`apt-get -y install build-essential autoconf m4 libncurses5-dev libwxgtk3.0-gtk3-dev libgl1-mesa-dev libglu1-mesa-dev libpng-dev libssh-dev unixodbc-dev xsltproc fop libxml2-utils libncurses-dev openjdk-11-jdk`

## Arch Linux
#### Arch Linux
Provides most of the needed build tools.
`pacman -S --needed base-devel`

Expand All @@ -88,38 +81,7 @@ For building ssl
ODBC support
`sudo pacman -S unixodbc`

## OSX

Note, for MacOS 10.15.4 and newer, 22.3.1 is the earliest version that can be installed through `kerl` (and, therefore, `asdf`). Earlier versions will fail to compile. See [this issue](https://github.com/kerl/kerl/issues/335#issuecomment-605487028) for details.

Install the build tools
`brew install autoconf`

For building with wxWidgets (start observer or debugger!)
`brew install wxmac`

### Dealing with OpenSSL issues on macOS

You may encounter an SSL error with an output along these lines:

```
crypto : No usable OpenSSL found
ssh : No usable OpenSSL found
ssl : No usable OpenSSL found
```

This issue has been documented [on
`kerl`](https://github.com/kerl/kerl#compiling-crypto-on-macs). If you see this
error, you can use the `--with-ssl` flag with a path before installing Erlang. Here is
an example that skips the java dependency and also sets a specific (and existing)
path for OpenSSL installed via brew on macOS.

```
$ export KERL_CONFIGURE_OPTIONS="--without-javac --with-ssl=$(brew --prefix openssl)"
$ asdf install erlang <version>
```

## CentOS & Fedora
#### CentOS & Fedora

These steps assume a most recent build of CentOS (currently
tested on CentOS 7.5 x64 & Fedora 28 x64)
Expand Down Expand Up @@ -148,7 +110,7 @@ ODBC support
for the documentation to be built
`sudo yum install -y libxslt fop`

## Solus
#### Solus

Install the build tools

Expand Down Expand Up @@ -183,7 +145,7 @@ sudo eopkg it -c system.devel
sudo eopkg install wxwidgets-devel mesalib-devel libglu-devel fop unixodbc-devel openjdk-8 openjdk-8-devel
```

### OpenJDK issues on Solus
#### OpenJDK issues on Solus

I ran into an issue where `javac` wasn't a recognized command in the terminal despite having installed `openjdk-8` and `openjdk-8-devel`. Turns out it wasn't added to `PATH` by default. So simply add it to `PATH` like so:

Expand All @@ -196,24 +158,76 @@ PATH=$PATH:$JAVA_HOME/bin
source ~/.bashrc
```

## Getting Erlang documentation
## Use

Check [asdf](https://github.com/asdf-vm/asdf) readme for instructions on how to install & manage versions of Erlang. To specify custom options you [can set environment variables just as you would when using kerl](https://github.com/kerl/kerl#build-configuration).

### `KERL_CONFIGURE_OPTIONS `
To use custom build options you could set:

```shell
$ export KERL_CONFIGURE_OPTIONS="--disable-debug --without-javac"
$ asdf install erlang <version>
```
By default it will be set to:

```shell
--disable-debug --disable-silent-rules --enable-dynamic-ssl-lib
--enable-hipe --enable-sctp --enable-shared-zlib --enable-smp-support
--enable-threads --enable-wx --without-javac
additional for macOS
--with-ssl=$(brew --prefix openssl) --enable-darwin-64bit --enable-kernel-poll --with-dynamic-trace=dtrace

```

### `OTP_GITHUB_URL`
To use a different Erlang source from git set the url to a fork:

```shell
$ asdf install erlang ref:master

$ export OTP_GITHUB_URL="https://github.com/basho/otp"
$ asdf install erlang ref:basho
```

### Opting out of prebuilt for macOS

By default macOS will use prebuilt binaries if they're available but you can opt out by setting any of these:
* `OTP_GITHUB_URL`,
* `KERL_CONFIGURE_OPTIONS`
* `ASDF_ERLANG_FROM_SOURCE`

It will also opt out if `ASDF_INSTALL_TYPE` is `ref`


### Opting out of Erlang documentation
To opt out of building documenation you could set:
```shell
export KERL_BUILD_DOCS=NO
```

Erlang may come with documentation included (as man pages, pdfs and html files). This allows typing `erl -man mnesia` to get info on `mnesia` module. asdf-erlang uses kerl for builds, and [kerl](https://github.com/kerl/kerl) is capable of building the docs for specified version of Erlang.

Erlang may come with documentation included (as man pages, pdfs and html files). This allows typing `erl -man mnesia` to get info on `mnesia` module. asdf-erlang uses kerl for builds, and [kerl](https://github.com/kerl/kerl) is capable of building the docs for specified version of Erlang.
For kerl to be able to build Erlang documentation requirements have to be met with additional dependencies have to be installed. For detailed list of dependencies for your OS please refer to the specific section above.

For kerl to be able to build Erlang documentation two requirements have to be met:
1. `KERL_BUILD_DOCS` environment variable has to be set
2. Additional dependencies have to be installed. For detailed list of dependencies for your OS please refer to the specific section above

**Note:** Environment variable has to be set before `asdf install erlang <version>` is executed, to take effect.
### Use a specific version of Kerl

### Setting the environment variable in bash
To use a different version of kerl you could set:
```shell
export ASDF_KERL_VERSION="2.1.1"
```

### Kerl Config

Type: `export KERL_BUILD_DOCS=yes` to create `KERL_BUILD_DOCS` environment variable and set it to `true`. This line could be added to your `.bashrc` in case you want `KERL_BUILD_DOCS` to be set for future (future installations of Erlang).
Note that the `KERL_BASE_DIR` and `KERL_CONFIG` environment variables are set by the plugin to:
```shell
KERL_BASE_DIR="${ASDF_KERL_BASE_DIR:-${ASDF_DATA_DIR:-$HOME/.asdf}/tmp/$(plugin_name)/kerl}"
KERL_CONFIG="${KERL_BASE_DIR:-$(kerl_path)}/.kerlrc"
```
You can override both.

To remove environment variable: `unset KERL_BUILD_DOCS`.
See [kerl](https://github.com/kerl/kerl#locations-on-disk) for the complete list of customization options.

### Setting the environment variable in fish shell

Type: `set -xg KERL_BUILD_DOCS yes` to set environment variable. In case you want it to be persisted between sessions (machine reboots - for example for future installations) type `set -xU KERL_BUILD_DOCS yes`.

To remove environment variable type: `set -e KERL_BUILD_DOCS`.
120 changes: 87 additions & 33 deletions bin/install
Original file line number Diff line number Diff line change
@@ -1,54 +1,108 @@
#!/usr/bin/env bash

export KERL_BUILD_DOCS="${KERL_BUILD_DOCS:-yes}"

set -e

# shellcheck source=../bin/utils.sh
source "$(dirname "$0")/utils.sh"


# shellcheck source=../lib/utils.sh
source "$(dirname $0)/../lib/utils.sh"
ensure_kerl_setup


install_erlang() {
ensure_kerl_setup
local asdf_activation_version
local build_name

build_name="asdf_$ASDF_INSTALL_VERSION"
if [ -z "$OTP_GITHUB_URL" ] && [ "$ASDF_INSTALL_TYPE" = "version" ] && [ -z "$KERL_CONFIGURE_OPTIONS"] && [ -z "$ASDF_ERLANG_FROM_SOURCE" ] && os_name="$(get_macos_marketing_name)"; then
if download_url="$(macos_get_download_url $os_name)"; then
macos_install_from_prebuilt "$download_url"
else
printf 'Fallback to building from source. \n'
install_from_source
fi
else
install_from_source
fi
}



macos_install_from_prebuilt() {
macos_check_homebrew_setup

mkdir -p "$ASDF_INSTALL_PATH"
mkdir -p "$ASDF_DOWNLOAD_PATH"

local download_url="$1"

printf 'Downloading %s. \n' "$download_url"
# Strip "erlang/23.3" folder structure off the tarball when extracting.
curl -L "$download_url" | tar xf - --directory="$ASDF_DOWNLOAD_PATH" --strip-components=2

# We're not keeping the same directory structure as Homebrew.
local replacement_pattern="@@HOMEBREW_CELLAR@@/erlang/$ASDF_INSTALL_VERSION/lib/erlang"

# Replace the homebrew URL with something compatible with asdf
grep -rl --null "$replacement_pattern" "$ASDF_DOWNLOAD_PATH/lib/erlang" | xargs -0 sed -i '' "s:$replacement_pattern:$ASDF_INSTALL_PATH:g"

local linked_libs=(
"$ASDF_DOWNLOAD_PATH/lib/erlang/lib/"crypto-*"/priv/lib/crypto.so"
"$ASDF_DOWNLOAD_PATH/lib/erlang/lib/"wx-*"/priv/wxe_driver.so"
)

# Link Crypto & Wx to brew prefix
macos_update_linked_paths "${linked_libs[@]}"

# Move from download to install
# In the future, maybe copy would be better, but I think keeping downloads is a bad design.
mv -f "$ASDF_DOWNLOAD_PATH/lib/erlang/"* "$ASDF_INSTALL_PATH"
}


install_from_source() {
printf 'Building version %s %s for from source' "$(plugin_name)" "$ASDF_INSTALL_VERSION"
if [ "$KERL_BUILD_DOCS" != "yes" ]; then
unset KERL_BUILD_DOCS
printf ' without documentation. \n'
else
printf ' with documentation. \n'
fi

if [ -z "$KERL_CONFIGURE_OPTIONS" ]; then
printf 'KERL_CONFIGURE_OPTIONS is not set, will use default settings. \n'

export KERL_CONFIGURE_OPTIONS="--disable-debug --disable-silent-rules --enable-dynamic-ssl-lib"
export KERL_CONFIGURE_OPTIONS="$KERL_CONFIGURE_OPTIONS --enable-hipe --enable-sctp --enable-shared-zlib --enable-smp-support"
export KERL_CONFIGURE_OPTIONS="$KERL_CONFIGURE_OPTIONS --enable-threads --enable-wx --without-javac"

if [ "$(uname -s)" = "Darwin" ]; then
macos_check_homebrew_setup "SOURCE"
export KERL_CONFIGURE_OPTIONS="$KERL_CONFIGURE_OPTIONS --with-ssl=$(brew --prefix openssl) --enable-darwin-64bit --enable-kernel-poll --with-dynamic-trace=dtrace"
fi
fi


printf 'With KERL_CONFIGURE_OPTIONS set to: \n %s \n' "$KERL_CONFIGURE_OPTIONS"


local build_name="asdf_$ASDF_INSTALL_VERSION"

export MAKEFLAGS="-j$ASDF_CONCURRENCY"

$(kerl_path) delete installation "$build_name" || true
$(kerl_path) delete build "$build_name" || true

if [ "$ASDF_INSTALL_TYPE" = "ref" ]; then
asdf_activation_version="$ASDF_INSTALL_TYPE:$ASDF_INSTALL_VERSION"
$(kerl_path) build git "${OTP_GITHUB_URL:-https://github.com/erlang/otp.git}" "$ASDF_INSTALL_VERSION" "$build_name"
$(kerl_executable) build git "${OTP_GITHUB_URL:-https://github.com/erlang/otp.git}" "$ASDF_INSTALL_VERSION" "$build_name"
else
asdf_activation_version="$ASDF_INSTALL_VERSION"
$(kerl_path) build "$ASDF_INSTALL_VERSION" "$build_name"
$(kerl_executable) build "$ASDF_INSTALL_VERSION" "$build_name"
fi

$(kerl_path) install "$build_name" "$ASDF_INSTALL_PATH"
$(kerl_path) cleanup "$ASDF_INSTALL_VERSION"
$(kerl_executable) install "$build_name" "$ASDF_INSTALL_PATH"

link_app_executables "$ASDF_INSTALL_PATH"
if [ -z "${ASDF_KERL_BASE_DIR:-}" ]; then
rm -rf "$KERL_BASE_DIR"
fi

echo
echo "Erlang $ASDF_INSTALL_VERSION has been installed. Activate globally with:"
echo
echo " asdf global erlang $asdf_activation_version"
echo
echo "Activate locally in the current folder with:"
echo
echo " asdf local erlang $asdf_activation_version"
echo
}

link_app_executables() {
local install_path=$1

# Link other executables to the bin directory so that asdf shims are created for them
cd "$install_path/bin"

# ln call may fail if multiple executables are found with the same name
ln -s ../lib/*/bin/* ../lib/*/priv/bin/* . || true
}

install_erlang
9 changes: 5 additions & 4 deletions bin/list-all
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
#!/usr/bin/env bash

source "$(dirname $0)/utils.sh"
# shellcheck source=../lib/utils.sh
source "$(dirname $0)/../lib/utils.sh"
ensure_kerl_setup

list_all() {
ensure_kerl_setup

echo "$("$(kerl_path)" list releases | sed -e 's:Run.*::' | tr '\n' ' ')"
list_all() {
printf "$("$(kerl_executable)" list releases | sed -e 's:Run.*::' | tr '\n' ' ')"
}

list_all
Loading