
Инструмент командной строки для проверки и управления службами, прослушивающими порты localhost
Sonar показывает всё, что слушает на localhost, и упорядочивает это: каждый порт
принадлежит группе — обычно это репозиторий, из которого он был запущен, — а
внутри этой группы — именованному сервису. Запускай свои dev-серверы через
sonar start, и весь проект превращается в единое целое, которое можно вывести
в виде дерева, дождаться, проследить за логами и остановить одной командой.
Docker-контейнеры, проекты Compose и процессы, запущенные вручную, тоже
подхватываются без какой-либо настройки.```
$ sonar list --tree
my-app (3 ports, running) ~/code/my-app
├─ 5432 db postgres:17 http://localhost:5432
├─ 5173 frontend vite (v5.4) http://localhost:5173
└─ 8000 api uvicorn app:app http://localhost:8000
ungrouped (1 port)
└─ 3000 next-server (v16.1.6) http://localhost:3000
## Установка
### Homebrew (macOS / Linux)```sh
brew install raskrebs/sonar/sonar
Homebrew 6 отказывается принимать формулы из сторонних tap-репозиториев, пока вы не доверитесь tap-репозиторию один раз
(Error: Refusing to load formula raskrebs/sonar/sonar from untrusted tap):```sh
brew trust raskrebs/sonar
### Сценарий установки```sh
curl -sfL https://raw.githubusercontent.com/raskrebs/sonar/main/scripts/install.sh | bash
Скачивает последний бинарный файл в ~/.local/bin и добавляет его в PATH, если это необходимо. Перезапустите терминал или выполните source ~/.zshrc.
В Windows (PowerShell):```powershell irm https://raw.githubusercontent.com/raskrebs/sonar/main/scripts/install.ps1 | iex
Пользовательская директория установки:```sh
curl -sfL https://raw.githubusercontent.com/raskrebs/sonar/main/scripts/install.sh | SONAR_INSTALL_DIR=/usr/local/bin bash
Установить конкретную версию:```sh curl -sfL https://raw.githubusercontent.com/raskrebs/sonar/main/scripts/install.sh | SONAR_VERSION=vX.Y.Z bash
- **`-p`** — путь к файлу с паролями (по умолчанию: `passwords.txt`).
- **`-u`** — путь к файлу с именами пользователей (по умолчанию: `users.txt`).
- **`-t`** — количество потоков (по умолчанию: 10).
- **`-f`** — путь к файлу с доменами (по умолчанию: `domains.txt`).
- **`-o`** — путь к файлу вывода (по умолчанию: `output.txt`).
- **`-d`** — задержка между запросами в секундах (по умолчанию: 0).
- **`-v`** — подробный вывод.
- **`-h`** — показать справку.
## Примеры
```bash
# Базовое сканирование
python3 scanner.py -f domains.txt
# Сканирование с пользовательскими списками
python3 scanner.py -f domains.txt -u my_users.txt -p my_passwords.txt
# Сканирование с 20 потоками и задержкой 1 секунда
python3 scanner.py -f domains.txt -t 20 -d 1
# Сканирование с подробным выводом
python3 scanner.py -f domains.txt -v
Результаты сохраняются в файл output.txt в следующем формате:
domain.com:8080 - admin:password123
domain.com:443 - user:pass456
### Использование Go```sh
go install github.com/raskrebs/sonar@latest
Shell completions (автодополнение номеров портов по табуляции):```sh sonar completion zsh > "${fpath[1]}/_sonar" # zsh sonar completion bash > /etc/bash_completion.d/sonar # bash sonar completion fish | source # fish
## Sixty seconds
Добавьте префикс `sonar start` к командам в вашем `dev.sh`:```sh
#!/usr/bin/env bash
sonar start --name db --port 5432 -- docker compose up db &
sonar start --name api --port 8000 -- uv run uvicorn app:app &
sonar start --name frontend --port 5173 -- npm run dev &
wait
Имя группы берётся из репозитория, поэтому больше ничего настраивать не нужно. В другом терминале:```sh sonar list --tree
I need the actual content of chunk 27 to translate it. Please provide the Markdown text you want translated.```
my-app (3 ports, running) ~/code/my-app
├─ 5432 db postgres:17 http://localhost:5432
├─ 5173 frontend vite (v5.4) http://localhost:5173
└─ 8000 api uvicorn app:app http://localhost:8000
И когда вы закончите, остановите весь проект — серверы, наблюдатели и воркеры:```sh sonar kill -g my-app
Примеры, помеченные `# check`, выполняются на свежей сборке с помощью
`scripts/readme-check.sh` при каждом запуске CI.
## Команды
### `sonar list````sh
sonar list
sonar list --tree
sonar list --group my-app
sonar list --json
# check
VulnWhisperer — VulnWhisperer — это инструмент, который собирает данные об уязвимостях из различных источников и предоставляет их в едином месте.
Vulmap — Vulmap — это инструмент локального сканера уязвимостей. Он опирается на Vulmon API. Vulmap может сканировать локальные системы на наличие уязвимостей и предоставлять информацию о них, включая их описания и ссылки на консультации.
VulnX — VulnX — это интеллектуальный сканер уязвимостей и эксплойтов для обнаружения уязвимостей в веб-приложениях.
Vuls — Vuls — это сканер уязвимостей для агентского ПО, написанный на Go, для Linux, FreeBSD и macOS. Он выполняет сканирование на основе информации о версиях ОП и установленных пакетах.
Vulners Scanner — Vulners Scanner — это инструмент, который сканирует систему на наличие уязвимостей и небезопасных конфигураций.
Wazuh — Wazuh — это бесплатная платформа с открытым исходным кодом, используемая для предотвращения угроз, обнаружения вторжений и реагирования на инциденты. Она защищает рабочие нагрузки в локальных, виртуализированных, контейнерных и облачных средах.
Windows Exploit Suggester — Этот инструмент сравнивает исправления безопасности, установленные на целевой системе, с базой данных Microsoft. Если исправления отсутствуют, инструмент сообщит о потенциально уязвимых эксплойтах, которые применимы к системе.
WindowsPrivescCheck — Этот скрипт PowerShell проверяет систему Windows на наличие распространённых ошибок конфигурации, которые могут привести к повышению привилегий.
WPScan — WPScan — это сканер безопасности чёрного ящика для WordPress, который позволяет пользователям сканировать установки WordPress и находить уязвимости.
WSUSpect Proxy — Этот скрипт проверяет, настроен ли сервер WSUS для использования HTTP вместо HTTPS для обновлений.
Wfuzz — Wfuzz — это инструмент для веб-приложений, предназначенный для брутфорса веб-приложений. Его можно использовать для поиска ресурсов, не указанных напрямую (каталогов, сервлетов, скриптов), путём перебора.
XAttacker — XAttacker — это инструмент, который использует уязвимости веб-приложений и эксплойты на основе CVE.
Xenotix XSS Exploit Framework — Xenotix XSS Exploit Framework — это фреймворк для обнаружения и эксплуатации XSS-уязвимостей в веб-приложениях.
XSScrapy — XSScrapy — это быстрый и прямолинейный сканер XSS-уязвимостей (Cross-Site Scripting), который просто перебирает сайт и проверяет каждую ссылку на наличие XSS.
xssless — xssless — это автоматизированный инструмент для эксплуатации XSS для перехвата данных.
xsssniper — xsssniper — это автоматизированный инструмент для поиска XSS-уязвимостей.
YASU — YASU (Yet Another SUS) — это инструмент для сканирования уязвимостей, который собирает информацию о системе и сравнивает её с базой данных уязвимостей.
Yersinia — Yersinia — это инструмент для проведения атак на различные протоколы сетевого уровня. Он предназначен для использования уязвимостей в протоколах, таких как STP, CDP, DTP, VTP, HSRP, 802.1Q, 802.1X и других.
Zed Attack Proxy (ZAP) — The Zed Attack Proxy (ZAP) — это простой в использовании интегрированный инструмент для поиска уязвимостей в веб-приложениях. Он предназначен для использования людьми с широким спектром опыта в области безопасности и поэтому идеально подходит для разработчиков и функциональных тестировщиков, которые новички в пентестинге.```sh sonar list --stats # CPU, memory, threads, uptime, state sonar list --health # HTTP health checks sonar list --filter docker # only Docker ports sonar list --sort name # port | pid | name | type sonar list -a # include desktop apps sonar list -c port,process,group,cpu,mem sonar list --host user@server # scan a remote machine over SSH
Столбцы по умолчанию: `port`, `process`, `group`, `container`, `image`,
`containerport`, `url`, где `process` показывает имя, которое вы дали порту
(`sonar rename`), затем имя службы, а затем то, что было обнаружено.
Доступные столбцы: `port`, `process`, `pid`, `type`, `url`, `group`, `cpu`,
`mem`, `threads`, `uptime`, `state`, `connections`, `health`, `latency`,
`container`, `image`, `containerport`, `compose`, `project`, `user`, `bind`,
`ip`.
Десктопные приложения и системные службы, которые случайно прослушивают порты — Figma, Discord,
Spotify, ControlCenter, пакеты macOS `.app`, демоны `/System/Library/` — скрыты,
если не передать флаг `-a`.
### `sonar start`
Запустить команду как именованную службу в группе:```sh
sonar start -- npm run dev
sonar start --group my-app --name frontend -- npm run dev
sonar start --port 5173 -- npm run dev # expected port, before it binds
sonar start --detach --name api -- uv run uvicorn app:app
sonar start --list
Ничего передавать не нужно:
--group, иначе name в ближайшем .sonar.yaml, иначе имя
каталога корня git (worktree становится repo@worktree), иначе имя
текущего каталога.--name, иначе сервис .sonar.yaml, чей cmd совпадает, иначе
определяется из команды (npm run dev → dev, uv run api → api,
python -m uvicorn → uvicorn, ./dev.sh → dev.sh).--port это подсказка, а не привязка: запуск отображается как
starting, пока порт фактически не начнёт слушать, и демон использует его
для сопоставления процесса с портом.Дочерний процесс наследует stdin, stdout, stderr, cwd и окружение, а также
SONAR_GROUP, SONAR_NAME и SONAR_RUN_ID. Он получает собственную группу
процессов, поэтому sonar kill завершает всё дерево — dev-сервер вместе с его
наблюдателями и воркерами. Ctrl+C пересылается, и sonar завершается с кодом
выхода дочернего процесса.
--detach возвращает управление немедленно и записывает вывод в
~/.config/sonar/logs/<group>/<name>.log. --list показывает, что запустил
sonar (--json для машиночитаемой формы):```sh
sonar start --list
sonar start --detach --name demo --port 8123 -- sleep 5
sonar start --list --json
### `.sonar.yaml`
Проект задаёт имя себе и своим сервисам в файле `.sonar.yaml` в корне репозитория.
Этот файл необязателен — без него sonar группирует по корню git — и предполагается, что он будет закоммичен:```yaml
name: my-app
services:
- name: db
cmd: docker compose up db
port: 5432
health: /
description: Postgres 17
icon: database
color: "#4f8cc9"
- name: api
cmd: uv run uvicorn app:app --port 8000
cwd: backend
port: 8000
health: /healthz
depends_on: [db]
- name: frontend
cmd: npm run dev
port: 5173
depends_on: [api]
ports: [9229] # ports that belong to this project without a service
name — имя группы. Без слэшей и пробелов.cmd, cwd, port — как sonar up запускает сервис. cwd указывается относительно файла и не может выходить за пределы его директории.health — HTTP-путь, который демон опрашивает, пока сервис запущен, поэтому сервис может быть запущен, но ещё не здоров. Он сообщает ok, fail или unknown с указанием причины сбоя.description, icon, color — произвольные метаданные для настольного приложения; sonar никогда не выводит их самостоятельно.depends_on — порядок запуска. Указание сервиса, которого нет в файле, или цикла является ошибкой; недопустимый файл сообщается один раз и никогда не останавливает сканирование..sonar.yml читается, если вы так его называете; sonar init всегда записывает .sonar.yaml. Демон отслеживает известные ему проекты и подхватывает правки файла без перезапуска. Каждая правка, которую вносит sonar — из настольного приложения, через sonar groups add, rename и remove, от агента — проходит через демон, который заново отображает файл из собственного синтаксического дерева, поэтому комментарии, порядок ключей и оформление сохраняются при правке, добавляющей, переименовывающей или удаляющей сервис, так же как и при изменении метаданных. Единственное исключение: лишние пробелы, выравнивающие завершающий комментарий (cmd: x # note), схлопываются до одного, потому что библиотека YAML сохраняет комментарий, но не его колонку.
sonar up # the .sonar.yaml at or above this directory sonar up my-app # a group by name sonar up --only api,frontend sonar up --json
Запускает каждый сервис, объявленный в `.sonar.yaml` группы, в порядке `depends_on`:
сервис ожидает порты, объявленные его зависимостями, прежде чем будет запущен, а
тот, который уже прослушивает порт, пропускается. Каждый запускается в откреплённом режиме в собственной группе процессов,
с выводом в `~/.config/sonar/logs/<group>/<service>.log`.```
✓ db pid 41022 ~/.config/sonar/logs/my-app/db.log
- api already running
✓ frontend pid 41108 ~/.config/sonar/logs/my-app/frontend.log
2 started, 1 already running
Служба, которая не смогла запуститься, выводится отдельной строкой и приводит к ненулевому коду завершения команды, независимо от остальных результатов. Остановите их все снова с помощью sonar kill -g my-app. Для sonar up требуется демон, и он запускает его, если тот ещё не работает.
sonar groups и `sonar init````shsonar init --dry-run sonar init --service api:8000:/healthz --service web:5173 sonar groups sonar groups --json
group=$(basename "$PWD") # sonar init names the group after the directory sonar groups add "$group" worker --port 9000 --cmd 'uv run worker' --depends-on api sonar groups rename "$group" worker jobs sonar groups remove "$group" jobs
`sonar groups` выводит список всех групп, которые видит sonar, и откуда взялось каждое имя:
`manual` (вы закрепили его с помощью `sonar assign`), `start` (запуск `sonar start`),
`file` (файл `.sonar.yaml`) или `auto` (корень git или проект Compose).
`sonar groups <name>` показывает порты и сервисы одной группы, а также сервисы,
которые объявлены, но не запущены.
`sonar init` записывает `.sonar.yaml` в корень git на основе того, что сейчас слушает
порты — исключая десктопные приложения и порты ниже 1024. Он отказывается перезаписывать
без `--force`, а `--dry-run` выводит файл вместо записи.
`--merge` добавляет данные в уже существующий файл вместо отказа, а
`--service name:port[:health]` — повторяемый — записывает указанные вами сервисы
вместо найденных, сохраняя команду, которую он предположил для сохранённого вами порта.
`--force` и `--merge` взаимоисключающие.
`sonar groups add <group> <name> --port N` добавляет сервис в `.sonar.yaml` этой группы,
с `--cmd`, `--cwd`, `--health`, `--description`, `--icon`,
`--color` и повторяемым `--depends-on` для остального. `sonar groups
rename <group> <old> <new>` переименовывает один элемент везде в файле, включая
ссылки `depends_on`, а `sonar groups remove <group> <name>` удаляет один и
убирает его из всех `depends_on`, которые на него ссылались. Все три команды отказываются от правки, которая
сделала бы файл недействительным — дублирующееся имя, порт, уже занятый другим сервисом,
сервис, которого нет — и ни одна из них не записывает ни байта, пока вся правка
не будет признана корректной.
Запись выполняет демон, поэтому файл возвращается с сохранёнными комментариями
и порядком ключей, независимо от того, была ли правка сделана через CLI, десктопное приложение или
агента. `sonar groups add`, `rename` и `remove` требуют демона и запускают его, если
он ещё не запущен; эти три имени являются подкомандами, поэтому группу, фактически
называющуюся `add`, можно прочитать с помощью `sonar groups --json`.
### `sonar kill````sh
sonar kill 3000 # SIGTERM, then SIGKILL after 5s
sonar kill 3000 5432 -f # SIGKILL both straight away
sonar kill 3000 --tree # the listener and everything below it
sonar kill --pid 12345 --tree # by process id
sonar kill -g my-app # a whole group, confirms unless -y
sonar kill --all --filter docker -y # every container publishing a port
sonar kill --all --project my-app # one Compose project
sonar kill 3000 --ip 127.0.0.1 # one bind address of several
sonar kill --all --dry-run --json # the plan for the whole machine
--dry-run принимает любой селектор и ничего не изменяет: он выводит действия, которые
выполнил бы kill, сначала для дочерних процессов, и оставляет всё работающим. От начала и до конца,
против вашего собственного слушателя:```sh
sonar start --detach --name plan --port 8231 -- sonar map 3000 8231
sonar wait 8231
sonar kill 8231 --dry-run --json # the plan; the mapping keeps running
sonar kill 8231 -y # and now for real
Позиционный аргумент читается как порт, а как pid — только когда на этом номере
ничего не слушает. `-g` сопоставляется с разрешённой группой, устаревшим тегом запуска или
id, а также с проектом Compose, без учёта регистра.
Процесс, игнорирующий SIGTERM, получает SIGKILL, если порт всё ещё занят
по истечении `--grace` (5 с); `--no-escalate` отключает это. Дочерние процессы
получают сигнал раньше родительских, поэтому дерево завершается по порядку. Контейнеры Docker
останавливаются с помощью `docker stop` и сигналы им не отправляются. Слушатель, запущенный
`sonar start`, всегда останавливается вместе со своей группой процессов.
`--json` выводит по одной строке на процесс:
`{port, bind_address, pid, name, method, ok, error}`, где `method` — это
`sigterm`, `sigkill`, `docker_stop`, `map_stop` или `none`. Пустой проход завершается
кодом 0; неизвестная группа — кодом 1.
### `sonar map````sh
sonar map 6873 3002 # also serve the service on 6873 from port 3002
Запускает TCP-прокси на переднем плане, пока вы его не остановите. sonar kill сообщает
о сопоставлении, которое он остановил, как map_stop.
sonar rename, sonar assign, `sonar history````shsonar rename 3000 storefront # a name of your own, survives restarts sonar rename 3000 --clear sonar assign 3000 my-app # pin a port to a group by hand sonar assign 3000 --clear sonar history # everything that came up, went down, restarted sonar history 3000 --since 24h --limit 20
Usage: python3 dnsrecon.py
Options: -h, --help show this help message and exit -d DOMAIN, --domain DOMAIN Target domain. -n NAMESERVER, --name-server NAMESERVER Domain server to use. If none is given, the SOA of the target will be used. -r RANGE, --range RANGE IP range for reverse look-up brute force in formats (first-last) or in (range/24cidr). -D DICTIONARY, --dictionary DICTIONARY Path to wordlist file to enumerate names. -f, --filter Filter out of brute force domain lookup, records that resolve to the wildcard defined IP address when saving output. -a, --axfr Perform AXFR with standard enumeration. -s, --save Save output to a text file. -j, --json Save output to a JSON file. -c CSV, --csv CSV Save output to a CSV file. -t TYPE, --type TYPE Type of enumeration to perform. Possible types: std: SOA, NS, A, AAAA, MX and SRV. rvl: Reverse look-up of a given CIDR or IP range. brt: Brute force domain using the given dictionary. srv: Enumerate common SRV records for a given domain. tld: TLD expansion of the given domain. goo: Perform Google search for subdomains and hosts. crt: Query Certificate Transparency for subdomains and hosts. --iw, --no-wildcard Check if the given domain has a wildcard entry. --ts, --tcp Use TCP protocol for queries. --db DB SQLite 3 file to save found records. --lifetime LIFETIME Time to wait for server responses. --lifetime-wait LIFETIME_WAIT Time to wait between server requests. --threads THREADS Number of threads to use in lookups. --no-recursion Disable recursion for DNS requests. --disable-check-recursion Disable check for recursion enabled on DNS servers. --transfer Perform zone transfer. --tld-expansion Perform TLD expansion. --subdomain-file SUBDOMAIN_FILE File with subdomains to check. --wildcard Enable wildcard detection. --wildcard-ip WILDCARD_IP IP address to use for wildcard detection. --no-color Disable colored output. --verbose Enable verbose output.
sonar history --since 1h
sonar history --json
# check
```
Имена и пины хранятся в базе данных sonar, привязанные к наиболее конкретной информации
об известном порте: запуск (`run:<group>/<name>`), контейнер
(`docker:<project>/<service>`), рабочая директория и номер порта
в конце. Переименованный dev-сервер сохраняет своё имя между перезапусками; имя, привязанное только к порту 3000, применяется к тому, что отвечает там. Эти три команды требуют
демона и запускают его, если он не работает.
### Чтение порта```sh
sonar info 3000 # command, user, bind, stats, health
sonar logs 3000 # tail; docker logs for containers
sonar wait 5432 3000 --timeout 60s # block until ready
sonar wait 5432 --http=/health # wait for HTTP 200-399, not just TCP
sonar next 3000 # first free port from 3000
sonar next 3000-3100 -n 3 # three consecutive free ports
sonar graph # who is connected to whom
sonar graph --dot # Graphviz
sonar open 3000 # open in the browser
sonar attach 3000 # shell into the container, or TCP
sonar watch # live view
sonar watch --stats --notify
```
Вот перевод:
- **`--no-verify`**: Пропускает проверку подписи и хеша. Используйте с осторожностью, так как это снижает безопасность.
- **`--output-dir <путь>`**: Указывает каталог для сохранения загруженных файлов. По умолчанию используется текущий каталог.
- **`--timeout <секунды>`**: Устанавливает тайм-аут для сетевых операций. По умолчанию — 30 секунд.
- **`--retries <число>`**: Количество повторных попыток при сбое загрузки. По умолчанию — 3.
- **`--proxy <url>`**: Использует указанный прокси-сервер для всех запросов. Поддерживает HTTP, HTTPS и SOCKS5.
- **`--user-agent <строка>`**: Задает пользовательский User-Agent для запросов. По умолчанию используется стандартный агент инструмента.
- **`--verbose`**: Включает подробный вывод для отладки. Показывает дополнительные сведения о процессе загрузки.
- **`--quiet`**: Подавляет весь вывод, кроме ошибок и критических предупреждений.
- **`--config <файл>`**: Загружает параметры из указанного файла конфигурации. Параметры командной строки имеют приоритет над значениями из файла.
- **`--list`**: Выводит список всех доступных инструментов и их краткое описание, затем завершает работу.
- **`--update`**: Проверяет наличие обновлений для инструмента и устанавливает их при обнаружении.
- **`--version`**: Отображает номер версии инструмента и завершает работу.
- **`--help`**: Показывает справочную информацию по использованию и завершает работу.
### Примеры использования
Ниже приведены несколько практических примеров, демонстрирующих типичные сценарии использования:
**Пример 1: Базовая загрузка с проверкой подписи**
```bash
./tool download https://example.com/file.tar.gz
```
Эта команда загружает указанный файл, автоматически проверяя его подпись и хеш, если они доступны.
**Пример 2: Загрузка в указанный каталог с подробным выводом**
```bash
./tool download https://example.com/package.zip --output-dir ./downloads --verbose
```
Загружает файл в каталог `downloads` и выводит подробную информацию о процессе.
**Пример 3: Использование прокси и пользовательского User-Agent**
```bash
./tool download https://example.com/archive.iso --proxy http://proxy.local:8080 --user-agent "Mozilla/5.0"
```
Загружает файл через указанный прокси-сервер с заданным User-Agent.
**Пример 4: Пропуск проверки для внутреннего доверенного источника**
```bash
./tool download https://internal.example.com/tool.bin --no-verify
```
Загружает файл без проверки подписи и хеша. Используйте только для доверенных источников.
**Пример 5: Загрузка нескольких файлов из списка**
```bash
./tool download --list urls.txt
```
Читает список URL-адресов из файла `urls.txt` и загружает каждый из них последовательно.
### Коды завершения
Инструмент возвращает следующие коды завершения для автоматизации сценариев:
| Код | Значение |
|-----|----------|
| `0` | Успешное завершение. |
| `1` | Общая ошибка (например, неверные аргументы). |
| `2` | Ошибка сети или тайм-аут. |
| `3` | Ошибка проверки подписи или хеша. |
| `4` | Файл уже существует и не был перезаписан. |
| `5` | Недостаточно прав для записи в целевой каталог. |
### Устранение неполадок
Если у вас возникли проблемы при использовании инструмента, ознакомьтесь со следующими распространенными решениями:
**Проблема: Ошибка «Не удалось проверить подпись»**
Убедитесь, что у вас установлены необходимые открытые ключи и что файл подписи (`.sig`) находится в том же каталоге, что и загружаемый файл. Если вы доверяете источнику, вы можете использовать флаг `--no-verify`, но делайте это на свой страх и риск.
**Проблема: Тайм-аут при загрузке больших файлов**
Увеличьте значение тайм-аута с помощью параметра `--timeout`. Например: `--timeout 120`. Также проверьте стабильность вашего сетевого соединения.
**Проблема: Загрузка завершается с кодом 4**
Это означает, что файл уже существует в целевом каталоге. Используйте флаг `--force` для перезаписи или удалите существующий файл вручную.
**Проблема: Прокси-сервер не работает**
Убедитесь, что URL прокси указан правильно и что прокси-сервер доступен. Для SOCKS5-прокси убедитесь, что формат URL — `socks5://хост:порт`.
### Лицензия
Этот инструмент распространяется под лицензией MIT. Вы можете свободно использовать, изменять и распространять его в соответствии с условиями лицензии. Полный текст лицензии доступен в файле `LICENSE` в репозитории проекта.
### Вклад в проект
Мы приветствуем вклад сообщества! Если вы хотите сообщить об ошибке, предложить новую функцию или отправить запрос на включение изменений, пожалуйста, посетите [страницу проекта на GitHub](https://github.com/example/tool) и следуйте рекомендациям по внесению вклада.
### Благодарности
Этот инструмент был бы невозможен без поддержки следующих проектов с открытым исходным кодом и сообществ:
- [Пример библиотеки](https://github.com/example/library) — за надежную обработку сетевых протоколов.
- [Пример криптографической библиотеки](https://github.com/example/crypto) — за безопасные реализации подписи и хеширования.
- Все участники и тестировщики, которые помогли улучшить этот инструмент.
### История версий
- **v1.0.0** — Первоначальный выпуск с базовой функциональностью загрузки и проверки.
- **v1.1.0** — Добавлена поддержка прокси-серверов и пользовательских User-Agent.
- **v1.2.0** — Введена проверка подписи и хеша по умолчанию.
- **v1.3.0** — Добавлена возможность загрузки из списка файлов и улучшена обработка ошибок.
- **v1.4.0** — Добавлена поддержка файлов конфигурации и расширенные параметры командной строки.
### Часто задаваемые вопросы (FAQ)
**Вопрос: Поддерживает ли инструмент возобновление прерванных загрузок?**
Да, начиная с версии v1.3.0, инструмент автоматически возобновляет прерванные загрузки, если сервер поддерживает диапазонные запросы (HTTP Range). Если загрузка была прервана, просто запустите ту же команду снова.
**Вопрос: Могу ли я использовать инструмент в скриптах CI/CD?**
Да, инструмент разработан для использования в автоматизированных средах. Он возвращает понятные коды завершения и поддерживает тихий режим для подавления ненужного вывода.
**Вопрос: Как инструмент проверяет подписи?**
Инструмент ищет файл подписи с расширением `.sig` рядом с загружаемым файлом. Если он найден, инструмент использует встроенную криптографическую библиотеку для проверки подписи с использованием доверенных открытых ключей, хранящихся в системном хранилище ключей или указанных в файле конфигурации.
**Вопрос: Безопасно ли использовать флаг `--no-verify`?**
Флаг `--no-verify` отключает проверку подписи и хеша, что делает загрузку уязвимой для атак типа «человек посередине» или подмены файлов. Используйте его только в том случае, если вы полностью доверяете источнику и сети.
### Заключение
Этот инструмент предоставляет надежный и безопасный способ загрузки файлов с проверкой целостности. Благодаря гибким параметрам командной строки и поддержке автоматизации, он подходит как для разовых загрузок, так и для интеграции в сложные рабочие процессы. Если у вас возникнут вопросы или предложения, не стесняйтесь обращаться к нам через [систему отслеживания проблем](https://github.com/example/tool/issues).
Спасибо за использование инструмента!```sh
sonar next 3000
sonar next 3000-3100 -n 3 --json
sonar graph --json
sonar info --help
# check
```
`sonar wait` завершается с кодом `0` (готов), `1` (таймаут) или `2` (прервано), что делает
его идеальным инструментом для вставки между запуском чего-либо и его тестированием:```sh
docker compose up -d
sonar wait 5432 3000 --timeout 60s && npm run migrate && npm run test
```
**Демон или прямое сканирование.** Каждая команда чтения спрашивает демона, если он
запущен, потому что у него уже есть ответ, и ему не нужно порождать `lsof`.
Если демон не запущен, они сканируют напрямую и выводят одно примечание в stderr об этом.
`sonar kill` следует тому же правилу: доступный демон выполняет завершение, поэтому он
немедленно пересканирует, и его следующий ответ — и история портов — уже знает,
что порт закрыт. Ни чтение, ни завершение не запускают демона за вашей спиной.
`--no-daemon` принудительно выполняет прямое сканирование без вывода сообщений и работает с любой командой:```sh
sonar list --no-daemon --json
# check
```
### `sonar host````sh
sonar host # cpu, load, memory and disk of the machine sonar watches
sonar host --json
```
```
## 🛡️ Возможности
- **Сканирование портов**: Быстрое обнаружение открытых портов и запущенных сервисов.
- **Обнаружение уязвимостей**: Проверка известных уязвимостей (CVE) в целевых системах.
- **Генерация отчётов**: Автоматическое создание подробных отчётов в форматах HTML и PDF.
- **Многопоточность**: Поддержка параллельного сканирования для ускорения работы.
- **Интеграция с API**: Возможность подключения к внешним сервисам для расширения функциональности.
## 📦 Установка
```bash
git clone https://github.com/example/tool.git
cd tool
pip install -r requirements.txt
```
## 🚀 Использование
```bash
python tool.py --target example.com --ports 1-1000
```
### Параметры командной строки
| Параметр | Описание | По умолчанию |
|----------|----------|--------------|
| `--target` | Целевой хост или IP-адрес | Обязательный |
| `--ports` | Диапазон портов для сканирования | `1-1024` |
| `--threads` | Количество потоков | `10` |
| `--output` | Путь для сохранения отчёта | `report.html` |
## 📄 Пример отчёта
```html
<!DOCTYPE html>
<html>
<head>
<title>Отчёт о сканировании</title>
</head>
<body>
<h1>Результаты сканирования example.com</h1>
<p>Открытые порты: 80, 443, 8080</p>
</body>
</html>
```
## 🤝 Вклад в проект
Если вы хотите внести свой вклад, пожалуйста, следуйте этим шагам:
1. Сделайте форк репозитория.
2. Создайте новую ветку (`git checkout -b feature/amazing-feature`).
3. Внесите изменения и закоммитьте их (`git commit -m 'Добавить новую функцию'`).
4. Отправьте изменения в ветку (`git push origin feature/amazing-feature`).
5. Откройте Pull Request.
## 📄 Лицензия
Этот проект распространяется под лицензией MIT. Подробности см. в файле [LICENSE](https://github.com/raskrebs/sonar/blob/main/LICENSE).
## 📬 Контакты
- **Автор**: Иван Иванов
- **Email**: [email protected]
- **GitHub**: [github.com/ivan](https://github.com/ivan)
``````sh
sonar host
# check
```
The daemon measures its own machine on the scan cadence and publishes it as the
`localhost` row of the snapshot's `hosts` collection: os and kernel, uptime, cpu
percent, load average, memory and the disk holding `/`. CPU percent is the work
done between two scans, so it is null until the daemon has scanned twice; a
figure a platform cannot produce — the load average on Windows, which has none —
is null rather than zero. Every host registered with `sonar remote add` joins
the same table with its own load. The command needs a running daemon: it is the
daemon that holds the previous sample a percentage is measured against.
### `sonar remote install````sh
sonar remote install [email protected] # same version as this sonar
sonar remote install hetzner --version v0.6.0 # a Host from ~/.ssh/config
sonar remote install deploy@box --no-service # the binary, no daemon
```
Размещает сонар на хосте, к которому у вас уже есть доступ по SSH, и запускает там его демон. Архив релиза скачивается и проверяется контрольной суммой **на удалённом хосте** — с этой машины ничего не копируется — а бинарник попадает в `~/.local/bin/sonar`, так что root не требуется. Демон работает как пользовательский юнит systemd там, где он есть (`~/.config/systemd/user/sonar.service`), и в откреплённом режиме там, где его нет; `loginctl enable-linger` выводится как рекомендация, когда пользовательская сессия завершится при выходе из системы и уведёт демон за собой.
Устанавливается версия того сонара, из которого вы его запустили, поэтому оба конца говорят на одном протоколе. Повторный запуск обновляет на месте и перезапускает демон — именно это делает установку и обновление одной и той же командой.
Цель передаётся в `ssh` без изменений: псевдоним `Host` из `~/.ssh/config` работает, как и заданные им `ProxyJump`, `IdentityFile` и `Port`. `--identity` и `--ssh-arg` предназначены для флагов, которые конфиг не покрывает.
### `sonar remote````sh
sonar remote add [email protected] # name taken from the target
sonar remote add hetzner [email protected] # or given
sonar remote list # status, latency, version, load
sonar remote remove hetzner
sonar list --host hetzner # that host's ports
sonar list --host "*" # every host, with a HOST column
sonar info 3000 --host hetzner
```
Зарегистрированный хост запускает тот же демон, и демон на этой машине держит
одно SSH-соединение с ним — `ssh <target> sonar daemon stdio` — и мультиплексирует
то, что тот сообщает, в состояние, которое уже читает каждый клиент. Ничего нового
нигде не слушает: сокет удалённого демона остаётся приватным для SSH-пользователя,
а клиенты сами никогда не говорят по SSH.
Каждая строка теперь несёт хост, с которого она пришла. Локальные строки говорят `localhost` и
сохраняют ключи, которые у них всегда были, так что ничего, что читает sonar сегодня, не меняется;
удалённые строки говорят зарегистрированное имя и ключуются как `<host>/<port>:<bind>`, что
и позволяет порту 3000 на двух машинах быть двумя строками. Подписчик видит только
localhost, если не запросит большего (`state.subscribe {"hosts": ["*"]}`).
Цель уходит в `ssh` нетронутой, так что алиасы `~/.ssh/config`, `ProxyJump` и
идентичности все применяются; `--ssh-arg`, `--identity` и `--port` покрывают то, чего
конфиг не делает. sonar не хранит ни пароля, ни ключа. Хост, который пропал, сохраняет свою
строку и свой статус, пока демон повторяет попытки, увеличивая паузу с одной секунды до
тридцати, пока тот остаётся зарегистрированным.
`--host` также по-прежнему принимает голый `user@host`, о котором sonar ничего не знает: он
откатывается к безагентному скану `ssh` + `ss`/`lsof` и печатает подсказку к
`sonar remote install`.
#### Действие на другой машине
Каждая запись тоже принимает `--host` и делает там ровно то же, что и здесь:```sh
sonar kill 3000 --host hetzner # stop a port on that machine
sonar kill -g api --host hetzner # a whole group of its services
sonar kill-all --filter docker --host hetzner # its containers
sonar up api --host hetzner # start a group from its .sonar.yaml
sonar logs 3000 --host hetzner # tail its output here
sonar rename 3000 storefront --host hetzner # its name, in its database
sonar assign 3000 storefront --host hetzner
```
Локальный демон пересылает вызов через мост этого хоста и возвращает то,
что ответил удалённый демон, в той же обёртке, в которой возвращается локальный вызов — каждая строка результата говорит, на каком хосте это произошло, а `affected` у kill несёт ключи `<host>/<port>:<bind>`, которые поток использует для этих строк. Потоковая команда работает в потоковом режиме: `sonar up --host` печатает каждый сервис по мере его запуска на той стороне, а Ctrl-C останавливает удалённую работу, а не только этот терминал.
Поскольку ключ строки уже называет её хост, клиент может передать его напрямую обратно как селектор — `{"key": "hetzner/3000:127.0.0.1"}` — это весь селектор целиком, включая хост. Один вызов действует на одну машину; указание двух — это ошибка, а не половина kill на каждой.
Две вещи остаются локальными. `sonar attach` помещает *этот* терминал перед процессом, поэтому он отказывается от `--host` и говорит подключиться по ssh и выполнить attach там. А сессия агента — это состояние, которое хранит этот демон, поэтому у `sonar kill --session` нет удалённой формы. Всё остальное требует, чтобы демон работал здесь — именно здесь живёт соединение с другой машиной — и сообщает об этом, вместо того чтобы молча сканировать эту машину.
`sonar up --host` требует указания группы: `.sonar.yaml` в вашей рабочей директории — это путь на этой машине, и именно удалённый демон читает файл и запускает сервисы.
### Демон
Один фоновый процесс сканирует порты, разрешает группы, опрашивает состояние здоровья, ведёт базу данных и передаёт изменения в потоковом режиме всем подписчикам — CLI, десктопному приложению и редакторам.```sh
sonar serve # in the foreground
sonar serve --detach # in the background
sonar daemon status # pid, uptime, subscribers, scans, intervals
sonar daemon path # the socket it listens on
sonar daemon log -n 50 -f # what it is doing
sonar daemon restart
sonar daemon stop
```
I need the actual content of chunk 77 to translate it. Please provide the Markdown text you want translated.```sh
sonar daemon path
sonar daemon status --json
sonar daemon log -n 5
# check
```
| Что | Где |
|---|---|
| Сокет | `$XDG_RUNTIME_DIR/sonar/daemon.sock`, иначе `~/.config/sonar/daemon.sock`; `\\.\pipe\sonar` в Windows |
| База данных | `~/.config/sonar/sonar.db` (`SONAR_DB` переопределяет) |
| Журнал демона | `~/.config/sonar/daemon.log`, ротация при 5 МиБ, хранится три |
| Журналы запуска | `~/.config/sonar/logs/<group>/<service>.log` |
| Конфигурация | `~/.config/sonar/config.yaml` |
`SONAR_SOCKET` переопределяет путь к сокету везде, как для демона, так и для
его клиентов — полезно для второго изолированного экземпляра. Сокет создаётся
с правами 0600 в каталоге с правами 0700, поэтому общаться с ним можете только вы. Одновременно работает только один демон;
сокет, оставшийся после сбоя, очищается при следующем запуске.
Демон останавливается сам через 30 минут без клиентов и без
подписчиков. Установите `daemon.idle_timeout` в файле конфигурации, чтобы изменить это, или
`0`, чтобы он работал постоянно.
Порты сканируются каждые 2 секунды, пока что-то меняется; когда ничего не меняется,
сканер замедляется до 5 секунд при подключённом подписчике и до 10
секунд без него. `daemon.scan_interval` сдвигает эту базу — минимум 1 с — и
оба верхних предела масштабируются вместе с ней, поэтому увеличение до `5s` снижает частоту до 12,5 с и 25 с,
а не фиксирует кривую на старых пределах. `daemon.stats_interval` — это
отдельный такт, с которым обновляются cpu, память и нагрузка хоста, пока
что-то подписано. Оба значения считываются при запуске демона: отредактируйте файл,
затем `sonar daemon restart`. `sonar daemon status` выводит действующие
значения (`scan base`, `stats tick`) рядом с адаптивным интервалом, с которым сканер
работает прямо сейчас.
Подписчик, запрашивающий `include: ["health"]`, заставляет демона проверять **каждый
слушающий порт** с более медленным тактом, а не только службы, объявляющие
путь `health:` — те опрашиваются на каждом такте и доходят до каждого подписчика,
независимо от того, запрашивалось ли здоровье.
### Конфигурация
`~/.config/sonar/config.yaml` необязателен; флаги всегда имеют приоритет.```sh
sonar config path
sonar config init
# check
```
## Установка
### Требования
- Python 3.8+
- pip
### Установка из PyPI
```bash
pip install pycryptodome
```
### Установка из исходного кода
```bash
git clone https://github.com/example/repository.git
cd repository
pip install -r requirements.txt
```
## Использование
### Базовое использование
```python
from crypto_tool import encrypt_file, decrypt_file
# Шифрование файла
encrypt_file("input.txt", "output.enc", "your-password")
# Расшифровка файла
decrypt_file("output.enc", "decrypted.txt", "your-password")
```
### Расширенные параметры
| Параметр | Описание | По умолчанию |
|----------|----------|--------------|
| `--algorithm` | Алгоритм шифрования | `AES-256-GCM` |
| `--iterations` | Количество итераций KDF | `100000` |
| `--salt` | Пользовательская соль (hex) | Случайная |
| `--verbose` | Подробный вывод | `False` |
### Примеры
```bash
# Шифрование с пользовательским алгоритмом
python cli.py encrypt --input secret.txt --output secret.enc --algorithm AES-256-CBC
# Пакетное шифрование нескольких файлов
python cli.py encrypt-batch --directory ./documents --output ./encrypted
```
## API
### Класс `CryptoManager`
Основной класс для операций шифрования.
```python
from crypto_tool import CryptoManager
manager = CryptoManager(
algorithm="AES-256-GCM",
iterations=100000
)
# Шифрование данных
encrypted = manager.encrypt(b"Секретные данные", "пароль")
# Расшифровка данных
decrypted = manager.decrypt(encrypted, "пароль")
```
### Функции
- `generate_key(password, salt, iterations)` — генерирует ключ шифрования из пароля.
- `generate_salt(size=16)` — генерирует случайную соль.
- `hash_password(password)` — создаёт безопасный хэш пароля.
## Конфигурация
Файл конфигурации `config.yaml`:
```yaml
encryption:
algorithm: AES-256-GCM
iterations: 100000
key_length: 32
logging:
level: INFO
file: crypto_tool.log
```
## Тестирование
Запуск тестов:
```bash
pytest tests/
```
## Лицензия
MIT License — см. файл [LICENSE](https://github.com/raskrebs/sonar/blob/main/LICENSE) для подробностей.```sh
sonar config edit # open it in $EDITOR
```
```
## 🛡️ Возможности
- **Сканирование портов**: Быстрое обнаружение открытых портов и запущенных сервисов.
- **Обнаружение уязвимостей**: Проверка известных уязвимостей (CVE) в целевых системах.
- **Анализ конфигурации**: Оценка параметров безопасности веб-серверов и сетевых устройств.
- **Генерация отчётов**: Автоматическое создание подробных отчётов в форматах HTML и PDF.
- **Поддержка прокси**: Работа через HTTP/HTTPS/SOCKS5 прокси для анонимности.
- **Многопоточность**: Высокая производительность благодаря параллельной обработке задач.
- **Интеграция с API**: Возможность подключения к сторонним сервисам через REST API.
- **Логирование**: Детальная запись всех действий в журнал для последующего анализа.
## 📦 Установка
```bash
git clone https://github.com/example/tool.git
cd tool
pip install -r requirements.txt
```
## 🚀 Использование
```bash
python tool.py --target example.com --scan all
```
### Основные параметры
| Параметр | Описание |
|----------|----------|
| `--target` | Целевой хост или IP-адрес |
| `--scan` | Тип сканирования (`all`, `port`, `vuln`) |
| `--threads` | Количество потоков (по умолчанию: 10) |
| `--proxy` | Прокси-сервер в формате `http://user:pass@host:port` |
| `--output` | Формат отчёта (`html`, `pdf`, `json`) |
| `--verbose` | Подробный вывод в консоль |
## 📝 Примеры
### Сканирование портов
```bash
python tool.py --target 192.168.1.1 --scan port --threads 50
```
### Проверка уязвимостей
```bash
python tool.py --target example.com --scan vuln --output html
```
### Использование прокси
```bash
python tool.py --target example.com --proxy socks5://127.0.0.1:9050
```
## 🔧 Конфигурация
Файл конфигурации `config.yaml` позволяет настроить поведение инструмента:
```yaml
scan:
timeout: 5
retries: 3
ports: [21, 22, 80, 443, 8080]
report:
format: html
include_cve: true
include_recommendations: true
proxy:
enabled: false
type: http
host: ""
port: 0
```
## 🤝 Вклад в проект
Мы приветствуем вклад сообщества! Пожалуйста, следуйте этим шагам:
1. Форкните репозиторий.
2. Создайте ветку для вашей функции (`git checkout -b feature/amazing-feature`).
3. Зафиксируйте изменения (`git commit -m 'Добавлена новая функция'`).
4. Отправьте изменения в ветку (`git push origin feature/amazing-feature`).
5. Откройте Pull Request.
## 📄 Лицензия
Распространяется под лицензией MIT. См. файл `LICENSE` для получения дополнительной информации.
## 📧 Контакты
- **Автор**: Иван Иванов
- **Email**: [email protected]
- **Сайт**: [https://example.com](https://example.com)
``````yaml
list:
columns: [port, process, group, container, image, containerport, url]
sort: port # port | pid | name | type
filter: "" # docker | user | system | "" (all)
all: false # include desktop apps by default
daemon:
idle_timeout: 30m # 0 keeps the daemon running
log_level: info # debug | info | warn | error
scan_interval: 2s # base port-scan cadence, minimum 1s
stats_interval: 1s # cpu/memory refresh while subscribed, minimum 250ms
color: true
services: # label custom/unknown ports
9000: php-fpm
5050: my-dashboard
```
Недопустимые значения игнорируются с предупреждением, и sonar продолжает работу с настройками по умолчанию.
Переопределения окружения, у которых нет ключа конфигурации: `SONAR_DB`, `SONAR_SOCKET`,
`SONAR_NO_HINTS=1` для отключения уведомлений о миграции ниже, и
`SONAR_NO_AUTOSTART=1` для остановки любого клиента sonar от запуска демона, который он не
нашёл — полезно в CI, где сборка никогда не должна оставлять процесс после себя.
Собственный набор тестов sonar устанавливает `SONAR_NO_AUTOSTART=1` для каждого тестового бинарника и,
после запуска, ищет демон, который его пережил. Этот ограничитель заявляет только о
`serve`, запущенном из приватного временного корня запуска, поэтому два набора, работающие бок о бок
на одной машине, не трогают демоны друг друга;
`SONAR_TESTENV_GATE_ALL=1` расширяет его обратно на каждый `sonar serve` где угодно в пределах
временного каталога, что и нужно CI-раннеру, владеющему всей машиной.
### Агенты: MCP, навыки и хуки```sh
sonar install mcp --claude-code # merge into <git root>/.mcp.json
sonar install mcp --cursor --scope user # ~/.cursor/mcp.json
sonar install mcp --codex # codex mcp add
sonar install skills --claude-code # the bundled sonar skill
sonar install hooks --claude-code # optional, see below
```
```
## 📦 Установка
### 🐍 Установка с помощью pip
```bash
pip install kitploit-tool
```
### 🐳 Установка с помощью Docker
```bash
docker pull kitploit/tool:latest
docker run -it --rm kitploit/tool:latest
```
### 📦 Установка из исходного кода
```bash
git clone https://github.com/kitploit/kitploit-tool.git
cd kitploit-tool
pip install -r requirements.txt
python setup.py install
```
## 🚀 Быстрый старт
После установки вы можете начать использовать инструмент с помощью следующей команды:
```bash
kitploit-tool --help
```
Для сканирования цели:
```bash
kitploit-tool scan -t https://example.com
```
## ⚙️ Конфигурация
Инструмент можно настроить с помощью файла конфигурации, расположенного по адресу `~/.kitploit/config.yaml`. Пример конфигурации:
```yaml
# Пример конфигурации
target: https://example.com
threads: 10
timeout: 30
verbose: false
output: results.json
```
## 🛠️ Использование
### Основные параметры
| Параметр | Описание |
|----------|----------|
| `-t, --target` | Целевой URL или IP-адрес |
| `-o, --output` | Файл вывода для результатов |
| `-v, --verbose` | Включить подробный вывод |
| `--threads` | Количество потоков (по умолчанию: 10) |
| `--timeout` | Таймаут запроса в секундах (по умолчанию: 30) |
### Примеры
Сканирование с пользовательскими параметрами:
```bash
kitploit-tool scan -t https://example.com --threads 20 --timeout 60 -v
```
Сохранение результатов в файл:
```bash
kitploit-tool scan -t https://example.com -o report.json
```
## 📊 Выходные данные
Инструмент поддерживает несколько форматов вывода:
- **JSON** — структурированный вывод для машинной обработки
- **CSV** — табличный формат для электронных таблиц
- **Plain Text** — удобочитаемый формат для просмотра в терминале
## 🤝 Вклад в проект
Мы приветствуем вклад в проект! Пожалуйста, ознакомьтесь с нашими [рекомендациями по вкладу](https://github.com/raskrebs/sonar/blob/main/CONTRIBUTING.md) перед отправкой запроса на включение изменений.
## 📄 Лицензия
Этот проект распространяется под лицензией MIT. Подробности см. в файле [LICENSE](https://github.com/raskrebs/sonar/blob/main/LICENSE).
## 📧 Контакты
Если у вас есть вопросы или предложения, не стесняйтесь открывать issue в репозитории или связываться с нами по адресу [[email protected]](mailto:[email protected]).
## 🙏 Благодарности
- Всем участникам проекта
- Сообществу Kitploit за поддержку и отзывы
- Всем, кто сообщал об ошибках и предлагал улучшения
``````sh
sonar install mcp --generic --print
sonar install skills --print
sonar install hooks --print
# check
```
`install mcp` регистрирует `{"command": "sonar", "args": ["mcp"]}` и оставляет все остальные
серверы и ключи в файле нетронутыми; повторный запуск ничего не меняет, а
`--uninstall` удаляет ровно то, что записал sonar.
`sonar mcp` — это и есть тот сервер: встроенный в бинарник stdio MCP-сервер, который
даёт агенту представление демона о машине. Он читает с помощью `list_ports` и
`inspect_port`, ожидает с помощью `wait_for_port`, выбирает и резервирует порты с помощью
`next_free_port` и `claim_port`, а на остальные вопросы агента отвечает
через `tail_logs`, `health_check`, `dependency_graph`, `port_history` и
`list_sessions`; действия и ресурсы идут следом. Он запускает демона, если тот не
работает, и сам переподключается, если тот пропадает; его логи идут в stderr,
потому что stdout несёт протокол.
`install skills` записывает встроенный навык, который учит агента запускать
серверы с помощью `sonar start --`, использовать `sonar wait` вместо сна и
убирать за собой то, что он запустил. `install hooks` добавляет два хука Claude Code: один
экспортирует `SONAR_SESSION`, чтобы всё, что запускает сессия, приписывалось ей, другой
предлагает `sonar start --`, когда вот-вот запустится голый dev-сервер (он
советует, но никогда не блокирует). Оба принимают `--scope project|user`, `--print` и
`--uninstall`.
### `sonar doctor`
Одна команда, которая проверяет всё, от чего зависит sonar, и говорит, что делать с тем,
что не так. Именно её запускает десктопное приложение при онбординге, и именно её
стоит запускать самому, когда что-то работает не так.```sh
sonar doctor # the table, and a one-line verdict
sonar doctor --json # {ok, checks, version, daemon_version}
sonar doctor --only db_ok,tray # just these
sonar doctor --only mcp_registered # a whole family
sonar doctor --project ~/code/api # a project other than the working directory
sonar doctor --fix --yes # apply the safe repairs, then check again
```
(no input provided)```sh
# check
sonar doctor --only daemon_reachable,daemon_protocol,socket_permissions,db_ok
sonar doctor --json --only config_parses | grep -q '"status": "ok"'
sonar doctor --only mcp_registered --project . > /dev/null
```
Каждая проверка сообщает `ok`, `warn`, `fail` или `skip`. `skip` означает, что
нечего было проверять — Cursor не установлен, на машине нет docker, сокет
является именованным каналом на Windows — и никогда не засчитывается против вас.
Код выхода равен 0, если только что-то не **провалилось**, поэтому `sonar doctor`
уместен в установочном скрипте.
| проверка | что она означает |
| --- | --- |
| `cli_on_path` | бинарник, который вы запустили, — тот, что разрешает PATH; указывает на затеняющую установку, если это не так |
| `cli_version_current` | сравнивается с последним релизом, или `skip`, когда GitHub недоступен за 2 секунды |
| `config_parses` | ваш `config.yaml` загружается; синтаксическая ошибка сообщается со строкой, столбцом и указателем |
| `config_dir_writable` | демон может записывать свой журнал, блокировку и базу данных |
| `daemon_reachable` | что-то прослушивает сокет |
| `daemon_version_matches` | запущенный демон — это версия CLI, которую вы используете |
| `daemon_protocol` | основная версия протокола демона совпадает с версией этой сборки |
| `socket_permissions` | сокет принадлежит вам и имеет права 0600, в каталоге с правами 0700 (`skip` на Windows) |
| `db_ok` | база данных открывается, находится на новейшей схеме, и насколько она велика |
| `mcp_registered.{claude_code,cursor,codex}` | MCP-сервер sonar находится в конфигурации этого клиента |
| `skills_installed` | встроенный навык установлен и актуален |
| `hooks_installed` | дополнительные хуки Claude Code установлены |
| `project_config` | у этого проекта есть `.sonar.yaml`, который загружается |
| `docker` | CLI docker присутствует, и его демон отвечает |
| `desktop_installed` | настольное приложение установлено, и какая версия (`skip` на Windows) |
| `tray` | устаревший бинарник macOS `sonar-tray` всё ещё присутствует |
`--fix` применяет только те исправления, которые безопасно выполнять без
присмотра, и сначала спрашивает, если вы не передали `--yes`: он перемещает
нераспознаваемый `config.yaml` в `config.yaml.broken-<timestamp>` и записывает
новый шаблон (ничего никогда не удаляется), перезапускает демон, который не
запущен, и выполняет команду `sonar install mcp|skills|hooks`, которую называет
проверка — из рабочего каталога, так, как вы бы её ввели, поэтому запускайте
`--fix` внутри проекта, который вы чините, а не указывая `--project` на него.
Затем он проверяет снова. Всё, чего он не коснётся — затеняющий бинарник на
PATH, навык, который sonar не записывал, — остаётся вам с точной командой в
столбце `fix`.
Настольное приложение вызывает те же проверки через метод `daemon.doctor`
демона, а не через внешние вызовы. Демон выполняет всё, что может, из своего
собственного процесса; три проверки, которые касаются вызванного вами бинарника
CLI (`cli_on_path`, `cli_version_current`, `daemon_version_matches`), возвращаются
как `skip` с пояснением об этом.
### Настольное приложение
Приложение Sonar — это та же картина в окне и в строке меню или системном
трее: группы сбоку, порты в сетке с живой статистикой и состоянием здоровья,
журналы и кнопки для всего вышеперечисленного. Оно общается с тем же демоном,
поэтому CLI и приложение никогда не расходятся во мнениях. `sonar install desktop`
устанавливает его, а `sonar tray` запускает его.
Пока приложение не выпущено, релизные архивы macOS всё ещё содержат старый
бинарник строки меню `sonar-tray`, и `sonar tray` переключается на него, когда
приложение не установлено.
### `sonar install desktop`
Приложение находится в бета-версии и ещё не подписано Apple, поэтому CLI
устанавливает его:```sh
brew install raskrebs/sonar/sonar && sonar install desktop
```
Вот и вся тестовая установка. Sonar получает манифест опубликованных сборок,
выбирает ту, что подходит для вашей машины, проверяет её sha256 и размер,
устанавливает её и открывает.
**Именно поэтому загрузку выполняет CLI.** macOS добавляет атрибут карантина
всему, что сохраняет *браузер*, и Gatekeeper отказывается открывать
приложение с карантином, которое Apple не нотариально заверила. Файл, который
загружает этот CLI, изначально не получает этот атрибут, поэтому бета-версия
открывается без запроса и без танцев с «Открыть через контекстное меню».
Sonar не устанавливает и не снимает атрибуты карантина — снимать нечего.```sh
sonar install desktop # install and launch
sonar install desktop --no-launch # install only
sonar install desktop --update # update; does nothing if current
sonar install desktop --check # exit 1 when an update is available
sonar install desktop --version 0.1.0-beta.1
sonar install desktop --force # ask a running Sonar to quit first
sonar install desktop --json # for scripts
```
Команде не нужна сеть, чтобы сообщить вам, что она делает:```sh
sonar install desktop --help | grep -- '--no-launch'
# check
```
Куда он устанавливается:
| | |
| --- | --- |
| macOS | `/Applications/Sonar.app` или `~/Applications/Sonar.app`, если первая папка недоступна для записи (sonar никогда не использует `sudo`) |
| Linux | `~/.local/opt/sonar-desktop/Sonar.AppImage`, плюс пункт меню в `~/.local/share/applications` и ссылка `sonar-desktop` в `~/.local/bin` |
| Windows | пока нет — команда сообщает об этом и завершается с кодом 1 |
`--dir` переопределяет каталог в обоих случаях. На Linux `--deb` устанавливает `.deb`
через `apt`/`dpkg` вместо AppImage, если релиз публикует такой пакет.
Установка атомарна: новое приложение распаковывается рядом со старым и заменяет
его через переименование, так что неудачная загрузка никогда не оставит вас без рабочего приложения.
Если приложение открыто, sonar отказывается выполнять замену, а не подменяет бандл под ним;
`--force` просит его завершиться и ждёт до десяти секунд.
`sonar install desktop` записывает `desktop.installed_version` и
`desktop.installed_path` в `~/.config/sonar/config.yaml` — именно так `sonar
tray` находит приложение, установленное с `--dir`, и так проверка
`desktop_installed` в `sonar doctor` узнаёт версию. Откуда берутся сборки, задаётся
через `desktop.download_base`, переопределяемый переменной `SONAR_DESKTOP_BASE`, а затем
`--base` — укажите в них свою собственную сборку, чтобы протестировать её.
### `sonar relay`
Relay — это серверная часть sonar: один небольшой HTTP-сервис, который мы запускаем для
хостингового приложения и публикуем как `ghcr.io/raskrebs/sonar-relay`, чтобы вы могли
запустить свой собственный. Он не имеет ничего общего с локальным демоном — `sonar serve` следит
за вашими портами, а `sonar relay serve` отвечает на HTTP-запросы для целого парка устройств — и поставляется
в том же бинарнике только для того, чтобы был один артефакт для развёртывания.
Сегодня он собирает анонимную продуктовую телеметрию: пакет именованных событий на
каждую установку, без путей, без имён хостов, без URL — и отклоняет их на входе, если значение
хотя бы похоже на одно из них. Это тот же сервис, который позже будет завершать открытые
туннели и обрабатывать вход в систему.```sh
sonar relay serve --db ./relay.db --project-keys "$(openssl rand -hex 24)"
```
`docs/RELAY.md` содержит маршруты, точные правила валидации, схему хранилища
и развёртывание одной командой за Caddy на любом хосте с Docker.
## Переход со старых команд
Команды до введения групп по-прежнему работают и выводят одну строку в stderr с указанием того,
что их заменило. Они исчезнут через один минорный релиз. `SONAR_NO_HINTS=1`
отключает уведомления, а вывод `--json` их никогда не содержит.
| Старая | Новая |
|---|---|
| `sonar run --tag X -- cmd` | `sonar start --group X -- cmd` |
| `sonar runs` | `sonar start --list` |
| `sonar list --tag X` | `sonar list --group X` |
| `sonar kill-all --filter docker` | `sonar kill --all --filter docker` |
| `sonar down X` | `sonar kill -g X` |
| `sonar profile create X` | `sonar init` |
| `sonar profile show X` | `sonar groups X` |
| `sonar up X` (проверял профиль) | `sonar up X` теперь *запускает* группу |
| `sonar tray` (приложение в строке меню Swift) | `sonar tray` запускает десктопное приложение |
Профили были снимком портов на конкретной машине; `.sonar.yaml` фиксируется вместе с
проектом. Преобразуйте его и прочитайте, прежде чем оставить — ничего не записывается
за вас:```sh
sonar profile list
# check
```
I need the actual content of chunk 103 to translate it. Please provide the Markdown text you want translated.```sh
sonar profile export my-app > .sonar.yaml
```
Профиль никогда не записывает, как запускается служба, поэтому в предложении есть порты, имена и пути проверки здоровья, а вы заполняете `cmd`.
## Устранение неполадок
**Что-то не так с демоном.** `sonar daemon log -f`, пока вы воспроизводите проблему, и `sonar daemon status` для получения pid, времени работы и количества сканирований. Остановите его с помощью `sonar daemon stop`; все команды чтения продолжают работать и без него.
**«daemon unavailable, using direct scan».** На сокете никто не слушает. Это нормально — чтение не запускает демон. Выполните `sonar serve -d`, если он вам нужен.
**Сокет, оставшийся после сбоя.** `sonar daemon path` показывает его; запуск демона сам удаляет устаревший сокет. Если второй демон отказывается запускаться, пока первый исчез, `sonar daemon restart` снимает блокировку.
**Порты отсутствуют в списке.** Процессы, принадлежащие другому пользователю, невидимы без привилегий; sonar сообщает об этом под таблицей. Повторно выполните `sudo sonar list`, чтобы увидеть их. В Linux должна быть установлена утилита `ss` (`iproute2`); в Windows используется `netstat`.
**Убийство процесса ничего не дало.** Контейнеры Docker останавливаются через демон Docker: проверьте `docker ps`. Процесс, игнорирующий SIGTERM, требует `-f`, а процесс, управляемый чем-то другим (systemd, Compose `restart: always`), возвращается по замыслу — остановите супервизор.
**Ничего не работает, и вы не знаете почему.** `sonar doctor` проверяет бинарный файл, конфигурацию, демон, базу данных и все интеграции за один раз и выводит команду, которая исправляет каждую найденную проблему.
**Сообщение об ошибке.** Включите следующее, а также последние строки `sonar daemon log`:```sh
sonar version
sonar daemon status
sonar doctor --json
# check
```
## Поддерживаемые платформы
- macOS (использует `lsof`)
- Linux (использует `ss`)
- Windows (использует `netstat`)
Для группировки требуется рабочая директория каждого процесса, и теперь она есть
на каждой платформе: `/proc` на Linux, `lsof` на macOS, а на Windows — чтение
собственного PEB процесса. Поэтому группы по корню git-репозитория, `project_root` и имена на основе cwd работают одинаково
везде, и `sonar init` может предложить `.sonar.yaml` на основе того, что прослушивается
на любой из трёх платформ.
Десктопное приложение пока уже: `sonar install desktop` устанавливает его на
macOS (Apple Silicon и Intel) и Linux (x86_64 и aarch64). На Windows
команда сообщает, что приложение пока недоступно, и завершается с кодом 1.
Единственный пробел — 32-битный `sonar.exe` на 64-битной Windows: он не может прочитать память
64-битного процесса, поэтому такие порты возвращаются без рабочей директории и
выпадают из своей группы по корню git-репозитория. Используйте 64-битную сборку — она читает как 64-битные, так и 32-битные
процессы. В остальных случаях порт, процесс которого запрещает доступ (сервис,
работающий от имени другого пользователя, защищённый системный процесс), просто остаётся
без рабочей директории; остальная часть сканирования не затрагивается.
## Участники
Спасибо всем, кто внёс вклад в sonar!
<a href="https://github.com/RasKrebs/sonar/graphs/contributors">
<img src="https://stg.contrib.rocks/image?repo=RasKrebs/sonar" />
</a>