Home / Alt manpages / nologin(8)

  • nologin(8)
  • Admin command
  • linux

Use nologin to Block Logins Without Locking an Account

You will finish with either a service account that refuses interactive logins, or a temporary system-wide login notice that you can remove cleanly. The two mechanisms are related but not interchangeable: nologin is a shell program, while /etc/nologin is a temporary gate used by login.

Allow about 10 minutes for an account-shell change and its checks. Allow longer for a system-wide lockout because you must plan an administrative escape route first. You need a root shell, or sudo access, for the changes in this guide. The commands that only inspect files or run nologin as a test do not need elevation.

Checkpoint: choose the scope

  • Use /usr/sbin/nologin for one account, normally a service or technical account that must not start a shell.
  • Use /etc/nologin for a short maintenance window when unprivileged users must be refused by login and shown a message.

Do not use either mechanism as a substitute for investigating a compromised account. A disabled login shell does not revoke existing sessions, terminate processes, remove keys, or change an account's password. Likewise, the global file does not mean every access path on the machine is stopped. Check the authentication and service configuration that actually applies to your system.

1. Confirm the local implementation

Read the installed documentation before copying an example. On this machine, the command comes from util-linux 2.41.3, while the installed section 8 manual identifies its source as shadow-utils 4.13. That packaging detail matters when comparing behaviour with another distribution.

command -v nologin
nologin --version
man 5 nologin
man 8 nologin

Typical output from the version check is:

 /usr/sbin/nologin
nologin from util-linux 2.41.3

The command itself prints a refusal and exits non-zero. Check that directly without changing an account:

/usr/sbin/nologin
printf 'exit status: %s\n' "$?"

Expected output includes This account is currently not available. and an exit status of 1. A non-zero result is the point here, so do not treat it as a failed installation.

2. Give one account a disabled shell

First identify the exact account. Replace svc_example with an existing account name, then inspect its current shell:

getent passwd svc_example

Only change the shell after confirming the returned record is the intended one. This is a security-sensitive change: a typo can affect the wrong identity, and a service may depend on a shell for a maintenance hook even when it does not offer interactive access.

Set the shell with usermod as root:

sudo usermod --shell /usr/sbin/nologin svc_example

Verify the result through the account database rather than assuming that the command changed local files:

getent passwd svc_example
getent passwd svc_example | awk -F: '{print "login shell: " $7}'

The final field should be /usr/sbin/nologin. A new login attempt that reaches this shell will print the refusal and return a non-zero status. Existing sessions remain active, so inspect and end them separately if that is part of your maintenance plan.

3. Undo the account change

Keep the original shell before changing it. If you did not record it, read it from a trusted account database record or the system's account-management documentation. For a normal Bash account, the undo command might be:

sudo usermod --shell /bin/bash svc_example
getent passwd svc_example | awk -F: '{print "login shell: " $7}'

Do not blindly substitute /bin/bash for a service account. Restore the shell that was actually intended for that account, such as /bin/sh or an application-specific wrapper. If the account came from LDAP, SSSD or another directory source, the authoritative shell may not be stored in local /etc/passwd.

4. Announce a temporary system-wide lockout

Before creating /etc/nologin, open a root-capable session that you will keep until the maintenance ends. The section 5 manual says that when this readable file exists, login allows access only to root, shows its contents to other users, and refuses their logins. This is deliberately disruptive.

Write a short, useful message as root. The redirection must run with elevation, so use sudo tee rather than placing sudo before a plain shell redirection:

printf '%s\n' 'System maintenance is in progress. Please try again after 23:00 UTC.' \
  | sudo tee /etc/nologin >/dev/null
sudo chmod 0644 /etc/nologin
sudo cat /etc/nologin

Expected verification output is the same maintenance sentence. Check that the file is readable before relying on it:

test -r /etc/nologin && echo 'system login gate is active'

This file is not a universal firewall. The documented behaviour is specifically for login. SSH, display managers, su-like tools, session managers and application-specific authentication can have additional rules or may already have an authenticated session. Test the access path you intend to restrict, without closing your administrative session.

5. Remove the system-wide gate

When maintenance is complete, remove the file from the same root-capable session:

sudo rm -- /etc/nologin
if test ! -e /etc/nologin; then
    echo 'system login gate is removed'
fi

Removal is the recovery action. Do not leave an old notice in place: users will continue to be refused by login until the file is gone. If you need another maintenance window later, create a fresh message after checking the date and expected end time.

Common traps

  • Confusing the names: setting an account's shell to nologin affects that account; creating /etc/nologin affects unprivileged logins handled by login.
  • Testing the wrong thing: running nologin only proves what the shell program does. It does not prove that SSH, a display manager or a directory service will select that shell.
  • Expecting a zero exit status: refusal is reported by a non-zero exit. Scripts should treat that as an intentional denial.
  • Forgetting active sessions: neither change logs out users who are already connected. Review sessions and processes separately before maintenance.
  • Breaking automation: a service account can still be used by processes that do not start its login shell, but changing its shell can break tools that do. Verify the service after the change.

Done means

  • The chosen scope is explicit: one account or a temporary login gate.
  • The installed nologin path and version were checked.
  • The account shell or /etc/nologin was verified after the change.
  • A root-capable recovery path remains available.
  • Existing sessions and service behaviour were considered separately.