Manage Linux control groups in PostgreSQL with pg_cgroups

09.2019 / Category: / Tags: |
pg_cgroups puts PostgreSQL in a cage
 © Laurenz Albe 2018

(This article and the extension pg_cgroups was written for cgroups v1. The extension won't work with cgroups v2, but the rest is still useful information.)

In another blog post, I described how Linux control groups work and how they are useful for PostgreSQL.

Here I will present my little PostgreSQL plugin pg_cgroups which makes this simple to handle for the DBA.

What is pg_cgroups good for?

If you have a machine dedicated to a single PostgreSQL cluster, you normally do not want to limit PostgreSQL's resource usage.

But sometimes you have more than one cluster running on a single machine, or you have an application server running on the same machine.
In that case, you may want to prevent one PostgreSQL cluster from using up so many resources that it starves the other programs on the same machine.

To some extent, the CPU and I/O schedulers can take care of that, but it can be nice to have some control. For example, you may want a small, unimportant database to not use up more than 10 percent of your CPU time and I/O bandwidth. And while you can limit PostgreSQL's memory usage through shared_buffers and work_mem, it might be nice to keep one cluster from blowing other cluster's data out of the file system cache.

How does pg_cgroups work?

I won't describe the complete setup here (see the project page for that), but here is a short description how it works:

  • Edit /etc/cgconfig.conf so that an empty control group /postgres is created at boot time. This control group can be administrated by the postgres operating system user.
  • Build and install pg_cgroups. This will require the PostgreSQL headers to be installed.
  • Add pg_cgroups to shared_preload_libraries in postgresql.conf and restart PostgreSQL.

pg_cgroups creates a new control group under /postgres postgres and moves the postmaster to this group. All PostgreSQL processes will automatically inherit the control group.

Now you can set and adjust resource consumption limits on the fly simply by changing parameters in postgresql.conf! There is support for limits on memory consumption, CPU time and I/O bandwidth. One particularly nice feature: this is the only way to limit the amount of file system cache that is used for PostgreSQL!

pg_cgroups makes this magic happen by modifying the control group limits whenever the parameter settings are changed.

What alternatives are there?

Of course, pg_cgroups is not the only way to manage Linux control groups. Alternatives include:

Managing control groups “by hand”

You can manage control groups directly via the /sys/fs/cgroup file system or using libcg tools like cgexec.

This usually requires root access to the machine, which DBAs often don't have. Sure, you can set up a control group hierarchy managed by the postgres user (like pg_cgroups does), but you still have to memorize the cgroup file hierarchy and commands.

Managing control groups via systemd

systemd services allow setting control group limits via directives in the service file.

This is a great way of setting limits for PostgreSQL, but there are some disadvantages:

  • You need root to change the settings.
  • Changing the settings requires a restart of PostgreSQL.

Using docker

Docker uses Linux control groups to enforce resource limits. So if you are already running PostgreSQL in a dockerized environment, that may be your first choice.

However, not everybody wants the added complexity of docker.

Is pg_cgroups ready for production?

The software is still in beta.

But since it is fairly simple and is not deeply tangled with PostgreSQL server code (all it does is define a few magic parameters), I don't expect many nasty bugs.

If you run into trouble, I am happy to help.


I think this nice little piece of software is useful for everybody who runs more than one PostgreSQL cluster per machine. I hope it makes the DBA's life a better one.

0 0 votes
Article Rating
Notify of
Newest Most Voted
Inline Feedbacks
View all comments
Adam Brusselback
Adam Brusselback
4 years ago

Love the idea, really cool way of making Postgres play nice with shared hardware resources and seems easier to manage than any other solutions.

4 years ago

Awesome. This is one area which people who migrate from complex database systems like Oracle often asks. many of those databases have built-in Resource Manager using which they can control the User level resource consumption also. Is there a way to assign PostgreSQL user accounts to subgroups?

4 years ago
Reply to  jobinau

That is not possible with the current simple architecture of pg_cgroups and would ask for something more complicated than inheriting cgroups. It would require hooks in PostgreSQL not only when a session is created, but probably also for SET ROLE and SET SESSION AUTHORIZATION and when entering or leaving a SECURITY DEFINER function.

It also requires solving complicated design questions:
- If a user calls a SECURITY DEFINER function, is the execution counted towards his quota?
- Are the quota counted for the current_user or for the session_user?

All that is a little out of scope for my little tool.

CYBERTEC Logo white
CYBERTEC PostgreSQL International GmbH
Römerstraße 19
2752 Wöllersdorf

+43 (0) 2622 93022-0

Get the newest PostgreSQL Info & Tools

    This site is protected by reCAPTCHA and the Google Privacy Policy & Terms of Service apply.

    CYBERTEC PostgreSQL International GmbH
    Would love your thoughts, please comment.x
    linkedin facebook pinterest youtube rss twitter instagram facebook-blank rss-blank linkedin-blank pinterest youtube twitter instagram