Last active
October 14, 2024 14:49
-
-
Save philsmy/1feeef1974fc58d5d547c6d0bcab3c1f to your computer and use it in GitHub Desktop.
Scripts for configuring an Ubuntu 22 machine (these don't work for 24). Use the first file to create the `deploy` user. Use the other files AS the deploy user to install all you need.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
######################## | |
### SCRIPT VARIABLES ### | |
######################## | |
# Name of the user to create and grant sudo privileges | |
USERNAME=deploy | |
# Whether to copy over the root user's `authorized_keys` file to the new sudo | |
# user. | |
COPY_AUTHORIZED_KEYS_FROM_ROOT=true | |
# Additional public keys to add to the new sudo user | |
# OTHER_PUBLIC_KEYS_TO_ADD=( | |
# "ssh-rsa AAAAB..." | |
# "ssh-rsa AAAAB..." | |
# ) | |
OTHER_PUBLIC_KEYS_TO_ADD=( | |
) | |
#################### | |
### SCRIPT LOGIC ### | |
#################### | |
# Add sudo user and grant privileges | |
useradd --create-home --shell "/bin/bash" --groups sudo "${USERNAME}" | |
# Check whether the root account has a real password set | |
encrypted_root_pw="$(grep root /etc/shadow | cut --delimiter=: --fields=2)" | |
if [ "${encrypted_root_pw}" != "*" ]; then | |
# Transfer auto-generated root password to user if present | |
# and lock the root account to password-based access | |
echo "${USERNAME}:${encrypted_root_pw}" | chpasswd --encrypted | |
passwd --lock root | |
else | |
# Delete invalid password for user if using keys so that a new password | |
# can be set without providing a previous value | |
passwd --delete "${USERNAME}" | |
fi | |
# Expire the sudo user's password immediately to force a change | |
# chage --lastday 0 "${USERNAME}" | |
# Create SSH directory for sudo user | |
home_directory="$(eval echo ~${USERNAME})" | |
mkdir --parents "${home_directory}/.ssh" | |
# Copy `authorized_keys` file from root if requested | |
if [ "${COPY_AUTHORIZED_KEYS_FROM_ROOT}" = true ]; then | |
cp /root/.ssh/authorized_keys "${home_directory}/.ssh" | |
fi | |
# Add additional provided public keys | |
for pub_key in "${OTHER_PUBLIC_KEYS_TO_ADD[@]}"; do | |
echo "${pub_key}" >> "${home_directory}/.ssh/authorized_keys" | |
done | |
# Adjust SSH configuration ownership and permissions | |
chmod 0700 "${home_directory}/.ssh" | |
chmod 0600 "${home_directory}/.ssh/authorized_keys" | |
chown --recursive "${USERNAME}":"${USERNAME}" "${home_directory}/.ssh" | |
# Disable root SSH login with password | |
# sed --in-place 's/^PermitRootLogin.*/PermitRootLogin no/g' /etc/ssh/sshd_config | |
sed --in-place 's/^PasswordAuthentication.*/PasswordAuthentication no/g' /etc/ssh/sshd_config | |
if sshd -t -q; then | |
systemctl restart sshd | |
fi | |
# Add exception for SSH and then enable UFW firewall | |
ufw allow OpenSSH | |
ufw --force enable | |
# get up to date | |
apt update && apt -y upgrade && apt-get autoclean && apt-get -y autoremove |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
# rbenv | |
sudo apt update | |
sudo apt install -y git-core curl zlib1g-dev build-essential libssl-dev libreadline-dev libyaml-dev libsqlite3-dev sqlite3 libxml2-dev libxslt1-dev libcurl4-openssl-dev software-properties-common libffi-dev dirmngr gnupg apt-transport-https ca-certificates redis-server redis-tools nodejs yarn | |
git clone https://github.com/rbenv/rbenv.git ~/.rbenv | |
echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bashrc | |
export PATH="$HOME/.rbenv/bin:$PATH" | |
echo 'eval "$(rbenv init -)"' >> ~/.bashrc | |
eval "$(rbenv init -)" | |
git clone https://github.com/rbenv/ruby-build.git ~/.rbenv/plugins/ruby-build | |
echo 'export PATH="$HOME/.rbenv/plugins/ruby-build/bin:$PATH"' >> ~/.bashrc | |
export PATH="$HOME/.rbenv/plugins/ruby-build/bin:$PATH" | |
git clone https://github.com/rbenv/rbenv-vars.git ~/.rbenv/plugins/rbenv-vars | |
# install the ruby version | |
rbenv install 3.3.1 | |
rbenv global 3.3.1 | |
ruby -v | |
gem install bundler |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
# This is optional (obviously) but if you want to install MySQL and ElasticSearch run this script | |
sudo apt install -y mysql-server | |
sudo systemctl start mysql.service | |
# see https://www.digitalocean.com/community/tutorials/how-to-install-mysql-on-ubuntu-22-04 | |
# for more instructions | |
# and elastic search | |
curl -fsSL https://artifacts.elastic.co/GPG-KEY-elasticsearch | sudo gpg --dearmor -o /usr/share/keyrings/elastic.gpg | |
echo "deb [signed-by=/usr/share/keyrings/elastic.gpg] https://artifacts.elastic.co/packages/7.x/apt stable main" | sudo tee -a /etc/apt/sources.list.d/elastic-7.x.list | |
sudo apt update | |
sudo apt install elasticsearch | |
# see https://www.digitalocean.com/community/tutorials/how-to-install-and-configure-elasticsearch-on-ubuntu-22-04 | |
# for more instructions | |
# if we just need localhost (like for staging) all is good | |
sudo systemctl start elasticsearch | |
sudo systemctl enable elasticsearch |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
# Update package list and install prerequisites | |
sudo apt update | |
sudo apt install -y nginx dirmngr gnupg apt-transport-https ca-certificates curl | |
# Add Phusion Passenger APT repository and key | |
curl https://oss-binaries.phusionpassenger.com/auto-software-signing-gpg-key.txt | gpg --dearmor | sudo tee /etc/apt/trusted.gpg.d/phusion.gpg >/dev/null | |
echo "deb https://oss-binaries.phusionpassenger.com/apt/passenger jammy main" | sudo tee /etc/apt/sources.list.d/passenger.list | |
# Update package list again and install Passenger + Nginx module | |
sudo apt update | |
sudo apt install -y libnginx-mod-http-passenger | |
# Enable Passenger Nginx module if not already enabled | |
if [ ! -f /etc/nginx/modules-enabled/50-mod-http-passenger.conf ]; then | |
sudo ln -s /usr/share/nginx/modules-available/mod-http-passenger.load /etc/nginx/modules-enabled/50-mod-http-passenger.conf | |
fi | |
# Create Passenger configuration file for Nginx | |
sudo tee /etc/nginx/conf.d/mod-http-passenger.conf > /dev/null <<EOF | |
passenger_root /usr/lib/ruby/vendor_ruby/phusion_passenger/locations.ini; | |
passenger_ruby /home/deploy/.rbenv/shims/ruby; | |
passenger_user_switching on; | |
passenger_user deploy; | |
passenger_group deploy; | |
EOF | |
# Restart Nginx to apply changes | |
sudo systemctl restart nginx | |
# Install Certbot for SSL certificate management | |
sudo snap install --classic certbot | |
sudo ln -s /snap/bin/certbot /usr/bin/certbot | |
# Configure UFW to allow 'Nginx Full' and remove 'Nginx HTTP' | |
sudo ufw allow 'Nginx Full' | |
sudo ufw delete allow 'Nginx HTTP' | |
# Ensure proper permissions for Passenger | |
chmod o+x $HOME | |
# Verify installations | |
if ! systemctl is-active --quiet nginx; then | |
echo "Error: Nginx service is not running." | |
exit 1 | |
else | |
echo "Nginx installed and running successfully." | |
fi | |
if ! command -v certbot >/dev/null 2>&1; then | |
echo "Error: Certbot installation failed." | |
exit 1 | |
else | |
echo "Certbot installed successfully." | |
fi | |
echo "Nginx with Passenger installation and configuration completed successfully." |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
# mysql client. May be unnecessary if you are not using mysql | |
sudo apt install -y mysql-client libmysqlclient-dev | |
# we are install node 18 here. You might want higher or lower version | |
sudo apt --fix-broken install | |
sudo apt update | |
sudo apt remove -y nodejs nodejs-doc | |
sudo apt purge nodejs | |
sudo apt autoremove -y | |
cd ~ | |
curl -sL https://deb.nodesource.com/setup_18.x -o nodesource_setup.sh | |
sudo bash nodesource_setup.sh | |
sudo apt install -y nodejs | |
node -v | |
# yarn | |
curl -sL https://dl.yarnpkg.com/debian/pubkey.gpg | gpg --dearmor | sudo tee /usr/share/keyrings/yarnkey.gpg >/dev/null | |
echo "deb [signed-by=/usr/share/keyrings/yarnkey.gpg] https://dl.yarnpkg.com/debian stable main" | sudo tee /etc/apt/sources.list.d/yarn.list | |
sudo apt-get update && sudo apt-get -y install yarn | |
# chromium for the pdf generation | |
sudo apt install -y chromium-browser | |
sudo apt-get update | |
sudo apt-get install -y libgbm1 | |
sudo apt install -y gconf-service libasound2 libatk1.0-0 libc6 libcairo2 libcups2 libdbus-1-3 libexpat1 libfontconfig1 libgcc1 libgconf-2-4 libgdk-pixbuf2.0-0 libglib2.0-0 libgtk-3-0 libnspr4 libpango-1.0-0 libpangocairo-1.0-0 libstdc++6 libx11-6 libx11-xcb1 libxcb1 libxcomposite1 libxcursor1 libxdamage1 libxext6 libxfixes3 libxi6 libxrandr2 libxrender1 libxss1 libxtst6 ca-certificates fonts-liberation libappindicator1 libnss3 lsb-release xdg-utils wget | |
# imagemagick for image processing | |
sudo apt install -y imagemagick |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
# Set APP_NAME from the command-line argument or the environment variable, with a default value if neither is provided | |
APP_NAME=${1:-${APP_NAME:-my-app}} | |
# Ensure APP_NAME is set | |
if [ -z "$APP_NAME" ]; then | |
echo "Error: No application name provided. Please provide it as a command-line argument or set the APP_NAME environment variable." | |
exit 1 | |
fi | |
# Create necessary directories and files | |
mkdir -p /home/deploy/$APP_NAME | |
touch /home/deploy/$APP_NAME/.rbenv-vars | |
# Update irbrc configuration | |
echo 'IRB.conf[:USE_AUTOCOMPLETE] = false' >> /home/deploy/.irbrc | |
# Update bashrc with environment settings and aliases | |
cat << EOF >> /home/deploy/.bashrc | |
export RAILS_ENV=production | |
alias all_logs='sudo tail -f /var/log/nginx/*.log $APP_NAME/shared/log/*.log' | |
alias nginx_logs='sudo tail -f /var/log/nginx/*.log' | |
alias app_logs='sudo tail -f /home/deploy/$APP_NAME/shared/log/production.log' | |
alias "cdcur=cd /home/deploy/$APP_NAME/current" | |
alias "console=cdcur && bundle exec rails console -- --nomultiline" | |
EOF | |
# Example of copying the env file (commented out as in the original script) | |
# scp -i ~/.ssh/${APP_NAME}_rsa .env.production [email protected]:$APP_NAME/.rbenv-vars | |
echo "Setup completed for application: $APP_NAME" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -euo pipefail | |
# Install prerequisites | |
sudo apt-get update | |
sudo apt-get install -y lsb-release curl gpg ufw | |
# Install Redis | |
sudo curl -fsSL https://packages.redis.io/gpg | sudo gpg --dearmor -o /usr/share/keyrings/redis-archive-keyring.gpg | |
echo "deb [signed-by=/usr/share/keyrings/redis-archive-keyring.gpg] https://packages.redis.io/deb $(lsb_release -cs) main" | sudo tee /etc/apt/sources.list.d/redis.list > /dev/null | |
sudo apt-get update | |
sudo apt-get install -y redis | |
# Configure Redis | |
sudo bash -c 'echo "supervised systemd" >> /etc/redis/redis.conf' | |
sudo systemctl restart redis.service | |
# Enable Redis to start on boot | |
sudo systemctl enable redis.service | |
# Allow Redis through the firewall | |
sudo ufw allow 6379 | |
# Verify Redis installation | |
if ! systemctl is-active --quiet redis; then | |
echo "Error: Redis service is not running." | |
exit 1 | |
else | |
echo "Redis installed and running successfully." | |
fi | |
# Install Memcached | |
sudo apt-get install -y memcached libmemcached-tools | |
# Enable Memcached to start on boot | |
sudo systemctl enable memcached.service | |
# Start Memcached service | |
sudo systemctl start memcached.service | |
# Verify Memcached installation | |
if ! systemctl is-active --quiet memcached; then | |
echo "Error: Memcached service is not running." | |
exit 1 | |
else | |
echo "Memcached installed and running successfully." | |
fi | |
echo "Redis and Memcached installation and configuration completed successfully." |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# goes in /etc/nginx/sites-available/my-app | |
# but really it's better to use ssl | |
server { | |
server_name _; | |
listen 80; | |
root /home/deploy/my-app/current/public; | |
passenger_enabled on; | |
passenger_app_env production; | |
passenger_preload_bundler on; | |
access_log /var/log/nginx/app.access.log; | |
error_log /var/log/nginx/app.error.log; | |
location /cable { | |
passenger_app_group_name my-app_websocket; | |
passenger_force_max_concurrent_requests_per_process 0; | |
} | |
# Allow uploads up to 100MB in size | |
client_body_buffer_size 10K; | |
client_header_buffer_size 1k; | |
client_max_body_size 100m; | |
large_client_header_buffers 4 4k; | |
client_body_timeout 12; | |
client_header_timeout 12; | |
keepalive_timeout 15; | |
send_timeout 10; | |
gzip on; | |
gzip_disable "msie6"; | |
gzip_vary on; | |
gzip_proxied any; | |
gzip_min_length 1024; | |
gzip_comp_level 6; | |
gzip_buffers 16 8k; | |
gzip_http_version 1.1; | |
gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript; | |
location ~ ^/(assets|packs) { | |
expires max; | |
gzip_static on; | |
} | |
location ~ /apple-icon.png { | |
return 204; | |
log_not_found off; | |
} | |
if (-f $document_root/system/maintenance.html) { | |
return 503; | |
} | |
error_page 503 @maintenance; | |
location @maintenance { | |
rewrite ^(.*)$ /system/maintenance.html break; | |
} | |
location ~* ^/(?:favicon|apple-touch-icon|android-chrome-|mstile-|safari-pinned-tab.svg|browserconfig.xml|mainfest.json) { | |
root /home/deploy/my-app/current/public; | |
} | |
location = /browserconfig.xml { | |
root /home/deploy/my-app/current/public; | |
} | |
location = /manifest.json { | |
root /home/deploy/my-app/current/public; | |
} | |
location = /ads.txt { | |
root /home/deploy/my-app/current/public; | |
} | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment