I have been running Redmine in Fedora Linux from Fedora Linux 16 to Fedora Linux 20. The instruction I am using to install and upgrade Redmine is from a
Redmine's wiki page. In this post, I would like to first briefly document the steps to install
Redmine on Feodra Linux, at present
Fedora Linux 20, integrate Redmine with the
Apache HTTP server, and then discuss a few issues that we would probably need to deal with when upgrading Fedora Linux and in turn when upgrading Redmine.
Note that the process described below can be automated by a shell script I wrote. See
this post for more detail.
Installing Redmine on Fedora Linux 20
The instruction is generally a copy of a
Redmine's wiki page with more detailed steps on Fedora Linux and with intention to answer the questions raised in the
page here.
Meeting Prerequisites
Before we begin, we will make sure that the Fedora Linux systems has the following software installed,
- Ruby and Ruby bundler
- Apache HTTP Server
- Phusion Passenger.
Although Redmine can run as a standalone server, it is recommended to integrate it with a HTTP server.
One may use Phusion Passenger, FCGI or a Rack server (Unicorn, Thin, Puma, hellip;) to integrate with the Apache
HTTP Server. In this post, we use Phusion Passenger.
- PostgreSQL database server and PostgreSQL development package.
Among two relational database management system that Redmine supports, MySQL and PostgreSQL, I personally prefer
PostgreSQL to MySQL as a result that PostgreSQL's license
is less restricted than MySQL's.
- The GNU C complier.
- The image display and manipulation tool
ImageMagick
and its development package
- The non-interactive network downloader
wget
- The archiver tool
tar
In addition, we assume that a user has an username what is in the "Administrator" group, i.e., the user can switch to user "root" using via <code>sudo</code>.
In this section, we show the steps to meet the prerequisites. If the prerequisites are already met, the following steps are expected not to have any impact on the system.
- Installing Ruby and Ruby bundler.
# install the Ruby package
sudo yum install ruby
# install the Ruby development package
sudo yum install ruby-devel
# install Ruby's bundler
sudo yum install rubygem-bundler
- Installing Apache HTTP Server.
# install the Apache HTTP Server
sudo yum install httpd
# enable the HTTPD service at system boot time
sudo systemctl enable httpd.service
# start the HTTPD service
sudo systemctl start httpd.service
- Installing Phusion Passenger for Apache HTTP Server.
sudo yum install mod_passenger
- Installing PostgreSQL database server and PostgreSQL development package.
# install the PostgreSQL database server package
sudo yum install postgresql-server postgresql-devel
# enable postgresql's start during the boot using following command
sudo systemctl enable postgresql.service
# initialize the postgresql database
sudo postgresql-setup initdb
# start the postgresql service.
sudo systemctl start postgresql.service
- Installing the GNU C complier.
sudo yum install gcc
- Installing the image display and manipulation tool
ImageMagick
sudo yum install ImageMagick ImageMagick-devel
- Installing the non-interactive network downloader
wget
.
sudo yum install wget
- Install the archiver tool
tar
.
sudo yum install tar
- Install a few additional packages to work with
subversion
.
yum install perl-DBI perl-Digest-SHA mod_dav_svn
Installing Redmine
-
Download and extract Redmine source.
The URL of Redmine sources are available in this page.
Assume that we are to download Redmine 2.6.0 (released on 2014-10-21) and plan to install it at the
directory /var/www/redmine.
cd /var/www/
sudo wget -q http://www.redmine.org/releases/redmine-2.6.0.tar.gz
sudo tar -xzf redmine-2.6.0.tar.gz
We can now verify that we have successfully downloaded and extracted the Redmine source.
$ ls -l redmine-2.6.0
total 76
drwxrwxr-x. 7 1000 1000 4096 Oct 21 15:13 app
drwxrwxr-x. 5 1000 1000 4096 Oct 21 15:13 config
-rw-rw-r--. 1 1000 1000 160 Oct 21 15:13 config.ru
-rw-rw-r--. 1 1000 1000 240 Oct 21 15:13 CONTRIBUTING.md
drwxrwxr-x. 3 1000 1000 4096 Oct 21 15:13 db
drwxrwxr-x. 2 1000 1000 4096 Oct 21 15:13 doc
drwxrwxr-x. 5 1000 1000 4096 Oct 21 15:13 extra
drwxrwxr-x. 2 1000 1000 4096 Oct 21 15:13 files
-rw-rw-r--. 1 1000 1000 3555 Oct 21 15:13 Gemfile
drwxrwxr-x. 8 1000 1000 4096 Oct 21 15:13 lib
drwxrwxr-x. 2 1000 1000 4096 Oct 21 15:13 log
drwxrwxr-x. 2 1000 1000 4096 Oct 21 15:13 plugins
drwxrwxr-x. 7 1000 1000 4096 Oct 21 15:13 public
-rw-rw-r--. 1 1000 1000 275 Oct 21 15:13 Rakefile
-rw-rw-r--. 1 1000 1000 205 Oct 21 15:13 README.rdoc
drwxrwxr-x. 2 1000 1000 4096 Oct 21 15:13 script
drwxrwxr-x. 9 1000 1000 4096 Oct 21 15:13 test
drwxrwxr-x. 8 1000 1000 4096 Oct 21 15:13 tmp
drwxrwxr-x. 2 1000 1000 4096 Oct 21 15:13 vendor
-
Creating an empty database and accompanying user for Redmine.
We now create a PostgreSQL database for Redmine. In the commands below, we assume the
password is "my_password" for demonstration and should choose a more thoughtful
one.
Also, we also name the database for Redmine
as "redmine". It does not
have to be and can be any valid PostgreSQL database name.
# switch to user postgres
sudo su - postgres
# create database role redmine
echo \
"CREATE ROLE redmine LOGIN ENCRYPTED
PASSWORD 'my_password' NOINHERIT VALID UNTIL 'infinity';" | \
psql
# create database named redmine for Redmine
echo \
"CREATE DATABASE redmine WITH ENCODING='UTF8' OWNER=redmine;" | \
psql
# edit PostgreSQL Client Authentication Configuration File
sed -e \
"/host.*all.*all.*::1\/128.*ident/i host redmine redmine ::1/128 md5" \
--in-place=.bu /var/lib/pgsql/data/pg_hba.conf
# restart PostgreSQL database server
sudo systemctl restart postgresql.service
# exit from user postgres
exit
The change to the PostgreSQL client authentication configuration file,
by default at /var/lib/pgsql/data/pg_hba.conf
is necessary
to Redmine to establish a connection to the database. The working
configuration depends on a few factors and can be an issue.
More discussion is available. However,
the above configuration works on a Fedora Linux distribution with
IPv6 enabled, which is the default setting.
-
Configuring database connection.
We will follow the instruction of Step 3 in the
Redmine wiki page.
We will copy ${REDMINE}/config/database.yml.example
to
${REDMINE}/config/database.yml
and edit
the file in order to configure the database settings for "production" environment. In this
example, ${REDMINE} is /var/www/redmine-2.6.0
.
With the PostgreSQL database parameters used in the above step, the "production" section of
${REDMINE}/config/database.yml
should be replaced as follows,
production:
adapter: postgresql
database: redmine
host: localhost
username: redmine
password: my_password
encoding: utf8
If you do not wish to use the MySQL database management system at all, comment out any sections that
refers to the MySQL database management system in the configuration file. In this post, we assume that
you do not use the MySQL database management system and your system many not have the MySQL client
library and development head files installed. To make the point clear, we list the content of a desired
database configuration file as follows,
$ cat ${REDMINE}/config/database.yml
production:
adapter: postgresql
database: redmine
host: localhost
username: redmine
password: my_password
encoding: utf8
where ${REDMINE} is /var/www/redmine-2.6.0
in this example.
More discussion on potential
dependency issue caused by the configuration file is available.
-
Installing
Redmine
Ruby
dependencies using the Ruby Dependency Management tool bundle
.
Following the generic instruction in
the Redmine wiki page,
We shall install Redmine's ruby
dependencies using bundle
.
There are some subtle issues to install Redmine's Ruby
dependencies using the
tool. We use a workaround to circumvent the issues, that is, we run
bundle
under a non-root user with login permission and specify the path in which
the dependencies will be installed. In this example, we assume that the non-root username is
your username foouser
and the directory to install the dependencies is
${REDMINE}/.bundle/ruby
where ${REDMINE} is /var/www/redmine-2.6.0
in
this example. Replace foouser
with your actual username.
# give your user userfoo read and write permission to ${REDMINE}
sudo chown -R userfoo ${REDMINE}
# make sure that the working directory is ${REDMINE}
# in this example, ${REDMINE} is /var/www/redmine-2.6.0
cd ${REDMINE}
# install Redmine's Ruby dependencies
/usr/bin/bundle install \
--path /var/www/redmine-2.6.0/.bundle \
--without development test
If success, the output of the above steps will be something similar to the following,
$ /usr/bin/bundle install \
--path /var/www/redmine-2.6.0/.bundle \
--without development test
Fetching gem metadata from https://rubygems.org/.........
Resolving dependencies...
Using rake 10.4.0
Using i18n 0.6.11
......
Your bundle is complete!
Gems in the groups development and test were not installed.
It was installed into ./.bundle
Post-install message from rdoc:
Depending on your version of ruby, you may need to install ruby rdoc/ri data:
<= 1.8.6 : unsupported
= 1.8.7 : gem install rdoc-data; rdoc-data --install
= 1.9.1 : gem install rdoc-data; rdoc-data --install
>= 1.9.2 : nothing to do! Yay!
......
Since on Fedora Linux 20, the version of Ruby is 2.0 or higher, there is nothing else to do for
the Ruby dependencies.
During the above process, a configuration file ${REDMINE}/.bundle/config
will be created.
The following shows an example of the configuration file created during the process.
$ cat ${REDMINE}/.bundle/config
---
BUNDLE_PATH: /var/www/redmine-2.6.0/.bundle
BUNDLE_WITHOUT: development:test
BUNDLE_DISABLE_SHARED_GEMS: '1'
The configuration file informs Redmine where the Ruby
dependencies is as indicated by the
BUNDLE_PATH
variable in the configuraiton file.
-
Generating session store secret.
We simply follow the instruction
in the Redmine wiki page. Note that
in this example, ${REDMINE}
is /var/www/redmine-2.6.0
.
/usr/bin/bundle exec \
"${REDMINE}/.bundle/ruby/bin/rake generate_secret_token"
-
Loading Redmine database default data set.
Again, we simply follow the instruction
in the Redmine wiki page.
/usr/bin/bundle exec "RAILS_ENV=production rake db:migrate"
-
Setting up file system permissions.
Again, we simply follow the instruction
in the Redmine wiki page. However,
there is a minor deviation since we set up Redmine using your username. We will make necessary changes
to integrate it with the Apache HTTP Server in next section.
Again ${REDMINE}$
in this example is
/var/www/redmine-2.6.0
.
mkdir -p ${REDMINE}/tmp ${REDMINE}/tmp/pdf ${REDMINE}/public/plugin_assets
chmod 755 ${REDMINE}/tmp ${REDMINE}/tmp/pdf ${REDMINE}/public/plugin_assets
Again, in this example, ${REDMINE}
is /var/www/redmine-2.6.0
.
-
Testing the Redmine installation.
We follow the instrucion in
the Redmine wiki page.
$ ruby script/rails server webrick -e production
=> Booting WEBrick
=> Rails 3.2.19 application starting in production on http://0.0.0.0:3000
=> Call with -d to detach
=> Ctrl-C to shutdown server
[2014-11-30 19:05:45] INFO WEBrick 1.3.1
[2014-11-30 19:05:45] INFO ruby 2.0.0 (2013-11-22) [x86_64-linux]
[2014-11-30 19:05:45] INFO WEBrick::HTTPServer#start: pid=6454 port=3000
Pointing a browser to http://localhost:3000
, you will see Redmine's welcome page, which indicates
that Redmine runs OK. However, as indicated in
the Redmine wiki page,
this is not intended means of running
Redmine.
Changing Redmine Admin User's Initial Password
Redmine's has an Admin user "admin" with initial password "admin". Before we make the Redmine available to
the outside world, we should change the password of the Admin user "admin". When we test the Redmine in
previous step, log in as
admin
and reset the password.
Integrating Redmine with Apache HTTP Server via Phusion Passenger
We shall integrate Redmine with the Apache HTTP Server
via Phusion Passenger. Fedora Linux by default has
SeLinux enabled. SeLinux can be a source of problems. We will defer configuration for SeLinux in
next section. Then, we will temporarily disable SeLinux.
- Temporarily disabling SeLinux
sudo setenforce false
- Change Redmine installaiton's ownership
To create a workaround to install Redmine's Ruby dependencies using bundle
, we changed the
ownership of the Redmine installation to your username. We now change the ownership to the user as
whom the Apache HTTP Server, i.e., user apache
is running and remove access to the
installation from any users but user apache
and group apache
.
sudo chown -R apache:apache ${REDMINE}
sudo chmod o-rwx ${REDMINE}
Note that ${REDMINE}
is /var/www/redmine-2.6.0
in this example.
-
Configuring the Phusion Passenger module to integrate Redmine with the Apache Web server.
When the Phusion Passenger module package is installed, an Apache HTTP Server configuration file will
be installed at /etc/httpd/conf.d/
. The configuration file is
/etc/httpd/conf.d/passenger.conf
. We will append the following lines to the configuration
file.
<VirtualHost *:80>
SetEnv GEM_HOME /var/www/redmine-2.6.0/.bundle/ruby
ServerName localhost.localdomain
DocumentRoot /var/www/redmine-2.6.0/public
<Directory /var/www/redmine-2.6.0/public>
AllowOverride all
Options -MultiViews
</Directory>
</VirtualHost>
In the above, the environment variable GEM_HOME
is important. Without its pointing to
the location of the Gem files installed by bundle
, i.e.,
/var/www/redmine-2.6.0/.bundle/ruby
, Redmine will complains that it cannot find the
required Gem files. More discussion on this issue is available.
Configuring SeLinux for Redmine
Redmine has a wiki page
Redmine, Phusion Passenger, Ruby Enterprise Edition, Apache and ... SELinux that is our beginning point.
Fedora Linux 20 has a SeLinux policy module that properly set up SeLinux permissions for Phusion Passenger,
which makes the steps simpler than the
Redmine's wiki page. The following steps is a minor revision of the
RedmineAndSELinux script in the Redmine wiki page.
APACHE_USER=apache
REDMINE=/var/www/redmine-2.6.0
GEM_HOME=${REDMINE}/.bundle
# Base permissions.
sudo chown -R ${APACHE_USER}:${APACHE_USER} ${REDMINE}
sudo chmod -R u=rw,g=r,o-rwx ${REDMINE}
sudo chmod -R ug+X ${REDMINE}
sudo chcon -R -u system_u -t httpd_sys_content_t ${REDMINE}
# Writable directories.
sudo chown -R ${APACHE_USER}:${APACHE_USER} ${REDMINE}/log
sudo chcon -R -t httpd_log_t ${REDMINE}/log
sudo chown -R ${APACHE_USER}:${APACHE_USER} ${REDMINE}/tmp
sudo chcon -R -t httpd_tmpfs_t ${REDMINE}/tmp
sudo chown -R ${APACHE_USER}:${APACHE_USER} ${REDMINE}/files
sudo chcon -R -t httpd_sys_script_rw_t ${REDMINE}/files
sudo chown -R ${APACHE_USER}:${APACHE_USER} ${REDMINE}/public/plugin_assets
sudo chcon -R -t httpd_sys_script_rw_t ${REDMINE}/public/plugin_assets
# Set permission to the shared objects used by Ruby GEM files
sudo find -P ${GEM_HOME} -type f -name "*.so*" -exec chcon -t lib_t {} \;
# enable SeLinux
sudo setenforce 1
# allow Apache to connect to database
sudo setsebool -P httpd_can_network_connect_db 1
# restart the Apache HTTP Server
sudo systemctl restart httpd.service
Alternatively, you may download and execute the shell script
selinuxforredmine.sh
at Github, for instance,
sudo ./selinuxforredmine.sh /var/www/redmine-2.6.0
sudo setenforce 1
sudo systemctl restart httpd.service
Configuring Firewall
To allow the outside world to connect to the Redmine instance on the Fedora Linux system, we will have to configure
the firewall to allow incoming connection at TCP port 80.
One of my previous post discusses how we can add an allowed
port in Fedora's firewalld.
This is final step, we are now done.
Common Issues During Redmine Installation on Fedora Linux
Authentication with PostgreSQL Database
In the
above, the PostgreSQL client authentication configuration
file works for a Fedora Linux system with IPv6 enabled since
::1/128
is an IPv6 address.
IPv6 is enabled on Fedora Linux 20 by default.
If the IPv6
is disabled, then the line to be added to the configuration file, by default at
/var/lib/pgsql/data/hg_hba.conf
should be,
host redmine redmine 127.0.0.1/32 md5
Be aware that the order of such configuration lines in the configuration file matters. The line must appear
before a more generic configuration line, as such, the segment of the configuration upon addition
of the line should resemble the following,
host redmine redmine 127.0.0.1/32 md5
host all all 127.0.0.1/32 ident
If you place the line after the more generic configuration line, the more restrictive line
wil have no effect. For instance, the segment of configuration is as follows, a database
client program will attempt to connect to the datbase using the "ident" method and fail
to establish the connection.
host all all 127.0.0.1/32 ident
host redmine redmine 127.0.0.1/32 md5
Potential Dependency Issues Caused by database.yml
The configuration file ${REDMINE}/config/database.yml specifies what database management
system and databases that Redmine relies on. For instance, the configuration file has
a section as follows,
development:
adapter: mysql2
database: redmine_development
host: localhost
username: root
password: ""
encoding: utf8
The configuration file creates a dependency on the MySQL database management system and
the Ruby Dependency Management Tool
bundle
will attempt to install the
MySQL Gem file. If the system does not have required the MySQL client library and the
MySQL development header files, the
bundle
installation process will fail
as shown in the example below,
$ /usr/bin/bundle install \
--path /var/www/redmine-2.6.0/.bundle \
--without development test
Fetching gem metadata from https://rubygems.org/.........
Resolving dependencies...
Using rake 10.4.0
Using i18n 0.6.11
Using multi_json 1.10.1
......
Using jquery-rails 3.1.2
Gem::Installer::ExtensionBuildError: ERROR: Failed to build gem native extension.
/usr/bin/ruby extconf.rb
checking for ruby/thread.h... yes
checking for rb_thread_call_without_gvl() in ruby/thread.h... yes
......
checking for mysql_query() in -lmysqlclient... no
......
*** extconf.rb failed ***
Could not create Makefile due to some reason, probably lack of necessary
libraries and/or headers. Check the mkmf.log file for more details. You may
need configuration options.
Provided configuration options:
--with-opt-dir
.....
--without-mysqlclientlib
--with-mygcclib
--without-mygcclib
--with-mysqlclientlib
--without-mysqlclientlib
Gem files will remain installed in /var/www/redmine-2.6.0/.bundle/ruby/gems/mysql2-0.3.17 for inspection.
Results logged to /var/www/redmine-2.6.0/.bundle/ruby/gems/mysql2-0.3.17/ext/mysql2/gem_make.out
An error occurred while installing mysql2 (0.3.17), and Bundler cannot continue.
Make sure that `gem install mysql2 -v '0.3.17'` succeeds before bundling.
The existence of such a dependency is a fact. Therefore, the error remains even if you
instruct bundle
explicitly not to install MySQL Gem files, e.g.,
$ /usr/bin/bundle install \
--path /var/www/redmine-2.6.0/.bundle \
--without development test mysql mysql2
Using Ruby Dependency Management Tool
We install Redmine's
ruby
dependencies using
bundle
.
The instruction in
the
Redmine wiki page
is a generic description that some appear to be confused with what to do.
In the
Redmine's wiki page,
The
Ruby bundle
is installed via
gem
as in
gem install bundler
.
However, it will install it in your local directory unless you run
gem
as
root
.
When you install it as root, i.e.,
sudo gem install bundler
. The
bundler
will
be located in
/usr/local
. You will to make sure that
/usr/local/bin
in your
search path. In the step above, I simplify it by installing Fedora Linux's
bundler
package,
and then
bundle
will be in
/usr/bin
.
We need to first identify a user under whom the Redmine's
ruby
dependencies
should be installed. In this post, we assume that we will integrate Redmine with the Apache
web server. Then the user under whom Redmine's
ruby
dependencies should be
installed is the user
apache
since in Fedora Linux, the Apache web server
is run under user
apache
.
The challenge is that in a typical Fedora Linux installation, you cannot switch to user
apache
since the user is created without the login permission. Furthermore,
if you attempt to install the Redmine's
ruby
dependencies under
user
root
, you will observe an error as shown below,
$ sudo bundle install --without development test
Don't run Bundler as root. Bundler can ask for sudo if it is needed, and
installing your bundle as root will break this application for all
non-root users on this machine.
Could not locate Gemfile
In the above, we use a workaround. Assume that your username is
userfoo
.
We install Redmine's
ruby
dependencies under the username
userfoo
at
a specific directory, in this example,
${REDMINE}/.bundle/ruby
.
Again, ${REDMINE} is
/var/www/redmine-2.6.0
.
Locating Gem Files
You may install Gem files to any directory using
bundle
. However, you will set
the value of environmental variable
GEM_HOME
to the directory. In the
above, we set the environment variable in the Apache
HTTP Server's configuration file
/etc/httpd/conf.d/passenger.conf
. For instance,
if we comment out the
SetEnv
line from the configuration file, we will observe
an error with the error messages as follows,
You have already activated rake 10.0.4, but your Gemfile requires rake 10.4.0.
Prepending `bundle exec` to your command may solve this. (Gem::LoadError)
/usr/share/gems/gems/bundler-1.7.6/lib/bundler/runtime.rb:34:in `block in setup'
/usr/share/gems/gems/bundler-1.7.6/lib/bundler/runtime.rb:19:in `setup'
/usr/share/gems/gems/bundler-1.7.6/lib/bundler.rb:121:in `setup'
......
The effect of the environment variable can be demonstrated using the two examples below, one
without the environment variable's value being set, one with the value being set.
$ gem env
RubyGems Environment:
- RUBYGEMS VERSION: 2.1.11
- RUBY VERSION: 2.0.0 (2013-11-22 patchlevel 353) [i386-linux]
......
- GEM PATHS:
- /home/foouser/.gem/ruby
- /usr/share/gems
- /usr/local/share/gems
......
$ gem list
Note the above, GEM PATHS do not include the directory
/var/www/redmine-2.6.0/.bundle/ruby
. Then,
Ruby will not be able to locate the Gem files installed
using
bundle
.
$ gem list
*** LOCAL GEMS ***
bigdecimal (1.2.0)
bundler (1.7.6)
daemon_controller (1.1.8)
io-console (0.4.2)
json (1.7.7)
net-http-persistent (2.9.4)
passenger (4.0.18)
psych (2.0.0)
rack (1.5.2)
rake (10.0.4)
rdoc (4.0.1)
thor (0.18.1)
We see from the above that the activated
Rake
is of version
10.0.4
that is indicated in the error message shown above. However,
we will observe different results if we set the
GEM_HOME
directory
to the directory where we install Gem files using
bundle
.
$ GEM_HOME=/var/www/redmine-2.6.0/.bundle/ruby gem env
RubyGems Environment:
......
- GEM PATHS:
- /var/www/redmine-2.6.0/.bundle/ruby
- /home/foouser/.gem/ruby
- /usr/share/gems
- /usr/local/share/gems
.....
Now
/var/www/redmine-2.6.0/.bundle/ruby
is in GEM PATHS.
$ GEM_HOME=/var/www/redmine-2.6.0/.bundle/ruby gem list
*** LOCAL GEMS ***
actionmailer (3.2.19)
......
rake (10.4.0, 10.0.4)
......
We now see that the Gem files installed using
bundle
are listed. It
also shows that it finds two version of
Rake
.