Tag Archives: install

Install Oracle Enterprise Manager Cloud Control 12c Release 3 on Oracle Linux 6

Introduction

This post is intended to document the process of installing Oracle Enterprise Manager Cloud Control 12c Release 3 on Oracle Linux 6.

Licensing

OEM Cloud Control is used as a centralised management point for Oracle Database installations in your environment.

You can install this for free and use the base functionalities for free as long as you have an active support subscription with Oracle for any targets (database, hosts, etc.) you want to manage.

The list of the base functionalities you can use for free can be reviewed on the OEM Cloud Control Licensing Guide.

Server setup

First, we start with a minimal installation of Oracle Linux 6 with 8GB of RAM and 100GB hard disk.  A swap space of 8GB is configured.

Install Oracle Database

OEM Cloud Control will use an Oracle Database to store OEM data, and this database will have to have been installed when you run the OEM Cloud Control installer.  The OEM Cloud Control installer will not install the Oracle Database as part of the installation.

You may use an existing Oracle Database for this purpose or you can install a separate database specifically for it.

From the Licensing Guide:

Enterprise Manager includes a restricted-use license of the Oracle Database for use only with the Oracle Management Repository or other complementary repositories included with Enterprise Manager (such as, Ops Center, Real User Experience Insight, Load Testing, and Test Manager).

Additional database options or additional servers for disaster recovery require separate licensing. Customers receive one single-instance database with the Cloud Control, or RMAN, repository. To protect the repository with Data Guard, customers need to purchase a license for the standby site. To protect the repository with Oracle Real Application Clusters, customers must license the second node for the database, and both nodes require an Oracle Real Application Clusters license.

As long as you use a single-instance installation of Oracle Database and do not use this database for anything other than OEM, the database is considered properly licensed.

Prep the server for Oracle Database installation

Funnily enough, at the time of writing, the highest version of Oracle Database certified to be used as the OEM repository is 11gR2.  12c is not certified.

You can check the certifications via My Oracle Support by following the steps in the Installation Guide.

Now we install the 11gR2 pre-requisite RPM to prepare the server for Oracle Database installation.

[root@server ~]# yum install oracle-rdbms-server-11gR2-preinstall

The preinstall RPM will have added the oracle OS user, as well as the oinstall and dba OS groups.

Next, we create the directory structure to hold the Oracle Database files.

[root@server ~]# mkdir -p /u01/app/oracle
[root@server ~]# chown -R oracle:oinstall /u01

Get the Oracle Database installer from OTN, and copy the files into the server.  Finally, unzip the installation files.

Perform Oracle Database Installation

Set up X forwarding, and run the installer as the oracle user.

[oracle@server ~]$ cd database
[oracle@server database]$ ./runInstaller

Choose to configure a database during installation.

Choose to configure database during installation.

Choose a server class installation.

Choose server class

Choose single instance installation.

Choose single-instance installation.

Choose Enterprise Edition, and de-select all options except Partitioning, which is required by OEM Cloud Control 12c.  We remove all unnecessary options to avoid future trouble with Oracle Licensing.

Choose Enterprise EditionDe-select all options except Partitioning.

Proceed with the rest of the installation as usual.  Just accept all the defaults for the database configuration, as we will remove this database later and create a new one.

Create repository instance

After the installation has completed, run the Database Configuration Assistant (DBCA) and remove the instance configured during the database installation.

Then use DBCA to create a new instance from scratch.  Using any of the seed databases supplied by Oracle will not do as the database for the OEM repository should not have the SYSMAN schema present.

The settings for the new database should match your expected deployment size.  Refer to the Advanced Installation and Configuration Guide for sizing guide.  For this article, I will be using the SMALL deployment size, which have the following settings for the repository database:

Parameter Minimum Value
processes 300
pga_aggregate_target* 1024 MB
sga_target* 2 GB
redo log file size 300 MB
shared_pool_size 600 MB
*memory_target of 3 GB can be used in place of sga_target and pga_aggregate_target

We can now begin creating the database using DBCA.

Choose to create a database.

Choose Create a Database

Choose to create a custom database.

Choose Custom Database

Uncheck the Configure Enterprise Manager and Enable automatic maintenance tasks checkboxes.

Uncheck Configure Enterprise ManagerUncheck enable automatic maintenance tasks

Remove all the optional database components

Remove all optional componentsRemove all optional components

Check the Use Automatic Memory Management checkbox and make sure the memory size is more than 3 GB.

Enable Automatic Memory Management

Set processes to 300.

Set processes to 300

Change all three redo log file sizes to 300 MB.

Set redo log file size to 300 MB.

Complete the database creation.

Install Oracle Enterprise Manager Cloud Control 12c Release 3

With the repository database ready, it is time to install the OEM proper.

Review package requirements.

First, review the operating system package requirements from the Installation Guide.

For my installation, since the oracle-rdbms-server-11gR2-preinstall package was already installed, the only missing package is the glibc-devel 32-bit package.  So, that will now be installed using yum.

[root@server ~]# yum install glibc-devel.i686

Next, get the installer from OTN.

Unzip the files, and run the installer as the oracle user.

[oracle@server oem]$ ./runInstaller

Configure the email and software updates if you want to, and click Next.

The pre-requisite checks will be performed, and in my case, all the tests were successful.

Pre-requisite checks

Choose to create a new Advanced Enterprise Manager System.

Choose Advanced Installation

Next, specify the location to install the Middleware and Agent components of OEM Cloud Control.  I chose to use the ORACLE_BASE of the database installation as the base directory, with directories for the Middleware and Agent components located in this base.

Specify middleware and agent directories

The next page we will be able to choose which management plugins we wish to install.  For my install, I will only use OEM Cloud Control to manage Oracle Databases.  Therefore, I will not install any additional plugins.

Choose plugins to install.

Next, provide passwords WebLogic and Node Manager, and specify installation directory for OMS.  Again, I used the same directory structure as the Oracle Database installation.

Provide passwords and specify OMS installation directory.

Step 8: Provide the details of the repository database.  Here we insert the details of the repository database which we have installed earlier, and select the corresponding deployment size.

Insert database details and deployment size.

When I clicked Next, an error popped out saying that a CBO statistics collection job must be disabled.  The installer offered to fix this automatically, and I accept.

Click Yes to disable CBO stats gathering job.

After clicking Yes, the installer presented me with several warnings regarding database parameter mis-matches that will affect the performance of the OEM Cloud Control.  I can choose to fix them now, or proceed with the installation and fix them later.

Database parameter mis-match warnings.

The first warning is about the memory_target parameter.  However, checking the parameter shows that the parameter is set up correctly for the SMALL deployment size.

SQL> show parameter memory_target

NAME                                 TYPE        VALUE
------------------------------------ ----------- ------------------------------
memory_target                        big integer 3200M

The second warning is for the session_cached_cursors parameter.  Change this to the recommended value.  This parameter is not changeable online, so a database restart is required.

SQL> show parameter session_cached_cursors

NAME                                 TYPE        VALUE
------------------------------------ ----------- ------------------------------
session_cached_cursors               integer     50

SQL> alter system set session_cached_cursors=500 scope=SPFILE;

System altered.

SQL> shutdown immediate
Database closed.
Database dismounted.
ORACLE instance shut down.
SQL> startup
ORACLE instance started.

Total System Global Area 3340451840 bytes
Fixed Size                  2257840 bytes
Variable Size            1811942480 bytes
Database Buffers         1509949440 bytes
Redo Buffers               16302080 bytes
Database mounted.
Database opened.
SQL> show parameter session_cached_cursors;

NAME                                 TYPE        VALUE
------------------------------------ ----------- ------------------------------
session_cached_cursors               integer     500


The third and final change is to the shared_pool_size parameter.

SQL> show parameter shared_pool_size

NAME                                 TYPE        VALUE
------------------------------------ ----------- ------------------------------
shared_pool_size                     big integer 0
SQL> alter system set shared_pool_size=600M scope=both;

System altered.

SQL> show parameter shared_pool_size

NAME                                 TYPE        VALUE
------------------------------------ ----------- ------------------------------
shared_pool_size                     big integer 608M

Now, we return to the installer and click Cancel and re-run the database check.  Now, only one warning appears, which I guess is an installer glitch in reading the memory parameter.  Click Ok to resume with the installation.

The remaining database parameter mis-match warning.

Step 9: On this page of the installer, we specify the passwords for SYSMAN and registration.  This SYSMAN password will be used in the initial login to the OEM Cloud Control.  You can change the default locations of the tablespaces to be created, and also the location of the software library to be used by OEM Cloud Control.

Provide passwords and tablespace locations.

Step 10: Review the port assignments for OEM Cloud Control, or change them if you wish.

Review port assignments.

Step 11: Finally, we get to the review page.  Click Install to begin OEM Cloud Control installation.

Review Page.

The installer will prompt for execution of root scripts.  Run the script.

[root@server ~]# /u01/app/oracle/middleware/oms/allroot.sh

Starting to execute allroot.sh .........

Starting to execute /u01/app/oracle/middleware/oms/root.sh ......
Running Oracle 11g root.sh script...

The following environment variables are set as:
    ORACLE_OWNER= oracle
    ORACLE_HOME=  /u01/app/oracle/middleware/oms

Enter the full pathname of the local bin directory: [/usr/local/bin]: <Press Enter>
The file "dbhome" already exists in /usr/local/bin.  Overwrite it? (y/n)
[n]:<Press Enter>
The file "oraenv" already exists in /usr/local/bin.  Overwrite it? (y/n)
[n]:<Press Enter>
The file "coraenv" already exists in /usr/local/bin.  Overwrite it? (y/n)
[n]:<Press Enter>

Entries will be added to the /etc/oratab file as needed by
Database Configuration Assistant when a database is created
Finished running generic part of root.sh script.
Now product-specific root actions will be performed.
/etc exist

Creating /etc/oragchomelist file...
/u01/app/oracle/middleware/oms
Finished execution of  /u01/app/oracle/middleware/oms/root.sh ......


Starting to execute /u01/app/oracle/agent/core/12.1.0.3.0/root.sh ......
Finished product-specific root actions.
/etc exist
Finished execution of  /u01/app/oracle/agent/core/12.1.0.3.0/root.sh ......

The installation is now completed.

Configure firewall for OEM Cloud Control

Now we we will need to configure the firewall to enable OEM Cloud Control to work properly.  Of course, you can disable the firewall instead should you choose to.

Check the Port List

First, check the list of ports used by your installation.  This list can be located inside your middleware installation directory <path_to_middleware>/oms/install/portlist.ini.

[root@server ~]# cat /u01/app/oracle/middleware/oms/install/portlist.ini
Enterprise Manager Upload Http Port=4889
Enterprise Manager Upload Http SSL Port=4903
Enterprise Manager Central Console Http SSL Port=7802
Node Manager Http SSL Port=7403
Managed Server Http Port=7202
Enterprise Manager Central Console Http Port=7788
Oracle Management Agent Port=3872
Admin Server Http SSL Port=7102
Managed Server Http SSL Port=7301

Configure Firewall

Next, configure the firewall to allow incoming connections from all the ports listed above.

[root@server ~]# iptables -I INPUT 5 -m state --state NEW -p tcp --dport 4889 -j ACCEPT
[root@server ~]# iptables -I INPUT 6 -m state --state NEW -p tcp --dport 4903 -j ACCEPT
[root@server ~]# iptables -I INPUT 7 -m state --state NEW -p tcp --dport 7802 -j ACCEPT
[root@server ~]# iptables -I INPUT 8 -m state --state NEW -p tcp --dport 7403 -j ACCEPT
[root@server ~]# iptables -I INPUT 9 -m state --state NEW -p tcp --dport 7202 -j ACCEPT
[root@server ~]# iptables -I INPUT 10 -m state --state NEW -p tcp --dport 7788 -j ACCEPT
[root@server ~]# iptables -I INPUT 11 -m state --state NEW -p tcp --dport 3872 -j ACCEPT
[root@server ~]# iptables -I INPUT 12 -m state --state NEW -p tcp --dport 7102 -j ACCEPT
[root@server ~]# iptables -I INPUT 13 -m state --state NEW -p tcp --dport 7301 -j ACCEPT
[root@server ~]# service iptables save
iptables: Saving firewall rules to /etc/sysconfig/iptables:[  OK  ]

Login to OEM Cloud Control

Now, we are ready to login for the first time to the OEM Cloud Control installation.  Open up a browser and go to the following URL:

https://server:<port>/em

The port should be the port listed for Enterprise Manager Central Console Http SSL Port in the portlist.ini file that we checked earlier.

Login Page

Login with username SYSMAN and the password for SYSMAN that was set during the OEM Cloud Control installation earlier.

You will be presented with a License Agreement Page.

License Agreement Page

Read the license agreement and click I Accept.

You will now be presented with the Welcome Page.  You can now start using OEM Cloud Control 12c.

Set up FTP server on CentOS 6

Introduction

The purpose of this post is to document the steps to set up FTP server on CentOS 6. The FTP server software used is the default FTP server daemon for CentOS 6 at the time of writing, which is vsftpd.  The FTP server is run behind an iptables firewall and SELinux, so this post will include iptables and SELinux settings that are needed.

Install FTP server software

To start things off, the FTP server software is installed.

[hazrul@server ~]$ sudo yum grouplist | grep -i ftp
   FTP server
[hazrul@server ~]$ sudo yum groupinstall "FTP server"

Check FTP server configuration file

The vsftpd config files are located in /etc/vsftpd.  The main configuration file vsftpd.conf is edited to check the configuration, and modified where necessary.

[hazrul@server ~]$ sudo vi /etc/vsftpd/vsftpd.conf
# Example config file /etc/vsftpd/vsftpd.conf
#
# The default compiled in settings are fairly paranoid. This sample file
# loosens things up a bit, to make the ftp daemon more usable.
# Please see vsftpd.conf.5 for all compiled in defaults.
#
# READ THIS: This example file is NOT an exhaustive list of vsftpd options.
# Please read the vsftpd.conf.5 manual page to get a full idea of vsftpd's
# capabilities.
#
# Allow anonymous FTP? (Beware - allowed by default if you comment this out).
#anonymous_enable=YES
anonymous_enable=NO
#
# Uncomment this to allow local users to log in.
local_enable=YES
#
# Uncomment this to enable any form of FTP write command.
write_enable=YES
#
# Default umask for local users is 077. You may wish to change this to 022,
# if your users expect that (022 is used by most other ftpd's)
local_umask=022
#
# Uncomment this to allow the anonymous FTP user to upload files. This only
# has an effect if the above global write enable is activated. Also, you will
# obviously need to create a directory writable by the FTP user.
#anon_upload_enable=YES
#
# Uncomment this if you want the anonymous FTP user to be able to create
# new directories.
#anon_mkdir_write_enable=YES
#
# Activate directory messages - messages given to remote users when they
# go into a certain directory.
dirmessage_enable=YES
#
# The target log file can be vsftpd_log_file or xferlog_file.
# This depends on setting xferlog_std_format parameter
xferlog_enable=YES
#
# Make sure PORT transfer connections originate from port 20 (ftp-data).
connect_from_port_20=YES
#
# If you want, you can arrange for uploaded anonymous files to be owned by
# a different user. Note! Using "root" for uploaded files is not
# recommended!
#chown_uploads=YES
#chown_username=whoever
#
# The name of log file when xferlog_enable=YES and xferlog_std_format=YES
# WARNING - changing this filename affects /etc/logrotate.d/vsftpd.log
#xferlog_file=/var/log/xferlog
#
# Switches between logging into vsftpd_log_file and xferlog_file files.
# NO writes to vsftpd_log_file, YES to xferlog_file
xferlog_std_format=YES
#
# You may change the default value for timing out an idle session.
#idle_session_timeout=600
#
# You may change the default value for timing out a data connection.
#data_connection_timeout=120
#
# It is recommended that you define on your system a unique user which the
# ftp server can use as a totally isolated and unprivileged user.
#nopriv_user=ftpsecure
#
# Enable this and the server will recognise asynchronous ABOR requests. Not
# recommended for security (the code is non-trivial). Not enabling it,
# however, may confuse older FTP clients.
#async_abor_enable=YES
#
# By default the server will pretend to allow ASCII mode but in fact ignore
# the request. Turn on the below options to have the server actually do ASCII
# mangling on files when in ASCII mode.
# Beware that on some FTP servers, ASCII support allows a denial of service
# attack (DoS) via the command "SIZE /big/file" in ASCII mode. vsftpd
# predicted this attack and has always been safe, reporting the size of the
# raw file.
# ASCII mangling is a horrible feature of the protocol.
#ascii_upload_enable=YES
#ascii_download_enable=YES
#
# You may fully customise the login banner string:
#ftpd_banner=Welcome to blah FTP service.
#
# You may specify a file of disallowed anonymous e-mail addresses. Apparently
# useful for combatting certain DoS attacks.
#deny_email_enable=YES
# (default follows)
#banned_email_file=/etc/vsftpd/banned_emails
#
# You may specify an explicit list of local users to chroot() to their home
# directory. If chroot_local_user is YES, then this list becomes a list of
# users to NOT chroot().
#chroot_local_user=YES
chroot_local_user=YES
#chroot_list_enable=YES
# (default follows)
#chroot_list_file=/etc/vsftpd/chroot_list
#
# You may activate the "-R" option to the builtin ls. This is disabled by
# default to avoid remote users being able to cause excessive I/O on large
# sites. However, some broken FTP clients such as "ncftp" and "mirror" assume
# the presence of the "-R" option, so there is a strong case for enabling it.
#ls_recurse_enable=YES
#
# When "listen" directive is enabled, vsftpd runs in standalone mode and
# listens on IPv4 sockets. This directive cannot be used in conjunction
# with the listen_ipv6 directive.
listen=YES
#
# This directive enables listening on IPv6 sockets. To listen on IPv4 and IPv6
# sockets, you must run two copies of vsftpd with two configuration files.
# Make sure, that one of the listen options is commented !!
#listen_ipv6=YES

pam_service_name=vsftpd
userlist_enable=YES
userlist_DENY=NO
tcp_wrappers=YES

The default configuration provided by CentOS 6 allows the following users to log in:-

  1. Anonymous users – Read-only access to /var/ftp and its subdirectories.
  2. Local users – Read-write access to the whole filesystem, governed only by file permission.

However, if SELinux is turned on, the default SELinux configuration will stop any writes from happening.

The default vsftpd configuration is a bit loose for my liking.  I prefer not to have anonymous users logging into the server, and I prefer to have the local users confined to their home directories.  Therefore, the configuration was modified as highlighted above.

To deny anonymous users, anonymous_enable is set to NO.

To confine local users to their home directories, chroot_local_user is set to YES.

An extra line is also added to the configuration file which is userlist_deny=NO.  By default, vsftpd will check for the file /etc/vsftpd/user_list, and deny access to the users listed in that file.  By setting userlist_deny=NO, ONLY users listed in that file is allowed access.

Therefore, the initial user list file will have to be changed.

[hazrul@server ~]$ sudo cat /etc/vsftpd/user_list
# vsftpd userlist
# If userlist_deny=NO, only allow users in this file
# If userlist_deny=YES (default), never allow users in this file, and
# do not even prompt for a password.
# Note that the default vsftpd pam config also checks /etc/vsftpd/ftpusers
# for users that are denied.
root
bin
daemon
adm
lp
sync
shutdown
halt
mail
news
uucp
operator
games
nobody
[hazrul@server ~]$ sudo mv /etc/vsftpd/user_list /etc/vsftpd/user_list.bak
[hazrul@server ~]$ sudo touch /etc/vsftpd/user_list

The user list is now empty, and must be later filled with the usernames of the users that are to be allowed FTP access.

Configure SELinux to work with vsftpd

SELinux controls vsftpd on a tight leash.  To make the FTP server work as intended, at least one SELinux boolean needs to be modified.  First, all the booleans related to FTP is listed.

[hazrul@server ~]$ sudo getsebool -a | grep -i ftp
allow_ftpd_anon_write --> off
allow_ftpd_full_access --> off
allow_ftpd_use_cifs --> off
allow_ftpd_use_nfs --> off
ftp_home_dir --> off
ftpd_connect_db --> off
ftpd_use_fusefs --> off
ftpd_use_passive_mode --> off
httpd_enable_ftp_server --> off
tftp_anon_write --> off
tftp_use_cifs --> off
tftp_use_nfs --> off

In this particular setup, the boolean that needs to be changed is ftp_home_dir.  This will allow users to read and write to their home directories located in /home/username.

[hazrul@server ~]$ sudo setsebool -P ftp_home_dir on
[hazrul@server ~]$ sudo getsebool ftp_home_dir
ftp_home_dir --> on

Start and configure the vsftpd service

Next, the FTP server is started, and configured to start at boot.

[hazrul@server ~]$ sudo service vsftpd start
Starting vsftpd for vsftpd:                                [  OK  ]
[hazrul@server ~]$ sudo chkconfig vsftpd on

Configure iptables firewall to allow FTP

FTP is an interesting protocol; it requires two TCP connections: one for command, and another for data.

In active mode, the client initiates the command TCP connection on port 21 of the FTP server while providing a port number to the server for the data connection.  The FTP server then connects to the provided port from port 20 of the server.

In passive mode, similarly the client initiates the command TCP connection on port 21 of the server.  However, instead of providing a port number, the client then sends a PASV command indicating the intention to use passive mode.  The server receives the PASV command and opens up an unregistered port for the client to connect to for the data connection.  The server then sends the port number to the client for the client to initiate the connection.

A more detailed explanation of this can be found here.

To configure the iptables firewall for FTP is quite straight-forward for active mode.  Just open up incoming connections on port 21, and allow outgoing connections on port 20.

Passive mode is a bit tricky.  For the command connection, similarly port 21 is opened for incoming connections.  However, for the data connection, the port number that is needed to be opened changes from one session to another.  To open up all the unregistered port is not an acceptable solution security-wise as that is virtually one step below disabling the firewall altogether.

Fortunately, there exists an iptables module called ip_conntrack_ftp that uses the connection tracking feature of iptables to automatically open up ports for passive mode. All that is needed to be done is to load this module when iptables is started.

To recap, the following configuration needs to be performed on iptables to allow vsftpd to work properly:

  1. Open up incoming port 21.
  2. Open up outgoing port 20 (unnecessary if using the default iptables rules provided by CentOS which already opened all outgoing ports).
  3. Load the ip_conntrack_ftp module.

To open port 21, the following command is used:

[hazrul@server ~]$ sudo iptables -I INPUT 5 -m state --state NEW -p tcp --dport 21 -j ACCEPT
[hazrul@server ~]$ sudo service iptables save
iptables: Saving firewall rules to /etc/sysconfig/iptables:[  OK  ]

To load the ip_conntrack_ftp module, the iptables configuration file is modified to include the module, and the iptables service is restarted.

[hazrul@server ~]$ sudo vi /etc/sysconfig/iptables-config
# Load additional iptables modules (nat helpers)
#   Default: -none-
# Space separated list of nat helpers (e.g. 'ip_nat_ftp ip_nat_irc'), which
# are loaded after the firewall rules are applied. Options for the helpers are
# stored in /etc/modprobe.conf.
IPTABLES_MODULES="ip_conntrack_ftp"
[hazrul@server ~]$ sudo service iptables restart
iptables: Setting chains to policy ACCEPT: filter          [  OK  ]
iptables: Flushing firewall rules:                         [  OK  ]
iptables: Unloading modules:                               [  OK  ]
iptables: Applying firewall rules:                         [  OK  ]
iptables: Loading additional modules: ip_conntrack_ftp     [  OK  ]

Create a user and test FTP access

The FTP server is now properly set up and can be tested.

Begin by creating a new user.

[hazrul@server ~]$ sudo useradd ftpuser
[hazrul@server ~]$ sudo passwd ftpuser
Changing password for user ftpuser.
New password:<password>
Retype new password:<password>
passwd: all authentication tokens updated successfully.

Add the user to the vsftpd user list.

[hazrul@server ~]$ sudo bash -c "echo ftpuser >> /etc/vsftpd/user_list"

Connect to the server using an FTP client.  The connection should succeed, and transfer of files to and from the server should now work as expected.

That concludes this post on how to set up FTP server on CentOS 6.

Set up WordPress on CentOS

The purpose of this post is to document the steps to set up WordPress on a server.

The server operating system is going to be CentOS which currently is my preferred server operating system.

The final objective is to have a WordPress website accessible via wordpress.hazrulnizam.com.

Perform operating system installation

First of all, the latest version of CentOS, which is 6.4, is installed on the server and the server is given the hostname server.hazrulnizam.com.  A minimal install is chosen to prevent unwanted programs to be installed, which can both be a security risk and a waste of disk space.

A non-root user is then created.

[root@server ~]# useradd hnizam
[root@server ~]# passwd hnizam
Changing password for user hnizam.
New password:<type password here>
Retype new password:<re-type password here>
passwd: all authentication tokens updated successfully.

This user is then given sudo permissions.

[root@server ~]# vi /etc/sudoers
## Next comes the main part: which users can run what software on
## which machines (the sudoers file can be shared between multiple
## systems).
## Syntax:
##
##      user    MACHINE=COMMANDS
##
## The COMMANDS section may have other options added to it.
##
## Allow root to run any commands anywhere
root    ALL=(ALL)       ALL
hnizam  ALL=(ALL)       NOPASSWD: ALL

This user is going to be used for all subsequent commands, to limit exposure on the root account.

The OS is then updated to the latest version.

[hnizam@server ~]$ sudo yum check-update

[hnizam@server ~]$ sudo yum upgrade

[hnizam@server ~]$ sudo shutdown -ry now

Check WordPress requirements

Now that the operating system is properly set up, it is time to begin the process of installing WordPress.  First, the requirements for installing WordPress should be reviewed.  At the time of writing, the current version of WordPress is 3.7.1 and according to the WordPress requirements page, the requirements for installing WordPress are:

  • PHP version 5.2.4 or greater
  • MySQL version 5.0 or greater
  • Web server capable of supporting the above (Apache or Nginx is recommended)

To enable pretty permalinks, the Apache module mod_rewrite is needed.

Apache is being chosen as the web server for this particular case as it is one of the earliest web servers and also one of the most used web server software.

Install web server (Apache)

Install the Apache software

The package group feature of the yum package manager is used to install the Apache web server software.

[hnizam@server ~]$ sudo yum grouplist | grep -i web
   Web Server
   Web Servlet Engine
   Web-Based Enterprise Management
[hnizam@server ~]$ sudo yum groupinstall "Web Server"

The Apache web server is installed as the httpd service.  The chkconfig command is used to enable the httpd service at server boot-up.

[hnizam@server ~]$ sudo chkconfig httpd --list
httpd           0:off   1:off   2:off   3:off   4:off   5:off   6:off
[hnizam@server ~]$ sudo chkconfig httpd on
[hnizam@server ~]$ sudo chkconfig httpd --list
httpd           0:off   1:off   2:on    3:on    4:on    5:on    6:off

Next, the Apache web server is started, and the ports used by the web server (port 80 for http and port 443 for https) is opened at the firewall to enable the web server to be accessed by the public.

[hnizam@server ~]$ sudo service httpd start
Starting httpd:                                            [  OK  ]
[hnizam@server ~]$ sudo iptables -L -vn
Chain INPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
 1930  156K ACCEPT     all  --  *      *       0.0.0.0/0            0.0.0.0/0           state RELATED,ESTABLISHED
    3   236 ACCEPT     icmp --  *      *       0.0.0.0/0            0.0.0.0/0
    0     0 ACCEPT     all  --  lo     *       0.0.0.0/0            0.0.0.0/0
    1    60 ACCEPT     tcp  --  *      *       0.0.0.0/0            0.0.0.0/0           state NEW tcp dpt:22
   98 26516 REJECT     all  --  *      *       0.0.0.0/0            0.0.0.0/0           reject-with icmp-host-prohibited

Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
    0     0 REJECT     all  --  *      *       0.0.0.0/0            0.0.0.0/0           reject-with icmp-host-prohibited

Chain OUTPUT (policy ACCEPT 1317 packets, 168K bytes)
 pkts bytes target     prot opt in     out     source               destination
[hnizam@server ~]$ sudo iptables -I INPUT 5 -m state --state NEW -p tcp --dport 80 -j ACCEPT
[hnizam@server ~]$ sudo iptables -I INPUT 6 -m state --state NEW -p tcp --dport 443 -j ACCEPT
[hnizam@server ~]$ sudo iptables -L -vn
Chain INPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
 2277  186K ACCEPT     all  --  *      *       0.0.0.0/0            0.0.0.0/0           state RELATED,ESTABLISHED
    3   236 ACCEPT     icmp --  *      *       0.0.0.0/0            0.0.0.0/0
    0     0 ACCEPT     all  --  lo     *       0.0.0.0/0            0.0.0.0/0
    1    60 ACCEPT     tcp  --  *      *       0.0.0.0/0            0.0.0.0/0           state NEW tcp dpt:22
    0     0 ACCEPT     tcp  --  *      *       0.0.0.0/0            0.0.0.0/0           state NEW tcp dpt:80
    0     0 ACCEPT     tcp  --  *      *       0.0.0.0/0            0.0.0.0/0           state NEW tcp dpt:443
  108 29500 REJECT     all  --  *      *       0.0.0.0/0            0.0.0.0/0           reject-with icmp-host-prohibited

Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
    0     0 REJECT     all  --  *      *       0.0.0.0/0            0.0.0.0/0           reject-with icmp-host-prohibited

Chain OUTPUT (policy ACCEPT 5 packets, 920 bytes)
 pkts bytes target     prot opt in     out     source               destination
[hnizam@server ~]$ sudo service iptables save
iptables: Saving firewall rules to /etc/sysconfig/iptables:[  OK  ]

Post-installation checks

At this point, the URLs http://server.hazrulnizam.com and https://server.hazrulnizam.com should be accessible, and the default CentOS Apache welcome page is shown when these URLs are opened in a browser.

Set up WordPress - CentOS Apache http welcome page

For the https page, the browser will show a certificate error, because the SSL certificate used by the default Apache installation is a self-signed certificate based on the hostname of the system.

Set up WordPress - Certificate error

The certificate error should be ignored as it is the expected behavior.  To make SSL work without the browser showing a certificate error will require acquiring a certificate from a certificate authority like VeriSign or Comodo, which is outside the scope of this post.  A welcome page similar to the one from the http page is shown after the certificate error is ignored:

Set up WordPress - CentOS Apache https welcome page

The details of the self-signed certificate is shown when the padlock with the red cross is clicked and then ‘Certificate information’ is clicked.  Notice that the ‘Issued to:’ and ‘Issued by:’ fields are the same, which confirms that it is a self-signed certificate.

Set up WordPress - Self-signed certificate details

Install database server (MySQL)

Now that the web server has been successfully installed, it is time to install the database server.

Install the MySQL software

The method used to install MySQL is the same as the method used to install Apache, which is via yum.

[hnizam@server ~]$ sudo yum grouplist | grep -i mysql
   MySQL Database client
   MySQL Database server
[hnizam@server ~]$ sudo yum groupinstall "MySQL Database server"

The MySQL database server is installed as the mysqld service.  The chkconfig command is used to enable the mysqld service at server boot-up.

[hnizam@server ~]$ sudo chkconfig mysqld --list
mysqld          0:off   1:off   2:off   3:off   4:off   5:off   6:off
[hnizam@server ~]$ sudo chkconfig mysqld on
[hnizam@server ~]$ sudo chkconfig mysqld --list
mysqld          0:off   1:off   2:on    3:on    4:on    5:on    6:off

Next, the mysqld service is started for the first time.

[hnizam@server ~]$ sudo service mysqld start
Initializing MySQL database:  Installing MySQL system tables...
OK
Filling help tables...
OK

To start mysqld at boot time you have to copy
support-files/mysql.server to the right place for your system

PLEASE REMEMBER TO SET A PASSWORD FOR THE MySQL root USER !
To do so, start the server, then issue the following commands:

/usr/bin/mysqladmin -u root password 'new-password'
/usr/bin/mysqladmin -u root -h server.hazrulnizam.com password 'new-password'

Alternatively you can run:
/usr/bin/mysql_secure_installation

which will also give you the option of removing the test
databases and anonymous user created by default.  This is
strongly recommended for production servers.

See the manual for more instructions.

You can start the MySQL daemon with:
cd /usr ; /usr/bin/mysqld_safe &

You can test the MySQL daemon with mysql-test-run.pl
cd /usr/mysql-test ; perl mysql-test-run.pl

Please report any problems with the /usr/bin/mysqlbug script!

                                                           [  OK  ]
Starting mysqld:                                           [  OK  ]

Post-installation tasks

Now that the MySQL database server is installed and running, it is time to run the secure installation command as per advised by the MySQL first-time-start script.  The command offers to change the MySQL root password, remove anonymous user access to the MySQL database, and several other changes to help secure the database.

[hnizam@server ~]$ sudo /usr/bin/mysql_secure_installation

NOTE: RUNNING ALL PARTS OF THIS SCRIPT IS RECOMMENDED FOR ALL MySQL
      SERVERS IN PRODUCTION USE!  PLEASE READ EACH STEP CAREFULLY!

In order to log into MySQL to secure it, we'll need the current
password for the root user.  If you've just installed MySQL, and
you haven't set the root password yet, the password will be blank,
so you should just press enter here.

Enter current password for root (enter for none): <Enter>
OK, successfully used password, moving on...

Setting the root password ensures that nobody can log into the MySQL
root user without the proper authorisation.

Set root password? [Y/n] Y
New password: mysqlrootpassword
Re-enter new password: mysqlrootpassword
Password updated successfully!
Reloading privilege tables..
 ... Success!

By default, a MySQL installation has an anonymous user, allowing anyone
to log into MySQL without having to have a user account created for
them.  This is intended only for testing, and to make the installation
go a bit smoother.  You should remove them before moving into a
production environment.

Remove anonymous users? [Y/n] Y
 ... Success!

Normally, root should only be allowed to connect from 'localhost'.  This
ensures that someone cannot guess at the root password from the network.

Disallow root login remotely? [Y/n] Y
 ... Success!

By default, MySQL comes with a database named 'test' that anyone can
access.  This is also intended only for testing, and should be removed
before moving into a production environment.

Remove test database and access to it? [Y/n] Y
 - Dropping test database...
 ... Success!
 - Removing privileges on test database...
 ... Success!

Reloading the privilege tables will ensure that all changes made so far
will take effect immediately.

Reload privilege tables now? [Y/n] Y
 ... Success!

Cleaning up...

All done!  If you've completed all of the above steps, your MySQL
installation should now be secure.

Thanks for using MySQL!

Install PHP

The next step is to install the PHP interpreter.

Install the PHP interpreter software.

Same as previously, the yum package manager is used to perform the installation.

[hnizam@server ~]$ sudo yum grouplist | grep -i php
   PHP Support
[hnizam@server ~]$ sudo yum groupinstall "PHP Support"

To be able to set up WordPress properly, the PHP-MySQL extension must also be installed.

[hnizam@server ~]$ sudo yum install php-mysql

Test PHP installation

To test whether the PHP interpreter is working correctly, first the web server needs to be restarted.

[hnizam@server ~]$ sudo service httpd restart
Stopping httpd:                                            [  OK  ]
Starting httpd:                                            [  OK  ]

Next, a test file containing the phpinfo() function is created in the web server root directory.

[hnizam@server ~]$ sudo vi /var/www/html/test.php
<?php
phpinfo();
?>

Now when the browser is set to http://server.hazrulnizam.com/test.php or https://server.hazrulnizam.com/test.php, a page with a lot of details about the system is shown similar to the screenshot below.

Set up WordPress - PHP info page

This indicates that the PHP installation is successful and that the PHP interpreter is working correctly with the web server.

The test file is then deleted.

[hnizam@server ~]$ sudo rm /var/www/html/test.php

Install and set up WordPress

With all the prerequisites now installed, it is time to install and set up WordPress itself, using the installation guide from the WordPress.org website.

Create the database and database user

A new database is created inside the installed MySQL database server to be used by WordPress and a new database user that owns the privileges to the new database is also created.

[hnizam@server ~]$ mysql -u root -p
Enter password: mysqlrootpassword
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 10
Server version: 5.1.69 Source distribution

Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql> create database wordpressdb;
Query OK, 1 row affected (0.00 sec)

mysql> grant all privileges on wordpressdb.* to "wordpressdbuser"@"localhost" identified by "wordpressdbpassword";
Query OK, 0 rows affected (0.00 sec)

mysql> flush privileges;
Query OK, 0 rows affected (0.00 sec)

mysql> exit
Bye
[hnizam@server ~]$

The above commands create a database named wordpressdb and a user named wordpressdbuser whose password is wordpressdbpassword.  Any other names can be used for the database, username, and password if desired.

Download and extract the WordPress software

The latest version of the WordPress software is downloaded to the server using wget and then extracted using the tar command.

[hnizam@server ~]$ sudo yum install wget
[hnizam@server ~]$ wget http://wordpress.org/latest.tar.gz
[hnizam@server ~]$ tar -xzvf latest.tar.gz

The above commands result in an extracted folder named wordpress which contains the WordPress software.

[hnizam@server ~]$ ls -l
total 4492
-rw-rw-r--. 1 hnizam hnizam 4594818 Oct 30 04:08 latest.tar.gz
drwxr-xr-x. 5 hnizam hnizam    4096 Oct 30 04:08 wordpress

Copy extracted WordPress folder into www folder

The extracted folder is then copied into /var/www/ folder to ensure that the SELinux contexts are properly set for Apache web server.  The WordPress site will be served by Apache from this location.  Moving the folder using the mv command will preserve the SELinux contexts from the original location which is not what is desired.  Therefore, the folder is copied using the cp command.

[hnizam@server ~]$ sudo cp -R wordpress /var/www/

Next, the owner of the WordPress folder is changed to the Apache user to enable the Apache web server to read and write to that folder.

[hnizam@server ~]$ sudo chown -R apache:apache /var/www/wordpress

Set up Apache virtual host

The Apache web server needs to be configured to make it use the directory above when a browser asks for http://wordpress.hazrulnizam.com or https://wordpress.hazrulnizam.com.

First, the httpd.conf file is modified.

[hnizam@server ~]$ sudo vi /etc/httpd/conf/httpd.conf
### Section 3: Virtual Hosts
#
# VirtualHost: If you want to maintain multiple domains/hostnames on your
# machine you can setup VirtualHost containers for them. Most configurations
# use only name-based virtual hosts so the server doesn't need to worry about
# IP addresses. This is indicated by the asterisks in the directives below.
#
# Please see the documentation at
# <URL:http://httpd.apache.org/docs/2.2/vhosts/>
# for further details before you try to setup virtual hosts.
#
# You may use the command line option '-S' to verify your virtual host
# configuration.

#
# Use name-based virtual hosting.
#
#NameVirtualHost *:80
NameVirtualHost *:80
NameVirtualHost *:443
#
# NOTE: NameVirtualHost cannot be used without a port specifier
# (e.g. :80) if mod_ssl is being used, due to the nature of the
# SSL protocol.
#

#
# VirtualHost example:
# Almost any Apache directive may go into a VirtualHost container.
# The first VirtualHost section is used for requests without a known
# server name.
#
#<VirtualHost *:80>
#    ServerAdmin webmaster@dummy-host.example.com
#    DocumentRoot /www/docs/dummy-host.example.com
#    ServerName dummy-host.example.com
#    ErrorLog logs/dummy-host.example.com-error_log
#    CustomLog logs/dummy-host.example.com-access_log common
#</VirtualHost>

<VirtualHost _default_:80>
    DocumentRoot "/var/www/html"
</VirtualHost>

<VirtualHost *:80>
    DocumentRoot "/var/www/wordpress"
    ServerName wordpress.hazrulnizam.com
    <Directory "/var/www/wordpress">
        Options FollowSymLinks
        AllowOverride All
    </Directory>
    ErrorLog logs/wordpress.hazrulnizam.com-error_log
    CustomLog logs/wordpress.hazrulnizam.com-access_log combined
</VirtualHost>

Next, the SSL key and certificate for the https site are generated.

[hnizam@server ~]$ openssl genrsa -out wordpress.key -des3 2048
Generating RSA private key, 2048 bit long modulus
................................................+++
......................................................................................................................................................................+++
e is 65537 (0x10001)
Enter pass phrase for wordpress.key: passphrase
Verifying - Enter pass phrase for wordpress.key: passphrase
[hnizam@server ~]$ openssl req -new -key wordpress.key -out wordpress.csr
Enter pass phrase for wordpress.key: passphrase
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [XX]:MY
State or Province Name (full name) []:Kuala Lumpur
Locality Name (eg, city) [Default City]:Kuala Lumpur
Organization Name (eg, company) [Default Company Ltd]:hazrulnizam.com
Organizational Unit Name (eg, section) []:wordpress
Common Name (eg, your name or your server's hostname) []:wordpress.hazrulnizam.com
Email Address []:

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:
An optional company name []:
[hnizam@server ~]$ openssl x509 -req -days 365 -in wordpress.csr -signkey wordpress.key -out wordpress.crt
Signature ok
subject=/C=MY/ST=Kuala Lumpur/L=Kuala Lumpur/O=hazrulnizam.com/OU=wordpress/CN=wordpress.hazrulnizam.com
Getting Private key
Enter pass phrase for wordpress.key: passphrase

The generated key and certificate are then copied to their proper destinations to apply correct SELinux contexts on them.  The read permissions are modified so that only the root user has access to them.

[hnizam@server ~]$ sudo cp wordpress.key /etc/pki/tls/private/
[hnizam@server ~]$ sudo chmod 600 /etc/pki//tls/private/wordpress.key
[hnizam@server ~]$ sudo cp wordpress.crt /etc/pki/tls/certs/
[hnizam@server ~]$ sudo chmod 600 /etc/pki//tls/certs/wordpress.crt
[hnizam@server ~]$ rm wordpress.crt wordpress.csr wordpress.key

Next, the virtual host configuration is added to the Apache SSL configuration file.

[hnizam@server ~]$ sudo vi /etc/httpd/conf.d/ssl.conf
<VirtualHost *:443>
    DocumentRoot "/var/www/wordpress"
    ServerName wordpress.hazrulnizam.com:443
    <Directory "var/www/wordpress">
        Options FollowSymLinks
        AllowOverride All
    </Directory>
    ErrorLog logs/wordpress.hazrulnizam.com-ssl_error_log
    CustomLog logs/wordpress.hazrulnizam.comssl_access_log combined
    LogLevel warn
    SSLEngine on
    SSLProtocol all -SSLv2
    SSLCipherSuite ALL:!ADH:!EXPORT:!SSLv2:RC4+RSA:+HIGH:+MEDIUM
    SSLCertificateFile /etc/pki/tls/certs/wordpress.crt
    SSLCertificateKeyFile /etc/pki/tls/private/wordpress.key
</VirtualHost>

The Apache web server is then restarted to load the new configurations.

[hnizam@server ~]$ sudo service httpd restart
Stopping httpd:                                            [  OK  ]
Starting httpd: Apache/2.2.15 mod_ssl/2.2.15 (Pass Phrase Dialog)
Some of your private key files are encrypted for security reasons.
In order to read them you have to provide the pass phrases.

Server wordpress.hazrulnizam.com:443 (RSA)
Enter pass phrase:passphrase

OK: Pass Phrase Dialog successful.
                                                           [  OK  ]

Notice that there is a prompt for the passphrase of the private key when Apache is starting up.  This passphrase is going to be asked every time the Apache web server is started, including during server restarts.  This can be avoided by using a private key that is not protected by a pass phrase (do not use the -des3 flag when creating the key using the openssl genrsa command).  However, care must be taken to protect the key from being accessed by anyone else.

At this point, provided that the DNS entry for wordpress.hazrulnizam.com has been correctly added, pointing a browser to http://wordpress.hazrulnizam.com will show the following page:

Set up WordPress - WordPress error page

This shows that Apache is correctly reading the WordPress files and together with the PHP interpreter is serving out dynamic PHP pages to the browser.

Enable WordPress to send emails

Before proceeding with the final step of WordPress installation, SELinux needs to be configured to allow WordPress to send emails out from the system.  There are a few events that triggers WordPress to send notification emails such as when a new comment has been posted to a post.

The setsebool command is used to change the corresponding SELinux boolean to allow Apache, and in turn WordPress, to send out emails.

[hnizam@server ~]$ sudo getsebool httpd_can_sendmail
httpd_can_sendmail --> off
[hnizam@server ~]$ sudo setsebool httpd_can_sendmail on
[hnizam@server ~]$ sudo getsebool httpd_can_sendmail
httpd_can_sendmail --> on

Install and set up WordPress via the browser

The final step of installing WordPress involves creating a WordPress configuration file.  This configuration file can either be manually created at the server, or can be created by WordPress itself via the browser.  This post will continue via the browser method as all the prerequisites to make it successful has been performed above.

The URL http://wordpress.hazrulnizam.com is entered in the browser address bar.

Set up WordPress - WordPress error page

The ‘Create a Configuration File’ button is then clicked.

Set up WordPress - Create configuration file page

The next page shows that several information is needed to complete the installation such as database name, database username, database password, and database host.  The corresponding information are the one used in the ‘Create the database and database user’ section above.

The ‘Let’s go’ button is then clicked.

Set up WordPress - Setup Configuration page

The Database Name is changed to wordpressdb, while User Name is changed to wordpressdbuser and Password is changed to wordpressdbpassword.  The Database Host and Table Prefix fields are left at the default values.

The page is then submitted.

Set up WordPress - Configuration success

WordPress is now communicating correctly with the database.  The ‘Run the install’ button is then clicked.

Set up WordPress - Install page

On this page, the Site Title, Username, Password and email address will have to be provided.  The Site Title will be the title shown when the WordPress site is accessed once it is installed.  The Username and Password are different than the database username and password.  This will be the username that will be used to log in to the WordPress administration pages.

Once all the required fields are filled in and the ‘Install WordPress’ button pressed, the WordPress installation is completed and the website is now usable.

Set up WordPress - Install success page

An email about the new WordPress website will also be sent to the email address specified on the install page.

Set up WordPress - New WordPress Site email

This marks the end of the WordPress install.

Optional tasks

Force SSL on login and administration

The WordPress website is now working, but when you click ‘Log in’ from the main page, it will bring you to the http version of the login page.  The username and password that you type will be sent in clear-text through the internet, making them vulnerable to anyone who would want to steal your password.

WordPress has a built-in feature to force logins and/or the administration pages to be served via https instead of http.

To enable this, edit the WordPress config file and add the following line near the end.

[hnizam@server wordpress]$ sudo vi wp-config.php
/**
 * For developers: WordPress debugging mode.
 *
 * Change this to true to enable the display of notices during development.
 * It is strongly recommended that plugin and theme developers use WP_DEBUG
 * in their development environments.
 */
define('WP_DEBUG', false);

define('FORCE_SSL_ADMIN', true);

/* That's all, stop editing! Happy blogging. */

/** Absolute path to the WordPress directory. */
if ( !defined('ABSPATH') )
        define('ABSPATH', dirname(__FILE__) . '/');

/** Sets up WordPress vars and included files. */
require_once(ABSPATH . 'wp-settings.php');

You can use FORCE_SSL_LOGIN instead of FORCE_SSL_ADMIN if you just want to protect the login page.  The administration pages will not be served via https unless you specifically asks for the https protocol via the browser.

Enable pretty permalinks

One of the first things that should be done after a WordPress install is to enable pretty permalinks.  The word-based URL will help the website to rank higher in search engine results compared to the default post ID URL.

Just go to the Settings > Permalinks via the administration pages, and choose Postname-based permalinks instead of the default.  If you followed the install steps above, pretty permalinks should work correctly.

Install plugins and themes

One of the great things about WordPress is the abundance of plugins and themes that exist in the ecosystem.  Use them to customize the website and to help in managing the website.

Installing GlassFish Server Open Source Edition 4.0 on CentOS 6.4

I have been reading up on Oracle APEX Listener, and I want to try using it to serve Oracle APEX instead of the Embedded PL/SQL Gateway (EPG).  EPG is the default option for the APEX that is included in Oracle Database XE; it works, but many of the features of APEX like RESTful services cannot be used with it.

Oracle APEX Listener must run on top of an application server, and the only supported servers are Oracle WebLogic and GlassFish Server.  Since WebLogic costs money, the free way to try APEX Listener is by first installing GlassFish Server.

This post is intended to document the process of installing GlassFish 4.0 server on CentOS 6.4.

Let’s start with a minimal CentOS 6.4 installation.

Then, install Java SDK by going to the Java SDK Download Page (via a desktop, as wget won’t work) and copying the rpm over to the server.  Proceed with installation of the rpm.

# rpm -Uvh jdk-7u25-linux-x64.rpm

After that, grab the GlassFish Server Open Source Edition installer from the GlassFish Server website.

# yum install wget
# wget http://download.java.net/glassfish/4.0/release/glassfish-4.0-unix.sh

The installer chosen above is a graphical installer (there are other install options, which will not be covered in this post), so we will need to install x11 and configure forwarding with SSH.

# yum install xorg-x11-xauth xorg-x11-utils

Ensure the hostname of the server can be resolved via DNS (the installation will flag errors during the config stage if the server hostname is not resolvable.

# hostname
host.domain.tld

# ping host.domain.tld

Login again via SSH and enable X11 forwarding, and run the installer.

# sh glassfish-4.0-unix.sh
Extracting the installer archive...
Extracting the installer runtime...
Extracting the installer resources...
Extracting the installer metadata...

Welcome to GlassFish installer

Using the user defined JAVA_HOME : /usr
Entering setup...
SwixML 1.5 (#144)

The graphical installer will then load.

GlassFish Install 1 - IntroductionClick Next.

The next page is supposed to give a choice of installation type, but only one type (Typical Installation) is available.

GlassFish Install 02 - Installation TypeClick Next.

In the next page you can specify the directory in which you wish to install GlassFish Server Open Source Edition.  The default directory is ~/glassfish4.

GlassFish Install 03 - Install DirectoryI will accept the default.  Click Next.

The next page is the JDK selection page.

GlassFish Install 04 - JDK SelectionThe installer has detected correctly the JDK which was installed earlier.  There is an option to type in another custom location of any JDK you want to use instead.  Click Next.

Next comes the update tool page.  The installer will install an update tool that will check for GlassFish Server updates.  You can uncheck this if you want.

GlassFish Install 05 - Update ToolI will leave it installed.  Click Next.

Then comes the summary page before finalising the install.

GlassFish Install 07 - Ready to InstallClick Install.

Installation will then begin.

GlassFish Install 08 - ProgressAfter the installation has finished, the installer will perform some configuration, and the next page will show the configuration results.

GlassFish Install 09 - Config ResultsTake note of the Admin Port.  In this case it is 4848.  Click Next.

Finally, the installer will show a summary of the installation.

GlassFish Install 10 - SummaryClick Exit to close the installer.

By default, the GlassFish console running on the Admin Port (4848 as noted during the installation) will not accept remote connections.  Therefore, we have to run a browser from the server itself.

# yum install firefox
# dbus-uuidgen > /var/lib/dbus/machine-id
# firefox

Key in localhost:4848 to the address bar, and the GlassFish console will load!

GlassFish Install 11 - GlassFish ConsoleGlassFish Server Open Source Edition is now ready to be used.


Update 30 August 2013 – Securing the Admin Port

It turns out, to enable remote access to the GlassFish Console is easy.  Just use the enable-secure-admin command:

# /root/glassfish4/bin/asadmin enable-secure-admin
remote failure: At least one admin user has an empty password, which secure admin does not permit. Use the change-admin-password command or the admin console to create non-empty passwords for admin accounts.
Command enable-secure-admin failed.

The command failed because the default password for the GlassFish Console admin is blank.  We need to set it to a non-blank password before enabling secure admin.

# /root/glassfish4/bin/asadmin change-admin-password
Enter admin user name [default: admin]>
Enter the admin password>
Enter the new admin password>
Enter the new admin password again>
Command change-admin-password executed successfully.

Now try the enable-secure-admin command again.

# /root/glassfish4/bin/asadmin enable-secure-admin
Authentication failed with password from login store: /root/.gfclient/pass
Enter admin password for user "admin">
You must restart all running servers for the change in secure admin to take effect.
Command enable-secure-admin executed successfully.

Restart the domain for the changes to take effect.

# /root/glassfish4/bin/asadmin stop-domain
Waiting for the domain to stop .
Command stop-domain executed successfully.

# /root/glassfish4/bin/asadmin start-domain
Waiting for domain1 to start ............................
Successfully started the domain : domain1
domain  Location: /root/glassfish4/glassfish/domains/domain1
Log File: /root/glassfish4/glassfish/domains/domain1/logs/server.log
Admin Port: 4848
Command start-domain executed successfully.

Don’t forget to open up port 4848 at the firewall.

# iptables -I INPUT 5 -m state --state NEW -p tcp --dport 4848 -j ACCEPT

Now the GlassFish Console is accessible outside of localhost.  Key in hostname:4848 in the address bar of your browser, and you will be presented with the GlassFish Console login page.  Your browser might throw a certificate error due to the self-signed certificate; just ignore this and add an exception.

GlassFish Install 12 - GlassFish Console Login PageUser Name should be ‘admin’ and the password will be the password you keyed in during the change-admin-password command earlier.

Install Zenoss 4.2.4 on CentOS 6.4

I have not been checking up on Zenoss updates since my initial installation a few months ago.  I did not realise that Zenoss released a bugfix update 4.2.4 in July.

My 4.2.3 install has been working well so far, and I plan to update to 4.2.4 soon.  However, firstly I want to revisit the process of installing a fresh version.  I will repeat the steps of my 4.2.3 installation, and see if anything changed.

Start with a minimal CentOS 6.4 installation.  Then disable SELinux.

Remove the mysql-libs package that has been installed as part of the minimal CentOS install.

# yum remove mysql-libs

Install wget and grab the Zenoss 4.2.4 auto-deploy script.

# yum install wget
# wget --no-check-certificate https://github.com/zenoss/core-autodeploy/tarball/4.2.4 -O auto.tar.gz

Unpack the auto-deploy script.

# tar xzvf auto.tar.gz

Go into the unpacked directory and run the auto-deploy script.

# cd zenoss-core-autodeploy-*
# ./core-autodeploy.sh
Welcome to the Zenoss Core auto-deploy script!

This auto-deploy script installs the Oracle Java Runtime Environment (JRE).
To continue, please review and accept the Oracle Binary Code License Agreement
for Java SE.

Press Enter to continue.

Hit Enter, read the agreement, and press q to exit the agreement page.

Type yes and press Enter to accept the agreement.

The install will proceed and finish successfully.

Zenoss Core 4.2.4 install completed successfully!

Please visit http://127.0.0.1:8080 in your favorite Web browser to complete
setup.

NOTE: You may need to disable or modify this server's firewall to access port
8080. To disable this system's firewall, type:

# service iptables save
# service iptables stop
# chkconfig iptables off

Alternatively, you can modify your firewall to enable incoming connections to
port 8080. Here is a full list of all the ports Zenoss accepts incoming
connections from, and their purpose:

        8080 (TCP)                 Web user interface
        11211 (TCP and UDP)        memcached
        514 (UDP)                  syslog
        162 (UDP)                  SNMP traps

If you encounter problems with this script, please report them on the
following wiki page:

http://wiki.zenoss.org/index.php?title=Talk:Install_Zenoss

Thank you for using Zenoss. Happy monitoring!

Now, set up the firewall rules and the zenoss page can be accessed at http://<hostname>:8080

# iptables -I INPUT 5 -p tcp --dport 8080 -j ACCEPT
# iptables -I INPUT 6 -p tcp --dport 11211 -j ACCEPT
# iptables -I INPUT 7 -p udp --dport 11211 -j ACCEPT
# iptables -I INPUT 8 -p udp --dport 514 -j ACCEPT
# iptables -I INPUT 9 -p udp --dport 162 -j ACCEPT
# service iptables save

That’s it!

Installing vSphere CLI 5.1 U1 on CentOS 6.4

My attempt to monitor ESXi 5.1 hosts using Zenoss failed spectacularly at the install vCLI phase.  I have since been able to complete vCLI installation, and managed to run the resxtop command successfully.  However, the new version of resxtop (5.1 U1) returns too much output, and will not work with Zenoss’s esxtop ZenPack.  I guess I will have to wait until the Zenoss community comes up with a ZenPack for Zenoss 4.2 to work with the newer ESXi versions.

This post is to document the installation of vSphere CLI 5.1 U1 on CentOS 6.4, which is NOT supported by VMware (they only support vCLI installations on CentOS 5.5).

I will start with a minimal install of CentOS 6.4.  Then SELinux is disabled by editing /etc/sysconfig/selinux and rebooting the system.  Then, a yum upgrade is performed to update the kernel and all packages to the latest versions.  And a reboot, of course.

The vSphere installation will use these packages:

  • perl-CPAN = the installer will use CPAN to install PERL modules.
  • make & gcc = CPAN will use make and gcc to compile codes.
  • openssl-devel = the installer will run a check for this package before it can proceed.
  • perl-YAML = some of the PERL modules required by the installer will need this.
  • libxml2-devel = XML PERL modules will require this library.
  • libuuid-devel = the UUID PERL module will require this.

So let’s install them.

# yum install perl-CPAN make gcc openssl-devel perl-YAML libxml2-devel libuuid-devel

The installation script will also use some environment variables to be fed as arguments.  These environment variables will be needed to be set before installation.

# export http_proxy=
# export ftp_proxy=

Next, download the vSphere CLI installation package, and extract the archive.

# tar xzvf VMware-vSphere-CLI-5.1.0-1060453.x86_64.gz

Travel into the extracted directory, and run the installation program.

# cd vmware-vsphere-cli-distrib
# ./vmware-install.pl
Creating a new vSphere CLI installer database using the tar4 format.

Installing vSphere CLI 5.1.0 build-1060453 for Linux.

You must read and accept the vSphere CLI End User License Agreement to
continue.
Press enter to display it.

-- LICENSE AGREEMENT --

Do you accept? (yes/no) yes

Thank you.

Please wait while configuring CPAN ...

Please wait while configuring perl modules using CPAN ...

CPAN is downloading and installing pre-requisite Perl module "Archive::Zip" .

CPAN is downloading and installing pre-requisite Perl module "Compress::Zlib" .

CPAN is downloading and installing pre-requisite Perl module
"Compress::Raw::Zlib" .

CPAN is downloading and installing pre-requisite Perl module "Crypt::SSLeay" .

CPAN is downloading and installing pre-requisite Perl module
"IO::Compress::Base" .

CPAN is downloading and installing pre-requisite Perl module
"IO::Compress::Zlib::Constants" .

CPAN is downloading and installing pre-requisite Perl module
"Class::MethodMaker" .

CPAN is downloading and installing pre-requisite Perl module "HTML::Parser" .

CPAN is downloading and installing pre-requisite Perl module "UUID" .

CPAN is downloading and installing pre-requisite Perl module "Data::Dump" .

CPAN is downloading and installing pre-requisite Perl module "SOAP::Lite" .

CPAN is downloading and installing pre-requisite Perl module "URI" .

CPAN is downloading and installing pre-requisite Perl module "XML::SAX" .

CPAN is downloading and installing pre-requisite Perl module
"XML::NamespaceSupport" .

CPAN is downloading and installing pre-requisite Perl module
"XML::LibXML::Common" .

CPAN is downloading and installing pre-requisite Perl module "XML::LibXML" .

CPAN is downloading and installing pre-requisite Perl module "LWP" .

CPAN is downloading and installing pre-requisite Perl module
"LWP::Protocol::https" .

In which directory do you want to install the executable files?
[/usr/bin]

Please wait while copying vSphere CLI files...

The installation of vSphere CLI 5.1.0 build-1060453 for Linux completed
successfully. You can decide to remove this software from your system at any
time by invoking the following command:
"/usr/bin/vmware-uninstall-vSphere-CLI.pl".

This installer has successfully installed both vSphere CLI and the vSphere SDK
for Perl.

The following Perl modules were found on the system but may be too old to work
with vSphere CLI:

version 0.78 or newer

Enjoy,

--the VMware team

Checking /usr/bin/ shows a bunch of commands that has been installed like resxtop, vicfg-*, esxcfg-* and others.

Let’s install Zenoss 4! Part 3

Okay, so now the server is up and running, it is time to install Zenoss.

First let’s go through the Zenoss requirements once again.

  1. SELinux is disabled.
    # sestatus
    SELinux status:                 enabled
    SELinuxfs mount:                /selinux
    Current mode:                   enforcing
    Mode from config file:          enforcing
    Policy version:                 24
    Policy from config file:        targeted

    SELinux is enabled by default and will have to be disabled manually.  This is done by modifying the line ‘SELINUX=enforcing’ to ‘SELINUX=disabled’ in /etc/sysconfig/selinux and then rebooting the server.

    # sestatus
    SELinux status:                 disabled
  2. Directory /opt/zenoss is not a symlink to another location.
    # ls -al /opt | grep zenoss
    drwxr-xr-x.  3 root root 4096 May 12 11:06 zenoss
  3. umask is set to 022
    # umask
    0022
  4. /home directory is writable by root (or /home/zenoss exists as user zenoss’s home directory)
    # ls -al /home
    total 24
    drwxr-xr-x.  3 root root  4096 Sep 23  2011 .
    dr-xr-xr-x. 22 root root  4096 May 12 23:49 ..
    drwx------.  2 root root 16384 May 12 11:06 lost+found
  5. connected to the internet
  6. DNS is available
    # wget google.com
    -bash: wget: command not found
    # yum install wget
    ...
    Complete!
    # wget google.com
    (successfully downloaded index.html)

Let’s start installing Zenoss proper.

# wget --no-check-certificate https://github.com/zenoss/core-autodeploy/tarball/4.2.3 -O auto.tar.gz
(successfully downloaded auto.tar.gz)
# tar xvf auto.tar.gz
zenoss-core-autodeploy-3200e76/
zenoss-core-autodeploy-3200e76/README.rst
zenoss-core-autodeploy-3200e76/core-autodeploy.sh
zenoss-core-autodeploy-3200e76/secure_zenoss.sh
zenoss-core-autodeploy-3200e76/zenpack_actions.txt

Now let’s  check the contents of zenpack_actions.txt and core-autodeploy.sh.

zenpack_actions.txt contains the list of zenpacks to be installed by default.  I am going to leave it unmodified.

core-autodeploy.sh will do the following:

  1. Set umask to 022
  2. Check if /opt/zenoss is a symlink, and exit if it is.
  3. Check if MySQL has already been installed and exit if it has.
  4. Disable SELinux (I guess I did not have to disable it manually).
  5. Install Zenoss, MySQL, RabbitMQ, JRE, and rrdtool.

Let’s see it in action!

# ./core-autodeploy.sh

It appears that the distro-supplied version of MySQL is at least partially installed,
or a prior installation attempt failed.

Please remove these packages, as well as their dependencies (often postfix), and then
retry this script:

mysql-libs-5.1.69-1.el6_4.x86_64

It looks like the minimal CentOS 6.4 installation did include mysql-libs, and it has to be removed before running the Zenoss auto-deploy script.

# rpm -e mysql-libs-5.1.69-1.el6_4.x86_64
error: Failed dependencies:
        libmysqlclient.so.16()(64bit) is needed by (installed) postfix-2:2.6.6-2.2.el6_1.x86_64
        libmysqlclient.so.16(libmysqlclient_16)(64bit) is needed by (installed) postfix-2:2.6.6-2.2.el6_1.x86_64
        mysql-libs is needed by (installed) postfix-2:2.6.6-2.2.el6_1.x86_64

I guess postfix will have to be removed as well.

# rpm -e mysql-libs-5.1.69-1.el6_4.x86_64 postfix-2.6.6-2.2.el6_1.x86_64
error: Failed dependencies:
        /usr/sbin/sendmail is needed by (installed) cronie-1.4.4-7.el6.x86_64

Ok this is getting annoying. Let’s use yum.

# yum remove mysql-libs
Loaded plugins: fastestmirror
Setting up Remove Process
Resolving Dependencies
--> Running transaction check
---> Package mysql-libs.x86_64 0:5.1.69-1.el6_4 will be erased
--> Processing Dependency: libmysqlclient.so.16()(64bit) for package: 2:postfix-2.6.6-2.2.el6_1.x86_64
--> Processing Dependency: libmysqlclient.so.16(libmysqlclient_16)(64bit) for package: 2:postfix-2.6.6-2.2.el6_1.x86_64
--> Processing Dependency: mysql-libs for package: 2:postfix-2.6.6-2.2.el6_1.x86_64
--> Running transaction check
---> Package postfix.x86_64 2:2.6.6-2.2.el6_1 will be erased
--> Processing Dependency: /usr/sbin/sendmail for package: cronie-1.4.4-7.el6.x86_64
--> Running transaction check
---> Package cronie.x86_64 0:1.4.4-7.el6 will be erased
--> Processing Dependency: cronie = 1.4.4-7.el6 for package: cronie-anacron-1.4.4-7.el6.x86_64
--> Running transaction check
---> Package cronie-anacron.x86_64 0:1.4.4-7.el6 will be erased
--> Processing Dependency: /etc/cron.d for package: crontabs-1.10-33.el6.noarch
--> Restarting Dependency Resolution with new changes.
--> Running transaction check
---> Package crontabs.noarch 0:1.10-33.el6 will be erased
--> Finished Dependency Resolution

Dependencies Resolved

=================================================================================================================================================================================
 Package                              Arch                         Version                                  Repository                                                      Size
=================================================================================================================================================================================
Removing:
 mysql-libs                           x86_64                       5.1.69-1.el6_4                           @updates                                                       4.0 M
Removing for dependencies:
 cronie                               x86_64                       1.4.4-7.el6                              @anaconda-CentOS-201303020151.x86_64/6.4                       166 k
 cronie-anacron                       x86_64                       1.4.4-7.el6                              @anaconda-CentOS-201303020151.x86_64/6.4                        43 k
 crontabs                             noarch                       1.10-33.el6                              @anaconda-CentOS-201303020151.x86_64/6.4                       2.4 k
 postfix                              x86_64                       2:2.6.6-2.2.el6_1                        @anaconda-CentOS-201303020151.x86_64/6.4                       9.7 M

Transaction Summary
=================================================================================================================================================================================
Remove        5 Package(s)

Installed size: 14 M
Is this ok [y/N]: y
Downloading Packages:
Running rpm_check_debug
Running Transaction Test
Transaction Test Succeeded
Running Transaction
  Erasing    : cronie-anacron-1.4.4-7.el6.x86_64                                                                                                                             1/5
  Erasing    : crontabs-1.10-33.el6.noarch                                                                                                                                   2/5
  Erasing    : cronie-1.4.4-7.el6.x86_64                                                                                                                                     3/5
  Erasing    : 2:postfix-2.6.6-2.2.el6_1.x86_64                                                                                                                              4/5
  Erasing    : mysql-libs-5.1.69-1.el6_4.x86_64                                                                                                                              5/5
  Verifying  : crontabs-1.10-33.el6.noarch                                                                                                                                   1/5
  Verifying  : cronie-1.4.4-7.el6.x86_64                                                                                                                                     2/5
  Verifying  : cronie-anacron-1.4.4-7.el6.x86_64                                                                                                                             3/5
  Verifying  : 2:postfix-2.6.6-2.2.el6_1.x86_64                                                                                                                              4/5
  Verifying  : mysql-libs-5.1.69-1.el6_4.x86_64                                                                                                                              5/5

Removed:
  mysql-libs.x86_64 0:5.1.69-1.el6_4

Dependency Removed:
  cronie.x86_64 0:1.4.4-7.el6             cronie-anacron.x86_64 0:1.4.4-7.el6             crontabs.noarch 0:1.10-33.el6             postfix.x86_64 2:2.6.6-2.2.el6_1

Complete!

Ok now that’s settled, let’s run the auto-deploy script again.

# ./core-autodeploy.sh
...
   (a whole lot of downloading and installing)
...
MySQL is configured with a blank root password.
Configure a secure MySQL root password? [Yn]:Y
  Enter new MySQL root password:
Confirm new MySQL root password:
...
   (more installation..)
...
Zenoss installation completed.
Securing configuration files...
Zenoss Core 4.2.3 install completed successfully!

Please visit http://127.0.0.1:8080 in your favorite Web browser to complete
setup.

NOTE: You may need to disable or modify this server's firewall to access port
8080. To disable this system's firewall, type:

# service iptables save
# service iptables stop
# chkconfig iptables off

Alternatively, you can modify your firewall to enable incoming connections to
port 8080. Here is a full list of all the ports Zenoss accepts incoming
connections from, and their purpose:

        8080 (TCP)                 Web user interface
        11211 (TCP and UDP)        memcached
        514 (UDP)                  syslog
        162 (UDP)                  SNMP traps

If you encounter problems with this script, please report them on the
following wiki page:

http://wiki.zenoss.org/index.php?title=Talk:Install_Zenoss

Thank you for using Zenoss. Happy monitoring!

I am quite surprised that the auto-deploy script worked so well.

Now let’s modify the firewall as per the advice at the end of the installation.

# iptables -L -v
Chain INPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
 357K  410M ACCEPT     all  --  any    any     anywhere             anywhere            state RELATED,ESTABLISHED
    1    64 ACCEPT     icmp --  any    any     anywhere             anywhere
  148  8880 ACCEPT     all  --  lo     any     anywhere             anywhere
    1    52 ACCEPT     tcp  --  any    any     anywhere             anywhere            state NEW tcp dpt:ssh
  977  118K REJECT     all  --  any    any     anywhere             anywhere            reject-with icmp-host-prohibited

Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
    0     0 REJECT     all  --  any    any     anywhere             anywhere            reject-with icmp-host-prohibited

Chain OUTPUT (policy ACCEPT 269K packets, 60M bytes)
 pkts bytes target     prot opt in     out     source               destination

# iptables -I INPUT 5 -p tcp --dport 8080 -j ACCEPT
# iptables -I INPUT 6 -p tcp --dport 11211 -j ACCEPT
# iptables -I INPUT 7 -p udp --dport 11211 -j ACCEPT
# iptables -I INPUT 8 -p udp --dport 514 -j ACCEPT
# iptables -I INPUT 9 -p udp --dport 162 -j ACCEPT
# iptables -L -v
Chain INPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
 441K  439M ACCEPT     all  --  any    any     anywhere             anywhere            state RELATED,ESTABLISHED
    1    64 ACCEPT     icmp --  any    any     anywhere             anywhere
  165  9868 ACCEPT     all  --  lo     any     anywhere             anywhere
    1    52 ACCEPT     tcp  --  any    any     anywhere             anywhere            state NEW tcp dpt:ssh
    0     0 ACCEPT     tcp  --  any    any     anywhere             anywhere            tcp dpt:webcache
    0     0 ACCEPT     tcp  --  any    any     anywhere             anywhere            tcp dpt:memcache
    0     0 ACCEPT     udp  --  any    any     anywhere             anywhere            udp dpt:memcache
    0     0 ACCEPT     udp  --  any    any     anywhere             anywhere            udp dpt:syslog
    0     0 ACCEPT     udp  --  any    any     anywhere             anywhere            udp dpt:snmptrap
 1991  244K REJECT     all  --  any    any     anywhere             anywhere            reject-with icmp-host-prohibited

Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination
    0     0 REJECT     all  --  any    any     anywhere             anywhere            reject-with icmp-host-prohibited

Chain OUTPUT (policy ACCEPT 166 packets, 41427 bytes)
 pkts bytes target     prot opt in     out     source               destination
# service iptables save
iptables: Saving firewall rules to /etc/sysconfig/iptables:[  OK  ]

Now the Zenoss web interface should be available via http://hostname:8080.

Zenoss first start pageLet’s click Get Started!  The next page asks to specify a password for the admin user, as well as creating a new user.

Set admin password and create new userNext comes the page where you can start adding devices.  I add devices later so I’ll just click Finish.

Skip adding devicesThe next screen is the Zenoss dashboard.

Zenoss dashboardThat concludes the Zenoss Core 4 installation on CentOS 6.4.