Keep Your Raspberry Pi Online: Fixing WiFi Drops and SSH Disconnects

Raspberry Pi going offline randomly? WiFi power save is likely the culprit. Here is how to keep your Pi accessible 24/7 with systemd services and network recovery.

The Pi was working fine yesterday. SSH connected instantly. Scripts ran on schedule. Then this morning - nothing.

$ ssh atd@raspberrypi.local
ssh: connect to host raspberrypi.local port 22: Host is down

I walked over to the Pi. Green LED blinking happily. Power fine. But the network was gone. A reboot fixed it, but two hours later - same thing.

If your Raspberry Pi stays online for a while then randomly becomes unreachable, you are not alone. This is one of the most common issues with headless Pi setups, and the culprit is almost always the same: WiFi power save mode.

Why Your Pi Goes Offline

Raspberry Pi OS enables WiFi power management by default. This makes sense for battery-powered devices - turn off the radio when idle to save power. But for a Pi running on wall power 24/7, it is counterproductive and annoying.

Why Pi goes offline

The symptoms are predictable:

  • Pi works fine for hours, then becomes unreachable
  • ping raspberrypi.local times out
  • Physical reboot fixes it temporarily
  • Problem returns after some idle time

The Fix: Disable WiFi Power Save

First, check if power save is enabled:

iw wlan0 get power_save

If it says Power save: on, that is your problem.

Quick Fix (Temporary)

Disable it immediately:

sudo iw wlan0 set power_save off

This works until the next reboot.

Permanent Fix (Systemd Service)

Create a systemd service that disables power save on every boot:

sudo tee /etc/systemd/system/disable-wifi-powersave.service > /dev/null << 'EOF'
[Unit]
Description=Disable WiFi Power Save Mode
After=network.target

[Service]
Type=oneshot
ExecStart=/usr/sbin/iw wlan0 set power_save off
RemainAfterExit=true

[Install]
WantedBy=multi-user.target
EOF

Enable and start it:

sudo systemctl daemon-reload
sudo systemctl enable --now disable-wifi-powersave.service

Verify it worked:

iw wlan0 get power_save
# Should show: Power save: off

This single change fixes 90% of Pi connectivity issues.

SSH Keepalive Settings

Even with WiFi power save disabled, SSH connections can drop if the network goes idle. Configure the SSH server to send keepalive packets:

# Edit SSH config
sudo nano /etc/ssh/sshd_config

Add or modify these lines:

ClientAliveInterval 60
ClientAliveCountMax 3

This sends a keepalive packet every 60 seconds. If 3 packets go unanswered, the connection is considered dead.

Apply the changes:

sudo systemctl restart sshd

You can also configure this on your client side in ~/.ssh/config:

Host raspberrypi.local
    ServerAliveInterval 60
    ServerAliveCountMax 3

Auto-Recovery: The Gentle Approach

Sometimes the network genuinely drops - router reboots, ISP hiccups, interference. For a truly reliable Pi, add automatic recovery.

Recovery strategies

Network Recovery Service

This script checks connectivity every 5 minutes. If the network is down, it restarts the WiFi interface instead of rebooting the whole system:

sudo tee /usr/local/bin/network-recover.sh > /dev/null << 'EOF'
#!/bin/bash
TARGET_HOST="google.com"
INTERFACE="wlan0"

if ! ping -c1 -W5 "$TARGET_HOST" > /dev/null 2>&1; then
    logger "[network-recover] Network unreachable. Restarting $INTERFACE"

    /sbin/ip link set "$INTERFACE" down
    sleep 2
    /sbin/ip link set "$INTERFACE" up
    sleep 5

    if ! ping -c1 -W5 "$TARGET_HOST" > /dev/null 2>&1; then
        logger "[network-recover] WiFi recovery failed"
    else
        logger "[network-recover] WiFi successfully recovered"
    fi
fi
EOF

sudo chmod +x /usr/local/bin/network-recover.sh

Systemd Timer (Better Than Cron)

Create the service:

sudo tee /etc/systemd/system/network-recover.service > /dev/null << 'EOF'
[Unit]
Description=Recover WiFi if network unreachable

[Service]
Type=oneshot
ExecStart=/usr/local/bin/network-recover.sh
EOF

Create the timer:

sudo tee /etc/systemd/system/network-recover.timer > /dev/null << 'EOF'
[Unit]
Description=Run network recovery every 5 minutes

[Timer]
OnBootSec=5min
OnUnitActiveSec=5min
Persistent=true

[Install]
WantedBy=timers.target
EOF

Enable it:

sudo systemctl daemon-reload
sudo systemctl enable --now network-recover.timer

Check status:

systemctl list-timers | grep network-recover

View logs:

journalctl -u network-recover.service

The Nuclear Option: Reboot If Offline

If gentle recovery is not enough, you can configure the Pi to reboot itself when the network is unreachable. This is aggressive but effective for critical applications.

sudo tee /usr/local/bin/network-check-reboot.sh > /dev/null << 'EOF'
#!/bin/bash
if ! ping -c1 -W5 google.com > /dev/null 2>&1; then
    logger "[network-check] Network unreachable. Rebooting..."
    /sbin/reboot
fi
EOF

sudo chmod +x /usr/local/bin/network-check-reboot.sh

Create systemd service and timer (same pattern as above):

sudo tee /etc/systemd/system/network-check-reboot.service > /dev/null << 'EOF'
[Unit]
Description=Reboot if network unreachable

[Service]
Type=oneshot
ExecStart=/usr/local/bin/network-check-reboot.sh
EOF

sudo tee /etc/systemd/system/network-check-reboot.timer > /dev/null << 'EOF'
[Unit]
Description=Check network every 5 minutes, reboot if down

[Timer]
OnBootSec=5min
OnUnitActiveSec=5min
Persistent=true

[Install]
WantedBy=timers.target
EOF

sudo systemctl daemon-reload
sudo systemctl enable --now network-check-reboot.timer

Warning: This will reboot your Pi every 5 minutes if your internet is actually down. Use the gentle recovery approach first.

Alternative: Cron Job

If you prefer cron over systemd timers:

# Add to root crontab
sudo crontab -e

Add this line:

*/5 * * * * ping -c1 google.com > /dev/null 2>&1 || /sbin/reboot

This does the same thing - checks every 5 minutes, reboots if offline.

Complete Setup Script

Here is everything combined into one script you can run on a fresh Pi:

#!/bin/bash
set -e

echo "=== Raspberry Pi Network Reliability Setup ==="

# 1. Disable WiFi power save
echo "[1/3] Disabling WiFi power save..."
sudo tee /etc/systemd/system/disable-wifi-powersave.service > /dev/null << 'EOF'
[Unit]
Description=Disable WiFi Power Save Mode
After=network.target

[Service]
Type=oneshot
ExecStart=/usr/sbin/iw wlan0 set power_save off
RemainAfterExit=true

[Install]
WantedBy=multi-user.target
EOF

sudo systemctl daemon-reload
sudo systemctl enable --now disable-wifi-powersave.service

# 2. Configure SSH keepalive
echo "[2/3] Configuring SSH keepalive..."
sudo sed -i 's/^#ClientAliveInterval.*/ClientAliveInterval 60/' /etc/ssh/sshd_config
sudo sed -i 's/^#ClientAliveCountMax.*/ClientAliveCountMax 3/' /etc/ssh/sshd_config
# Add if not present
grep -q "^ClientAliveInterval" /etc/ssh/sshd_config || echo "ClientAliveInterval 60" | sudo tee -a /etc/ssh/sshd_config
grep -q "^ClientAliveCountMax" /etc/ssh/sshd_config || echo "ClientAliveCountMax 3" | sudo tee -a /etc/ssh/sshd_config
sudo systemctl restart sshd

# 3. Setup network recovery
echo "[3/3] Setting up network recovery..."
sudo tee /usr/local/bin/network-recover.sh > /dev/null << 'SCRIPT'
#!/bin/bash
if ! ping -c1 -W5 google.com > /dev/null 2>&1; then
    logger "[network-recover] Network unreachable. Restarting wlan0"
    /sbin/ip link set wlan0 down
    sleep 2
    /sbin/ip link set wlan0 up
fi
SCRIPT

sudo chmod +x /usr/local/bin/network-recover.sh

sudo tee /etc/systemd/system/network-recover.service > /dev/null << 'EOF'
[Unit]
Description=Recover WiFi if network unreachable

[Service]
Type=oneshot
ExecStart=/usr/local/bin/network-recover.sh
EOF

sudo tee /etc/systemd/system/network-recover.timer > /dev/null << 'EOF'
[Unit]
Description=Run network recovery every 5 minutes

[Timer]
OnBootSec=5min
OnUnitActiveSec=5min
Persistent=true

[Install]
WantedBy=timers.target
EOF

sudo systemctl daemon-reload
sudo systemctl enable --now network-recover.timer

echo ""
echo "=== Setup Complete ==="
echo "WiFi power save: disabled"
echo "SSH keepalive: enabled (60s interval)"
echo "Network recovery: enabled (5 min checks)"
echo ""
echo "Verify with:"
echo "  iw wlan0 get power_save"
echo "  systemctl list-timers | grep network"

Save this as pi-network-setup.sh and run with:

chmod +x pi-network-setup.sh
sudo ./pi-network-setup.sh

Monitoring and Debugging

Check WiFi Power Save Status

iw wlan0 get power_save

View Recovery Logs

journalctl -u network-recover.service --since "1 hour ago"

List Active Timers

systemctl list-timers --all | grep network

Check WiFi Signal Strength

iwconfig wlan0 | grep -i signal

Network Interface Status

ip link show wlan0

When This Does Not Work

If your Pi still goes offline after these fixes, check:

  1. Router issues - Some routers aggressively disconnect idle clients. Check your router’s DHCP lease time and WiFi settings.

  2. Interference - 2.4GHz is crowded. If possible, use 5GHz or Ethernet.

  3. Power supply - Underpowered Pi can cause WiFi instability. Use the official power supply.

  4. Distance - WiFi signal degrades with distance and obstacles. Move the Pi closer to the router or add a WiFi extender.

  5. USB WiFi dongle issues - If using an external dongle, try a different one or the built-in WiFi.

Quick Reference

ProblemSolution
Pi goes offline after idleDisable WiFi power save
SSH connections dropEnable SSH keepalive
Network occasionally failsAdd recovery timer
Nothing else worksNuclear reboot option

The Reliable Pi

After applying these fixes, my Pi has been online for weeks without a single dropout. The combination of disabled power save, SSH keepalive, and automatic recovery handles everything the network throws at it.

The green LED still blinks happily. But now when I SSH in, it actually connects.


This post is part of a series on Raspberry Pi. See also: Raspberry Pi Headless SSH Setup and Identify Your Raspberry Pi Hardware.

About the Author

Ashish Anand

Ashish Anand

Founder & Lead Developer

Full-stack developer with 10+ years experience in Python, JavaScript, and DevOps. Creator of DevGuide.dev. Previously worked at Microsoft. Specializes in developer tools and automation.