Задать вопрос
@Andrew_Lays

Как заставить работать SendKeys через RDP?

Есть удалённый Windows сервер, на нём стоит программа PROGRAM, также установлен Open Server, с открытым доступом извне. Open Server я установил, чтобы запускать на сервере нужные python-скрипты просто стучась извне по IP-адресу сервера, для этих целей написан php-скрипт, который при вызове запускает нужный python-скрипт. Итого, чтобы запустить python-скрипт на сервере, я запускаю скрипт server.domain/script.php. Дальше python-скрипт должен, к примеру, запустить блокнот и напечатать в нём текст, для этого использую такой python-код:
import SendKeys
from pywinauto.application import Application

app = Application().Start('notepad')

SendKeys.SendKeys('some text')

Потом, когда я захожу на сервер я вижу только открытое окно блокнота, пустое, без текста.
Если я перезапущу этот же python-скрипт на сервере через консоль, то откроется блокнот и в него напечатается текст "some text". В результате гугления и тестов я понял, что не работает набор текста и управление мышью через RDP для обеспечения безопасности. Так же нашёл несколько советов использовать SendInput и SendMessage, но не смог применить их к python. Как напечатать текст удалённо, может снять ограничения системы безопасности?
  • Вопрос задан
  • 1205 просмотров
Подписаться 1 Средний Комментировать
Пригласить эксперта
Ответы на вопрос 2
vasily-v-ryabov
@vasily-v-ryabov
Python, UI Automation, pywinauto
Для сохранения активного десктопа можно использовать VNC (например, мы пользуем TightVNC в качестве клиента и сервера) вместо RDP. Только, если всё же зашли по RDP, то потом надо перезагрузить сервер, чтобы VNC сессия нормально работала. А ещё скрипт на сервере нельзя запускать как сервис (из сервиса активный GUI context недоступен). Для VNC, возможно, ещё потребуется обновить видеодрова, т.к. он отображает реальный выход с видеокарты в отличие от виртуального RDP.

Что касается pywinauto, то там SendKeys как раз использует системную функцию SendInput. В ветке UIA на гитхабе (релиз запланирован на июль) уже есть метод send_chars(...), который посылает WM_CHAR через SendMessage (работает для свёрнутого окна и при залоченной винде). Но этот метод нужно использовать для конкретного окна, а не просто глобально для системы. Пример:
app = Application().start('notepad.exe')
app.UntitledNotepad.Edit.send_chars('Hello World!') # не нужен GUI context
app.UntitledNotepad.Edit.type_keys('\nTyping to the active window...', with_newlines=True) # нужен GUI context

Вызов метода для конкретного контрола ещё и автоматически ждёт, когда окно/контрол реально появится и будет готов к вводу.
Ответ написан
FantomNotaBene
@FantomNotaBene
Программист, трейсер
ожидание сделайте между строкой где запускается приложение и SendKeys()
from time import sleep
...
sleep(3)
...
думается мне, все работает как надо, но, как сказали выше, текст отправляется в текущее активное окно, а на момент когда передаются нажатия клавиш, блокнот просто не успевает открыться и оказаться в фокусе
а нажатия клавиш передаются, полагаю, пустому рабочему столу, где, разумеется, не вызывают никакой реакции на себя
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы