function ai { <# .SYNOPSIS Red Team AI Terminal Assistant полностью inmemory реализация на PowerShell. .DESCRIPTION Скрипт собирает системную информацию, использует встроенную YAML-конфигурацию для формирования подсказок, генерирует JSONpayload и обращается к Groq API (используя переменную OPENAI_API_KEY, имя не меняется). Вся логика выполняется в памяти без доступа к диску подход Red Team для минимизации следов. .PARAMETER InputCommand Естественная языковая команда для преобразования в команду терминала. .EXAMPLE ai -InputCommand "организовать эти файлы семантически в текущем каталоге по дате" #> #region Системные функции function Get-SystemInfo { $osInfo = Get-CimInstance Win32_OperatingSystem $osCaption = $osInfo.Caption $osVersion = $osInfo.Version $machine = $env:COMPUTERNAME $processor = (Get-CimInstance Win32_Processor).Name return "OS: $osCaption, Version: $osVersion, Machine: $machine, Processor: $processor" } function Get-WorkingDirectory { return (Get-Location).Path } function Get-PackageManagers { $pmList = @("choco", "scoop", "winget", "npm", "pip") $installed = @() foreach ($pm in $pmList) { if (Get-Command $pm -ErrorAction SilentlyContinue) { $installed += $pm } } return $installed -join ", " } function Get-ShellVersion { return $PSVersionTable.PSVersion.ToString() } #endregion #region Функция замены плейсхолдеров в шаблоне function Replace-Placeholders { param( [string]$Template, [hashtable]$Values ) foreach ($key in $Values.Keys) { $Template = $Template -replace "\{$key\}", [regex]::Escape($Values[$key]) } return $Template } #endregion #region Встроенная YAML-конфигурация (inmemory) $PromptsYaml = @" common: messages: - role: system content: | You're a {shell} terminal assistant, and your job is to translate natural language instructions to a single raw, executable {shell} command. Это должна быть одна команда на одной строке или несколько команд, разбросанных по нескольким строкам (без сепараторов, таких как ; или &&). Дайте краткое объяснение в {shell} комментариях перед командой. Используйте самую благоприятную версию команды. Если вам нужно использовать команду, которая недоступна в системе, объясните в комментарии, что она делает, и предложите ее установить. Если инструкция неясна, используйте комментарий, чтобы попросить разъяснения. Если вам нужно вывести буквальную строку, которую пользователь должен написать, что не является командой или комментарием, префикс ее #>. Use cli tools where possible (such as gh, aws, azure). The shell is running on the following system: {system_info} Shell version: {shell_version}. Current working directory: {working_directory}. If installing a package is required, use one of the following managers, which are already installed: {package_managers}. The user has {sudo} access. - role: user content: play a game with me - role: assistant content: > # I can only provide you with {shell} commands. I can't play games with you. powershell: messages: - role: user content: list files - role: assistant content: | # Show all files and folders in the current directory (including hidden ones). Get-ChildItem bash: messages: - role: user content: list files - role: assistant content: | # Show all files and folders in the current directory (including hidden ones). ls -a "@ $Prompts = $PromptsYaml | ConvertFrom-Yaml #endregion #region Формирование сообщений для запроса к API function Generate-ChatGPTMessages { param( [string]$InputText ) $values = @{ shell = "powershell" system_info = Get-SystemInfo working_directory= Get-WorkingDirectory package_managers = Get-PackageManagers sudo = "no" # В Windows sudo отсутствует shell_version = Get-ShellVersion } $commonMessages = @() foreach ($msg in $Prompts.common.messages) { $content = Replace-Placeholders -Template $msg.content -Values $values $commonMessages += @{ role = $msg.role; content = $content } } $shellMessages = @() if ($Prompts.PSObject.Properties.Name -contains "powershell") { foreach ($msg in $Prompts.powershell.messages) { $shellMessages += $msg } } else { foreach ($msg in $Prompts.bash.messages) { $shellMessages += $msg } } $userMessage = @{ role = "user"; content = $InputText } return $commonMessages + $shellMessages + $userMessage } #endregion #region Обращение к Groq API function Get-BashCommand { param( [array]$Messages ) $apiKey = $env:OPENAI_API_KEY if (-not $apiKey) { Write-Error "OPENAI_API_KEY environment variable is not set." return $null } $uri = "https://api.groq.com/openai/v1/chat/completions" $payload = @{ model = "qwen-2.5-32b" messages = $Messages max_tokens = 1000 temperature = 0.7 } $jsonPayload = $payload | ConvertTo-Json -Depth 10 # Перекодируем в UTF-8 и удаляем возможный BOM (символ U+FEFF) $jsonPayload = [System.Text.Encoding]::UTF8.GetString([System.Text.Encoding]::UTF8.GetBytes($jsonPayload)) $jsonPayload = $jsonPayload -replace "^\uFEFF", "" $headers = @{ "Authorization" = "Bearer $apiKey" "Content-Type" = "application/json; charset=utf-8" "Accept-Charset" = "utf-8" } try { $response = Invoke-RestMethod -Method Post -Uri $uri -Headers $headers -Body $jsonPayload return $response.choices[0].message.content.Trim() } catch { Write-Error "API error: $($_.Exception.Message)" return $null } } #endregion #region Вывод команд с цветовой подсветкой function Show-Commands { param( [string]$CommandsText ) $lines = $CommandsText -split "`n" foreach ($line in $lines) { if ($line.TrimStart().StartsWith("#")) { Write-Host $line -ForegroundColor Green } else { Write-Host $line -ForegroundColor Yellow } } } #endregion #region Основная функция ai function ai { [CmdletBinding()] param( [Parameter(Mandatory=$true)] [string]$InputCommand ) Write-Host " Processing..." -ForegroundColor Cyan $messages = Generate-ChatGPTMessages -InputText $InputCommand $bashCommand = Get-BashCommand -Messages $messages if ($bashCommand) { Write-Host " Response received:" -ForegroundColor Cyan Show-Commands -CommandsText $bashCommand } else { Write-Error "Failed to get command from API." } } #endregion #region Автозапуск при загрузке через IEX if ($args.Count -gt 0) { ai -InputCommand ($args -join " ") } else { Write-Host "Usage: ai -InputCommand 'your command here'" -ForegroundColor Magenta } #endregion }