How to Install Discourse on a CentOS 7 Cloud VPS

Discourse is a simple and clean, open-source forum platform built with Ruby on Rails. This tutorial describes how to install Discourse on a CentOS 7 Cloud VPS.

Before we start installing Discourse, ensure that you have the following minimum versions installed on your VPS:

  • Ruby version 2.3+
  • PostgreSQL version 9.3+
  • Redis 2.6+

In this tutorial, we will cover the installation of all these requirements.

Login to your CentOS 7 VPS via SSH as user root

ssh root@IP_Address

and update all services installed on your VPS

yum -y update

Install the following dependencies

yum install -y patch libyaml-devel patch readline-devel libffi-devel openssl-devel bzip2 libtool bison sqlite-devel sudo

Create a new system user for Discourse

adduser --shell /bin/bash discourse
mkdir /var/www/discourse
install -d -m 755 -o discourse -g discourse /var/www/discourse

Install Nginx web server, start it and enable it to automatically start on boot

yum install nginx
systemctl start nginx
systemctl enable nginx

Discourse uses Redis as key-value data store cache. Run the following command to install Redis on your VPS

yum install redis

Once it is installed, start Redis and enable it to start at system boot

systemctl start redis
systemctl enable redis

Install a mail server on your VPS

yum install -y postfix

Configure postfix based on your requirements and setup.

Discourse stores its data in a PostgreSQL database, so now, we will install PostgreSQL server

yum install postgresql-server postgresql-devel  postgresql-contrib

Create a new PostgreSQL database cluster:

postgresql-setup initdb

And run the following commands to start the SQL server and enable it to start on boot

systemctl start postgresql
systemctl enable postgresql

Create a Discourse database user

su postgres
createuser -s discourse
psql -c "alter user discourse password 'PASSWORD';"
exit

Install RVM

su discourse
curl -s -S -L https://get.rvm.io | bash -s stable
rvm install ruby

And now install Ruby using RVM

rvm install ruby
bash --login
rvm use ruby

You can check if Ruby is properly installed using the following command

ruby -v
ruby 2.3.3p222 (2016-11-21 revision 56859) [x86_64-linux]

Install Bundler

gem install bundler

Fetching: bundler-1.13.7.gem (100%)
Successfully installed bundler-1.13.7
Parsing documentation for bundler-1.13.7
Installing ri documentation for bundler-1.13.7
Done installing documentation for bundler after 5 seconds
1 gem installed

Install and setup Bluepill

gem install bluepill
echo 'alias bluepill="NOEXEC_DISABLE=1 bluepill --no-privileged -c ~/.bluepill"' >> ~/.bashrc
source ~/.bashrc
rvm wrapper $(rvm current) bootup bluepill
rvm wrapper $(rvm current) bootup bundle

and create a cronjob for Bluepill

crontab -e
@reboot RUBY_GC_MALLOC_LIMIT=90000000 RAILS_ROOT=/var/www/discourse RAILS_ENV=production NUM_WEBS=2 /home/discourse/.rvm/bin/bootup_bluepill --no-privileged -c ~/.bluepill load /var/www/discourse/config/discourse.pill

Pull down Discourse from their official GitHub account

cd /var/www/discourse
git clone git://github.com/discourse/discourse.git .

Create configuration files and setup Discourse

cp config/discourse.pill.sample config/discourse.pill
cp config/discourse_defaults.conf config/discourse.conf

Edit the discourse.conf file and enter your hostname, all necessary information about the PostgreSQL database and user and your mail server information.

Create and initialize Discourse PostgreSQL database

createdb discourse
RUBY_GC_MALLOC_LIMIT=90000000 RAILS_ENV=production bundle exec rake db:migrate
RUBY_GC_MALLOC_LIMIT=90000000 RAILS_ENV=production bundle exec rake assets:precompile

Now, execute the following command to start Discourse

RUBY_GC_MALLOC_LIMIT=90000000 RAILS_ROOT=/var/www/discourse RAILS_ENV=production NUM_WEBS=2 bluepill --no-privileged -c ~/.bluepill load /var/www/discourse/config/discourse.pill
exit

Create Nginx configuration files and configure it for Discourse

cp /var/www/discourse/config/nginx.global.conf /etc/nginx/conf.d/local-server.conf
cp var/www/discourse/config/nginx.sample.conf /etc/nginx/conf.d/discourse.conf
mkdir -p /var/nginx/cache

edit the /etc/nginx/conf.d/discourse.conf file, change the server_name with your domain name.

Restart nginx for the changes to take effect.

systemctl restart nginx

If you closely followed this tutorial, you will able to access Discourse in your favorite web browser at http://yourdomain.tld . For more information about Discourse please visit their official website.


Of course, you don’t have to do any of this if you use one of our Linux Cloud VPS Hosting services, in which case you can simply ask our expert Linux admins to install this on your server for you. They are available 24×7 and will take care of your request immediately.

PS. If you liked this post please share it with your friends on the social networks using the buttons on the left or simply leave a reply below. Thanks.

5 thoughts on “How to Install Discourse on a CentOS 7 Cloud VPS”

  1. Hi, great guide!

    I’m following it, but there are a few errors I’m getting… I’m using latest CentOS 7.

    ruby version currently is: ruby 2.4.0p0 (2016-12-24 revision 57164) [x86_64-linux]

    The errors appear when I execute:
    RUBY_GC_MALLOC_LIMIT=90000000 RAILS_ENV=production bundle exec rake db:migrate

    And this is the output:
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/rake-11.2.2/lib/rake/ext/fixnum.rb:4: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/sprockets-3.6.3/lib/sprockets/digest_utils.rb:47: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/sprockets-3.6.3/lib/sprockets/digest_utils.rb:51: warning: constant ::Bignum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/sprockets-3.6.3/lib/sprockets/processor_utils.rb:110: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/sprockets-3.6.3/lib/sprockets/processor_utils.rb:111: warning: constant ::Bignum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/concurrent-ruby-1.0.2/lib/concurrent/map.rb:206: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/thread_safe-0.3.5/lib/thread_safe/cache.rb:155: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/redis-3.3.1/lib/redis/client.rb:459: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/thread_safe-0.3.5/lib/thread_safe/cache.rb:155: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/core_ext/numeric/conversions.rb:121: warning: constant ::Fixnum is deprecated
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/core_ext/numeric/conversions.rb:121: warning: constant ::Bignum is deprecated
    rake aborted!
    SystemStackError: stack level too deep
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/core_ext/numeric/conversions.rb:124:in `block (2 levels) in ‘
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/core_ext/numeric/conversions.rb:131:in `block (2 levels) in ‘
    …..
    [like a thousand lines ommited with the same output]
    …..
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/core_ext/numeric/conversions.rb:131:in `block (2 levels) in ‘
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/core_ext/numeric/conversions.rb:131:in `block (2 levels) in ‘
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/bundler-1.14.6/lib/bundler/rubygems_integration.rb:352:in `!~’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/bundler-1.14.6/lib/bundler/rubygems_integration.rb:352:in `block (2 levels) in replace_gem’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activerecord-4.2.7.1/lib/active_record/connection_adapters/postgresql_adapter.rb:16:in `’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:274:in `require’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:274:in `block in require’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:240:in `load_dependency’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:274:in `require’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activerecord-4.2.7.1/lib/active_record/connection_adapters/connection_specification.rb:175:in `spec’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activerecord-4.2.7.1/lib/active_record/connection_handling.rb:50:in `establish_connection’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activerecord-4.2.7.1/lib/active_record/railtie.rb:120:in `block (2 levels) in ‘
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/lazy_load_hooks.rb:38:in `instance_eval’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/lazy_load_hooks.rb:38:in `execute_hook’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/lazy_load_hooks.rb:28:in `block in on_load’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/lazy_load_hooks.rb:27:in `each’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/lazy_load_hooks.rb:27:in `on_load’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activerecord-4.2.7.1/lib/active_record/railtie.rb:116:in `block in ‘
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/initializable.rb:30:in `instance_exec’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/initializable.rb:30:in `run’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/initializable.rb:55:in `block in run_initializers’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/initializable.rb:54:in `run_initializers’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/application.rb:352:in `initialize!’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/railtie.rb:194:in `public_send’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/railtie.rb:194:in `method_missing’
    /opt/discourse/config/environment.rb:5:in `’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:274:in `require’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:274:in `block in require’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:240:in `load_dependency’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/activesupport-4.2.7.1/lib/active_support/dependencies.rb:274:in `require’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/application.rb:328:in `require_environment!’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/railties-4.2.7.1/lib/rails/application.rb:457:in `block in run_tasks_blocks’
    /home/discourse/.rvm/gems/ruby-2.4.0/gems/rake-11.2.2/exe/rake:27:in `’
    /home/discourse/.rvm/gems/ruby-2.4.0/bin/ruby_executable_hooks:15:in `eval’
    /home/discourse/.rvm/gems/ruby-2.4.0/bin/ruby_executable_hooks:15:in `’
    Tasks: TOP => db:migrate => environment
    (See full trace by running task with –trace)

    And the same happens with the next command:
    RUBY_GC_MALLOC_LIMIT=90000000 RAILS_ENV=production bundle exec rake assets:precompile

    Do you know what’s wrong with this? Unfortunately I don’t have experience with ruby deploys…

    Thanks in advance!!

    Reply
      • Hi admin,
        Thanks for your fast reply!

        I’ve checked that, according to https://www.ruby-lang.org/en/, ruby 2.4.0 seems to be the latest version…

        Do you consider the docker version of discourse to be production-ready?

        Thanks again!!

        Reply

Leave a Comment