If you've ever dealt a bit more seriously with PostgreSQL, and gone through different online articles and examples, chances are that you've ran to
pg_ctl command. Being Ubuntu user, I've often wondered what is the difference between starting PostgreSQL by using Ubuntu-native
service command and
pg_ctl. After some research I've found out what is the catch, and here I'll share this with you.
When you install PostgreSQL on Ubuntu from apt package repository, you get Ubuntu service script automatically installed, and convenience to start / stop / restart / status... postgresql service in a way you are accustomed to:
$ service postgresql start $ service postgresql stop $ update-rc.d postgresql disable $ update-rc.d postgresql enable
Then you'll see that in majority of resources
pg_ctl command is used instead, and you start getting scared if you are doing something wrong. Well, let's demystify this by understanding the differences.
There are few things you should know about service command used above:
- It affects all PostgreSQL database clusters on machine (if you have more than one), and all PostgreSQL versions, if you have more than one running side-by-side;
PostgreSQL service script internally uses
pg_ctlclustercommand, meaning that even if you execute
servicecommand, internally it executes
pg_ctlcluster, and as will be shown later - everything finishes by executing
Comparing to service command,
pg_ctl offers you more options and flags, and most importantly - it offers you a way to start / stop / restart particular database cluster, without affecting any other clusters, i.e.:
$ pg_ctl -w -D /var/lib/postgresql/9.5/main start
Keep calm, I know that the previous command won't run on Ubuntu - it is not added to PATH. But you can run it by using its full path (
/usr/lib/postgresql/9.5/bin/pg_ctl), or you can use its wrapper -
pg_ctlcluster explained below. Another important thing to say is that if you've tried to execute
pg_ctl without specifying its full path, you've probably got something like:
$ The program 'pg_ctl' is currently not installed. To run 'pg_ctl' please ask your administrator to install the package 'postgres-xc'
Don't do that! Don't install
postgres-xc! It is nothing more than hugely misleading, deeply wrong message.
There are few things you should know about
At the end of the day it is the command that actually does do job. As will be shown later,
pg_ctlclustercommand is nothing more than a
pg_ctlwrapper, meaning that it internally executes
It is version specific, meaning that if you have multiple PostgreSQL versions installed on the same machine - you'll also have multiple
pg_ctlversions. You should always pick the right version of the command to use.
pg_ctlcluster is Ubuntu-specific
pg_ctl wrapper. The original documentation is perfectly clear: "It determines the cluster version and data path and calls the right version of
pg_ctl with appropriate configuration parameters and paths." Example:
$ pg_ctlcluster 9.5 main status
Significant characteristics of
pg_ctlcluster command is that (as you can see above), it forces you to specify PostgreSQL version (i.e.
9.5) and database cluster (i.e.
We can conclude that if you have only one database cluster on the machine,
pg_ctl also) commands are completely equivalent. For example, there's no any difference between the following lines:
$ service postgresql restart $ pg_ctlcluster 9.5 main restart
So you haven't did anything wrong while using
service command. Even if you have multiple database clusters, the previous two lines are identical from the main database cluster's point of view, and again you haven't did anything wrong except restarting other database clusters needlessly.
In fact the commands are so equivalent that you can use them interchangeably. For example, you can start a database cluster by using
pg_ctlcluster and later stop it by using
service, and vice versa.
Hey I came across this blog while struggling with pg_ctl and pg_ctlcluster on RHEL and Ubuntu resp. :)
Thanks for the writeup
May I ask a couple of more questions ;)
I need to move postgresql from RHEL 7.2 to Ubuntu 16.04
- The admin who did the setup on RHEL made many changes to postgresql.service file on RHEL. On Ubuntu there are multiple .service files for postgres. And there is an /etc/init.d file too
Where to make the changes ?
- The service file on postgresql starts the server with different DB location and port, defined in service file. Also issues 'postgresql-setup initdb' with that file. Where to make similar changes on Ubuntu ?
To add to the agony, I need to put all of this in a script :(
Add new comment
Anonymous comments require solving captcha, and waiting for administrator's approval.