Skip to content

Instantly share code, notes, and snippets.

@b4tman
Last active February 16, 2024 06:41
Show Gist options
  • Save b4tman/347e08f83d6f3e569200 to your computer and use it in GitHub Desktop.
Save b4tman/347e08f83d6f3e569200 to your computer and use it in GitHub Desktop.
Скрипт отрубающий всех (на клиентском компе) забывчивых от сервера 1с, с обратным отсчетом. Прописывается в планировщик на конец рабочего дня.
# --------------- раздел переменных -----------------------------------
New-Variable -Name log_file -Value "C:\1C\1c_close.log" -Option Constant
New-Variable -Name server -Value "server1c" -Option Constant #сервер 1С
New-Variable -Name admin_user -Value "" -Option Constant # пользователь - администратор кластера
New-Variable -Name admin_pass -Value "" -Option Constant # пароль администратора кластера
New-Variable -Name client -Value $env:computername.ToUpper() -Option Constant # имя хоста текущей машины
$Title = @"
Автоматическое завершение сеансов на сервере 1С.
Следующие сеансы будут завершены:`n
"@
$close_msg = @"
Закрытие сеанса #{0}: "{1}" ( {2} ) @ {3} - {4}
"@
$COMConnector = $null # объект для подключения
$agent = $null # агент управления
$cluster = $null # описание кластера серверов 1С предприятия
$to_close = @() # массив сеансов подлежащих закрытию
# --------------- раздел функций -----------------------------------
function global:Write-log # Функция пишет сообщения в лог-файл и выводит на экран.
{param($message,[string]$type="info",[string]$logfile=$log_file,[switch]$silent)
$dt=Get-Date -Format "dd.MM.yyyy HH:mm:ss"
$msg=$dt + "`t" + $type + "`t" + $message #формат: 01.01.2001 01:01:01 [tab] error [tab] Сообщение
Out-File -FilePath $logfile -InputObject $msg -Append -encoding unicode
if (-not $silent.IsPresent)
{
switch ( $type.toLower() )
{
"error"
{
$global:errorcount++
write-host $msg -ForegroundColor red
}
"warning"
{
$global:warningcount++
write-host $msg -ForegroundColor yellow
}
"completed"
{
write-host $msg -ForegroundColor green
}
"info"
{
write-host $msg
}
default
{
write-host $msg
}
}
}
}
function global:CountDown # Функция выводит на экран обратный отсчет + позволяет отказаться или подтвердить действие нажатием клавиш
{param([int]$Minutes=1)
New-Variable -Name timeText -Value "{0}:{1}:{2}" -Option Constant
New-Variable -Name oneSec -Value ([TimeSpan]::FromSeconds(1)) -Option Constant
[bool]$ret = $true
$window = $Host.UI.Rawui.WindowSize
$origin = $Host.UI.RawUI.CursorPosition
$Countdown = [TimeSpan]::FromMinutes($Minutes)
$cursor = $Host.UI.RawUI.CursorPosition
while ($Countdown.TotalSeconds -gt 0)
{
# Очистка области от курсора до конца буфера окна
$space = New-Object System.Management.Automation.Host.BufferCell -ArgumentList ' ', $Host.UI.RawUI.ForegroundColor, $Host.UI.RawUI.BackgroundColor, "Complete"
$rect = New-Object System.Management.Automation.Host.Rectangle -ArgumentList $cursor.X, $cursor.Y, $Host.UI.RawUI.WindowSize.Width, $Host.UI.RawUI.WindowSize.Height
$Host.UI.RawUI.SetBufferContents($rect, $space)
# Отображение таймера
$Host.UI.RawUI.CursorPosition = $cursor
write-host ("Осталось: `t$timeText" -f ($Countdown.Days * 24 + $Countdown.Hours).ToString("D1"), $Countdown.Minutes.ToString("D2"), $Countdown.Seconds.ToString("D2"))
write-host "`t`t (ч:мин:cек)"
[System.Threading.Thread]::Sleep($oneSec.TotalMilliseconds)
$Countdown = $Countdown.Subtract($oneSec)
# проверка нажатия клавиши
if($Host.UI.RawUI.KeyAvailable)
{
$key = $Host.UI.RawUI.ReadKey("NoEcho,IncludeKeyDown,IncludeKeyUp").Character.toString().toUpper()
# проверка клавиш отмены
if ('Q', 'X' -contains $key) {
$ret = $false
break;
# проверка клавиш подтверждения
} elseif ('A', "S" -contains $key) {
break;
}
}
}
return $ret
}
function Close-Session {
Write-log ($close_msg -f $_.SessionID, $_.UserName, $_.Host, $_.InfoBase.Name, $_.AppID)
# завершаем сеанс
$agent.TerminateSession($cluster, $_)
}
# --------------- раздел основной -----------------------------------
Write-log "запуск" -silent
$COMConnector = New-Object -ComObject V83.COMConnector
$agent = $COMConnector.ConnectAgent($server)
$cluster = $agent.GetClusters()[0] # берём первый кластер
$agent.Authenticate($cluster, $admin_user, $admin_pass)
# получаем сеансы и ищем совпадения по имени хоста
$to_close = $agent.GetSessions($cluster) | Where-object {$client -eq $_.Host.ToUpper()}
if ($to_close.length -lt 1 -and $to_close.SessionID -lt 1) {
Write-log "Открытых сеансов не обнаружено" -type "completed"
exit
}
write-host $Title -ForegroundColor Red
$to_close|Select-Object @{Name=“Сеанс”;Expression={$_.SessionID}}, @{Name=“Пользователь”;Expression={$_.UserName}}, @{Name=“Компьютер”;Expression={$_.Host}}, @{Name=“Приложение”;Expression={$_.AppID}}, @{Name=“База”;Expression={$_.Infobase.Name}}|Sort-Object База, Сеанс|Format-Table
Write-Host "`n`n"
# выводим обратный отсчет и получаем код возврата
$continue = CountDown 2
# если пользователь прервал операцию нажатием Q или X
if (-not $continue) {
Write-log "Закрытие сеансов отменено" -type "warning"
exit
}
$to_close | %{Close-Session}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment