"Быстрый
<br />
Шпаргалка команд troubleshooting сети по симптому. Сайт не открывается — dig + curl. Тормозит — mtr. Порт закрыт — ss + nc. Канал забит — nethogs. Пакеты теряются — tcpdump. Иди по уровням OSI снизу вверх: link, IP, route, <a class="wpil_keyword_link" title="DNS" href="https://it-apteka.com/tag/dns/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2446">DNS</a>, порт, приложение.<br />
<h2>1. Диагноз — что сломалось и где искать</h2>
<p>Поднял сервер. Сайт не открывается. ping проходит, curl зависает. Знакомо? Это troubleshooting сети — и решается он не одной командой, а связкой по симптому.</p>
<p>В этой <a href="https://it-apteka.com/docker-shpargalka-i-primery/" title="Команды Docker: шпаргалка с примерами для сервера и продакшена" target="_blank" rel="noopener" data-wpil-monitor-id="2451">шпаргалке — команды</a>, которые покрывают 90% сетевых инцидентов. Не теория, а рабочий справочник: симптом — команда — что увидишь — что делать дальше. Время на освоение — 15 минут чтения, годы экономии нервов.</p>
<p>Что внутри:</p>
<ul>
<li>алгоритм диагностики по уровням OSI</li>
<li>команды для <a class="wpil_keyword_link" title="Linux" href="https://it-apteka.com/category/linux/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2450">Linux</a> и Windows бок о бок</li>
<li>усиленный блок про <a href="https://it-apteka.com/powershell-skripty-v-windows-kak-sozdat-zapustit-i-avtomatizirovat-vypolnenie/" title="PowerShell скрипты в Windows: как создать, запустить и автоматизировать выполнение" target="_blank" rel="noopener" data-wpil-monitor-id="2452">PowerShell и pktmon для Windows</a></li>
<li>боевые кейсы из продакшна с разбором</li>
<li>таблица «симптом — команда» под закладку</li>
<li>чит-коды для экстренных ситуаций</li>
<li>FAQ по типовым ошибкам новичков</li>
</ul>
<p>Дерево решений для самой частой жалобы «сайт не открывается» — вот так выглядит триаж:</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart TD
A["Сайт не открывается"] --> B{"ping шлюза"}
B -->|нет| C["Проверь IP, кабель, ethtool"]
B -->|да| D{"ping 8.8.8.8"}
D -->|нет| E["Проверь маршруты: ip route"]
D -->|да| F{"dig site.com"}
F -->|не резолвит| G["Проверь DNS: resolv.conf"]
F -->|ok| H{"nc -zv site.com 443"}
H -->|закрыт| I["Файрвол или сервис лёг"]
H -->|открыт| J{"curl -v site.com"}
J -->|SSL fail| K["Проверь сертификат, шифры"]
J -->|HTTP 502| L["Backend, логи приложения"]
J -->|медленно| M["mtr, iftop, QoS"]
style A fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style C fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style E fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style G fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style I fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style K fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style L fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style M fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
</pre>
<h2>2. Алгоритм — почему важен порядок</h2>
<p>Главная ошибка новичков — сразу лезть в tcpdump, когда не работает ping до шлюза. Так не надо. Сеть диагностируется снизу вверх по модели OSI.</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart TD
A["L1-L2: Линк, кабель, MAC"] --> B["L3: IP-адрес, маска, шлюз"]
B --> C["L3: Маршрутизация"]
C --> D["L7: DNS"]
D --> E["L4: Порт, TCP-handshake"]
E --> F["L7: Приложение, HTTP, SSL"]
style A fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style B fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style C fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style D fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style E fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style F fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
</pre>
<p>Причины почему алгоритм работает:</p>
<ul>
<li><strong>L1 ломается чаще всего</strong> — кабель, порт, duplex. Если линка нет — дальше идти бесполезно.</li>
<li><strong>L3 без шлюза = ничего не работает</strong> — проверь IP и default route первым делом, до DNS.</li>
<li><strong>DNS убивает 50% запросов</strong> — «сайт не открывается» в большинстве случаев именно про него.</li>
<li><strong>Порт может быть закрыт по сотне причин</strong> — сервис лёг, файрвол, bind на localhost. Это не L3.</li>
<li><strong>Приложение — последнее что проверяешь</strong> — 502 это часто не nginx, а backend.</li>
<li><strong>Пропустил уровень — копаешь не там</strong> — классика: час крутишь iptables, а кабель полусидит.</li>
</ul>
<p>Карта команд по уровням — какая команда на каком этаже стека работает:</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 40}
}}%%
flowchart LR
L1["L1 Физика"] --> T1["ethtool, ip link"]
L2["L2 Канальный"] --> T2["ip neigh, arp, tcpdump"]
L3["L3 Сетевой"] --> T3["ping, mtr, ip route, traceroute"]
L4["L4 Транспорт"] --> T4["nc, nmap, ss, Test-NetConnection"]
L7["L7 Приложение"] --> T7["dig, curl, wget, openssl"]
style L1 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L2 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L3 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L4 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L7 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style T1 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T2 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T3 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T4 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T7 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
</pre>
<h2>3. Шпаргалка — команда по симптому</h2>
<p>Главная таблица. Закладывай в избранное.</p>
<table>
<tbody>
<tr>
<th>Симптом</th>
<th>Уровень</th>
<th>Команда Linux</th>
<th>Команда <a class="wpil_keyword_link" href="https://it-apteka.com/category/windows-server/" target="_blank" rel="noopener" title="Windows Server" data-wpil-keyword-link="linked" data-wpil-monitor-id="2460">Windows</a></th>
</tr>
<tr>
<td>Линка нет</td>
<td>L1</td>
<td>ip link, ethtool</td>
<td>Get-NetAdapter</td>
</tr>
<tr>
<td>Нет IP-адреса</td>
<td>L3</td>
<td>ip addr</td>
<td>ipconfig /all</td>
</tr>
<tr>
<td>Шлюз не пингуется</td>
<td>L3</td>
<td>ping, ip route</td>
<td>ping, route print</td>
</tr>
<tr>
<td>Тормозит, потери пакетов</td>
<td>L3</td>
<td>mtr</td>
<td>pathping, tracert</td>
</tr>
<tr>
<td>Странный путь пакета</td>
<td>L3</td>
<td>traceroute, ip route</td>
<td>tracert</td>
</tr>
<tr>
<td>DNS не резолвит</td>
<td>L7</td>
<td>dig, nslookup</td>
<td>nslookup, Resolve-DnsName</td>
</tr>
<tr>
<td>Порт закрыт</td>
<td>L4</td>
<td>nc -zv, nmap</td>
<td>Test-NetConnection</td>
</tr>
<tr>
<td>Кто слушает порт</td>
<td>L4</td>
<td>ss -tulnp</td>
<td>Get-NetTCPConnection</td>
</tr>
<tr>
<td>Кто жрёт канал</td>
<td>L7</td>
<td>nethogs, iftop</td>
<td>Resource Monitor</td>
</tr>
<tr>
<td>Не понимаю что в кабеле</td>
<td>все</td>
<td>tcpdump</td>
<td>pktmon, Wireshark</td>
</tr>
<tr>
<td>HTTP отдаёт ошибку</td>
<td>L7</td>
<td>curl -v</td>
<td>Invoke-WebRequest</td>
</tr>
<tr>
<td>Дубль IP в сети</td>
<td>L2</td>
<td>ip neigh, <a class="wpil_keyword_link" title="arp" href="https://it-apteka.com/tag/arp/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2448">arp</a> -n</td>
<td>arp -a, Get-NetNeighbor</td>
</tr>
</tbody>
</table>
<p>Дальше — разбор каждой команды с боевыми примерами.</p>
<h2>4. ping и mtr — живой ли хост и где теряются пакеты</h2>
<p>ping — дедушка. Проверяет ICMP Echo. Если не отвечает — либо хост мёртв, либо ICMP режется файрволом. Не делай вывод «сервер лёг» по одному ping.</p>
<pre><code class="language-bash">
# Linux - 10 пакетов и стоп
ping -c 10 8.8.8.8
# Don't Fragment - проверка MTU
ping -M do -s 1472 8.8.8.8
# Тихий режим - только статистика
ping -c 100 -q 8.8.8.8
</code></pre>
<pre><code class="language-powershell">
# Windows - 10 пакетов
ping -n 10 8.8.8.8
# DF-флаг и размер - проверка MTU
ping -f -l 1472 8.8.8.8
# С меткой времени для логов
ping -t 8.8.8.8 | ForEach-Object {"{0} - {1}" -f (Get-Date),$_}
</code></pre>
<p>mtr намного полезнее в продакшне. Это traceroute, который не делает один снимок, а долбит маршрут постоянно и показывает потери на каждом хопе.</p>
<pre><code class="language-bash">
# Установка
sudo apt install mtr
# Отчёт по 100 пакетам
mtr -r -c 100 google.com
# Без DNS, с AS-номерами
mtr -rn --aslookup -c 1000 google.com
# TCP вместо ICMP - если ICMP режут
mtr --tcp -P 443 google.com
</code></pre>
"Кейс:
<br />
Клиент из Владивостока жалуется на лаги до сервера в Москве. Запустил mtr -r -c 100. На 4-м хопе backbone провайдера 15% потерь. Скрин mtr в тикет провайдеру — починили перегруженный линк за день.<br />
<pre><code class="language-bash">
sudo mtr -r -c 100 -n server-moscow.local
# HOST Loss% Snt Last Avg Best Wrst StDev
# 1. 192.168.1.1 0.0% 100 1.2 1.3 1.0 2.1 0.2
# 2. 10.0.0.1 0.0% 100 3.4 3.5 3.0 5.2 0.4
# 3. provider-gw.local 0.0% 100 12.3 12.5 11.8 18.3 1.2
# 4. provider-backbone.local 15.0% 100 45.6 46.2 44.1 89.3 12.5
# 5. moscow-gw.local 2.0% 100 78.3 78.9 77.1 92.1 3.2
</code></pre>
<p>Смотри на StDev. Если разброс задержки большой — проблема в jitter, а не в потерях. Для VoIP это смерть, для HTTP терпимо.</p>
<h2>5. ip и ipconfig — конфигурация интерфейсов</h2>
<p>Без правильного IP, маски и шлюза не работает ничего. Проверка занимает 5 секунд.</p>
<pre><code class="language-bash">
# Linux - современный ip из iproute2
ip addr show
ip a # короткая форма
ip -br addr # таблицей, очень компактно
# Маршруты
ip route show
ip route get 8.8.8.8 # покажет какой маршрут выберет ядро
# Соседи (ARP)
ip neigh show
# Поднять/опустить интерфейс
sudo ip link set eth0 up
sudo ip link set eth0 down
# Добавить IP
sudo ip addr add 192.168.1.50/24 dev eth0
</code></pre>
<pre><code class="language-powershell">
# Windows - PowerShell
Get-NetIPAddress
Get-NetIPConfiguration
Get-NetAdapter
# Старый ipconfig тоже жив
ipconfig /all
ipconfig /release
ipconfig /renew
ipconfig /flushdns
</code></pre>
"Кейс:
<br />
После <a href="https://it-apteka.com/10-oshibok-pri-nastrojke-domashnego-wi-fi-iz-za-kotoryh-tormozit-internet/" title="10 ошибок при настройке домашнего Wi-Fi, из-за которых тормозит интернет" target="_blank" rel="noopener" data-wpil-monitor-id="2453">настройки VLAN интернет</a> пропал. ip addr показывает eth0.10 в state DOWN. Забыл поднять интерфейс после создания. Классика, лечится одной командой.<br />
<pre><code class="language-bash">
ip link show eth0.10
# eth0.10@eth0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN
sudo ip link set eth0.10 up
ip link show eth0.10
# eth0.10@eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500
</code></pre>
<p>Запомни: после создания любого интерфейса — VLAN, bridge, bond — всегда делай ip link set up. Это не подразумевается по умолчанию.</p>
<h2>6. dig и nslookup — DNS-детективы</h2>
<p>Половина обращений в саппорт — это DNS. «Сайт не открывается» в 4 случаях из 10 = резолвер не работает или отдаёт старую запись.</p>
<p><a href="https://it-apteka.com/nslookup-i-dig-diagnostika-dns-dlja-sistemnogo-administratora/" title="nslookup и dig — диагностика DNS для системного администратора" target="_blank" rel="noopener" data-wpil-monitor-id="2454">dig в Linux мощнее nslookup</a>. В Windows nslookup тоже неплох, но Resolve-DnsName в PowerShell удобнее.</p>
<pre><code class="language-bash">
# Самое полезное - короткий ответ
dig google.com +short
# Конкретный DNS
dig @8.8.8.8 google.com
# MX для почты, TXT для SPF/DKIM, NS для делегирования
dig MX gmail.com +short
dig TXT google.com +short
dig NS cloudflare.com +short
# Reverse - по IP найти имя
dig -x 8.8.8.8 +short
# Trace - путь от корневых серверов
dig +trace google.com
# Конкретный resolver и таймаут
dig @1.1.1.1 +time=2 +tries=1 example.com
</code></pre>
<pre><code class="language-powershell">
# Windows
Resolve-DnsName google.com
Resolve-DnsName google.com -Type MX
Resolve-DnsName google.com -Server 8.8.8.8
# nslookup интерактивный
nslookup
> server 8.8.8.8
> set type=MX
> gmail.com
> exit
</code></pre>
"Правило
<br />
За день до смены A-записи уменьши TTL до 300 секунд. Поменял запись — подождал час — вернул TTL обратно. Иначе пользователи будут резолвить старый IP сутки.<br />
<p>Капля никотина убивает лошадь. Одна A-запись с TTL 86400 без предупреждения — весь отдел саппорта.</p>
<h2>7. ss и netstat — кто слушает и куда ходит</h2>
<p>netstat жив, но ss быстрее и информативнее. На современном Linux используй ss. netstat в Windows никуда не делся.</p>
<pre><code class="language-bash">
# Все слушающие TCP-порты с процессами
sudo ss -tulnp
# Только LISTEN
ss -tln
# Кто слушает 443
sudo ss -tlnp | grep :443
# Все ESTABLISHED соединения
ss -tn state established
# Считаем по состояниям - очень полезно
ss -tan | awk '{print $1}' | sort | uniq -c | sort -rn
# Сводка
ss -s
# Соединения к конкретному IP
ss -tn dst 8.8.8.8
</code></pre>
<pre><code class="language-powershell">
# Windows - кто слушает порт 80
Get-NetTCPConnection -LocalPort 80 -State Listen
Get-Process -Id (Get-NetTCPConnection -LocalPort 80).OwningProcess
# Или по-старому
netstat -ano | findstr :80
tasklist | findstr "PID"
</code></pre>
"Кейс:
<br />
Веб-сервер начал отваливаться. ss показал 1024 сокета в TIME-WAIT. Приложение не закрывало keep-alive нормально. Подкрутил sysctl — сервер стал держать в 3 раза больше соединений.<br />
<pre><code class="language-bash">
sudo sysctl -w net.ipv4.tcp_fin_timeout=30
sudo sysctl -w net.ipv4.tcp_tw_reuse=1
echo "net.ipv4.tcp_fin_timeout=30" | sudo tee -a /etc/sysctl.conf
echo "net.ipv4.tcp_tw_reuse=1" | sudo tee -a /etc/sysctl.conf
</code></pre>
<h2>8. nc и nmap — открыт ли порт</h2>
<p>Самый частый вопрос troubleshooting сети: «А порт-то открыт?». nc даёт ответ за секунду, nmap — за минуту с деталями.</p>
<p>Что происходит на проводе при проверке порта — классический three-way handshake:</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#f8fafc',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'noteBkgColor': '#fefce8',
'noteTextColor': '#713f12',
'noteBorderColor': '#fbbf24',
'actorBkg': '#f8fafc',
'actorBorder': '#94a3b8',
'actorTextColor': '#1e293b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'sequence': {
'mirrorActors': false,
'messageAlign': 'center',
'actorMargin': 120,
'width': 160,
'noteMargin': 12
}
}}%%
sequenceDiagram
participant C as Клиент
participant S as Сервер
Note over C,S: nc -zv server 443
C->>S: SYN
S->>C: SYN-ACK
C->>S: ACK
Note over C,S: Соединение установлено - порт открыт
C->>S: FIN
S->>C: FIN-ACK
</pre>
<pre><code class="language-bash">
# nc - проверка одного порта
nc -zv server.com 443
# Диапазон портов
nc -zv 192.168.1.100 20-25
# UDP
nc -zvu dns.server 53
# Без nc - встроенный bash
timeout 2 bash -c '</dev/tcp/server.com/443' && echo "open" || echo "closed"
# nmap - полное сканирование
nmap -F 192.168.1.100 # топ-100 портов
nmap -p- 192.168.1.100 # все 65535
nmap -p 22,80,443 192.168.1.0/24 # конкретные порты на подсети
# Версии сервисов и ОС
sudo nmap -sV -O 192.168.1.100
# Ping scan - найти живых
nmap -sn 192.168.1.0/24
</code></pre>
<pre><code class="language-powershell">
# Windows - Test-NetConnection
Test-NetConnection server.com -Port 443
Test-NetConnection -ComputerName server.com -Port 443 -InformationLevel Detailed
# Сокращение
tnc server.com -Port 443
</code></pre>
"Кейс:
<br />
Приложение не коннектится к БД. nc -zv 192.168.1.50 3306 — Connection refused. На сервере БД ss -tln показал bind на 127.0.0.1. Поправил bind-address в my.cnf — заработало.<br />
<pre><code class="language-bash">
# На сервере БД
sudo ss -tln | grep 3306
# tcp LISTEN 0 151 127.0.0.1:3306 0.0.0.0:*
# Правим /etc/mysql/mysql.conf.d/mysqld.cnf
# bind-address = 0.0.0.0
sudo systemctl restart mysql
sudo ss -tln | grep 3306
# tcp LISTEN 0 151 0.0.0.0:3306 0.0.0.0:*
</code></pre>
<p>Если порт открыт локально, но недоступен снаружи — проверь iptables/firewalld и security group у облачного провайдера.</p>
<h2>9. curl — HTTP-снайпер</h2>
<p>curl — не только «скачать файл». Это инструмент №1 для диагностики HTTP/HTTPS. Покажет где тормозит TLS, какие заголовки отдаёт сервер, как идут редиректы.</p>
<p>Что измеряют тайминги curl — вот вся цепочка от DNS до получения тела ответа:</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#f8fafc',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'noteBkgColor': '#fefce8',
'noteTextColor': '#713f12',
'noteBorderColor': '#fbbf24',
'actorBkg': '#f8fafc',
'actorBorder': '#94a3b8',
'actorTextColor': '#1e293b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'sequence': {
'mirrorActors': false,
'messageAlign': 'center',
'actorMargin': 100,
'width': 140
}
}}%%
sequenceDiagram
participant C as curl
participant D as DNS
participant S as Сервер
C->>D: A example.com
D->>C: 1.2.3.4
Note over C: time_namelookup
C->>S: TCP SYN
S->>C: TCP SYN-ACK
C->>S: TCP ACK
Note over C: time_connect
C->>S: TLS ClientHello
S->>C: TLS ServerHello + Cert
C->>S: TLS Finished
Note over C: time_appconnect
C->>S: HTTP GET /
S->>C: HTTP 200 OK
Note over C: time_starttransfer
S->>C: Body
Note over C: time_total
</pre>
<pre><code class="language-bash">
# Только заголовки
curl -I https://example.com
# Полный verbose - запрос и ответ
curl -v https://example.com
# Не следовать редиректам
curl -I https://example.com
# Следовать
curl -IL https://example.com
# Указать конкретный IP - обход DNS
curl --resolve example.com:443:1.2.3.4 https://example.com
# POST с JSON
curl -X POST -H "Content-Type: application/json" \
-d '{"key":"value"}' https://api.example.com/data
# Игнорировать SSL - только для теста
curl -k https://self-signed.com
# HTTP/2 или HTTP/1.1 принудительно
curl --http2 -I https://example.com
curl --http1.1 -I https://example.com
</code></pre>
<p>Главная фишка curl — тайминг по фазам запроса. Покажет точно где медленно.</p>
<pre><code class="language-bash">
# Создаём шаблон вывода
cat > curl-format.txt << 'EOF'
time_namelookup: %{time_namelookup}s
time_connect: %{time_connect}s
time_appconnect: %{time_appconnect}s
time_pretransfer: %{time_pretransfer}s
time_redirect: %{time_redirect}s
time_starttransfer: %{time_starttransfer}s
----------
time_total: %{time_total}s
EOF
curl -w "@curl-format.txt" -o /dev/null -s https://example.com
</code></pre>
"Кейс:
<br />
Сайт грузится за 2.5 секунды. curl показал time_appconnect 0.456s — SSL занимает половину времени. На сервере nmap —script ssl-enum-ciphers нашёл слабые шифры. Отключил RC4, 3DES — handshake упал до 89ms.<br />
<pre><code class="language-text">
# nginx ssl.conf
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384';
ssl_prefer_server_ciphers off;
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 1h;
</code></pre>
<h2>10. tcpdump — последняя инстанция</h2>
<p>Когда все остальные команды показывают «вроде ок», а пользователь говорит «не работает» — доставай tcpdump. Он показывает реальные пакеты на проводе. Не врёт.</p>
<pre><code class="language-bash">
# Базовый захват на интерфейсе
sudo tcpdump -i eth0
# Без DNS-резолва, с номерами портов - быстрее
sudo tcpdump -i eth0 -nn
# По хосту
sudo tcpdump -i eth0 host 192.168.1.100
# Между двумя хостами в обоих направлениях
sudo tcpdump -i eth0 'host 192.168.1.100 and host 192.168.1.200'
# По порту
sudo tcpdump -i eth0 'tcp port 443'
# Только SYN-пакеты - смотреть установление соединений
sudo tcpdump -i eth0 'tcp[tcpflags] & tcp-syn != 0'
# DNS-запросы
sudo tcpdump -i eth0 -nn 'udp port 53'
# Сохранить в pcap для Wireshark
sudo tcpdump -i eth0 -w capture.pcap host 192.168.1.100
# С ротацией - чтобы не забить диск
sudo tcpdump -i eth0 -w cap.pcap -C 100 -W 10
# Прочитать сохранённый дамп
tcpdump -r capture.pcap -nn
</code></pre>
"Кейс:
<br />
Телефония трещит, но ping чистый. Захватил RTP в pcap, открыл в Wireshark — Telephony — RTP — Streams. Jitter скачет от 5 до 150ms. Норма для VoIP — до 30ms. Виновник — кто-то качал торрент. Включил QoS с DSCP EF — заикания ушли.<br />
<p>Wireshark делает с pcap-файлом то, что tcpdump не покажет. Установи Wireshark и используй его для анализа, а tcpdump — для захвата на сервере. Под Windows есть встроенный pktmon — о нём ниже в Windows-разделе.</p>
<h2>11. ethtool — физика сети</h2>
<p>Когда сервер теряет пакеты, а ip route и iptables в порядке — спускайся на L1. ethtool покажет реальную скорость, duplex и ошибки на железе.</p>
<pre><code class="language-bash">
# Что говорит интерфейс
sudo ethtool eth0
# Speed: 1000Mb/s
# Duplex: Full
# Auto-negotiation: on
# Link detected: yes
# Статистика - ошибки CRC, фреймов, коллизии
sudo ethtool -S eth0 | grep -i error
# Драйвер и версия
sudo ethtool -i eth0
# Принудительная скорость и duplex - старое железо
sudo ethtool -s eth0 speed 1000 duplex full autoneg off
# Offload-функции
sudo ethtool -k eth0
</code></pre>
"Кейс:
<br />
Сервер в стойке начал терять 5-10% пакетов. ethtool: Speed 100Mb/s Half. Должно быть 1000Mb/s Full. На свитче порт настроен на 100/half. Поменял на gigabit/full с обеих сторон — всё чистое.<br />
<pre><code class="language-bash">
sudo ethtool -S eth0 | grep -i error
# rx_crc_errors: 15234
# rx_frame_errors: 8976
# tx_carrier_errors: 2341
# collisions: 45678
</code></pre>
<p>Коллизии в 2026 году — это всегда half-duplex с обеих сторон или плохой кабель. Full-duplex коллизий не имеет в принципе.</p>
<h2>12. nethogs и iftop — кто жрёт канал</h2>
<p>«Интернет тормозит» в офисе — значит кто-то качает. nethogs покажет по процессам, iftop — по соединениям.</p>
<pre><code class="language-bash">
# Установка
sudo apt install nethogs iftop
# nethogs - процесс и его трафик
sudo nethogs eth0
# iftop - соединения и скорость
sudo iftop -i eth0 -nNP
# Без -n будет резолвить - в забитой сети тормозит
</code></pre>
"Кейс:
<br />
Сотрудники жалуются на лаги Zoom. На шлюзе sudo nethogs eth0 — процесс transmission жрёт 15 MB/s upload из 20. Сотрудник скачивал торрент со станции. Настроил QoS с приоритетом для DSCP-маркированного трафика — звонки нормально, торрент в фоне.<br />
<pre><code class="language-bash">
# Базовый QoS через tc - ограничиваем torrent-порты
sudo tc qdisc add dev eth0 root handle 1: htb default 10
sudo tc class add dev eth0 parent 1: classid 1:10 htb rate 15mbit ceil 20mbit
sudo tc class add dev eth0 parent 1: classid 1:20 htb rate 2mbit ceil 5mbit
sudo tc filter add dev eth0 protocol ip parent 1:0 prio 1 \
u32 match ip dport 6881 0xffff flowid 1:20
</code></pre>
<h2>13. arp и ip neigh — дубликаты IP</h2>
<p>«С одной машины пингуется, с другой нет» — почти всегда конфликт MAC-адресов или ARP-spoofing.</p>
<p>Что происходит при ARP-конфликте — кто первый ответил, того и тапочки:</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 60, 'rankSpacing': 60}
}}%%
flowchart TD
A["Клиент A хочет 192.168.1.100"] --> B["ARP request: who has 192.168.1.100"]
B --> C["Сервер MAC 00:11:22"]
B --> D["Самозванец MAC AA:BB:CC"]
C --> E["ARP reply от 00:11:22"]
D --> F["ARP reply от AA:BB:CC"]
E --> G["Кеш клиента: запись от того кто первый"]
F --> G
G --> H["Трафик уходит не туда"]
style A fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style C fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style D fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style H fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
</pre>
<pre><code class="language-bash">
# Linux - современно
ip neigh show
# Linux - старая школа
arp -n
# Очистить кеш
sudo ip neigh flush all
sudo ip neigh flush dev eth0
# Удалить конкретную запись
sudo ip neigh del 192.168.1.50 dev eth0
# Статическая запись
sudo ip neigh add 192.168.1.50 lladdr 00:11:22:33:44:55 dev eth0 nud permanent
</code></pre>
<pre><code class="language-powershell">
# Windows
arp -a
arp -d 192.168.1.50
netsh interface ip delete arpcache
# PowerShell
Get-NetNeighbor
Remove-NetNeighbor -IPAddress 192.168.1.50
</code></pre>
"Кейс:
<br />
Пользователь не может попасть на сервер 192.168.1.100, у других работает. На его машине arp -a показал MAC aa-bb-cc, на работающей — 00-11-22. Два устройства держат один IP. Кто-то поднял виртуалку с тем же адресом. Снёс виртуалку, очистил ARP-кеши — вылечилось.<br />
<h2>14. route и ip route — таблица маршрутизации</h2>
<p>Если ping до шлюза работает, а в интернет нет — проверь маршруты. Особенно когда два канала.</p>
<pre><code class="language-bash">
# Linux
ip route show
# Какой маршрут выберет ядро для конкретного IP
ip route get 8.8.8.8
# Добавить
sudo ip route add 10.0.0.0/24 via 192.168.1.1
# Заменить default
sudo ip route replace default via 192.168.1.1
# С метрикой - меньше = приоритетнее
sudo ip route add default via 192.168.2.1 metric 200
</code></pre>
<pre><code class="language-powershell">
# Windows
route print
Get-NetRoute
# Добавить постоянный
route -p ADD 10.0.0.0 MASK 255.255.255.0 192.168.1.1
# PowerShell
New-NetRoute -DestinationPrefix "10.0.0.0/24" -NextHop "192.168.1.1" -InterfaceAlias "Ethernet"
</code></pre>
"Кейс:
<br />
Два канала — быстрый основной и резервный 4G. После настройки failover весь трафик пошёл через 4G. ip route показал у резервного метрику 100, у основного 200. Меньше метрика = выше приоритет. Поменял местами — всё пошло через основной, 4G ждёт failover.<br />
<p>Постоянные маршруты в Ubuntu/Debian — в /etc/netplan/, в RHEL — в /etc/sysconfig/network-scripts/route-eth0.</p>
<h2>15. Health check Linux — всё разом</h2>
<p>Скрипт для быстрой проверки всего за раз. Сохрани в /usr/local/bin/netcheck.sh.</p>
<pre><code class="language-bash">
#!/bin/bash
echo "=== Network Health Check ==="
echo
echo "[1] Interfaces:"
ip -br addr show | grep -v "^lo"
echo
echo "[2] Default Gateway:"
ip route | grep default
echo
echo "[3] DNS:"
grep nameserver /etc/resolv.conf
echo
echo "[4] Ping 8.8.8.8:"
ping -c 3 -W 2 8.8.8.8 | tail -3
echo
echo "[5] DNS resolve:"
dig google.com +short +time=2 +tries=1
echo
echo "[6] Connections:"
ss -s
echo
echo "[7] Listening ports:"
ss -tuln | grep LISTEN
echo
echo "[8] Errors on interfaces:"
ip -s link | grep -B1 errors | grep -A1 "^[0-9]"
echo
echo "=== Done ==="
</code></pre>
<p>Запусти — получи срез по сети за 5 секунд. Удобно класть в SSH banner или в <a class="wpil_keyword_link" title="Скрипты" href="https://it-apteka.com/category/scripts/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2445">скрипт</a> первичного триажа.</p>
<h2>16. Windows: PowerShell вместо классики</h2>
<p>В <a href="https://it-apteka.com/aktivacija-windows-11-i-office-cherez-powershell-komandy-skripty-diagnostika/" title="Активация Windows 11 и Office через PowerShell: команды, скрипты, диагностика" target="_blank" rel="noopener" data-wpil-monitor-id="2459">Windows старые команды</a> живут с NT 4.0 — и работают. Но PowerShell-командлеты дают объекты вместо текста, который надо парсить регуляркой. Для скриптов и автоматизации это разница в небо.</p>
<table>
<tbody>
<tr>
<th>Старая команда</th>
<th>PowerShell аналог</th>
<th>Что лучше</th>
</tr>
<tr>
<td>ipconfig /all</td>
<td>Get-NetIPConfiguration</td>
<td>Объекты, фильтрация по полям</td>
</tr>
<tr>
<td>ping</td>
<td>Test-Connection</td>
<td>Параллельные пинги, результат в массив</td>
</tr>
<tr>
<td>ping host порт</td>
<td>Test-NetConnection</td>
<td>Реальная проверка TCP-порта, не ICMP</td>
</tr>
<tr>
<td>nslookup</td>
<td>Resolve-DnsName</td>
<td>Все типы записей, DNSSEC, кеш</td>
</tr>
<tr>
<td>netstat -ano</td>
<td>Get-NetTCPConnection</td>
<td>Связь с процессом без findstr</td>
</tr>
<tr>
<td>route print</td>
<td>Get-NetRoute</td>
<td>Фильтрация, метрики, IPv6 раздельно</td>
</tr>
<tr>
<td>arp -a</td>
<td>Get-NetNeighbor</td>
<td>Состояние записи (Reachable/Stale)</td>
</tr>
<tr>
<td>tracert</td>
<td>Test-NetConnection -Traceroute</td>
<td>Объектный вывод</td>
</tr>
</tbody>
</table>
<h3>Test-NetConnection — швейцарский нож Windows</h3>
<p>Запомни одну команду — tnc. Заменяет ping, telnet, tracert и часть nmap.</p>
<pre><code class="language-powershell">
# Простой пинг
tnc google.com
# Проверить TCP-порт - то что telnet делал
tnc smtp.gmail.com -Port 587
tnc 192.168.1.50 -Port 3306
# Подробный отчёт - аналог curl -v на L4
tnc google.com -Port 443 -InformationLevel Detailed
# Traceroute
tnc google.com -TraceRoute
# Проверить порт через конкретный интерфейс
tnc 192.168.1.1 -Port 443 -SourceAddress 192.168.1.100
</code></pre>
<p>В отличие от telnet, tnc возвращает True/False — удобно в скриптах.</p>
<pre><code class="language-powershell">
# Проверка пачки портов одной строкой
22,80,443,3306,5432 | ForEach-Object {
$r = tnc 192.168.1.50 -Port $_ -WarningAction SilentlyContinue
[PSCustomObject]@{
Port = $_
Open = $r.TcpTestSucceeded
}
} | Format-Table -AutoSize
</code></pre>
<h3>Get-NetTCPConnection — кто слушает и куда ходит</h3>
<p>netstat в Windows жив, но Get-NetTCPConnection даёт объекты с PID сразу, без двойного поиска через tasklist.</p>
<pre><code class="language-powershell">
# Все слушающие порты
Get-NetTCPConnection -State Listen | Format-Table LocalAddress, LocalPort, OwningProcess
# Кто слушает 443 - с именем процесса
Get-NetTCPConnection -LocalPort 443 -State Listen |
Select-Object LocalAddress, LocalPort,
@{n='Process';e={(Get-Process -Id $_.OwningProcess).Name}}
# Все ESTABLISHED соединения с группировкой по процессу
Get-NetTCPConnection -State Established |
Group-Object OwningProcess |
Select-Object Count,
@{n='Process';e={(Get-Process -Id $_.Name -ErrorAction SilentlyContinue).Name}} |
Sort-Object Count -Descending |
Format-Table -AutoSize
# Сводка по состояниям TCP - аналог ss -s
Get-NetTCPConnection | Group-Object State | Format-Table Name, Count
</code></pre>
"Кейс:
<br />
IIS не стартует — ошибка "port 80 in use". Get-NetTCPConnection -LocalPort 80 показал OwningProcess 4 — это System. В системе поднят сервис World Wide Web Publishing, который и держит порт. Stop-Service W3SVC, IIS Express запустился.<br />
<h3>Захват трафика без Wireshark — pktmon</h3>
<p>С Windows 10 1809 в системе есть встроенный pktmon — легковесный аналог tcpdump. Wireshark не нужен на сервере, для анализа дамп переносишь на рабочую станцию.</p>
<pre><code class="language-powershell">
# Базовый захват всего на всех интерфейсах
pktmon start --capture
# ждём немного
pktmon stop
# С фильтром - только трафик на порт 443
pktmon filter add -p 443
pktmon start --capture --pkt-size 0
pktmon stop
pktmon filter remove
# Конвертация в pcapng для Wireshark
pktmon pcapng PktMon.etl -o capture.pcapng
# Только захват по IP
pktmon filter add MyFilter -i 192.168.1.50
pktmon start --capture
</code></pre>
<p>Альтернатива — tshark из пакета Wireshark CLI или netsh trace для совсем старых систем.</p>
<pre><code class="language-powershell">
# netsh trace - работает на Windows 7/Server 2008 R2 и выше
netsh trace start capture=yes tracefile=C:\trace.etl
# воспроизводим проблему
netsh trace stop
</code></pre>
<h3>Resolve-DnsName — dig для Windows</h3>
<p><a href="https://it-apteka.com/nslookup-shpargalka-it-inzhenera-s-primerami-dlja-windows-i-linux/" title="NSLOOKUP: шпаргалка IT-инженера с примерами для Windows и Linux" target="_blank" rel="noopener" data-wpil-monitor-id="2455">nslookup в Windows</a> жив, но Resolve-DnsName умеет больше: DNSSEC, фильтрация по типу, работа с кешем.</p>
<pre><code class="language-powershell">
# A-запись
Resolve-DnsName google.com
# Конкретный тип
Resolve-DnsName google.com -Type MX
Resolve-DnsName google.com -Type TXT
Resolve-DnsName google.com -Type NS
# Через конкретный DNS
Resolve-DnsName google.com -Server 8.8.8.8
# Без кеша - принудительный запрос
Resolve-DnsName google.com -DnsOnly
# Из кеша - что Windows запомнил
Get-DnsClientCache
# Очистить кеш
Clear-DnsClientCache
# Проверить настроенные DNS на интерфейсах
Get-DnsClientServerAddress -AddressFamily IPv4
# Поменять DNS на интерфейсе
Set-DnsClientServerAddress -InterfaceAlias "Ethernet" -ServerAddresses ("8.8.8.8","1.1.1.1")
</code></pre>
<h3>Сетевая статистика — что в Resource Monitor нет</h3>
<p>Get-NetAdapterStatistics показывает счётчики на уровне интерфейса — ошибки, дропы, пакеты. <a href="https://it-apteka.com/punto-switcher-i-analogi-dlja-windows-macos-i-linux/" title="Punto Switcher и аналоги для Windows, macOS и Linux" target="_blank" rel="noopener" data-wpil-monitor-id="2456">Аналог ip -s link в Linux</a>.</p>
<pre><code class="language-powershell">
# Статистика всех интерфейсов
Get-NetAdapterStatistics | Format-Table Name, ReceivedBytes, SentBytes, ReceivedDiscardedPackets, OutboundDiscardedPackets
# Только проблемные - где есть ошибки
Get-NetAdapterStatistics |
Where-Object {$_.ReceivedDiscardedPackets -gt 0 -or $_.OutboundDiscardedPackets -gt 0}
# Скорость и дуплекс - аналог ethtool
Get-NetAdapter | Format-Table Name, LinkSpeed, MediaConnectionState, FullDuplex
# Расширенные настройки адаптера
Get-NetAdapterAdvancedProperty -Name "Ethernet"
# Сменить скорость и duplex
Set-NetAdapterAdvancedProperty -Name "Ethernet" -DisplayName "Speed & Duplex" -DisplayValue "1.0 Gbps Full Duplex"
</code></pre>
<h3>Файрвол — быстрая диагностика</h3>
<p>Половина <a href="https://it-apteka.com/diagnostika-problem-s-diskom-v-windows-shpargalka-it-inzhenera/" title="Диагностика проблем с диском в Windows: шпаргалка IT-инженера" target="_blank" rel="noopener" data-wpil-monitor-id="2457">проблем</a> «не работает на Windows» — это Windows Defender Firewall. Проверка занимает минуту.</p>
<pre><code class="language-powershell">
# Профили файрвола - какие активны
Get-NetFirewallProfile | Format-Table Name, Enabled
# Найти правило, блокирующее порт
Get-NetFirewallRule -Direction Inbound -Action Block |
Where-Object Enabled -eq True |
Get-NetFirewallPortFilter |
Where-Object LocalPort -eq 80
# Открыть порт 443 во внешний мир
New-NetFirewallRule -DisplayName "Allow HTTPS" -Direction Inbound -Protocol TCP -LocalPort 443 -Action Allow
# Логирование заблокированных пакетов - диагностика
Set-NetFirewallProfile -Profile Domain,Public,Private -LogBlocked True -LogFileName "%systemroot%\system32\LogFiles\Firewall\pfirewall.log"
# Просмотр лога
Get-Content C:\Windows\System32\LogFiles\Firewall\pfirewall.log -Tail 50
</code></pre>
<h3>Health check для Windows</h3>
<pre><code class="language-powershell">
# Сохрани как netcheck.ps1
# Запуск: powershell -ExecutionPolicy Bypass -File netcheck.ps1
Write-Host "=== Windows Network Health Check ===" -ForegroundColor Cyan
Write-Host ""
Write-Host "[1] Active Adapters:" -ForegroundColor Yellow
Get-NetAdapter | Where-Object Status -eq "Up" |
Format-Table Name, InterfaceDescription, LinkSpeed, MediaConnectionState
Write-Host "[2] IP Configuration:" -ForegroundColor Yellow
Get-NetIPConfiguration | Where-Object IPv4Address |
Format-Table InterfaceAlias,
@{n='IPv4';e={$_.IPv4Address.IPAddress}},
@{n='Gateway';e={$_.IPv4DefaultGateway.NextHop}},
@{n='DNS';e={$_.DNSServer.ServerAddresses -join ', '}}
Write-Host "[3] Default Route:" -ForegroundColor Yellow
Get-NetRoute -DestinationPrefix "0.0.0.0/0" |
Format-Table NextHop, InterfaceAlias, RouteMetric, ifMetric
Write-Host "[4] Internet check:" -ForegroundColor Yellow
$ping = Test-Connection 8.8.8.8 -Count 4 -ErrorAction SilentlyContinue
if ($ping) {
$avg = ($ping | Measure-Object ResponseTime -Average).Average
Write-Host " 8.8.8.8 reachable, avg $([math]::Round($avg,1))ms" -ForegroundColor Green
} else {
Write-Host " 8.8.8.8 UNREACHABLE" -ForegroundColor Red
}
Write-Host "[5] DNS resolve test:" -ForegroundColor Yellow
try {
$dns = Resolve-DnsName google.com -Type A -ErrorAction Stop
Write-Host " google.com -> $($dns[0].IPAddress)" -ForegroundColor Green
} catch {
Write-Host " DNS FAILED: $_" -ForegroundColor Red
}
Write-Host "[6] HTTPS check:" -ForegroundColor Yellow
$https = tnc google.com -Port 443 -WarningAction SilentlyContinue
if ($https.TcpTestSucceeded) {
Write-Host " 443/tcp open" -ForegroundColor Green
} else {
Write-Host " 443/tcp BLOCKED" -ForegroundColor Red
}
Write-Host "[7] TCP connections by state:" -ForegroundColor Yellow
Get-NetTCPConnection | Group-Object State |
Format-Table Name, Count -AutoSize
Write-Host "[8] Listening ports:" -ForegroundColor Yellow
Get-NetTCPConnection -State Listen |
Select-Object LocalPort,
@{n='Process';e={(Get-Process -Id $_.OwningProcess -ErrorAction SilentlyContinue).Name}} -Unique |
Sort-Object LocalPort |
Format-Table -AutoSize
Write-Host "[9] Adapter errors:" -ForegroundColor Yellow
Get-NetAdapterStatistics |
Where-Object {$_.ReceivedDiscardedPackets -gt 0 -or $_.OutboundDiscardedPackets -gt 0} |
Format-Table Name, ReceivedDiscardedPackets, OutboundDiscardedPackets
Write-Host "[10] Firewall profiles:" -ForegroundColor Yellow
Get-NetFirewallProfile | Format-Table Name, Enabled, DefaultInboundAction
Write-Host "=== Done ===" -ForegroundColor Cyan
</code></pre>
"Кейс:
<br />
Половина клиентов перестала логиниться в домен. На DC запустил netcheck.<a class="wpil_keyword_link" title="PowerShell" href="https://it-apteka.com/tag/powershell/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2447">ps1</a>. На пункте 8 увидел: порт 88 (Kerberos) и 389 (LDAP) не в списке Listen. Проверил Get-Service NTDS — сервис стоит. Запустил, проверил Event Log на ошибки — вылез конфликт SPN. Лечится setspn, но сначала надо было найти где сломалось.<br />
<h2>17. Осложнения — типовые ошибки</h2>
<p>Краткий справочник по ошибкам и их причинам. Запоминается с первого раза.</p>
<table>
<tbody>
<tr>
<th>Ошибка</th>
<th>Что значит</th>
<th>Куда копать</th>
</tr>
<tr>
<td>Connection refused</td>
<td>Хост ответил, порт закрыт</td>
<td>Сервис не запущен или bind на localhost</td>
</tr>
<tr>
<td>Connection timeout</td>
<td>Пакеты не доходят</td>
<td>Файрвол, маршрут, хост лёг</td>
</tr>
<tr>
<td>No route to host</td>
<td>Нет маршрута в таблице</td>
<td>ip route, default gateway</td>
</tr>
<tr>
<td>Host unreachable</td>
<td>Хост в той же сети не отвечает на ARP</td>
<td>Хост лёг, не та подсеть, switch</td>
</tr>
<tr>
<td>Name or service not known</td>
<td>DNS не резолвит</td>
<td>/etc/resolv.conf, dig @8.8.8.8</td>
</tr>
<tr>
<td>SSL handshake failure</td>
<td>Не договорились о шифрах/версии</td>
<td>openssl s_client, nmap ssl-enum-ciphers</td>
</tr>
<tr>
<td>502 Bad Gateway</td>
<td>nginx не получил ответ от backend</td>
<td>ss на backend, логи приложения</td>
</tr>
<tr>
<td>504 Gateway Timeout</td>
<td>Backend ответил слишком долго</td>
<td>Backend перегружен, БД</td>
</tr>
</tbody>
</table>
"MTU
<br />
ping проходит, SSH работает, но SCP больших файлов виснет, страницы открываются наполовину. Это PMTU. Проверь MTU через ping -M do -s 1472. Если не проходит — уменьшай. На VPN-сервере добавь MSS clamping в iptables.<br />
<pre><code class="language-bash">
# MSS clamping для VPN
sudo iptables -t mangle -A FORWARD -p tcp --tcp-flags SYN,RST SYN \
-j TCPMSS --clamp-mss-to-pmtu
# Жёстко выставить MSS - 1360 безопасно для PPPoE/мобильных
sudo iptables -t mangle -A FORWARD -p tcp --tcp-flags SYN,RST SYN \
-j TCPMSS --set-mss 1360
</code></pre>
<p>Magic number: MSS = MTU — 40 для IPv4. MTU 1400 — значит MSS 1360.</p>
<p>Самая коварная ошибка — асимметричная маршрутизация. Файрвол клиента видит ответ с «не того» IP и дропает соединение:</p>
<pre class="mermaid">%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 60, 'rankSpacing': 60}
}}%%
flowchart TD
A["Клиент 192.168.1.10"] -->|SYN на 192.168.1.100| B["eth0: 192.168.1.100"]
B --> C["Сервер с двумя интерфейсами"]
C -->|default route через eth1| D["eth1: 10.0.0.100"]
D -->|SYN-ACK с src 10.0.0.100| E["Файрвол клиента"]
E -->|DROP - нет такого соединения| F["Соединение зависает"]
style A fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style B fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style D fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style F fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
</pre>
<p>Лечится policy-based routing — чтобы пакет уходил с того же интерфейса, на который пришёл:</p>
<pre><code class="language-bash">
# Создаём отдельную таблицу для управляющего интерфейса
echo "100 mgmt" | sudo tee -a /etc/iproute2/rt_tables
sudo ip route add 192.168.1.0/24 dev eth0 src 192.168.1.100 table mgmt
sudo ip route add default via 192.168.1.1 dev eth0 table mgmt
sudo ip rule add from 192.168.1.100 table mgmt
</code></pre>
<h2>18. Альтернативы — чем заменить классику</h2>
<p>Не все команды одинаково хороши в 2026 году. Вот что использовать вместо.</p>
<table>
<tbody>
<tr>
<th>Старое</th>
<th>Новое</th>
<th>Почему</th>
</tr>
<tr>
<td>ifconfig</td>
<td>ip addr</td>
<td>ifconfig deprecated, нет VLAN, медленнее</td>
</tr>
<tr>
<td>route</td>
<td>ip route</td>
<td>Не показывает policy routing, нет multipath</td>
</tr>
<tr>
<td>arp</td>
<td>ip neigh</td>
<td>Часть iproute2, единый CLI</td>
</tr>
<tr>
<td>netstat</td>
<td>ss</td>
<td>В разы быстрее на больших объёмах сокетов</td>
</tr>
<tr>
<td>traceroute</td>
<td>mtr</td>
<td>Снимает статистику, не одноразовый снимок</td>
</tr>
<tr>
<td>nslookup</td>
<td>dig</td>
<td>Подробнее, гибче, +trace</td>
</tr>
<tr>
<td>telnet</td>
<td>nc -zv</td>
<td>nc по умолчанию есть, telnet ставить надо</td>
</tr>
</tbody>
</table>
<p>В Windows старые команды никуда не делись и работают, но PowerShell-командлеты Get-NetTCPConnection, Test-NetConnection, Resolve-DnsName удобнее для скриптов.</p>
<h2>19. Профилактика — чтобы не звонили в 3 ночи</h2>
<p>Лучшая диагностика — та, которую делать не пришлось. Что настроить заранее:</p>
<ul>
<li><strong>Мониторинг линка</strong> — <a href="https://www.zabbix.com/" target="_blank" rel="noopener">Zabbix</a> или <a href="https://prometheus.io/" target="_blank" rel="noopener">Prometheus</a> с алертом на ifOperStatus и errors на интерфейсе. Заметишь деградацию до того как кабель отвалится.</li>
<li><strong>Внешний пинг до критичных хостов</strong> — <a href="https://oss.oetiker.ch/smokeping/" target="_blank" rel="noopener">smokeping</a> или <a href="https://github.com/louislam/uptime-kuma" target="_blank" rel="nofollow noopener">uptime-kuma</a> с графиками потерь и latency. Покажет где проблема — у тебя или у провайдера.</li>
<li><strong>Логи DNS-сервера</strong> — query log с ротацией. При DNS cache poisoning или массовых ошибках резолвинга найдёшь источник.</li>
<li><strong>Бэкап конфигов сети</strong> — оригиналы /etc/netplan, iptables-save в <a class="wpil_keyword_link" title="Git" href="https://it-apteka.com/tag/git/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2443">git</a> перед каждым изменением. Откат за 30 секунд.</li>
<li><strong>NTP на всех хостах</strong> — без синхронного времени логи не сопоставишь. Это не сетевая проблема, но без NTP диагностика становится в разы тяжелее.</li>
<li><strong>Документ «сетевая карта»</strong> — схема подсетей, VLAN, маршрутов в wiki. Через год сам себе скажешь спасибо.</li>
<li><strong>Скрипт netcheck в SSH banner</strong> — залогинился на <a href="https://it-apteka.com/dhcp-snooping-chto-jeto-takoe-i-kak-zashhitit-set-ot-rogue-dhcp-servera-2/" title="DHCP Snooping — что это такое и как защитить сеть от Rogue DHCP сервера" target="_blank" rel="noopener" data-wpil-monitor-id="2458">сервер — сразу видно состояние сети</a>. Экономит первые 30 секунд на каждом инциденте.</li>
</ul>
<h2>20. FAQ — что спрашивают чаще всего</h2>
<h3>Почему ping проходит, а сайт не открывается?</h3>
<p>ping проверяет ICMP до хоста, а сайт — это TCP на порт 443 плюс DNS плюс SSL плюс HTTP. Проверь по цепочке: dig для DNS, nc -zv host 443 для порта, curl -v для HTTP/SSL. Чаще всего виноват DNS или SSL handshake.</p>
<h3>Как проверить, что troubleshooting сети командой работает правильно?</h3>
<p>Прогони команду в две стороны. Если nc -zv server.com 443 говорит open — убедись что это тот сервер. Через —resolve в curl можно жёстко привязаться к IP, минуя DNS. Если результаты с двух разных машин в одной сети расходятся — проблема локальная, не глобальная.</p>
<h3>Что делать если порт открыт, но приложение не отвечает?</h3>
<p>Это L7-проблема, не сетевая. Логи приложения, нагрузка на CPU/память, БД. Сделай curl -v — увидишь, что отдаёт сервер. Если 502 — backend лёг. Если timeout после соединения — приложение зависло, не отвечает на запросы. Перезапуск сервиса поможет, но причину ищи в логах.</p>
<h3>Чем tcpdump отличается от Wireshark?</h3>
<p>tcpdump захватывает пакеты в консоли, Wireshark — в GUI. На сервере без GUI ставишь tcpdump, дамп сохраняешь в pcap, открываешь в Wireshark на ноуте. Wireshark лучше анализирует, tcpdump лучше захватывает в продакшне без оверхеда. На Windows есть встроенный pktmon — не нужно ставить ничего.</p>
<h3>Как найти, какой процесс жрёт сеть в Windows?</h3>
<p>Открой Resource Monitor (resmon.exe), вкладка <a class="wpil_keyword_link" title="Сети" href="https://it-apteka.com/category/networks/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2444">Network</a>. Там видно процессы и их трафик. Альтернативно — Get-NetTCPConnection в PowerShell с привязкой к процессу через OwningProcess. На Linux эту задачу решает nethogs одной командой.</p>
<h3>Почему mtr показывает потери на промежуточном хопе, но конечный работает?</h3>
<p>Это нормально. Промежуточные роутеры рейт-лимитят ICMP-ответы, чтобы не нагружать CPU. Если потери только на хопе N, а на N+1 их нет — это ложный сигнал. Реальные потери — те, что есть на конечном хосте и одинаковые на всех хопах после проблемного.</p>
<h3>Чем nc отличается от nmap для проверки портов?</h3>
<p>nc проверяет один порт за раз и подтверждает, что TCP-соединение установилось. nmap сканирует диапазон, определяет версии сервисов, ОС, может запускать NSE-скрипты на уязвимости. Для быстрой проверки «открыт ли» — nc. Для аудита сети — nmap.</p>
<h3>Можно ли все команды troubleshooting сети использовать без root?</h3>
<p>Большинство read-only команд работают без прав: ping, traceroute, dig, ss без -p, curl, nslookup. Команды для изменения конфигурации (ip addr add, ip route add), для захвата сырых пакетов (tcpdump) и для просмотра процессов в ss/netstat требуют root или sudo. nmap для SYN-сканов тоже хочет root.</p>
<h2>21. Прогноз — что у тебя теперь есть</h2>
<p>Шпаргалка собрана. У тебя теперь алгоритм диагностики по уровням OSI, рабочие команды под Linux и Windows, скрипты health check на <a class="wpil_keyword_link" title="Bash" href="https://it-apteka.com/tag/bash/" target="_blank" rel="noopener" data-wpil-keyword-link="linked" data-wpil-monitor-id="2449">bash</a> и PowerShell, разбор pktmon для Windows без Wireshark, и таблица типовых ошибок. Этого хватает на 90% сетевых инцидентов в продакшне — от «сайт не открывается» до «VoIP заикается».</p>
<p>Главное — не зубри команды, пойми порядок. Симптом — уровень — команда. Линк проверил, IP проверил, шлюз проверил, DNS проверил, порт проверил, приложение проверил. На каком-то шаге найдёшь. А когда не найдёшь — доставай tcpdump или pktmon и смотри что реально летит по проводу.</p>
<p>Если что-то из шпаргалки не сработало или нашёл косяк — пиши в комментарии, разберёмся.</p>
Быстрый ответ
Шпаргалка команд troubleshooting сети по симптому. Сайт не открывается — dig + curl. Тормозит — mtr. Порт закрыт — ss + nc. Канал забит — nethogs. Пакеты теряются — tcpdump. Иди по уровням OSI снизу вверх: link, IP, route,
DNS, порт, приложение.
1. Диагноз — что сломалось и где искать
Поднял сервер. Сайт не открывается. ping проходит, curl зависает. Знакомо? Это troubleshooting сети — и решается он не одной командой, а связкой по симптому.
В этой шпаргалке — команды, которые покрывают 90% сетевых инцидентов. Не теория, а рабочий справочник: симптом — команда — что увидишь — что делать дальше. Время на освоение — 15 минут чтения, годы экономии нервов.
Что внутри:
- алгоритм диагностики по уровням OSI
- команды для Linux и Windows бок о бок
- усиленный блок про PowerShell и pktmon для Windows
- боевые кейсы из продакшна с разбором
- таблица «симптом — команда» под закладку
- чит-коды для экстренных ситуаций
- FAQ по типовым ошибкам новичков
Дерево решений для самой частой жалобы «сайт не открывается» — вот так выглядит триаж:
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart TD
A["Сайт не открывается"] --> B{"ping шлюза"}
B -->|нет| C["Проверь IP, кабель, ethtool"]
B -->|да| D{"ping 8.8.8.8"}
D -->|нет| E["Проверь маршруты: ip route"]
D -->|да| F{"dig site.com"}
F -->|не резолвит| G["Проверь DNS: resolv.conf"]
F -->|ok| H{"nc -zv site.com 443"}
H -->|закрыт| I["Файрвол или сервис лёг"]
H -->|открыт| J{"curl -v site.com"}
J -->|SSL fail| K["Проверь сертификат, шифры"]
J -->|HTTP 502| L["Backend, логи приложения"]
J -->|медленно| M["mtr, iftop, QoS"]
style A fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style C fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style E fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style G fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style I fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style K fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style L fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style M fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
2. Алгоритм — почему важен порядок
Главная ошибка новичков — сразу лезть в tcpdump, когда не работает ping до шлюза. Так не надо. Сеть диагностируется снизу вверх по модели OSI.
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 50}
}}%%
flowchart TD
A["L1-L2: Линк, кабель, MAC"] --> B["L3: IP-адрес, маска, шлюз"]
B --> C["L3: Маршрутизация"]
C --> D["L7: DNS"]
D --> E["L4: Порт, TCP-handshake"]
E --> F["L7: Приложение, HTTP, SSL"]
style A fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style B fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style C fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style D fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style E fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style F fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
Причины почему алгоритм работает:
- L1 ломается чаще всего — кабель, порт, duplex. Если линка нет — дальше идти бесполезно.
- L3 без шлюза = ничего не работает — проверь IP и default route первым делом, до DNS.
- DNS убивает 50% запросов — «сайт не открывается» в большинстве случаев именно про него.
- Порт может быть закрыт по сотне причин — сервис лёг, файрвол, bind на localhost. Это не L3.
- Приложение — последнее что проверяешь — 502 это часто не nginx, а backend.
- Пропустил уровень — копаешь не там — классика: час крутишь iptables, а кабель полусидит.
Карта команд по уровням — какая команда на каком этаже стека работает:
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 50, 'rankSpacing': 40}
}}%%
flowchart LR
L1["L1 Физика"] --> T1["ethtool, ip link"]
L2["L2 Канальный"] --> T2["ip neigh, arp, tcpdump"]
L3["L3 Сетевой"] --> T3["ping, mtr, ip route, traceroute"]
L4["L4 Транспорт"] --> T4["nc, nmap, ss, Test-NetConnection"]
L7["L7 Приложение"] --> T7["dig, curl, wget, openssl"]
style L1 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L2 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L3 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L4 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style L7 fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style T1 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T2 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T3 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T4 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style T7 fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
3. Шпаргалка — команда по симптому
Главная таблица. Закладывай в избранное.
| Симптом |
Уровень |
Команда Linux |
Команда Windows |
| Линка нет |
L1 |
ip link, ethtool |
Get-NetAdapter |
| Нет IP-адреса |
L3 |
ip addr |
ipconfig /all |
| Шлюз не пингуется |
L3 |
ping, ip route |
ping, route print |
| Тормозит, потери пакетов |
L3 |
mtr |
pathping, tracert |
| Странный путь пакета |
L3 |
traceroute, ip route |
tracert |
| DNS не резолвит |
L7 |
dig, nslookup |
nslookup, Resolve-DnsName |
| Порт закрыт |
L4 |
nc -zv, nmap |
Test-NetConnection |
| Кто слушает порт |
L4 |
ss -tulnp |
Get-NetTCPConnection |
| Кто жрёт канал |
L7 |
nethogs, iftop |
Resource Monitor |
| Не понимаю что в кабеле |
все |
tcpdump |
pktmon, Wireshark |
| HTTP отдаёт ошибку |
L7 |
curl -v |
Invoke-WebRequest |
| Дубль IP в сети |
L2 |
ip neigh, arp -n |
arp -a, Get-NetNeighbor |
Дальше — разбор каждой команды с боевыми примерами.
4. ping и mtr — живой ли хост и где теряются пакеты
ping — дедушка. Проверяет ICMP Echo. Если не отвечает — либо хост мёртв, либо ICMP режется файрволом. Не делай вывод «сервер лёг» по одному ping.
# Linux - 10 пакетов и стоп
ping -c 10 8.8.8.8
# Don't Fragment - проверка MTU
ping -M do -s 1472 8.8.8.8
# Тихий режим - только статистика
ping -c 100 -q 8.8.8.8
# Windows - 10 пакетов
ping -n 10 8.8.8.8
# DF-флаг и размер - проверка MTU
ping -f -l 1472 8.8.8.8
# С меткой времени для логов
ping -t 8.8.8.8 | ForEach-Object {"{0} - {1}" -f (Get-Date),$_}
mtr намного полезнее в продакшне. Это traceroute, который не делает один снимок, а долбит маршрут постоянно и показывает потери на каждом хопе.
# Установка
sudo apt install mtr
# Отчёт по 100 пакетам
mtr -r -c 100 google.com
# Без DNS, с AS-номерами
mtr -rn --aslookup -c 1000 google.com
# TCP вместо ICMP - если ICMP режут
mtr --tcp -P 443 google.com
Кейс: 15% потерь у провайдера
Клиент из Владивостока жалуется на лаги до сервера в Москве. Запустил mtr -r -c 100. На 4-м хопе backbone провайдера 15% потерь. Скрин mtr в тикет провайдеру — починили перегруженный линк за день.
sudo mtr -r -c 100 -n server-moscow.local
# HOST Loss% Snt Last Avg Best Wrst StDev
# 1. 192.168.1.1 0.0% 100 1.2 1.3 1.0 2.1 0.2
# 2. 10.0.0.1 0.0% 100 3.4 3.5 3.0 5.2 0.4
# 3. provider-gw.local 0.0% 100 12.3 12.5 11.8 18.3 1.2
# 4. provider-backbone.local 15.0% 100 45.6 46.2 44.1 89.3 12.5
# 5. moscow-gw.local 2.0% 100 78.3 78.9 77.1 92.1 3.2
Смотри на StDev. Если разброс задержки большой — проблема в jitter, а не в потерях. Для VoIP это смерть, для HTTP терпимо.
5. ip и ipconfig — конфигурация интерфейсов
Без правильного IP, маски и шлюза не работает ничего. Проверка занимает 5 секунд.
# Linux - современный ip из iproute2
ip addr show
ip a # короткая форма
ip -br addr # таблицей, очень компактно
# Маршруты
ip route show
ip route get 8.8.8.8 # покажет какой маршрут выберет ядро
# Соседи (ARP)
ip neigh show
# Поднять/опустить интерфейс
sudo ip link set eth0 up
sudo ip link set eth0 down
# Добавить IP
sudo ip addr add 192.168.1.50/24 dev eth0
# Windows - PowerShell
Get-NetIPAddress
Get-NetIPConfiguration
Get-NetAdapter
# Старый ipconfig тоже жив
ipconfig /all
ipconfig /release
ipconfig /renew
ipconfig /flushdns
Кейс: VLAN не работает
После
настройки VLAN интернет пропал. ip addr показывает eth0.10 в state DOWN. Забыл поднять интерфейс после создания. Классика, лечится одной командой.
ip link show eth0.10
# eth0.10@eth0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN
sudo ip link set eth0.10 up
ip link show eth0.10
# eth0.10@eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500
Запомни: после создания любого интерфейса — VLAN, bridge, bond — всегда делай ip link set up. Это не подразумевается по умолчанию.
6. dig и nslookup — DNS-детективы
Половина обращений в саппорт — это DNS. «Сайт не открывается» в 4 случаях из 10 = резолвер не работает или отдаёт старую запись.
dig в Linux мощнее nslookup. В Windows nslookup тоже неплох, но Resolve-DnsName в PowerShell удобнее.
# Самое полезное - короткий ответ
dig google.com +short
# Конкретный DNS
dig @8.8.8.8 google.com
# MX для почты, TXT для SPF/DKIM, NS для делегирования
dig MX gmail.com +short
dig TXT google.com +short
dig NS cloudflare.com +short
# Reverse - по IP найти имя
dig -x 8.8.8.8 +short
# Trace - путь от корневых серверов
dig +trace google.com
# Конкретный resolver и таймаут
dig @1.1.1.1 +time=2 +tries=1 example.com
# Windows
Resolve-DnsName google.com
Resolve-DnsName google.com -Type MX
Resolve-DnsName google.com -Server 8.8.8.8
# nslookup интерактивный
nslookup
> server 8.8.8.8
> set type=MX
> gmail.com
> exit
Правило DNS-миграций
За день до смены A-записи уменьши TTL до 300 секунд. Поменял запись — подождал час — вернул TTL обратно. Иначе пользователи будут резолвить старый IP сутки.
Капля никотина убивает лошадь. Одна A-запись с TTL 86400 без предупреждения — весь отдел саппорта.
7. ss и netstat — кто слушает и куда ходит
netstat жив, но ss быстрее и информативнее. На современном Linux используй ss. netstat в Windows никуда не делся.
# Все слушающие TCP-порты с процессами
sudo ss -tulnp
# Только LISTEN
ss -tln
# Кто слушает 443
sudo ss -tlnp | grep :443
# Все ESTABLISHED соединения
ss -tn state established
# Считаем по состояниям - очень полезно
ss -tan | awk '{print $1}' | sort | uniq -c | sort -rn
# Сводка
ss -s
# Соединения к конкретному IP
ss -tn dst 8.8.8.8
# Windows - кто слушает порт 80
Get-NetTCPConnection -LocalPort 80 -State Listen
Get-Process -Id (Get-NetTCPConnection -LocalPort 80).OwningProcess
# Или по-старому
netstat -ano | findstr :80
tasklist | findstr "PID"
Кейс: 1024 соединения в TIME-WAIT
Веб-сервер начал отваливаться. ss показал 1024 сокета в TIME-WAIT. Приложение не закрывало keep-alive нормально. Подкрутил sysctl — сервер стал держать в 3 раза больше соединений.
sudo sysctl -w net.ipv4.tcp_fin_timeout=30
sudo sysctl -w net.ipv4.tcp_tw_reuse=1
echo "net.ipv4.tcp_fin_timeout=30" | sudo tee -a /etc/sysctl.conf
echo "net.ipv4.tcp_tw_reuse=1" | sudo tee -a /etc/sysctl.conf
8. nc и nmap — открыт ли порт
Самый частый вопрос troubleshooting сети: «А порт-то открыт?». nc даёт ответ за секунду, nmap — за минуту с деталями.
Что происходит на проводе при проверке порта — классический three-way handshake:
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#f8fafc',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'noteBkgColor': '#fefce8',
'noteTextColor': '#713f12',
'noteBorderColor': '#fbbf24',
'actorBkg': '#f8fafc',
'actorBorder': '#94a3b8',
'actorTextColor': '#1e293b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'sequence': {
'mirrorActors': false,
'messageAlign': 'center',
'actorMargin': 120,
'width': 160,
'noteMargin': 12
}
}}%%
sequenceDiagram
participant C as Клиент
participant S as Сервер
Note over C,S: nc -zv server 443
C->>S: SYN
S->>C: SYN-ACK
C->>S: ACK
Note over C,S: Соединение установлено - порт открыт
C->>S: FIN
S->>C: FIN-ACK
# nc - проверка одного порта
nc -zv server.com 443
# Диапазон портов
nc -zv 192.168.1.100 20-25
# UDP
nc -zvu dns.server 53
# Без nc - встроенный bash
timeout 2 bash -c '</dev/tcp/server.com/443' && echo "open" || echo "closed"
# nmap - полное сканирование
nmap -F 192.168.1.100 # топ-100 портов
nmap -p- 192.168.1.100 # все 65535
nmap -p 22,80,443 192.168.1.0/24 # конкретные порты на подсети
# Версии сервисов и ОС
sudo nmap -sV -O 192.168.1.100
# Ping scan - найти живых
nmap -sn 192.168.1.0/24
# Windows - Test-NetConnection
Test-NetConnection server.com -Port 443
Test-NetConnection -ComputerName server.com -Port 443 -InformationLevel Detailed
# Сокращение
tnc server.com -Port 443
Кейс: MySQL слушает только localhost
Приложение не коннектится к БД. nc -zv 192.168.1.50 3306 — Connection refused. На сервере БД ss -tln показал bind на 127.0.0.1. Поправил bind-address в my.cnf — заработало.
# На сервере БД
sudo ss -tln | grep 3306
# tcp LISTEN 0 151 127.0.0.1:3306 0.0.0.0:*
# Правим /etc/mysql/mysql.conf.d/mysqld.cnf
# bind-address = 0.0.0.0
sudo systemctl restart mysql
sudo ss -tln | grep 3306
# tcp LISTEN 0 151 0.0.0.0:3306 0.0.0.0:*
Если порт открыт локально, но недоступен снаружи — проверь iptables/firewalld и security group у облачного провайдера.
9. curl — HTTP-снайпер
curl — не только «скачать файл». Это инструмент №1 для диагностики HTTP/HTTPS. Покажет где тормозит TLS, какие заголовки отдаёт сервер, как идут редиректы.
Что измеряют тайминги curl — вот вся цепочка от DNS до получения тела ответа:
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#f8fafc',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'noteBkgColor': '#fefce8',
'noteTextColor': '#713f12',
'noteBorderColor': '#fbbf24',
'actorBkg': '#f8fafc',
'actorBorder': '#94a3b8',
'actorTextColor': '#1e293b',
'fontSize': '15px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'sequence': {
'mirrorActors': false,
'messageAlign': 'center',
'actorMargin': 100,
'width': 140
}
}}%%
sequenceDiagram
participant C as curl
participant D as DNS
participant S as Сервер
C->>D: A example.com
D->>C: 1.2.3.4
Note over C: time_namelookup
C->>S: TCP SYN
S->>C: TCP SYN-ACK
C->>S: TCP ACK
Note over C: time_connect
C->>S: TLS ClientHello
S->>C: TLS ServerHello + Cert
C->>S: TLS Finished
Note over C: time_appconnect
C->>S: HTTP GET /
S->>C: HTTP 200 OK
Note over C: time_starttransfer
S->>C: Body
Note over C: time_total
# Только заголовки
curl -I https://example.com
# Полный verbose - запрос и ответ
curl -v https://example.com
# Не следовать редиректам
curl -I https://example.com
# Следовать
curl -IL https://example.com
# Указать конкретный IP - обход DNS
curl --resolve example.com:443:1.2.3.4 https://example.com
# POST с JSON
curl -X POST -H "Content-Type: application/json" \
-d '{"key":"value"}' https://api.example.com/data
# Игнорировать SSL - только для теста
curl -k https://self-signed.com
# HTTP/2 или HTTP/1.1 принудительно
curl --http2 -I https://example.com
curl --http1.1 -I https://example.com
Главная фишка curl — тайминг по фазам запроса. Покажет точно где медленно.
# Создаём шаблон вывода
cat > curl-format.txt << 'EOF'
time_namelookup: %{time_namelookup}s
time_connect: %{time_connect}s
time_appconnect: %{time_appconnect}s
time_pretransfer: %{time_pretransfer}s
time_redirect: %{time_redirect}s
time_starttransfer: %{time_starttransfer}s
----------
time_total: %{time_total}s
EOF
curl -w "@curl-format.txt" -o /dev/null -s https://example.com
Кейс: SSL handshake 450ms
Сайт грузится за 2.5 секунды. curl показал time_appconnect 0.456s — SSL занимает половину времени. На сервере nmap —script ssl-enum-ciphers нашёл слабые шифры. Отключил RC4, 3DES — handshake упал до 89ms.
# nginx ssl.conf
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384';
ssl_prefer_server_ciphers off;
ssl_session_cache shared:SSL:10m;
ssl_session_timeout 1h;
10. tcpdump — последняя инстанция
Когда все остальные команды показывают «вроде ок», а пользователь говорит «не работает» — доставай tcpdump. Он показывает реальные пакеты на проводе. Не врёт.
# Базовый захват на интерфейсе
sudo tcpdump -i eth0
# Без DNS-резолва, с номерами портов - быстрее
sudo tcpdump -i eth0 -nn
# По хосту
sudo tcpdump -i eth0 host 192.168.1.100
# Между двумя хостами в обоих направлениях
sudo tcpdump -i eth0 'host 192.168.1.100 and host 192.168.1.200'
# По порту
sudo tcpdump -i eth0 'tcp port 443'
# Только SYN-пакеты - смотреть установление соединений
sudo tcpdump -i eth0 'tcp[tcpflags] & tcp-syn != 0'
# DNS-запросы
sudo tcpdump -i eth0 -nn 'udp port 53'
# Сохранить в pcap для Wireshark
sudo tcpdump -i eth0 -w capture.pcap host 192.168.1.100
# С ротацией - чтобы не забить диск
sudo tcpdump -i eth0 -w cap.pcap -C 100 -W 10
# Прочитать сохранённый дамп
tcpdump -r capture.pcap -nn
Кейс: VoIP заикается, потерь нет
Телефония трещит, но ping чистый. Захватил RTP в pcap, открыл в Wireshark — Telephony — RTP — Streams. Jitter скачет от 5 до 150ms. Норма для VoIP — до 30ms. Виновник — кто-то качал торрент. Включил QoS с DSCP EF — заикания ушли.
Wireshark делает с pcap-файлом то, что tcpdump не покажет. Установи Wireshark и используй его для анализа, а tcpdump — для захвата на сервере. Под Windows есть встроенный pktmon — о нём ниже в Windows-разделе.
11. ethtool — физика сети
Когда сервер теряет пакеты, а ip route и iptables в порядке — спускайся на L1. ethtool покажет реальную скорость, duplex и ошибки на железе.
# Что говорит интерфейс
sudo ethtool eth0
# Speed: 1000Mb/s
# Duplex: Full
# Auto-negotiation: on
# Link detected: yes
# Статистика - ошибки CRC, фреймов, коллизии
sudo ethtool -S eth0 | grep -i error
# Драйвер и версия
sudo ethtool -i eth0
# Принудительная скорость и duplex - старое железо
sudo ethtool -s eth0 speed 1000 duplex full autoneg off
# Offload-функции
sudo ethtool -k eth0
Кейс: Half duplex на 100Mb/s
Сервер в стойке начал терять 5-10% пакетов. ethtool: Speed 100Mb/s Half. Должно быть 1000Mb/s Full. На свитче порт настроен на 100/half. Поменял на gigabit/full с обеих сторон — всё чистое.
sudo ethtool -S eth0 | grep -i error
# rx_crc_errors: 15234
# rx_frame_errors: 8976
# tx_carrier_errors: 2341
# collisions: 45678
Коллизии в 2026 году — это всегда half-duplex с обеих сторон или плохой кабель. Full-duplex коллизий не имеет в принципе.
12. nethogs и iftop — кто жрёт канал
«Интернет тормозит» в офисе — значит кто-то качает. nethogs покажет по процессам, iftop — по соединениям.
# Установка
sudo apt install nethogs iftop
# nethogs - процесс и его трафик
sudo nethogs eth0
# iftop - соединения и скорость
sudo iftop -i eth0 -nNP
# Без -n будет резолвить - в забитой сети тормозит
Кейс: торрент в офисе
Сотрудники жалуются на лаги Zoom. На шлюзе sudo nethogs eth0 — процесс transmission жрёт 15 MB/s upload из 20. Сотрудник скачивал торрент со станции. Настроил QoS с приоритетом для DSCP-маркированного трафика — звонки нормально, торрент в фоне.
# Базовый QoS через tc - ограничиваем torrent-порты
sudo tc qdisc add dev eth0 root handle 1: htb default 10
sudo tc class add dev eth0 parent 1: classid 1:10 htb rate 15mbit ceil 20mbit
sudo tc class add dev eth0 parent 1: classid 1:20 htb rate 2mbit ceil 5mbit
sudo tc filter add dev eth0 protocol ip parent 1:0 prio 1 \
u32 match ip dport 6881 0xffff flowid 1:20
13. arp и ip neigh — дубликаты IP
«С одной машины пингуется, с другой нет» — почти всегда конфликт MAC-адресов или ARP-spoofing.
Что происходит при ARP-конфликте — кто первый ответил, того и тапочки:
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 60, 'rankSpacing': 60}
}}%%
flowchart TD
A["Клиент A хочет 192.168.1.100"] --> B["ARP request: who has 192.168.1.100"]
B --> C["Сервер MAC 00:11:22"]
B --> D["Самозванец MAC AA:BB:CC"]
C --> E["ARP reply от 00:11:22"]
D --> F["ARP reply от AA:BB:CC"]
E --> G["Кеш клиента: запись от того кто первый"]
F --> G
G --> H["Трафик уходит не туда"]
style A fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style C fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style D fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
style H fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
# Linux - современно
ip neigh show
# Linux - старая школа
arp -n
# Очистить кеш
sudo ip neigh flush all
sudo ip neigh flush dev eth0
# Удалить конкретную запись
sudo ip neigh del 192.168.1.50 dev eth0
# Статическая запись
sudo ip neigh add 192.168.1.50 lladdr 00:11:22:33:44:55 dev eth0 nud permanent
# Windows
arp -a
arp -d 192.168.1.50
netsh interface ip delete arpcache
# PowerShell
Get-NetNeighbor
Remove-NetNeighbor -IPAddress 192.168.1.50
Кейс: дубль IP
Пользователь не может попасть на сервер 192.168.1.100, у других работает. На его машине arp -a показал MAC aa-bb-cc, на работающей — 00-11-22. Два устройства держат один IP. Кто-то поднял виртуалку с тем же адресом. Снёс виртуалку, очистил ARP-кеши — вылечилось.
14. route и ip route — таблица маршрутизации
Если ping до шлюза работает, а в интернет нет — проверь маршруты. Особенно когда два канала.
# Linux
ip route show
# Какой маршрут выберет ядро для конкретного IP
ip route get 8.8.8.8
# Добавить
sudo ip route add 10.0.0.0/24 via 192.168.1.1
# Заменить default
sudo ip route replace default via 192.168.1.1
# С метрикой - меньше = приоритетнее
sudo ip route add default via 192.168.2.1 metric 200
# Windows
route print
Get-NetRoute
# Добавить постоянный
route -p ADD 10.0.0.0 MASK 255.255.255.0 192.168.1.1
# PowerShell
New-NetRoute -DestinationPrefix "10.0.0.0/24" -NextHop "192.168.1.1" -InterfaceAlias "Ethernet"
Кейс: трафик через резерв
Два канала — быстрый основной и резервный 4G. После настройки failover весь трафик пошёл через 4G. ip route показал у резервного метрику 100, у основного 200. Меньше метрика = выше приоритет. Поменял местами — всё пошло через основной, 4G ждёт failover.
Постоянные маршруты в Ubuntu/Debian — в /etc/netplan/, в RHEL — в /etc/sysconfig/network-scripts/route-eth0.
15. Health check Linux — всё разом
Скрипт для быстрой проверки всего за раз. Сохрани в /usr/local/bin/netcheck.sh.
#!/bin/bash
echo "=== Network Health Check ==="
echo
echo "[1] Interfaces:"
ip -br addr show | grep -v "^lo"
echo
echo "[2] Default Gateway:"
ip route | grep default
echo
echo "[3] DNS:"
grep nameserver /etc/resolv.conf
echo
echo "[4] Ping 8.8.8.8:"
ping -c 3 -W 2 8.8.8.8 | tail -3
echo
echo "[5] DNS resolve:"
dig google.com +short +time=2 +tries=1
echo
echo "[6] Connections:"
ss -s
echo
echo "[7] Listening ports:"
ss -tuln | grep LISTEN
echo
echo "[8] Errors on interfaces:"
ip -s link | grep -B1 errors | grep -A1 "^[0-9]"
echo
echo "=== Done ==="
Запусти — получи срез по сети за 5 секунд. Удобно класть в SSH banner или в скрипт первичного триажа.
16. Windows: PowerShell вместо классики
В Windows старые команды живут с NT 4.0 — и работают. Но PowerShell-командлеты дают объекты вместо текста, который надо парсить регуляркой. Для скриптов и автоматизации это разница в небо.
| Старая команда |
PowerShell аналог |
Что лучше |
| ipconfig /all |
Get-NetIPConfiguration |
Объекты, фильтрация по полям |
| ping |
Test-Connection |
Параллельные пинги, результат в массив |
| ping host порт |
Test-NetConnection |
Реальная проверка TCP-порта, не ICMP |
| nslookup |
Resolve-DnsName |
Все типы записей, DNSSEC, кеш |
| netstat -ano |
Get-NetTCPConnection |
Связь с процессом без findstr |
| route print |
Get-NetRoute |
Фильтрация, метрики, IPv6 раздельно |
| arp -a |
Get-NetNeighbor |
Состояние записи (Reachable/Stale) |
| tracert |
Test-NetConnection -Traceroute |
Объектный вывод |
Test-NetConnection — швейцарский нож Windows
Запомни одну команду — tnc. Заменяет ping, telnet, tracert и часть nmap.
# Простой пинг
tnc google.com
# Проверить TCP-порт - то что telnet делал
tnc smtp.gmail.com -Port 587
tnc 192.168.1.50 -Port 3306
# Подробный отчёт - аналог curl -v на L4
tnc google.com -Port 443 -InformationLevel Detailed
# Traceroute
tnc google.com -TraceRoute
# Проверить порт через конкретный интерфейс
tnc 192.168.1.1 -Port 443 -SourceAddress 192.168.1.100
В отличие от telnet, tnc возвращает True/False — удобно в скриптах.
# Проверка пачки портов одной строкой
22,80,443,3306,5432 | ForEach-Object {
$r = tnc 192.168.1.50 -Port $_ -WarningAction SilentlyContinue
[PSCustomObject]@{
Port = $_
Open = $r.TcpTestSucceeded
}
} | Format-Table -AutoSize
Get-NetTCPConnection — кто слушает и куда ходит
netstat в Windows жив, но Get-NetTCPConnection даёт объекты с PID сразу, без двойного поиска через tasklist.
# Все слушающие порты
Get-NetTCPConnection -State Listen | Format-Table LocalAddress, LocalPort, OwningProcess
# Кто слушает 443 - с именем процесса
Get-NetTCPConnection -LocalPort 443 -State Listen |
Select-Object LocalAddress, LocalPort,
@{n='Process';e={(Get-Process -Id $_.OwningProcess).Name}}
# Все ESTABLISHED соединения с группировкой по процессу
Get-NetTCPConnection -State Established |
Group-Object OwningProcess |
Select-Object Count,
@{n='Process';e={(Get-Process -Id $_.Name -ErrorAction SilentlyContinue).Name}} |
Sort-Object Count -Descending |
Format-Table -AutoSize
# Сводка по состояниям TCP - аналог ss -s
Get-NetTCPConnection | Group-Object State | Format-Table Name, Count
Кейс: процесс держит порт 80
IIS не стартует — ошибка «port 80 in use». Get-NetTCPConnection -LocalPort 80 показал OwningProcess 4 — это System. В системе поднят сервис World Wide Web Publishing, который и держит порт. Stop-Service W3SVC, IIS Express запустился.
Захват трафика без Wireshark — pktmon
С Windows 10 1809 в системе есть встроенный pktmon — легковесный аналог tcpdump. Wireshark не нужен на сервере, для анализа дамп переносишь на рабочую станцию.
# Базовый захват всего на всех интерфейсах
pktmon start --capture
# ждём немного
pktmon stop
# С фильтром - только трафик на порт 443
pktmon filter add -p 443
pktmon start --capture --pkt-size 0
pktmon stop
pktmon filter remove
# Конвертация в pcapng для Wireshark
pktmon pcapng PktMon.etl -o capture.pcapng
# Только захват по IP
pktmon filter add MyFilter -i 192.168.1.50
pktmon start --capture
Альтернатива — tshark из пакета Wireshark CLI или netsh trace для совсем старых систем.
# netsh trace - работает на Windows 7/Server 2008 R2 и выше
netsh trace start capture=yes tracefile=C:\trace.etl
# воспроизводим проблему
netsh trace stop
Resolve-DnsName — dig для Windows
nslookup в Windows жив, но Resolve-DnsName умеет больше: DNSSEC, фильтрация по типу, работа с кешем.
# A-запись
Resolve-DnsName google.com
# Конкретный тип
Resolve-DnsName google.com -Type MX
Resolve-DnsName google.com -Type TXT
Resolve-DnsName google.com -Type NS
# Через конкретный DNS
Resolve-DnsName google.com -Server 8.8.8.8
# Без кеша - принудительный запрос
Resolve-DnsName google.com -DnsOnly
# Из кеша - что Windows запомнил
Get-DnsClientCache
# Очистить кеш
Clear-DnsClientCache
# Проверить настроенные DNS на интерфейсах
Get-DnsClientServerAddress -AddressFamily IPv4
# Поменять DNS на интерфейсе
Set-DnsClientServerAddress -InterfaceAlias "Ethernet" -ServerAddresses ("8.8.8.8","1.1.1.1")
Сетевая статистика — что в Resource Monitor нет
Get-NetAdapterStatistics показывает счётчики на уровне интерфейса — ошибки, дропы, пакеты. Аналог ip -s link в Linux.
# Статистика всех интерфейсов
Get-NetAdapterStatistics | Format-Table Name, ReceivedBytes, SentBytes, ReceivedDiscardedPackets, OutboundDiscardedPackets
# Только проблемные - где есть ошибки
Get-NetAdapterStatistics |
Where-Object {$_.ReceivedDiscardedPackets -gt 0 -or $_.OutboundDiscardedPackets -gt 0}
# Скорость и дуплекс - аналог ethtool
Get-NetAdapter | Format-Table Name, LinkSpeed, MediaConnectionState, FullDuplex
# Расширенные настройки адаптера
Get-NetAdapterAdvancedProperty -Name "Ethernet"
# Сменить скорость и duplex
Set-NetAdapterAdvancedProperty -Name "Ethernet" -DisplayName "Speed & Duplex" -DisplayValue "1.0 Gbps Full Duplex"
Файрвол — быстрая диагностика
Половина проблем «не работает на Windows» — это Windows Defender Firewall. Проверка занимает минуту.
# Профили файрвола - какие активны
Get-NetFirewallProfile | Format-Table Name, Enabled
# Найти правило, блокирующее порт
Get-NetFirewallRule -Direction Inbound -Action Block |
Where-Object Enabled -eq True |
Get-NetFirewallPortFilter |
Where-Object LocalPort -eq 80
# Открыть порт 443 во внешний мир
New-NetFirewallRule -DisplayName "Allow HTTPS" -Direction Inbound -Protocol TCP -LocalPort 443 -Action Allow
# Логирование заблокированных пакетов - диагностика
Set-NetFirewallProfile -Profile Domain,Public,Private -LogBlocked True -LogFileName "%systemroot%\system32\LogFiles\Firewall\pfirewall.log"
# Просмотр лога
Get-Content C:\Windows\System32\LogFiles\Firewall\pfirewall.log -Tail 50
Health check для Windows
# Сохрани как netcheck.ps1
# Запуск: powershell -ExecutionPolicy Bypass -File netcheck.ps1
Write-Host "=== Windows Network Health Check ===" -ForegroundColor Cyan
Write-Host ""
Write-Host "[1] Active Adapters:" -ForegroundColor Yellow
Get-NetAdapter | Where-Object Status -eq "Up" |
Format-Table Name, InterfaceDescription, LinkSpeed, MediaConnectionState
Write-Host "[2] IP Configuration:" -ForegroundColor Yellow
Get-NetIPConfiguration | Where-Object IPv4Address |
Format-Table InterfaceAlias,
@{n='IPv4';e={$_.IPv4Address.IPAddress}},
@{n='Gateway';e={$_.IPv4DefaultGateway.NextHop}},
@{n='DNS';e={$_.DNSServer.ServerAddresses -join ', '}}
Write-Host "[3] Default Route:" -ForegroundColor Yellow
Get-NetRoute -DestinationPrefix "0.0.0.0/0" |
Format-Table NextHop, InterfaceAlias, RouteMetric, ifMetric
Write-Host "[4] Internet check:" -ForegroundColor Yellow
$ping = Test-Connection 8.8.8.8 -Count 4 -ErrorAction SilentlyContinue
if ($ping) {
$avg = ($ping | Measure-Object ResponseTime -Average).Average
Write-Host " 8.8.8.8 reachable, avg $([math]::Round($avg,1))ms" -ForegroundColor Green
} else {
Write-Host " 8.8.8.8 UNREACHABLE" -ForegroundColor Red
}
Write-Host "[5] DNS resolve test:" -ForegroundColor Yellow
try {
$dns = Resolve-DnsName google.com -Type A -ErrorAction Stop
Write-Host " google.com -> $($dns[0].IPAddress)" -ForegroundColor Green
} catch {
Write-Host " DNS FAILED: $_" -ForegroundColor Red
}
Write-Host "[6] HTTPS check:" -ForegroundColor Yellow
$https = tnc google.com -Port 443 -WarningAction SilentlyContinue
if ($https.TcpTestSucceeded) {
Write-Host " 443/tcp open" -ForegroundColor Green
} else {
Write-Host " 443/tcp BLOCKED" -ForegroundColor Red
}
Write-Host "[7] TCP connections by state:" -ForegroundColor Yellow
Get-NetTCPConnection | Group-Object State |
Format-Table Name, Count -AutoSize
Write-Host "[8] Listening ports:" -ForegroundColor Yellow
Get-NetTCPConnection -State Listen |
Select-Object LocalPort,
@{n='Process';e={(Get-Process -Id $_.OwningProcess -ErrorAction SilentlyContinue).Name}} -Unique |
Sort-Object LocalPort |
Format-Table -AutoSize
Write-Host "[9] Adapter errors:" -ForegroundColor Yellow
Get-NetAdapterStatistics |
Where-Object {$_.ReceivedDiscardedPackets -gt 0 -or $_.OutboundDiscardedPackets -gt 0} |
Format-Table Name, ReceivedDiscardedPackets, OutboundDiscardedPackets
Write-Host "[10] Firewall profiles:" -ForegroundColor Yellow
Get-NetFirewallProfile | Format-Table Name, Enabled, DefaultInboundAction
Write-Host "=== Done ===" -ForegroundColor Cyan
Кейс: domain controller перестал отвечать клиентам
Половина клиентов перестала логиниться в домен. На DC запустил netcheck.
ps1. На пункте 8 увидел: порт 88 (Kerberos) и 389 (LDAP) не в списке Listen. Проверил Get-Service NTDS — сервис стоит. Запустил, проверил Event Log на ошибки — вылез конфликт SPN. Лечится setspn, но сначала надо было найти где сломалось.
17. Осложнения — типовые ошибки
Краткий справочник по ошибкам и их причинам. Запоминается с первого раза.
| Ошибка |
Что значит |
Куда копать |
| Connection refused |
Хост ответил, порт закрыт |
Сервис не запущен или bind на localhost |
| Connection timeout |
Пакеты не доходят |
Файрвол, маршрут, хост лёг |
| No route to host |
Нет маршрута в таблице |
ip route, default gateway |
| Host unreachable |
Хост в той же сети не отвечает на ARP |
Хост лёг, не та подсеть, switch |
| Name or service not known |
DNS не резолвит |
/etc/resolv.conf, dig @8.8.8.8 |
| SSL handshake failure |
Не договорились о шифрах/версии |
openssl s_client, nmap ssl-enum-ciphers |
| 502 Bad Gateway |
nginx не получил ответ от backend |
ss на backend, логи приложения |
| 504 Gateway Timeout |
Backend ответил слишком долго |
Backend перегружен, БД |
MTU и MSS - тихий убийца
ping проходит, SSH работает, но SCP больших файлов виснет, страницы открываются наполовину. Это PMTU. Проверь MTU через ping -M do -s 1472. Если не проходит — уменьшай. На VPN-сервере добавь MSS clamping в iptables.
# MSS clamping для VPN
sudo iptables -t mangle -A FORWARD -p tcp --tcp-flags SYN,RST SYN \
-j TCPMSS --clamp-mss-to-pmtu
# Жёстко выставить MSS - 1360 безопасно для PPPoE/мобильных
sudo iptables -t mangle -A FORWARD -p tcp --tcp-flags SYN,RST SYN \
-j TCPMSS --set-mss 1360
Magic number: MSS = MTU — 40 для IPv4. MTU 1400 — значит MSS 1360.
Самая коварная ошибка — асимметричная маршрутизация. Файрвол клиента видит ответ с «не того» IP и дропает соединение:
%%{init: {
'theme': 'base',
'themeVariables': {
'primaryColor': '#ffffff',
'primaryTextColor': '#1e293b',
'primaryBorderColor': '#94a3b8',
'lineColor': '#64748b',
'fontSize': '14px',
'fontFamily': 'ui-sans-serif, system-ui, sans-serif'
},
'flowchart': {'curve': 'linear', 'nodeSpacing': 60, 'rankSpacing': 60}
}}%%
flowchart TD
A["Клиент 192.168.1.10"] -->|SYN на 192.168.1.100| B["eth0: 192.168.1.100"]
B --> C["Сервер с двумя интерфейсами"]
C -->|default route через eth1| D["eth1: 10.0.0.100"]
D -->|SYN-ACK с src 10.0.0.100| E["Файрвол клиента"]
E -->|DROP - нет такого соединения| F["Соединение зависает"]
style A fill:#f8fafc,stroke:#3b82f6,stroke-width:2px,color:#1e40af
style B fill:#f8fafc,stroke:#22c55e,stroke-width:2px,color:#15803d
style D fill:#f8fafc,stroke:#f97316,stroke-width:2px,color:#9a3412
style F fill:#f8fafc,stroke:#ef4444,stroke-width:2px,color:#991b1b
Лечится policy-based routing — чтобы пакет уходил с того же интерфейса, на который пришёл:
# Создаём отдельную таблицу для управляющего интерфейса
echo "100 mgmt" | sudo tee -a /etc/iproute2/rt_tables
sudo ip route add 192.168.1.0/24 dev eth0 src 192.168.1.100 table mgmt
sudo ip route add default via 192.168.1.1 dev eth0 table mgmt
sudo ip rule add from 192.168.1.100 table mgmt
18. Альтернативы — чем заменить классику
Не все команды одинаково хороши в 2026 году. Вот что использовать вместо.
| Старое |
Новое |
Почему |
| ifconfig |
ip addr |
ifconfig deprecated, нет VLAN, медленнее |
| route |
ip route |
Не показывает policy routing, нет multipath |
| arp |
ip neigh |
Часть iproute2, единый CLI |
| netstat |
ss |
В разы быстрее на больших объёмах сокетов |
| traceroute |
mtr |
Снимает статистику, не одноразовый снимок |
| nslookup |
dig |
Подробнее, гибче, +trace |
| telnet |
nc -zv |
nc по умолчанию есть, telnet ставить надо |
В Windows старые команды никуда не делись и работают, но PowerShell-командлеты Get-NetTCPConnection, Test-NetConnection, Resolve-DnsName удобнее для скриптов.
19. Профилактика — чтобы не звонили в 3 ночи
Лучшая диагностика — та, которую делать не пришлось. Что настроить заранее:
- Мониторинг линка — Zabbix или Prometheus с алертом на ifOperStatus и errors на интерфейсе. Заметишь деградацию до того как кабель отвалится.
- Внешний пинг до критичных хостов — smokeping или uptime-kuma с графиками потерь и latency. Покажет где проблема — у тебя или у провайдера.
- Логи DNS-сервера — query log с ротацией. При DNS cache poisoning или массовых ошибках резолвинга найдёшь источник.
- Бэкап конфигов сети — оригиналы /etc/netplan, iptables-save в git перед каждым изменением. Откат за 30 секунд.
- NTP на всех хостах — без синхронного времени логи не сопоставишь. Это не сетевая проблема, но без NTP диагностика становится в разы тяжелее.
- Документ «сетевая карта» — схема подсетей, VLAN, маршрутов в wiki. Через год сам себе скажешь спасибо.
- Скрипт netcheck в SSH banner — залогинился на сервер — сразу видно состояние сети. Экономит первые 30 секунд на каждом инциденте.
20. FAQ — что спрашивают чаще всего
Почему ping проходит, а сайт не открывается?
ping проверяет ICMP до хоста, а сайт — это TCP на порт 443 плюс DNS плюс SSL плюс HTTP. Проверь по цепочке: dig для DNS, nc -zv host 443 для порта, curl -v для HTTP/SSL. Чаще всего виноват DNS или SSL handshake.
Как проверить, что troubleshooting сети командой работает правильно?
Прогони команду в две стороны. Если nc -zv server.com 443 говорит open — убедись что это тот сервер. Через —resolve в curl можно жёстко привязаться к IP, минуя DNS. Если результаты с двух разных машин в одной сети расходятся — проблема локальная, не глобальная.
Что делать если порт открыт, но приложение не отвечает?
Это L7-проблема, не сетевая. Логи приложения, нагрузка на CPU/память, БД. Сделай curl -v — увидишь, что отдаёт сервер. Если 502 — backend лёг. Если timeout после соединения — приложение зависло, не отвечает на запросы. Перезапуск сервиса поможет, но причину ищи в логах.
Чем tcpdump отличается от Wireshark?
tcpdump захватывает пакеты в консоли, Wireshark — в GUI. На сервере без GUI ставишь tcpdump, дамп сохраняешь в pcap, открываешь в Wireshark на ноуте. Wireshark лучше анализирует, tcpdump лучше захватывает в продакшне без оверхеда. На Windows есть встроенный pktmon — не нужно ставить ничего.
Как найти, какой процесс жрёт сеть в Windows?
Открой Resource Monitor (resmon.exe), вкладка Network. Там видно процессы и их трафик. Альтернативно — Get-NetTCPConnection в PowerShell с привязкой к процессу через OwningProcess. На Linux эту задачу решает nethogs одной командой.
Почему mtr показывает потери на промежуточном хопе, но конечный работает?
Это нормально. Промежуточные роутеры рейт-лимитят ICMP-ответы, чтобы не нагружать CPU. Если потери только на хопе N, а на N+1 их нет — это ложный сигнал. Реальные потери — те, что есть на конечном хосте и одинаковые на всех хопах после проблемного.
Чем nc отличается от nmap для проверки портов?
nc проверяет один порт за раз и подтверждает, что TCP-соединение установилось. nmap сканирует диапазон, определяет версии сервисов, ОС, может запускать NSE-скрипты на уязвимости. Для быстрой проверки «открыт ли» — nc. Для аудита сети — nmap.
Можно ли все команды troubleshooting сети использовать без root?
Большинство read-only команд работают без прав: ping, traceroute, dig, ss без -p, curl, nslookup. Команды для изменения конфигурации (ip addr add, ip route add), для захвата сырых пакетов (tcpdump) и для просмотра процессов в ss/netstat требуют root или sudo. nmap для SYN-сканов тоже хочет root.
21. Прогноз — что у тебя теперь есть
Шпаргалка собрана. У тебя теперь алгоритм диагностики по уровням OSI, рабочие команды под Linux и Windows, скрипты health check на bash и PowerShell, разбор pktmon для Windows без Wireshark, и таблица типовых ошибок. Этого хватает на 90% сетевых инцидентов в продакшне — от «сайт не открывается» до «VoIP заикается».
Главное — не зубри команды, пойми порядок. Симптом — уровень — команда. Линк проверил, IP проверил, шлюз проверил, DNS проверил, порт проверил, приложение проверил. На каком-то шаге найдёшь. А когда не найдёшь — доставай tcpdump или pktmon и смотри что реально летит по проводу.
Если что-то из шпаргалки не сработало или нашёл косяк — пиши в комментарии, разберёмся.