
В настоящее время есть около 20-30 компьютеров, на которые я регулярно подключаюсь. В настоящее время я использую HyperTerminal на Windows XP SP3 для этого. Как только мой компьютер подключается к другому компьютеру, я получаю распечатку строки с некоторой информацией, которую я вручную просматриваю и ввожу в Excel.
Хотя это хорошо работает для ручных подключений, это утомительный процесс, который, как мне кажется, следует автоматизировать. Сейчас я делаю это раз в неделю, потому что это очень трудоемко (обычно 30-40 минут на одно), но в идеале я хотел бы, чтобы это запускалось как запланированная задача каждый день. Однако HyperTerminal, похоже, не предлагает никаких возможностей для создания скриптов. Кроме того, я пробовал использовать функцию ведения журнала сеанса, и она, похоже, работает не так надежно.
Есть ли способ, возможно, с помощью пакетного скрипта или скрипта VBS или PowerShell, чтобы я мог последовательно дозваниваться до ряда компьютеров, а затем автоматически регистрировать вывод терминала в текстовом файле с меткой времени?
Дополнительное предостережение: мне также нужно уметь обрабатывать исключения, например, если компьютер занят. В HyperTerminal есть функция «Повторный набор при занятости», и иногда я ее использую или набираю номер остальных компьютеров, а затем возвращаюсь к этому. Мне также нужно встроить это в свой скрипт.
Учитывая, что военный набор возможен, хотя он не регистрирует выход, а только отсутствие или наличие несущего тона, я чувствую, что это достижимо. Как я могу это реализовать?
Мне нужно решение Batch или VBS, если это возможно. Я не уверен, насколько хороша поддержка PowerShell в Windows XP, и по разным причинам я бы предпочел не устанавливать на машину никаких дополнительных инструментов (например, Python и т. д.).
Пояснение:У меня есть друг, который в какой-то момент сделал скрипт, который мог звонить с помощью команд Hayes на линию. Это легкая часть; сложная часть — это возможность обнаружить распечатку с удаленного компьютера и записать ее в текстовый файл.
Платная версия HyperTerminal предлагает возможности для написания сценариев подобных действий, но я хотел бы сделать это бесплатно, используя собственный сценарий, а также с возможностью обработки занятых номеров.
Спасибо!
PowerShell
Вот что я получаю при запуске скрипта PowerShell:
Вот скрипт, который я попробовал:
# Create your instance of the SerialPort Class
$serialPort = new-Object System.IO.Ports.SerialPort
# Set various COM-port settings
$serialPort.PortName = "COM3"
$serialPort.BaudRate = 1200
$serialPort.WriteTimeout = 500
$serialPort.ReadTimeout = 23000
$serialPort.DtrEnable = "true"
# or in one command
# $serialPort= new-Object System.IO.Ports.SerialPort COM#,Baudrate,None,8,one
# Open the connection
$serialPort.Open()
# write to it
$serialPort.WriteLine( "at+csq" + "`r" )
$serialPort.WriteLine( "atdt1NPANXXXXXX" + "`r" )
# wait
start-sleep -m 50
# read line
$line = $serialPort.ReadLine()
Write-Host $line
# write to it
$serialPort.Close()
Наиболее близкое решение на данный момент:
Ближе всего мне удалось подойти к этому с помощью AHK, который довольно капризный, но работает достаточно часто, чтобы быть полезным. Мой план — подключить его к пакетному скрипту, передавать каждое число и повторять, пока я успешно не получу распечатку с каждого компьютера.
решение1
AutoHotkey.com может оказаться полезным.
Я считаю, что ключевым трюком для надежной работы будет использование правильного подхода. Простое сбрасывание нажатий клавиш в Microsoft Windows, чтобы Windows передала их приложению переднего плана, не будет самым стабильным методом. Вот фрагмент кода, который я использовал для взаимодействия с PuTTY. Он работал достаточно хорошо, чтобы я мог запустить скрипт, который запускал PuTTY, и при этом программа могла затем взаимодействовать с правильным экземпляром PuTTY, даже если PuTTY находился в фоновом режиме.
(Вероятно, вам придется существенно адаптировать этот пример кода.)
sPuTTYloc:="C:\Users\\me\PuTTY\PuTTY.exe"
sSiteName:="NameOfSite"
Run, "%sPuTTYloc%" -load "%sSiteName%",,UseErrorLevel,sPuTTYPID
if %sPuTTYPID%
{
WinWait, ahk_pid %sPuTTYPID%
sleep ,5000
IfWinExist,ahk_pid %sPuTTYPID%
{
ControlSend,,{Enter},ahk_pid %sPuTTYPID%
; other stuff
else
{
MsgBox "PuTTY Window closed, spot #1"
return ; Apparently the PuTTY window closed
}
Sleep 1500
IfWinExist,ahk_pid %sPuTTYPID%
{
; do other stuff
}
else
{
MsgBox "PuTTY Window closed, spot #2"
return ; Apparently the PuTTY window closed
}
Sleep 1500
return
}
return
Не обязательно есть веская причина, по которой я все еще разбиваю все на части, вызывая "IfWinExist" несколько раз. Когда я создавал и изначально отлаживал скрипт, я нашел его полезным для отладки (или, по крайней мере, чувствовал, что лучше понимаю, что происходит), если удаленный конец прерывал соединение (что приводило к закрытию моего окна PuTTY).
Главное, что при использовании ControlSend для передачи нажатий клавиш программе с использованием PID, созданного моей командой «Выполнить», если случится что-то плохое, скрипт не будет продолжать пытаться отправлять нажатия клавиш в Windows и в конечном итоге не передаст их не той программе.
решение2
Инструмент, который может помочь решить вашу проблему, — это Приложение для настольного компьютера AT Command Tester, коммерческий продукт ($9,95) с 7-дневной бесплатной пробной версией.
Этот продукт может выполнять скрипт AT-команд на вкладке «Режим скрипта», где он может сохранять и загружать скрипт с локального компьютера.
Он также имеет режим командной строки, в котором его можно вызвать следующим образом:
atc –port portname –script filename
Инструмент также может собирать и сохранять журналы модема. Я не пробовал, так как у меня нет модема и я не знаю номера, по которому можно позвонить, но если журналы сохраняются в виде текстовых файлов, то написать небольшой скрипт текстового поиска для ошибок/успехов должно быть просто.
Если вы предпочитаете написать свой собственный, это можно сделать с помощью простого скрипта PowerShell, используя Класс System.IO.Ports.SerialPort.
Вот пример (непроверенный и весьма теоретический):
# Create your instance of the SerialPort Class
$serialPort = new-Object System.IO.Ports.SerialPort
# Set various COM-port settings
$serialPort.PortName = "COM1"
$serialPort.BaudRate = 19200
$serialPort.WriteTimeout = 500
$serialPort.ReadTimeout = 3000
$serialPort.DtrEnable = "true"
# or in one command
# $serialPort= new-Object System.IO.Ports.SerialPort COM#,Baudrate,None,8,one
# Open the connection
$serialPort.Open()
# write to it
$serialPort.WriteLine( "at+csq" + "`r" )
# wait
start-sleep -m 50
# read line
$line = $serialPort.ReadLine()
Write-Host $line
# write to it
$serialPort.Close()
Обратите внимание, что символ конца строки, используемый модемом, требует внимания.
Вот мой сеанс на виртуальной машине XP, где я установил .Net Framework 2.0 и КБ968930. Это почти сработало, за исключением того, что к COM1 ничего не подключено, поэтому он завис на вызове ReadLine(), пока не завершится по таймауту.
Обратите внимание, что в моем скрипте была ошибка копирования-вставки, теперь исправленная. Строка, которая не работала, была:
$line = $port.ReadLine()
Должно было быть:
$line = $serialPort.ReadLine()
решение3
Самый простой способ управления модемом — это отправка команд через последовательный порт. Почти все модемы dial-up поддерживаютAT-команды Hayes, например ATD
или ATH
(обычно в оборудовании для последовательных модемов, иногда эмулируется драйвером для модемов USB/PCI).
Примеры:
Linux/OpenBSD/FreeBSD: Все программы и библиотеки в конечном итоге используют
/dev/ttyS*
специальные файлы для доступа к последовательным портам. (Примечание: в Linux USB-последовательные адаптеры называются ttyUSB или ttyACM.)
В большинстве случаев ваша программа может просто открыть путь, как если бы это был обычный файл, затем записать/сбросить команду и прочитать ответ.Windows: Все программы в конечном итоге используют
\\.\COM1:
специальные файлы для доступа к последовательным портам. Первые четыре можно открыть просто какCOM1:
(ярлык — это пережиток MS-DOS).PowerShell: ЕстьБлог разработчиковна эту тему.
Питон: использованиеpySerial.
Другой метод в Windows может заключаться в использованииAPI телефонии. Однако я не могу найти, поддерживает ли он вызовы данных (терминальные) или только голосовые вызовы.
решение4
В качестве примечания: вот только две утилиты, которые я использую для управления модемами. Я отправляю и получаю много SMS, инструменты созданы для этого. Они поддерживают несколько модемов, а для инициализации модемов используются AT-команды. Хотя все функции так или иначе запрограммированы на работу с SMS, их можно гибко настраивать с помощью скриптов инициализации и т. д. Я не тестировал полный цикл, например, дозвониться до другого модема и как-то получить данные, но, возможно, стоит взглянуть на них:
http://smstools3.kekekasvi.com/index.php https://wammu.eu/smsd/