pywinauto - Getting property text - python

I'm using pywinauto and I want to select text from one of the properties. However, I can't figure out how to access it.
import pywinauto
pwa_app = pywinauto.application.Application()
path = r'C:\Users\me\Cisco\Cisco AnyConnect Secure Mobility Client\vpnui.exe'
pwa_app.start(path)
w_handle = pywinauto.findwindows.find_windows(title=u'Cisco AnyConnect Secure Mobility Client', class_name='#32770')[0]
window = pwa_app.window_(handle=w_handle)
window.SetFocus()
window.print_control_identifiers(2)
Control Identifiers:
Dialog - 'Cisco AnyConnect Secure Mobility Client' (L1421, T493, R1854, B690)
['Cisco AnyConnect Secure Mobility Client', 'Cisco AnyConnect Secure Mobility ClientDialog', 'Dialog']
child_window(title="Cisco AnyConnect Secure Mobility Client", class_name="#32770")
|
| #32770 - '' (L1441, T535, R1834, B647)
| ['#32770', 'VPN:#32770']
| child_window(class_name="#32770")
|
| Static - 'VPN:' (L1527, T548, R1551, B561)
| ['Static', 'VPN:Static', 'VPN:', 'Static0', 'Static1']
| child_window(title="VPN:", class_name="Static")
|
| ComboBox - 'Brock AppDMZ VPN' (L1527, T594, R1719, B615)
| ['ComboBox', 'Connected to Brock AppDMZ VPN.ComboBox', 'VPN:ComboBox', 'ComboBox0', 'ComboBox1', 'Connected to Brock AppDMZ VPN.ComboBox0', 'Connected to Brock AppDMZ VPN.ComboBox1']
| child_window(title="Brock AppDMZ VPN", class_name="ComboBox")
|
| Edit - 'Brock AppDMZ VPN' (L1530, T597, R1699, B612)
| ['Connected to Brock AppDMZ VPN.Edit', 'Edit']
| child_window(title="Brock AppDMZ VPN", class_name="Edit")
|
| ComboBox - '' (L1527, T594, R1719, B615)
| ['ComboBox2', 'Connected to Brock AppDMZ VPN.ComboBox2']
| child_window(class_name="ComboBox")
I want to access the value "Connected to Brock AppDMZ VPN" in order to determine whether I'm connected to my VPN but the documentation on this library isn't super clear about how to do this.

The output of print_control_identifiers() is incomplete (the target text label is not listed here, there are 3 static texts on the window), but fortunately I have the same Cisco VPN client on my PC. The problem is that this "static" text is dynamic. :) There are 2 ways how to handle this situation.
1) Just create a window specification and check if this window exists:
connected_label = window.child_window(title="Connected to Brock AppDMZ VPN.", class_name="Static")
# default timeout is pywinauto.timings.Timings.window_find_timeout (5 sec.)
if connected_label.exists(timeout=10):
pass # do whatever you want
2) Rely on the number of this static text and check its text every time you need the status of connection:
label = window.child_window(class_name="Static", found_index=1).wait('exists')
if label.window_text() == "Connected to Brock AppDMZ VPN.":
pass # do whatever you want

label = window.child_window(class_name="Static", found_index=1).wait('exists')
print label.get_value()
Try this, <element>.get_value() hope this will get you the text required.

Related

get image button with pywinauto

I want to click on the green plus button with pywinauto but I can't get the element.
I able to get the window with top_windows = Desktop(backend="uia")['Text File Export']
But then I see only the ListBox without the buttons that located above
top_windows.print_control_identifiers()
Control Identifiers:
Dialog - 'Text File Export' (L2198, T308, R2817, B1033)
['Dialog', 'Text File ExportDialog', 'Text File Export']
child_window(title="Text File Export", control_type="Window")
|
| Pane - 'Files to export' (L2206, T337, R2809, B503)
| ['Pane', 'Files to export', 'Files to exportPane', 'Pane0', 'Pane1']
| child_window(title="Files to export", auto_id="1578672", control_type="Pane")
| |
| | ListBox - '' (L2223, T380, R2792, B490)
| | ['ListBox', 'ListBox0', 'ListBox1']
| | child_window(auto_id="466446", control_type="List")
|
| Pane - 'File format' (L2203, T509, R2806, B959)
| ['Pane2', 'File formatPane', 'File format']
| child_window(title="File format", auto_id="599282", control_type="Pane")
Any idea how to click on the plus button?
Thanks!
Have you tried running your_variable.print_control_identifiers() method after assigning the element with auto_id 1578672 to a variable named your_variable?
Edit:
So you may need to click somewhere for the elements there to be available.
Your can try this.
app.Dialog.print_control_identifiers()
panel = app.Dialog.child_window(auto_id="1578672", control_type="Pane").wrapper_object()
panel.click_input()
app.Dialog.print_control_identifiers()

How to select a sub menu from a context menu?

I am trying to click on a sub menu(BTDecoder) item from a context menu(send to) using pywinauto.
I could click on the menu item from context list and click on it. But when i try to click on sub menu, its not happening. its showing there is no item like that.
Here is my code :
path=os.path.realpath(path)
os.startfile(path) # open the folder named "FW"
app = pywinauto.Desktop(backend='uia').window(best_match='FW')
win = app.window(title_re='WRT_FW_27_12_2018_11_19_59_000001')
win.click_input(button='left')
win.click_input(button='right') # right click on one file listed there
app1 = pywinauto.Desktop(backend='uia').window(best_match='ContextMenu',top_level_only = True)
win1 = app1.window(title_re="Send to")
win1.click_input() # click on "Send to" context menu
app.print_control_identifiers()
app2 = pywinauto.Desktop(backend='uia').window(best_match='ContextMenuItem',top_level_only = True)
win2 = app2.window(title_re="BTDecoder")
win2.click_input() # trying to click on sub menu item called "BTDecoder" which not happening.
after clicking the "send to" contextmenu, sub menu context is appeared. after that for app.print_control_identifiers, am able to find the sub menu as shown below:
Dialog - 'FW' (L85, T151, R1250, B728)
['FW', 'FWDialog', 'Dialog', 'FW0', 'FW1']
child_window(title="FW", control_type="Window")
|
| Menu - 'Send to' (L31, T101, R468, B573)
| ['Menu', 'Send toMenu', 'Send to', 'Menu0', 'Menu1']
| child_window(title="Send to", control_type="Menu")
| |
| | MenuItem - 'Bluetooth device' (L34, T104, R465, B128)
| | ['Bluetooth device', 'MenuItem', 'Bluetooth deviceMenuItem', 'MenuItem0', 'MenuItem1']
| | child_window(title="Bluetooth device", auto_id="31011", control_type="MenuItem")
| |
| | MenuItem - 'BT Decoder CLI' (L34, T128, R465, B150)
| | ['BT Decoder CLI', 'BT Decoder CLIMenuItem', 'MenuItem2']
| | child_window(title="BT Decoder CLI", auto_id="31012", control_type="MenuItem")
| |
| | MenuItem - 'BT FW Trace Viewer' (L34, T150, R465, B172)
| | ['BT FW Trace ViewerMenuItem', 'MenuItem3', 'BT FW Trace Viewer']
| | child_window(title="BT FW Trace Viewer", auto_id="31013", control_type="MenuItem")
| |
| | MenuItem - 'BTDecoder' (L34, T172, R465, B194)
| | ['BTDecoderMenuItem', 'MenuItem4', 'BTDecoder']
| | child_window(title="BTDecoder", auto_id="31014", control_type="MenuItem")
| |
| | MenuItem - 'Compressed (zipped) folder' (L34, T194, R465, B216)
| | ['Compressed (zipped) folderMenuItem', 'MenuItem5', 'Compressed (zipped) folder']
| | child_window(title="Compressed (zipped) folder", auto_id="31015", control_type="MenuItem")
| |
| | MenuItem - 'Desktop (create shortcut)' (L34, T216, R465, B238)
| | ['Desktop (create shortcut)', 'Desktop (create shortcut)MenuItem', 'MenuItem6']
| | child_window(title="Desktop (create shortcut)", auto_id="31016", control_type="MenuItem")
```````````````````````````````````````````````````
how to click on this sub menu item?
you should be using backend ='uia' and below is the code you need to use to click on context menu's submenu item
popup_menu = Desktop(backend='uia').window(title="Context")
popup_menu[submenu].click_input()
path=os.path.realpath(path)
os.startfile(path) # open the folder named "FW"
app = pywinauto.Desktop(backend='uia').window(best_match='FW')
win = app.window(title_re='WRT_FW_27_12_2018_11_19_59_000001')
win.click_input(button='left')
win.click_input(button='right') # right click on one file listed there
app1 = pywinauto.Desktop(backend='uia').window(best_match='ContextMenu',top_level_only = True)
win1 = app1.window(title_re="Send to")
win1.click_input()
Add the below lines
app2 = Desktop(backend='win32')
app2.PopupMenu.menu_item('BTDecoder').click_input()
I was doing the similar kind of work to access the sub context menu for mmc (snap in console) type of app.
I was able to interact with the sub context menu by using below line of code-
# To access context menu item
app.ContextMenu.child_window(title='Send To', control_type='MenuItem').click_input()
# To access the sub context menu use the PopupMenu control type.
app.PopupMenu.child_window(title='BTDecoder', control_type='MenuItem').click_input()

Using SLIM to write Fitnesse tests using Python

I downloaded and ran the fitnesse-standalone to test how does the SLIM protocol work.
Below is the directory structure
/Users
|
-redmont
|
-fitnesse-standalone.jar
|
-Calc.py
|
-FitNesseRoot/
FitNesse Wiki
!contents -R2 -g -p -f -h
!This is a test page
!define TEST_SYSTEM {slim}
!define SLIM_VERSION {0.1}
!path /Users/redmont/Calc.py
!path /Users/redmont/fitnesse-standalone.jar
!define COMMAND_PATTERN {python -m waferslim.server --syspath 8080}
|import|
|waferslim.examples.decision_table|
|Calc.MyCalc|
|my calc|
|A |B |multiply? |
|1 |2 |2 |
|1 |0 |0 |
|3 |5 |15 |
Calc.py
from waferslim.converters import convert_arg, convert_result, YesNoConverter
class MyCalc(object):
"""
Base test class
"""
def __init__(self):
"""
Initialise instance variables a and b to multiply
"""
self._A = 0
self._B = 0
self._multiply = 0
#convert_arg(to_type=int)
def setA(self, A):
"""
Decorated method to the variable 'a' as an int.
The decorator uses the implicitly registered int converter to
translate from a standard slim string value to an int.
"""
self._A = A
#convert_arg(to_type=int)
def setB(self, B):
self._B = B
#convert_result(to_type=str)
def multiply(self):
return self._A * self._B
I start the fitnesse-standalone using
java -jar fitnesse-standalone.jar -p 8080 -v
The logs in the terminal are
Socket class: class java.net.Socket
Remote address = /0:0:0:0:0:0:0:1:57853
Local socket address = /0:0:0:0:0:0:0:1:8080
Closed = false
Connected = true
Bound = true
isInputShutdown = false
isOutputShutdown = false
Creating plain socket on port: 0
Trying to connect to host: localhost on port: 57859 SSL=false timeout setting: 10
Creating plain client: localhost:57859
Socket class: class java.net.Socket
Connected to host: localhost on port: 57859 SSL=false timeout setting: 10
Remote address = /127.0.0.1:57860
Local socket address = /127.0.0.1:57859
Closed = false
Connected = true
Bound = true
isInputShutdown = false
isOutputShutdown = false
Read Slim Header: >Slim -- V0.4<
Got Slim Header: Slim -- V0.4, and Version 0.4
When I run this fixture in FitNesse with debug, I get the following error:
Could not invoke constructor for MyCalc[0]
1 The instance decisionTable_1.setA. does not exist
2 The instance decisionTable_1.setB. does not exist
2 The instance decisionTable_1.multiply. does not exist
I am unable to understand why isn't FitNesse able to find my fixture code?
Is it because of some permission?
I have also installed waferslim using its egg from cheese shop.
Reinstalling waferslim somehow solved my problem.

python SIP log file processing

i have a sniff/log file for VoIP/SIP generated by python scapy in format
time | src | srcport | dst | dstport | payload
the sniff python script looks like this:
## Import Scapy module
from scapy.all import *
import sys
sys.stdout = open('data.txt', 'w')
pkts = sniff(filter="udp and port 5060 and not port 22", count=0,prn=lambda x:x.sprintf("%sent.time% | %IP.src% | %IP.sport% | %IP.dst% | %IP.dport% | Payload {Raw:%Raw.load%\n}"))
each packet in one line and each line can have different size depends on SIP message type (Register, 200 OK, Invite, Notify and so on...)
What i would like to get from the file are fields
time, src, srcport, dst, dstport and from Payload type (just right after Payload) of SIP message, From, To, Call-iD, Contact
and the whole payload and then prepare these to insert into MySQL database.
1st msg:
07:57:01.894990 | 192.168.1.10 | 5060 | 192.168.1.1 | 5060 | Payload 'INVITE sip:210#test-lab.org SIP/2.0\r\nVia:
SIP/2.0/UDP 192.168.1.10:5060;rport;branch=z9hG4bK-9cbb0ba8\r\nRoute: <sip:192.168.1.1:5060;lr>\r\nFrom: "test-311" <sip:311#test-lab.org>;tag=3d13bd6f\r\n
To: <sip:210#test-lab.org>\r\nCall-ID: 21b0e2c755973976d6d06702ca33b32f#10.193.40.249\r\nCSeq: 1 INVITE\r\n
Contact: "test-311" <sip:311#192.168.1.10:5060;transport=UDP>\r\nMax-Forwards: 70\r\n
Supported: 100rel,replaces\r\nAllow: ACK, BYE, CANCEL, INFO, INVITE, OPTIONS, NOTIFY, PRACK, REFER, UPDATE, MESSAGE\r\nContent-Type: application/sdp\r\nContent-Length: 276\r\n\r\nv=0\r\no=- 3506863524 285638052 IN IP4 192.168.1.10\r\ns=-\r\nc=IN IP4 192.168.1.10\r\nt=0 0\r\nm=audio 8000 RTP/AVP 8 0 18 101\r\nc=IN IP4 192.168.1.10\r\na=rtpmap:8 PCMA/8000\r\na=rtpmap:0 PCMU/8000\r\na=rtpmap:18 G729/8000\r\na=rtpmap:101 telephone-event/8000\r\na=fmtp:101 0-15\r\na=ptime:20\r\n'
2nd msg:
07:57:01.902618 | 192.168.1.1 | 5060 | 192.168.1.10 | 5060 | Payload 'SIP/2.0 100 Trying\r\nVia: SIP/2.0/UDP 192.168.1.10:5060;received=192.168.1.10;branch=z9hG4bK-9cbb0ba8;rport=5060\r\nFrom: "test-311" <sip:+38551311#test-lab.org>;tag=3d13bd6f\r\nTo: <sip:210#test-lab.org>\r\nCall-ID: 21b0e2c755973976d6d06702ca33b32f#192.168.1.10\r\nCSeq: 1 INVITE\r\n\r\n'
I have tried to read line by line and split but I do not know how to split and take data from payload part.
Any help is more then welcome.
Well, you can enter the data into mysql straight from this program too; it might very well be the easiest approach.
from scapy.all import *
import sys
# connect to mysql
connection = ...
def insert_into_mysql(packet):
# now you can use packet.src, packet.sport, packet.dst, packet.dport, and
# I believe packet['Raw'].load
connection.execute(...)
# to not print the packet
return None
# to print the packet
return x.sprintf("%sent.time% | %IP.src% | %IP.sport% | %IP.dst% | %IP.dport% | Payload {Raw:%Raw.load%\n}"
pkts = sniff(filter="udp and port 5060", count=0, store=0, prn=insert_into_mysql)
But if you need to use the existing log, I think you need to use:
for line in open('log.txt'):
sent_time, src, sport, dst, dport, payload = line.split(' | ', 6)
payload = payload.replace('Payload ', '')
# to get the unquoted payload, I'd guess (can't test SIP though)
from ast import literal_eval
payload = literal_eval(payload)
from scapy.all import *
import MySQLdb, string, sys
def insert_into_mysql(packet):
db = MySQLdb.connect("localhost","test","testpwd","my_db" )
cursor = db.cursor()
# now you can use packet.src, packet.sport, packet.dst, packet.dport,
# and packet['Raw'].load
add_sip = ("INSERT INTO py_sniff "
"(time, src_ip, src_port, dst_ip, dst_port, message) "
"VALUES (%s, %s, %s, %s, %s, %s)")
# data from sniff
add_sip = {
'time': packet.sprintf("%sent.time%"),
'src_ip': packet.sprintf("%IP.src%"),
'src_port': packet.sprintf("%IP.sport%"),
'dst_ip': packet.sprintf("%IP.dst%"),
'dst_port': packet.sprintf("%IP.dport%"),
'message': packet.sprintf("{Raw:%Raw.load%}"),
}
# to print the packet
# return packet.sprintf("%sent.time% | %IP.src% | %IP.sport% | %IP.dst% | %IP.dport% | Payload {Raw:%Raw.load%\n}"
cursor.execute(add_sip)
db.commit()
pkts = sniff(iface="eth0", filter="udp and port 5060", count=0, store=0, prn=insert_into_mysql)

Can't seem to get pexpect to print data from command

I'm steadily working on how to ssh and parse data on a device by running a command. I have had a few questions along the way of this endeavor and much help with the questions I have asked. I'm now working with pexpect and I'm not seeing much in documentation with what I am doing. Basically I need to ssh in, as I said, and then run a command that will print out data, then get that data to print to my console.
Here is my code:
import pexpect
import pxssh
import getpass
child = pexpect.spawn('ssh www.example.com')
password = getpass.getpass('password: ')
child.sendline ('foo bar')
data = (child.read_nonblocking(size=1000, timeout=100))
print data
OUTPUT:
password:
foo bar
In the foo bar command the first line of the print out is foo bar so I am wondering if this is trying to print this data but only printing the first line. I add the read_nonblocking(size=1000, timeout=100) trying to set the size to be greater and a timeout to let the data print.
UPDATE with PXSSH
I have also tried to use the pxssh samples to do this and get only the list of commands that foo can run. I need to get the print out of foo bar which is the list of configs. My guess is that you can't have commands with spaces? Here is the code I have tried:
import pxssh
import getpass
try:
s = pxssh.pxssh()
s.force_password = True
hostname = raw_input('hostname: ')
username = raw_input('username: ')
password = getpass.getpass('password: ')
s.login (hostname, username, password)
s.sendline ('foo bar') # run a command
s.prompt() # match the prompt
print s.before # print everything before the prompt.
s.logout()
except pxssh.ExceptionPxssh, e:
print "pxssh failed on login."
print str(e)
Which gives me this back in console:
pxssh failed on login.
could not set shell prompt
:
Session idle time out is disabled
SSH> unset PROMPT_COMMAND
Error - Command [unset PROMPT_COMMAND] not found.
foo [ bar | bart | ran | up
| cmd | bee | hvac | monkey
| selective | list | help ]
check[v,nv,beep] [ list | help ]
delete [ all | bee | neewb | stuff
| up | cmd | fooconfig | root
| app | list | hvac | monkey
| selective | <filename> | confirmed | list | help ]
exit [ help ]
get [ vcf | nvcf | snmpcf | help ] [<filename>]
verbose [ help ]
help [ <command> | help ]
up arrow - brings up old command lines
down arrow - brings up newer command lines
right arrow - moves cursor to the right
left arrow - moves cursor to the left
insert - inserts a space at the cursor
delete - deletes character at the cursor
SSH> PS1='[PEXPECT]\$ '
Error - Command [PS1='[PEXPECT]\$ '] not found.
foo [ bar | bart | ran | up
| cmd | bee | hvac | monkey
| selective | list | help ]
check[v,nv,beep] [ list | help ]
delete [ all | bee | neewb | stuff
| up | cmd | fooconfig | root
| app | list | hvac | monkey
| selective | <filename> | confirmed | list | help ]
exit [ help ]
get [ vcf | nvcf | snmpcf | help ] [<filename>]
verbose [ help ]
help [ <command> | help ]
up arrow - brings up old command lines
down arrow - brings up newer command lines
right arrow - moves cursor to the right
left arrow - moves cursor to the left
insert - inserts a space at the cursor
delete - deletes character at the cursor
And as I mentioned I'm just trying to get the console to print out the foo bar command configs. This is the code I had working with python-exscript before finding out I needed to work in older Python 2.4.
CODE THAT I HAD WORKING IN EXSCRIPT THAT I NEED PEXPECT TO DO
account = read_login()
conn = SSH2()
conn.connect('example.com')
conn.login(account)
conn.execute('foo bar')
data = conn.response
conn.send('exit\r')
conn.close()
print data
Any help on how to get this code to work is greatly appreciated! Thanks!
Figured out the issue. I was missing a s.prompt()
try:
s = pxssh.pxssh(timeout=60, maxread=2000000)
s.force_password = True
hostname = raw_imput('hostname: ')
username = raw_input('password: ')
password = getpass.getpass('password: ')
s.PROMPT= 'SSH> '
s.login (hostname, username, password, auto_prompt_reset=False)
s.prompt()
s.sendline('foo bar')
s.prompt()
data = s.before
print data
s.logout()
except pxssh.ExceptionPxssh, e:
print "pxssh failed on login."
print str(e)

Categories