Automatyczne przełączanie WiFi i Ethernet w Linuxie

Zauważyliście, że posiadając komputer z kilkoma interfejsami sieciowymi — na przykład Ethernet i WiFi — system nie wyłącza automatycznie WiFi po podłączeniu kabla? To niby nic wielkiego, ale czy nie warto byłoby jednak dezaktywować interfejsu radiowego, gdy korzystamy z połączenia przewodowego?

W tym artykule pokażę, jak w prosty sposób zautomatyzować ten proces w systemach Linux. Dzięki temu będziecie mogli zapomnieć o ręcznym włączaniu i wyłączaniu WiFi, na przykład podczas podłączania laptopa do huba USB z kartą sieciową lub stacji dokującej.

Zakładam, że czytelnicy znają podstawy obsługi systemu Linux — nie będę więc wracał do absolutnych podstaw. Skupię się na praktycznej automatyzacji zachowania usług sieciowych i rozwiązaniu konkretnego, codziennego problemu.

Pierwsze kroki

Aby w ogóle zacząć pisanie jakiegokolwiek skryptu, musimy poznać konfigurację naszego systemu. To od niej zależy, jakie narzędzia i rozwiązania będziemy mogli wykorzystać. Posiadana przez was dystrybucja nie ma aż takiego znaczenia, ale różne systemy mogą korzystać z różnych usług do zarządzania siecią. Dlatego ważne jest, aby sprawdzić, jak właściwie jest skonfigurowany nasz system.

Dobrym początkiem będzie poznanie nazwy interfejsu Ethernet, możemy to zrobić, wywołując poniższe polecenie:

ip addrCode language: Shell Session (shell)

Polecenie to wyświetli nam wszystkie interfejsy sieciowe w naszym systemie, w poniższy sposób:

1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host noprefixroute 
       valid_lft forever preferred_lft forever
2: enxf01: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc fq_codel state UP group default qlen 1000
    link/ether aa:bb:cc:dd:ee:01 brd ff:ff:ff:ff:ff:ff
    inet 192.168.0.100/24 brd 192.168.0.255 scope global noprefixroute enxf01
       valid_lft forever preferred_lft forever
    inet6 fe80::dead:beef/64 scope link noprefixroute 
       valid_lft forever preferred_lft forever
3: wlo1: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN group default qlen 1000
    link/ether aa:bb:cc:dd:ee:02 brd ff:ff:ff:ff:ff:ff
    altname wlp0s20f3
    altname wlx2cdb074e9aeeCode language: Shell Session (shell)

Jak widać, w moim systemie są widoczne trzy interfejsy sieciowe, pierwszy z nich to loopback i nie musimy sobie nim zaprzątać głowy. Drugi enxf01 jest moją zewnętrzną kartą sieciową w hubie USB podłączonym do portu USB-C, natomiast trzeci wlo1 to moja wbudowana karta WiFi w laptopie.

Ważne: w różnych systemach nazwy interfejsów mogą przybierać różne nazwy dlatego ważne, abyście zweryfikowali, jak to wygląda u was. Do przygotowania skryptów potrzebna będzie jedynie nazwa interfejsu Ethernet, ponieważ to na podstawie jego stanu będziemy włączać i wyłączać WiFi. Dlatego skopuj ją sobie i trzymaj pod ręką, będzie ona potrzebna później.


Teraz pozostało nam już tylko sprawdzenie jakiej usługi do zarządzania siecią używa nasz system. W systemach Linux mamy do dyspozycji systemd-networkd i NetworkManager, obie usługi służą do zarządzania siecią, nie będę się jednak rozpisywał nad różnicami między nimi. Powiem tylko, że systemd-networkd jest menadżerem zintegrowanym z systemd i używany głównie w systemach bez GUI np. serwerach. Natomiast NetworkManager lepiej sprawdza się w środowiskach desktopowych i laptopowych.

Na początek zweryfikujemy czy usługa systemd-networkd jest uruchomiona, robimy to poniższym poleceniem:

sudo systemctl status systemd-networkdCode language: Shell Session (shell)

Co powinno przynieść efekt podobny do poniższego:

○ systemd-networkd.service - Network Configuration
     Loaded: loaded (/usr/lib/systemd/system/systemd-networkd.service; disabled; preset: enabled)
     Active: inactive (dead)Code language: Shell Session (shell)

Jak widać, w moim przypadku usługa ta jest nieaktywna, co oznacza, że mój system korzysta z NetworkManager do zarządzania siecią, ale potwierdźmy to, wywołując poniższe polecenie:

sudo systemctl status NetworkManagerCode language: Shell Session (shell)

Które powinno zwrócić mniej więcej taki wynik:

● NetworkManager.service - Network Manager
     Loaded: loaded (/usr/lib/systemd/system/NetworkManager.service; enabled; preset: enabled)
     Active: active (running) since Tue 2026-02-03 10:03:14 CET; 1h 21min agoCode language: Shell Session (shell)

Jak widać, usługa jest aktywna, co oznacza, że w moim przypadku muszę dodać skrypt właśnie dla NetworkManager. Nie oznacza to jednak, że w waszych systemach będzie tak samo, dlatego pokażę wam jak przygotować skrypty zarówno dla systemd-networkd⁣, jak iNetworkManager. Ważne, abyście sprawdzili, które skrypty zadziałają w waszych systemach.

Skrypty dla NetworkManager

W pierwszej kolejności opiszę przygotowanie skryptów dla NetworkManager, ponieważ jeśli korzystacie z desktopowego Linuxa, to prawdopodobnie tej usługi używa wasz system. Usługa ta posiada mechanizm dispatcher.d, który reaguje na zmianę stanu interfejsów sieciowych i to właśnie ten mechanizm wykorzystamy do automatycznego przełączania WiFi.

Właściwie wystarczy dodać jeden krótki skrypt, do jego utworzenia możesz użyć poniższego polecenia w konsoli:

sudo nano /etc/NetworkManager/dispatcher.d/99-wifi-eth-switchCode language: Shell Session (shell)

Polecenie to otworzy plik /etc/NetworkManager/dispatcher.d/99-wifi-eth-switch w edytorze nano w trybie administratora. Nazwa pliku może być dowolna, pamiętaj jednak, że skrypty z katalogu, w którym umieszczamy plik, są uruchamiane alfabetyczne, a cyfra na początku nazwy pliku pozwala określić, jaki priorytet ma nasz skrypt. Nie przejmujcie się tym, że plik nie istnieje, nano sobie z tym poradzi. Jeśli wolicie, możecie też użyć trybu graficznego – nie zmuszam do używania konsoli.

Przejdźmy teraz do naszego skryptu, oto on:

#!/bin/bash
IFACE=$1
STATUS=$2

# Pamiętaj o zmianie nazwy interfejsu.
if [ "$IFACE" = "enxf01" ]; then
    if [ "$STATUS" = "up" ]; then
        nmcli radio wifi off
    elif [ "$STATUS" = "down" ]; then
        nmcli radio wifi on
    fi
fi
Code language: Bash (bash)

Jak widzicie, skrypt nie jest długi i dość prosty. Omówię go teraz pokrótce, abyście zrozumieli, co tak właściwie robicie.

Pierwsza linia to ścieżka do interpretera, w tym przypadku używamy bash. Druga i trzecia linia ustawia zmienne, których wartości są pobierane z parametrów wywołania skryptu i są to kolejno: nazwa interfejsu i jego status.

Następnie sprawdzamy, czy nazwa interfejsu jest identyczna z nazwą naszego interfejsu Ethernet – pamiętajcie o zmianie nazwy na tę, która odpowiada waszemu systemowi. Jeśli nazwy są identyczne, to sprawdzamy, czy interfejs został podniesiony up, czy odłączony down. W zależności od stanu interfejsu wyłączamy lub włączamy WiFi.

Aby skrypt mógł zostać wywołany przez system, musimy nadać mu odpowiednie uprawnienia, w tym celu wywołujemy poniższe polecenie:

sudo chmod +x /etc/NetworkManager/dispatcher.d/99-wifi-eth-switchCode language: Shell Session (shell)

Ustawia ono uprawnienia do wykonywania pliku dla wszystkich użytkowników i grup w systemie. Jest to istotne, aby usługa NetworkManager mogła wywołać nasz skrypt, gdy zadziała mechanizm dispatcher.d.

Na koniec uruchamiamy ponownie usługę NetworkManager, możecie to zrobić poleceniem:

sudo systemctl restart NetworkManagerCode language: Shell Session (shell)

Ewentualnie uruchomcie ponownie komputer, to działa zawsze. Teraz możecie sprawdzić, czy jeśli podłączycie kabel Ethernet do waszego komputera, to WiFi wyłączy się automatycznie i na odwrót, jeśli odłączycie kabel, to WiFi powinno się włączyć.

Skrypt dla systemd-networkd

W tym przypadku musimy dodać dwa skrypty, jeden w katalogu /etc/networkd-dispatcher/routable.d i drugi w /etc/networkd-dispatcher/no-carrier.d.  Zasada działania jest podobna do NetworkManager i mechanizmu dispatcher.d, ale akcje zostały podzielone na kilka katalogów. Skrypty z routable.d wykonywane są w momencie, kiedy interfejs zostanie podniesiony i otrzyma adres IP. Natomiast skrypty z no-carrier.d w momencie, kiedy interfejs zostanie rozłączony.

Przejdźmy teraz do skryptów, na początek wyłączanie WiFi, kiedy kabel Ethernet zostanie podłączony:

sudo nano /etc/networkd-dispatcher/routable.d/50-disable-wifiCode language: Shell Session (shell)

A oto skrypt:

#!/bin/sh

# Pamiętaj o zmianie nazwy interfejsu.
if [ "$IFACE" = enxf01 ] && [ "$ADMIN_STATE" = up ]; then
    nmcli radio wifi off
fi
Code language: Bash (bash)

Jak widzicie, sposób działania jest podobny do skryptu dla NetworkManager, kiedy nazwa interfejsu jest identyczna z naszą nazwą interfejsu Ethernet i jego status zostanie zmieniony na podniesiony up, to WiFi, zostanie wyłączone. Pamiętajcie o zmianie nazwy interfejsu w skrypcie, na tę odpowiadającą waszemu systemowi.

Teraz jeszcze tylko nadajmy odpowiednie uprawnienia do pliku:

sudo chmod +x /etc/networkd-dispatcher/routable.d/50-disable-wifiCode language: Shell Session (shell)

Połowa za nami, teraz czas na skrypt, który włączy WiFi, jeśli kabel Ethernet zostanie odłączony. Otwieramy plik w edytorze:

sudo nano /etc/networkd-dispatcher/no-carrier.d/50-enable-wifiCode language: Shell Session (shell)

W którym dodajemy następujący skrypt:

#!/bin/sh

# Pamiętaj o zmianie nazwy interfejsu.
if [ "$IFACE" = enxf01 ]; then
    nmcli radio wifi on
fi
Code language: Bash (bash)

W tym skrypcie wystarczy jedynie porównać nazwy interfejsu, ponieważ skrypt wywoła się tylko w przypadku, kiedy interfejs utraci połączenie. Pamiętajcie o wstawieniu swojej nazwy interfejsu.

Dodajemy uprawnienia do wykonywania pliku:

sudo chmod +x /etc/networkd-dispatcher/no-carrier.d/50-enable-wifiCode language: Shell Session (shell)

Pozostało nam teraz przeładowanie usługi, robimy to poniższym poleceniem:

sudo systemctl restart systemd-networkdCode language: Shell Session (shell)

Ewentualnie robimy restart komputera. Możecie teraz przetestować, czy WiFi reaguje na odłączanie i podłączanie kabla.

Najczęstsze problemy i ograniczenia

Jeśli wasze skrypty nie działają, oto lista najczęstszych błędów:

  • Użyliście skryptów dla złej usługi zarządzania siecią – zweryfikujcie jeszcze raz, z jakiej usługi korzysta wasz system;
  • Nazwa interfejsu w skrypcie jest niepoprawna – zweryfikujcie jeszcze raz, czy wprowadziliście poprawną nazwę interfejsu;
  • Nie nadaliście skryptowi uprawnień wywołania – sprawdźcie, czy plik jest na pewno wykonywalny;
  • Nie uruchomiliście ponownie usługi – przeładujcie usługę menadżera sieci albo uruchomcie ponownie komputer.

Kolejną ważną sprawą są pewne ograniczenia, o których warto pamiętać.

Skrypty te działają dla interfejsu o konkretnej nazwie, jeśli zaczniecie używać innego interfejsu, pamiętajcie o modyfikacji nazwy w skryptach.

Kolejna sprawa, system nie zareaguje, jeśli zmiana nastąpi przy wyłączonym urządzeniu, np. Jeśli wyłączycie komputer przy podłączonym kablu Ethernet, a włączycie już z odłączony, to WiFi pozostanie wyłączone i będziecie musieli je włączyć samodzielnie. Nie jest to duży problem, ale warto o tym pamiętać.

Podsumowanie

Zaprezentowałem wam prosty sposób na zautomatyzowanie działania interfejsów sieciowych w waszych systemach. Nie jest to nic szczególnie skomplikowanego – wiele osób nawet nie myśli o wyłączaniu WiFi po podłączeniu kabla Ethernet. Skoro jednak dotarliście do tego miejsca, zakładam, że zależało wam właśnie na automatyzacji tego procesu. Mam nadzieję, że ten artykuł okazał się w tym pomocny.