4 ## Do we have enough memory and disk space for Discourse?
6 check_disk_and_memory
() {
8 avail_mem
="$(LANG=C free -m | grep '^Mem:' | awk '{print $2}')"
9 if [ "$avail_mem" -lt 900 ]; then
10 echo "WARNING: Discourse requires 1GB RAM to run. This system does not appear"
11 echo "to have sufficient memory."
13 echo "Your site may not work properly, or future upgrades of Discourse may not"
14 echo "complete successfully."
18 if [ "$avail_mem" -lt 1800 ]; then
19 total_swap
="$(LANG=C free -m | grep ^Swap: | awk '{print $2}')"
20 if [ "$total_swap" -lt 1000 ]; then
21 echo "WARNING: Discourse requires at least 1GB of swap when running with less "
22 echo "than 2GB of RAM. This system does not appear to have sufficient swap space."
24 echo "Without sufficient swap space, your site may not work properly, and future"
25 echo "upgrades of Discourse may not complete successfully."
27 read -p "Press ENTER to create a 2GB swapfile automatically, or Ctrl-C to exit"
30 ## derived from https://meta.discourse.org/t/13880
32 install -o root
-g root
-m 0600 /dev
/null
/swapfile
33 dd if=/dev
/zero of
=/swapfile bs
=1k count
=2048k
36 echo "/swapfile swap swap auto 0 0" | sudo
tee -a /etc
/fstab
37 sudo sysctl
-w vm.swappiness
=10
38 echo vm.swappiness
= 10 | sudo
tee -a /etc
/sysctl.conf
40 total_swap
="$(LANG=C free -m | grep ^Swap: | awk '{print $2}')"
41 if [ "$total_swap" -lt 1000 ]; then
42 echo "Failed to create swap, sorry!"
49 free_disk
="$(df /var | tail -n 1 | awk '{print $4}')"
50 if [ "$free_disk" -lt 5000 ]; then
51 echo "WARNING: Discourse requires at least 5GB free disk space. This system"
52 echo "does not appear to have sufficient disk space."
54 echo "Insufficient disk space may result in problems running your site, and"
55 echo "may not even allow Discourse installation to complete successfully."
57 echo "Please free up some space, or expand your disk, before continuing."
59 echo "Run \`apt-get autoremove && apt-get autoclean\` to clean up unused"
60 echo "packages and \`./launcher cleanup\` to remove stale Docker containers."
68 ## If we have lots of RAM or lots of CPUs, bump up the defaults to scale better
72 local changelog
=/tmp
/changelog.
$PPID
73 # grab info about total system ram and physical (NOT LOGICAL!) CPU cores
74 avail_mem
="$(LANG=C free -m | grep '^Mem:' | awk '{print $2}')"
75 avail_gb
=$
(( $avail_mem / 950 ))
76 avail_cores
=`cat /proc/cpuinfo | grep "cpu cores" | uniq | awk '{print $4}'`
77 echo "Found ${avail_gb}GB of memory and $avail_cores physical CPU cores"
79 # db_shared_buffers: 128MB for 1GB, 256MB for 2GB, or 256MB * GB, max 4096MB
80 if [ "$avail_gb" -eq "1" ]
84 if [ "$avail_gb" -eq "2" ]
88 db_shared_buffers
=$
(( 256 * $avail_gb ))
91 db_shared_buffers
=$
(( db_shared_buffers
< 4096 ? db_shared_buffers
: 4096 ))
93 sed -i -e "s/^ #db_shared_buffers:.*/ db_shared_buffers: \"${db_shared_buffers}MB\"/w $changelog" $config_file
96 echo "setting db_shared_buffers = ${db_shared_buffers}MB"
100 # UNICORN_WORKERS: 2 * GB for 2GB or less, or 2 * CPU, max 8
101 if [ "$avail_gb" -le "2" ]
103 unicorn_workers
=$
(( 2 * $avail_gb ))
105 unicorn_workers
=$
(( 2 * $avail_cores ))
107 unicorn_workers
=$
(( unicorn_workers
< 8 ? unicorn_workers
: 8 ))
109 sed -i -e "s/^ #UNICORN_WORKERS:.*/ UNICORN_WORKERS: ${unicorn_workers}/w $changelog" $config_file
112 echo "setting UNICORN_WORKERS = ${unicorn_workers}"
120 ## standard http / https ports must not be occupied
125 echo "Ports 80 and 443 are free for use"
130 ## check a port to see if it is already in use
134 local valid
=$
(netstat
-tln |
awk '{print $4}' |
grep ":${1}\$")
136 if [ -n "$valid" ]; then
137 echo "Port ${1} appears to already be in use."
139 echo "If you are trying to run Discourse simultaneously with another web"
140 echo "server like Apache or nginx, you will need to bind to a different port"
142 echo "See https://meta.discourse.org/t/17247"
148 ## prompt user for typical Discourse config file values
150 ask_user_for_config
() {
152 local changelog
=/tmp
/changelog.
$PPID
153 local hostname
="discourse.example.com"
154 local developer_emails
="me@example.com,you@example.com"
155 local smtp_address
="smtp.example.com"
156 local smtp_user_name
="postmaster@discourse.example.com"
157 local smtp_password
=""
158 local letsencrypt_account_email
="me@example.com"
159 local letsencrypt_status
="ENTER to skip"
167 while [[ "$config_ok" == "n" ]]
169 if [ ! -z $hostname ]
171 read -p "Hostname for your Discourse? [$hostname]: " new_value
172 if [ ! -z $new_value ]
178 if [ ! -z $developer_emails ]
180 read -p "Email address for admin account? [$developer_emails]: " new_value
181 if [ ! -z $new_value ]
183 developer_emails
=$new_value
187 if [ ! -z $smtp_address ]
189 read -p "SMTP server address? [$smtp_address]: " new_value
190 if [ ! -z $new_value ]
192 smtp_address
=$new_value
196 if [ "$smtp_address" == "smtp.sparkpostmail.com" ]
198 smtp_user_name
="SMTP_Injection"
201 if [ "$smtp_address" == "smtp.sendgrid.net" ]
203 smtp_user_name
="apikey"
206 if [ ! -z $smtp_user_name ]
208 read -p "SMTP user name? [$smtp_user_name]: " new_value
209 if [ ! -z $new_value ]
211 smtp_user_name
=$new_value
215 read -p "SMTP password? [$smtp_password]: " new_value
216 if [ ! -z $new_value ]
218 smtp_password
=$new_value
221 if [ ! -z $letsencrypt_account_email ]
223 read -p "Let's Encrypt account email? ($letsencrypt_status) [$letsencrypt_account_email]: " new_value
224 if [ ! -z $new_value ]
226 letsencrypt_account_email
=$new_value
227 if [ "$new_value" == "off" ]
229 letsencrypt_status
="ENTER to skip"
231 letsencrypt_status
="Enter 'OFF' to disable."
236 echo -e "\nDoes this look right?\n"
237 echo "Hostname : $hostname"
238 echo "Email : $developer_emails"
239 echo "SMTP address : $smtp_address"
240 echo "SMTP username : $smtp_user_name"
241 echo "SMTP password : $smtp_password"
243 if [ "$letsencrypt_status" == "Enter 'OFF' to disable." ]
245 echo "Let's Encrypt : $letsencrypt_account_email"
249 read -p "Press ENTER to continue, 'n' to try again, or ^C to exit: " config_ok
252 sed -i -e "s/^ DISCOURSE_HOSTNAME:.*/ DISCOURSE_HOSTNAME: $hostname/w $changelog" $config_file
257 echo "DISCOURSE_HOSTNAME change failed."
261 sed -i -e "s/^ DISCOURSE_DEVELOPER_EMAILS:.*/ DISCOURSE_DEVELOPER_EMAILS: \'$developer_emails\'/w $changelog" $config_file
266 echo "DISCOURSE_DEVELOPER_EMAILS change failed."
270 sed -i -e "s/^ DISCOURSE_SMTP_ADDRESS:.*/ DISCOURSE_SMTP_ADDRESS: $smtp_address/w $changelog" $config_file
275 echo "DISCOURSE_SMTP_ADDRESS change failed."
279 sed -i -e "s/^ #DISCOURSE_SMTP_USER_NAME:.*/ DISCOURSE_SMTP_USER_NAME: $smtp_user_name/w $changelog" $config_file
284 echo "DISCOURSE_SMTP_USER_NAME change failed."
288 sed -i -e "s/^ #DISCOURSE_SMTP_PASSWORD:.*/ DISCOURSE_SMTP_PASSWORD: $smtp_password/w $changelog" $config_file
293 echo "DISCOURSE_SMTP_PASSWORD change failed."
297 if [ "$letsencrypt_status" != "ENTER to skip" ]
299 sed -i -e "s/^ #LETSENCRYPT_ACCOUNT_EMAIL:.*/ LETSENCRYPT_ACCOUNT_EMAIL: $letsencrypt_account_email/w $changelog" $config_file
304 echo "LETSENCRYPT_ACCOUNT_EMAIL change failed."
307 local src
='^ #- "templates\/web.ssl.template.yml"'
308 local dst
=' \- "templates\/web.ssl.template.yml"'
309 sed -i -e "s/$src/$dst/w $changelog" $config_file
312 echo "web.ssl.template.yml enabled"
315 echo "web.ssl.template.yml NOT ENABLED--was it on already?"
317 local src
='^ #- "templates\/web.letsencrypt.ssl.template.yml"'
318 local dst
=' - "templates\/web.letsencrypt.ssl.template.yml"'
320 sed -i -e "s/$src/$dst/w $changelog" $config_file
323 echo "letsencrypt.ssl.template.yml enabled"
326 echo "letsencrypt.ssl.template.yml NOT ENABLED -- was it on already?"
330 if [ "$update_ok" == "y" ]
332 echo -e "\nConfiguration file at $config_file updated successfully!\n"
334 echo -e "\nUnfortunately, there was an error changing $config_file\n"
340 ## is our config file valid? Does it have the required fields set?
346 for x
in DISCOURSE_SMTP_ADDRESS DISCOURSE_SMTP_USER_NAME DISCOURSE_SMTP_PASSWORD \
347 DISCOURSE_DEVELOPER_EMAILS DISCOURSE_HOSTNAME
349 config_line
=`grep "^ $x:" $config_file`
351 local default
="example.com"
355 if [[ $config_line = *"$default"* ]]
357 echo "$x left at incorrect default of example.com"
360 config_val
=`echo $config_line | awk '{print $2}'`
361 if [ -z $config_val ]
363 echo "$x was left blank"
367 echo "$x not present"
372 if [ "$valid_config" != "y" ]; then
373 echo -e "\nSorry, these $config_file settings aren't valid -- can't continue!"
380 ## template file names
383 template_path
=samples
/standalone.yml
384 config_file
=containers
/$app_name.yml
385 changelog
=/tmp
/changelog
388 ## Check requirements before creating a copy of a config file we won't edit
390 check_disk_and_memory
394 ## make a copy of the simple standalone config file
396 if [ -a $config_file ]
398 echo "The configuration file $config_file already exists!"
400 echo "If you want to delete your old configuration file and start over:"
401 echo "rm $config_file"
404 cp $template_path $config_file
412 ## if we reach this point without exiting, OK to proceed
414 .
/launcher bootstrap
$app_name
415 .
/launcher start
$app_name