Log management with Logrotate

How to configure Logrotate for managing system and application logs.

When working with VPS or dedicated servers, tracking events and errors is essential for monitoring and diagnostics. Large log files create real problems: they're hard to parse, consume CPU and memory, and can cause application failures when a disk fills up.

Logrotate addresses this by automatically archiving current logs and creating fresh files for incoming data.

Checking the installation

Logrotate comes pre-installed on most Linux distributions and runs automatically via the cron scheduler. To check the version:

logrotate --version

Example output:

logrotate 3.21.0
    Default mail command: /usr/bin/mail
    Default compress command: /bin/gzip
    Default uncompress command: /bin/gunzip
    Default compress extension: .gz
    Default state file path: /var/lib/logrotate/status
    ACL support: yes
    SELinux support: yes

The output shows which tools Logrotate uses for compression and notifications, along with the path to the state file that tracks rotation history.

Configuration structure

Logrotate uses a hierarchical configuration structure. Global defaults are set in /etc/logrotate.conf, while per-application settings live in /etc/logrotate.d/.

Example /etc/logrotate.conf on Ubuntu:

# rotate log files weekly
weekly

# use the adm group by default
su root adm

# keep 4 weeks worth of backlogs
rotate 4

# create new (empty) log files after rotating old ones
create

# use date as a suffix of the rotated file
#dateext

# uncomment this if you want your log files compressed
#compress

# packages drop log rotation information into this directory
include /etc/logrotate.d

Key parameters:

  • weekly — logs are rotated once a week.
  • create — a new empty log file is created after rotation.
  • rotate 4 — four archived copies are kept.
  • su root adm — rotation runs as user root and group adm, preventing permission issues with system logs.
  • compress — archive compression (disabled by default).
  • include /etc/logrotate.d — loads per-application configuration files.

For the full list of directives:

man logrotate

Per-application configuration

Files in /etc/logrotate.d/ follow the same structure as the global config but apply only to specific logs. Settings in these files override global values from /etc/logrotate.conf. If a directive isn't specified in the application config, the global value is used.

Example /etc/logrotate.d/nginx:

/var/log/nginx/*.log {
    daily
    missingok
    rotate 14
    compress
    notifempty
}

If /etc/logrotate.conf sets rotate 4 and an application config doesn't define rotate, that application's logs will still keep four archived copies.

Rotation schedule

By default, Logrotate uses a time-based approach: logs are rotated on a fixed schedule. Supported intervals: hourly, daily, weekly, monthly, yearly.

Logrotate typically runs once a day via /etc/cron.daily/logrotate. To enable hourly rotation, move the job to cron.hourly:

sudo mv /etc/cron.daily/logrotate /etc/cron.hourly

For even more frequent runs, set up a custom cron job.

Size-based rotation

For services with unpredictable log volumes, rotation can be triggered by file size instead of a schedule.

size — rotate only when the file reaches the specified size, regardless of schedule:

/var/log/app/*.log {
    size 50M
}

size and time-based directives are mutually exclusive — whichever is listed last takes effect. If daily appears after size, logs will rotate daily and the size threshold will be ignored.

minsize — rotate on schedule, but only if the file has reached the minimum size:

/var/log/app/*.log {
    daily
    minsize 50M
}

maxsize — rotate immediately once the file exceeds the size limit, even if the scheduled time hasn't arrived yet:

/var/log/app/*.log {
    daily
    maxsize 50M
}

Sizes can be specified in bytes (default), kilobytes (k), megabytes (M), or gigabytes (G).

Rotation methods

Logrotate supports two main methods for handling active log files.

create (default) — renames the active file (app.logapp.log.1) and creates a new empty file with the original name. This is the recommended method and minimizes the risk of log data loss:

/var/log/app/*.log {
    create
    # create 644 appuser group — optionally set permissions, owner, and group
}

copytruncate — copies the current file's contents to an archive, then clears the original. Allows applications to keep writing to the same file descriptor. Recommended only for legacy applications that can't reopen log files after rotation:

/var/log/app/*.log {
    copytruncate
}

Archive file naming

By default, rotated files get sequential numbers: app.log.1, app.log.2, and so on. To add timestamps, use dateext:

/var/log/app/*.log {
    dateext
    # default: -%Y%m%d for daily, -%Y%m%d%H for hourly
}

A log rotated on June 25, 2025 would be named app.log-20250625.

For logs rotated multiple times per day, use a Unix timestamp for uniqueness:

/var/log/app/*.log {
    dateformat -%Y%m%d-%s
}

The dateyesterday directive stamps the file with the previous day's date — useful when rotation happens after midnight but the data belongs to the previous day.

Compression

The compress directive enables gzip compression:

/var/log/app/*.log {
    compress
}

To use a different compression tool:

/var/log/app/*.log {
    compress
    compresscmd /usr/bin/bzip2
    uncompresscmd /usr/bin/bunzip2
    compressext .bz2
}

delaycompress prevents the most recent rotated file from being compressed immediately — useful when an application keeps writing to the old file after rotation:

/var/log/app/*.log {
    compress
    delaycompress
}

compressoptions sets the gzip compression level from -1 (fast, low compression) to -9 (slow, maximum compression):

/var/log/app/*.log {
    compress
    compressoptions -9
}

Troubleshooting

The Logrotate state file shows when each log file was last rotated:

sudo cat /var/lib/logrotate/status

For a detailed analysis, run Logrotate in debug mode:

sudo logrotate --debug /etc/logrotate.conf

Help

If you have any questions or need assistance, please contact us through the ticket system — we're always here to help!

Need help?Our engineers will help you free of charge with any question in minutesContact us