1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98#!/bin/bash
set -eu
BUILDPACK_DIR="$(dirname "$(dirname "$0")")"
# see https://devcenter.heroku.com/articles/buildpack-api#bin-compile
BUILD_DIR=${1:-}
CACHE_DIR=${2:-}
cd "$BUILD_DIR"
mkdir -p "$CACHE_DIR"
### Install Node.js & pnpm and build frontend
JQ_VERSION="1.7"
JQ="$CACHE_DIR/jq-$JQ_VERSION"
if [ ! -x "$JQ" ]; then
echo "-----> Installing jq v$JQ_VERSION"
curl --proto '=https' --tlsv1.2 --location https://github.com/jqlang/jq/releases/download/jq-1.7/jq-linux-amd64 --output "$JQ"
chmod +x "$JQ"
else
echo "-----> jq v$JQ_VERSION already installed"
fi
echo "-----> Parsing pnpm version from \`package.json\` file"
PNPM_VERSION="$($JQ ".engines.pnpm" "package.json" --raw-output)"
export PNPM_VERSION
export PNPM_HOME="$CACHE_DIR/pnpm"
echo "-----> Installing pnpm v$PNPM_VERSION"
# see https://github.com/pnpm/get.pnpm.io/pull/35 for why the install script is vendored
ENV="$CACHE_DIR/.shrc" SHELL="$(which sh)" sh "$BUILDPACK_DIR/install_pnpm.sh"
export PATH="$PNPM_HOME:$PATH"
echo "-----> Parsing Node.js version from \`package.json\` file"
NODE_VERSION="$($JQ ".engines.node" "package.json" --raw-output)"
if [ ! -x "$PNPM_HOME/nodejs/$NODE_VERSION" ]; then
echo "-----> Installing Node.js v$NODE_VERSION"
pnpm env use --global "$NODE_VERSION"
else
echo "-----> Node.js v$NODE_VERSION already installed"
fi
echo "-----> pnpm install"
pnpm install
echo "-----> pnpm run build"
pnpm run build
echo "-----> rm -rf node_modules"
rm -rf node_modules
### Install Rust and build backend
export RUSTUP_HOME="$CACHE_DIR/rustup"
export CARGO_HOME="$CACHE_DIR/cargo"
export CARGO_TARGET_DIR="$CACHE_DIR/target"
if [ ! -x "$CARGO_HOME/bin/rustup" ]; then
echo "-----> Installing rustup"
curl --proto '=https' --tlsv1.2 https://sh.rustup.rs | sh -s -- --default-toolchain none -y
else
echo "-----> rustup already installed"
fi
export PATH="$CARGO_HOME/bin:$PATH"
echo "-----> rustup set profile minimal"
rustup set profile minimal
echo "-----> cargo build"
cargo build --release
echo "-----> Copying compiled binaries into \`./target/release\` folder"
mkdir -p target/release
find "$CARGO_TARGET_DIR/release" -maxdepth 1 -type f -executable -exec cp -a -t target/release {} \;
echo "-----> Cleaning up cache folder"
# We can remove this completely, as cargo will recreate this from `cache`
rm -rf "$CARGO_HOME/registry/src"
# Remove dependencies that haven't been touched in the past 20 days
if [ -d "$CARGO_TARGET_DIR/release/.fingerprint" ]; then
find "$CARGO_TARGET_DIR/release/.fingerprint" -maxdepth 1 -type d -mtime +20 -exec rm -rf {} \;
fi
if [ -d "$CARGO_TARGET_DIR/release/build" ]; then
find "$CARGO_TARGET_DIR/release/build" -maxdepth 1 -type d -mtime +20 -exec rm -rf {} \;
fi
if [ -d "$CARGO_TARGET_DIR/release/deps" ]; then
find "$CARGO_TARGET_DIR/release/deps" -maxdepth 1 -type d -mtime +20 -exec rm -rf {} \;
fi