I have to get the list(+ some parameters) of all the VDIs(Virtual Desktop Interfaces) which are connected to a Citrix Broker.
In PowerShell, I do it like this:
...
# credentials used for remote connection to citrix controllers
$pass=$(ConvertTo-SecureString -String $env:CitrixPassword -AsPlainText -Force)
[pscredential]$creds = New-Object System.Management.Automation.PSCredential ($env:CitrixUser,$pass)
#create the session
$session = New-PSSession -ComputerName $controller -Credential $creds -Authentication Negotiate
Write-Output -message "Session on $controller successfully established!"
Write-Output -message "loading citrix snapin"
Invoke-Command -Session $session -ScriptBlock {Add-PSSnapin citrix*} # pay attention here
Write-Output -message "Loading Snapin successful"
#get the stuff
Write-Output -message "Read the data..."
$controllers = Invoke-Command -Session $session -ScriptBlock {Get-BrokerController}
Write-Output -message "... controllers done"
$desktops = Invoke-Command -Session $session -ScriptBlock {Get-BrokerDesktop -MaxRecordCount 10000}
Write-Output -message "... desktop done"
...
I am struggling since some hours to find a solution for python, and I was testing a few stuff with python but nothing seems to be working. I have mostly played with WSman but I start to feel that this is not the right way... still not sure though.
My test looks like that:
...
# create the session
wsman = WSMan(citrix_ddc,
username = citrix_user,
password = citrix_pass,
auth = "basic",
port = 443,
cert_validation = False)
with RunspacePool(wsman) as pool:
ps = PowerShell(pool)
ps.add_cmdlet("Add-PSSnapin").add_parameter("citrix*")
ps.invoke()
# we will print the first object returned back to us
print(ps.output[0])
The endpoint seems to be wrong: https://<my_controller_ip>:443/wsman and the error is:
Code: 404, Content: <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN""http://www.w3.org/TR/html4/strict.dtd">
<HTML><HEAD><TITLE>Not Found</TITLE>
<META HTTP-EQUIV="Content-Type" Content="text/html; charset=us-ascii"></HEAD>
<BODY><h2>Not Found</h2>
<hr><p>HTTP Error 404. The requested resource is not found.</p>
</BODY></HTML>
This should be pretty similar with connecting with CmdLets to VMware or Nutanix, but I never did it with python and it seems that I can't figure out how to do it.
Can someone please help me to find a python based solution to this?
Additional info:
the script will run in a docker container on a linux based machine.
I have finally found an answer. The wsman is the right way to go, but when I was debugging the working powershell script using a debugger, I found out what I did wrong.
I should not be using SSL at all # this might not be the same for other situations, but it is for my particular case
because of previous mention, I had to remove the WSMan port
In PS script I was using auth=negotiate, therefore I did the same in Python.
All the rest the same, and it worked.
Here is my working code:
# create the session
wsman = WSMan(citrix_controller_ip,
username = citrix_user,
password = citrix_pass,
ssl = False,
auth = "negotiate",
encryption = 'never'
)
with RunspacePool(wsman) as pool:
ps = PowerShell(pool)
ps.add_cmdlet('Add-PSSnapin').add_parameter('Name', 'Citrix*')
ps.add_statement()
ps.add_cmdlet("Invoke-Expression").add_parameter("Command", "Get-BrokerDesktop -MaxRecordCount 1000000 | ConvertTo-Json -Compress")
ps.add_cmdlet("Out-String").add_parameter("Stream")
ps.invoke()
print(json.loads(ps.output[0])
Related
I'm modifying a script in python to run in securecrt 8.5.2 in order to backup the running-config of some cisco ASR9K equipment I have in charge, but the script seems to end abruptly after the second sucessful ssh2 hop (2nd tab) and does not send the commands I scripted (the exit in this specifical example), here's the code I have, as I'd said it's a modified version of the one's in vandyke page for opening ssh2.
One important thing is that I have to tab each session of each individual routers, because it doesn't permit doing an ssh direct from the active cli, so I had to improvise and implement this "connect in TAB", I'm suspecting that the secureCRT doesn't know if it is in the new tab I've opened so, it doesn't know where to send the commands.
I was playing with the line 30, but it doesn't seem to have any effect. I was changing the expected text, but it doesn't seem to recognize the correct tab or doesn't read the correct one.
Personal Background: A complete beginner in the python language.
# $language = "python"
# $interface = "1.0"
# Connect to an SSH server using the SSH2 protocol. Specify the
# username and password and hostname on the command line as well as
# some SSH2 protocol specific options.
host = "X.X.X.a"
host2 = "X.X.X.b"
def main():
crt.Screen.Synchronous = True
# Prompt for a username and password instead of embedding it in a script...
#
usr = crt.Dialog.Prompt("Enter the user name for" + host, "Username", "", True)
passwd = crt.Dialog.Prompt("Enter TACACS+ for" + host, "Login", "", True)
# Build a command-line string to pass to the Connect method.
cmd = "/SSH2 /L %s /PASSWORD %s /C AES-128-CTR /M SHA1 %s" % (usr, passwd, host)
crt.Session.Connect(cmd)
crt.Screen.WaitForString("X.X.X.a#")
crt.Screen.Send("copy running-config tftp:\r")
crt.Screen.WaitForString("Host name or IP address (control-c to abort): []?")
crt.Screen.Send("tftpserver.com\r")
crt.Screen.WaitForString("Destination file name (control-c to abort): [running-config]?")
crt.Screen.Send("X.X.X.a_running_config\r")
crt.Screen.WaitForString("X.X.X.a")
cmd2 = "/SSH2 /L %s /PASSWORD %s /C AES-128 /M SHA1 %s" % (usr, passwd, host2)
crt.Session.ConnectInTab(cmd2)
crt.Screen.WaitForString("X.X.X.b#")
crt.Screen.Send("exit\r")
main()
crt.Session.ConnectInTab(cmd2)
It connects to the equipment in a new tab, but what I expect is that the script will keep doing the same it did for the host1 (X.X.X.a) and send the same boring stuff to the host2 (X.X.X.b) via ssh2 tab, and continue the itterative process until I do this for all the equipments I need.
Thanks for reading me.
Well it's not even funny easy was to solve this very sub-optimal code or script but it was not much of a problem, the only thing is that I had to dissconect to the previous session when I inyected all the commands, so in order to put the cursor on the new tab, the previous session must be dissconected first.
The solution?
crt.Session.Disconnect()
By Default Duo Sync runs once Daily, due to the demand of business this needs to be done every 2 hours. looking at DUO API there is a Command for User Sync:
python -m duo_client.client --ikey <> --skey <> --host api-<>.duosecurity.com --method POST --path /admin/v1/users username=<> /directorysync/<DIR SYNC>/syncuser
However I don't see an API for a general overall sync with the Active Directory So to combat such, I was hoping to get all the users from the 2FA Group and Sync via username over a loop using the following:
import sys
import os
import duo_client
from ldap3 import Server, Connection, ALL, NTLM, ALL_ATTRIBUTES, ALL_OPERATIONAL_ATTRIBUTES, AUTO_BIND_NO_TLS, SUBTREE
from ldap3.core.exceptions import LDAPCursorError
server_name = ''
domain_name = ''
user_name = ''
password = '!'
admin_api = duo_client.Admin(
ikey= "",
skey= "",
host= "api-.duosecurity.com",)
format_string = '{:40}'
print(format_string.format('samaccountname'))
server = Server(server_name, get_info=ALL)
conn = Connection(server, user='{}\\{}'.format(domain_name, user_name), password=password, authentication=NTLM,
auto_bind=True)
conn.search('dc={},dc=int'.format(domain_name), '(&(objectCategory=user)(memberOf=CN=2FA,OU=,OU=,OU=,OU=,DC=,DC=int))',
attributes=[ALL_ATTRIBUTES, ALL_OPERATIONAL_ATTRIBUTES])
for e in sorted(conn.entries):
print(e.samaccountname)
os.system("python -m duo_client.client --ikey --skey --host api-.duosecurity.com --method POST --path /admin/v1/users username={}/directorysync//syncuser".format(e.samaccountname))"
The above code some what works, but for some users it also re-creates them as the following: User_IDs such as "username/Dir/DIRAPI/usersync". as showing in images below Duo API
Syncing User
It seemed the username={} was in the wrong
The below is to Create a new user hence why i was seeing username/..../....
Post /admin/v1/users username={}
Below is the Right way for using the API Call.
os.system("python -m duo_client.client --ikey --skey --host api-.duosecurity.com --method POST --path /admin/v1/users/directorysync/syncuser username={}".format(e.samaccountname))"
I am attempting to connect to a solr server using this tutorial. At this point, I am confident that my solr is set up correctly. I am able to run
> solr start -p 8983
and it appears to start something up.
sure enough
> solr status
Solr process 31421 running on port 8983
So now in my python code, I try what I think should be a basic connection script.
import solr
host = "http://localhost:8983/solr"
# also tried
# host = "http://localhost:8983"
# also tried
# host = "http://127.0.0.1:8983/solr"
# also tried
# host = "http://127.0.0.1:8983"
connection = solr.SolrConnection(host)
try:
connection.add(
id= 1,
title= "Lucene in Action",
author= ['Zack', 'Hank Hill']
)
except Exception as e:
import pdb
pdb.set_trace()
connection.commit()
My code never makes it to the connection.commit(), instead, it hits the debug point in the exception. Looking at exception e
HTTP code=404, Reason=Not Found, body=<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
<title>Error 404 Not Found</title>
</head>
<body><h2>HTTP ERROR 404</h2>
<p>Problem accessing /solr/update. Reason:
<pre> Not Found</pre></p><hr><i><small>Powered by Jetty://</small></i><hr/>
</body>
</html>
So it looks like the python client is not finding the solr server, due to the 404? This seems like it should be pretty simple, so I'm not sure where I messed up here. Can anyone point me in the right direction?
edit : I added this script to check various hosts, no go
hosts = [
'http://localhost:8983/solr',
'http://localhost:8983',
'http://127.0.0.1:8983/solr',
'http://127.0.0.1:8983'
]
def connect(host):
connection = solr.SolrConnection(host)
try:
connection.add(
id= 1,
title='Lucene in Action',
author= ['Zack Botkin', 'Hank Hill']
)
except:
raise
for host in hosts:
try:
connect(host)
except Exception as e:
import pdb
pdb.set_trace()
Each exception is the same, 404 error
edit 2 : I was able to
> telnet localhost 8983
and it connected, so I'm pretty sure the solr server is running on that port?
To index with solr you will need to also create a core and make sure to use that core in your url. For example, once solr has been started run this command to create a core named test:
solr create -c test
Once that has been created you should see it listed in the solr admin page. To use it you can simply add that core name to your connection url. Simple example python code:
import solr
# create a connection to a solr server
s = solr.SolrConnection('http://localhost:8983/solr/test')
# add 2 documents to the index
s.add(id=1, title='Lucene in Action', author=['bob', 'asdf'])
s.add(id=2, title='test2', author=['Joe', 'test'])
s.commit()
# do a search
response = s.query('joe')
for hit in response.results:
print hit['title']
More information here https://cwiki.apache.org/confluence/display/solr/Running+Solr
I am new to python and have run in to a problem with the following.
This is a code snippet from the Splunk api, thats used to connect to a splunk server then print the installed apps.
import splunklib.client as client
HOST = "server.splunk"
PORT = 8089
USERNAME = "UserABC"
PASSWORD = "Passw000rd"
# Create a Service instance and log in
service = client.connect(
host=HOST,
port=PORT,
username=USERNAME,
password=PASSWORD)
# Print installed apps to the console to verify login
for app in service.apps:
print app.name
I've tried it on my system in cmd and it works fine. However I intend to use this function in a Robot Framework test so the function needs to be defined in order to have a keyword I can use. I'm guessing something like the following:
import splunklib.client as client
def setServer(HOST, PORT, USERNAME, PASSWORD):
HOST = "server.splunk"
PORT = 8089
USERNAME = "UserABC"
PASSWORD = "Passw000rd"
service = client.connect(host=HOST,port=PORT,username=USERNAME,password=PASSWORD)
for app in service.apps:
print app.name
print ("\n")
My problem is when I run this nothing is printed to CMD at all. Any ideas
Thanks
A print in Python library is not displayed on the console of Robot Framework, that is the expected behaviour. If you want to check that the piece of code was run and the print was done, check the log.html produced by Robot. It should contain your print. Then if you really want to display something on Robot Console, then you have to use Log To Console keyword from your Robot Test. But as your print is in the python lib, you will have to import BuiltIn lib within your Python code. With all that, you should be fine.
I'm trying to use Paramiko to open (and maintain) a channel so that I can issue a few commands; however, I'm unable to find an example using paramiko.Transport AND using a private key. I have been able to connect to my server and just run a command using the following code:
ssh = paramiko.SSHClient()
paramiko.util.log_to_file("support_scripts.log")
private_key = paramiko.RSAKey.from_private_key_file(rsa_private_key)
ssh.connect(server, username=user, password='', pkey=private_key)
ssh_stdin, ssh_stdout, ssh_stderr = ssh.exec_command(cmd)
No problems there. From what I understand, that doesn't create an "interactive session", meaning I can't issue cd /home/my_user/my_scripts and then issue another command like python script_in_my_scripts_folder.py. Therefore, I'm trying to use the Paramiko Transport object which can help me maintain an interactive session. Searching high and low, none of the examples I've found work for me. Right now, the following code returns "SSHException: Channel is not open" on line 204, which is the exec_command below:
PRIVATEKEY = '/home/my_user/.ssh/id_rsa'
user = 'harperville'
server = '10.0.10.10'
port = 22
paramiko.util.log_to_file("support_scripts.log")
trans = paramiko.Transport((server,port))
rsa_key = paramiko.RSAKey.from_private_key_file(PRIVATEKEY)
trans.connect(username=user, pkey=rsa_key)
session = trans.open_channel("session")
session.exec_command('cd /home/harperville/my_scripts/')
I understand the gist of what it's telling me but I can't find or understand the documentation to help me get past this problem.
Thanks in advance.
I have found the issue with help from this site: http://j2labs.tumblr.com/post/4477180133/ssh-with-pythons-paramiko
If I change:
session = trans.open_channel("session")
to:
session = trans.open_session()
Then, I am allowed to run a command using:
session.exec_command('cd /home/harperville/my_scripts/')