I've got python code of the form:
(o,i) = os.popen2 ("/usr/bin/ssh host executable")
ios = IOSource(i,o)
Library code then uses this IOSource, doing writes() and read()s against inputstream i and outputstream o.
Yes, there is IPC going on here.. Think RPC.
I want to do this, but in an HTTP fashion rather than spawning an ssh.
I've done python http before with:
conn=httplib.HTTPConnection('localhost',8000)
conn.connect()
conn.request('POST','/someurl/')
response=conn.getresponse()
How do I get the inputstream/outputstream from the HTTPConnection so that my lib code can read from/write to just like the ssh example above?
for output:
output = response.read()
http://docs.python.org/library/httplib.html#httpresponse-objects
for input:
pass your data in the POST body of your request
Related
I have been writing python code for quite some time to get CSGO gamestate_integration, but I currently need to write something in vb.net to do the same thing and it's not working.
tl;dr version: vb.net won't accept the post request from CSGO, but a simple python script can echo the post request to vb.net and it works. The vb.net application IS being run as administrator.
I have a simple class file (obviously my URIs are private):
Imports System.IO
Imports System.ServiceModel
Imports System.ServiceModel.Web
Imports JSONReceiver
<ServiceContract()>
Public Interface iJSONReceiver
<OperationContract>
<WebGet()>
Function get_stats(ByVal data As String) As String
<OperationContract()>
<WebInvoke(RequestFormat:=WebMessageFormat.Json)>
Function post_stats(ByVal request As Stream) As String
End Interface
Public Class JSONReceiver
Implements iJSONReceiver
Public Function post_stats(ByVal request As Stream) As String Implements iJSONReceiver.post_stats
Dim reader As New StreamReader(request)
Console.WriteLine("In post_stats")
Console.WriteLine(reader.ReadToEnd())
Console.WriteLine()
Return "OK"
End Function
Public Function get_stats(ByVal data As String) As String Implements iJSONReceiver.get_stats
Console.WriteLine("In get_stats")
Console.WriteLine(data)
Console.WriteLine()
Return "OK"
End Function
End Class
And simple code to test it:
Public host As WebServiceHost
Public post_ep As ServiceEndpoint
Public Sub main()
host = New WebServiceHost(GetType(JSONReceiver), New Uri("http://192.168.1.102:8080"))
post_ep = host.AddServiceEndpoint(GetType(iJSONReceiver), New WebHttpBinding(), "")
host.Open()
Console.WriteLine("Press enter to quit...")
Console.ReadLine()
host.Close()
End Sub
I can use a web browser to point to the get_stats() endpoint, and it works just fine, but I am trying to use CSGOs gamestate_integration functionality to post the data to my service, and it just doesn't seem to like it.
So what I did was ripped my old python code to simply echo the request to the vb.net web service, it it works... the python code receives the data and simply posts it to the vb.net service, and the vb.net service happily accepts it.
So I change the URI for the vb JSONReceiver to port 8081, and run this script on the original uri (192.168.1.102:8080)
import web
import urllib2
class Stats(object):
def POST(self):
json_data = web.data()
try:
echo(json_data)
except Exception, e:
print(e.__str__())
return "OK"
def echo(data):
request = urllib2.Request("http://192.168.1.102:8081/post_stats")
request.add_data(data)
f = urllib2.urlopen(request)
print f.read()
urls = (
'/post_stats', 'Stats',
)
if __name__ == "__main__":
app = web.application(urls, globals())
app.run()
In short, the URI CSGO is using to post to my service is http://192.168.1.102:8080, which hits my python service, which then echoes the request verbatim to http://192.168.1.102:8081 (again, these are private URIs).
I don't know why, but it works... but having to run a wrapper to get this data is not only weird, it's really not an acceptable solution to the problem... obviously vb.net is handling post requests just fine when it's coming from my python script; obviously CSGO is posting requests correctly, or my python script wouldn't be able to receive it, so I'm having a problem finding the disconnect...
Is Python adding something to the request that CSGO might not be?
Do I need to fall back to socket programming?
I'm attempting to make use of cgminer's API using Python. I'm particularly interested in utilizing the requests library.
I understand how to do basic things in requests, but cgminer wants to be a little more specific. I'd like to shrink
import socket
import json
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect(('localhost', 4028))
sock.send(json.dumps({'command': 'summary'}))
using requests instead.
How does one specify the port using that library, and how does one send such a json request and await a response to be stored in a variable?
Request is an HTTP library.
You can specify the port in the URL http://example.com:4028/....
But, from what I can read in a hurry here cgminer provides a RPC API (or JSON RPC?) not an HTTP interface.
As someone who has learned some of the common pitfalls of python networking the hard way, I'm adding this answer to emphasize an important-but-easy-to-mess-up point about the 1st arg of requests.get():
localhost is an alias which your computer resolves to 127.0.0.1, the IP address of its own loopback adapter. foo.com is also an alias, just one that gets resolved further away from the host.
requests.get('foo.com:4028') #<--fails
requests.get('http://foo.com:4028') #<--works usually
& for loopbacks:
requests.get('http://127.0.0.1:4028') #<--works
requests.get('http://localhost:4028') #<--works
this one requires import socket & gives you the local ip of your host (aka, your address within your own LAN); it goes a little farther out from the host than just calling localhost, but not all the way out to the open-internet:
requests.get('http://{}:4028'.format(socket.gethostbyname(socket.gethostname()))) #<--works
You can specify the port for the request with a colon just as you would in a browser, such as
r = requests.get('http://localhost:4028'). This will block until a response is received, or until the request times out, so you don't need to worry about awaiting a response.
You can send JSON data as a POST request using the requests.post method with the data parameter, such as
import json, requests
payload = {'command': 'summary'}
r = requests.post('http://localhost:4028', data=json.dumps(payload))
Accessing the response is then possible with r.text or r.json().
Note that requests is an HTTP library - if it's not HTTP that you want then I don't believe it's possible to use requests.
I've created some web services using pysimplesoap like on this documentation:
https://code.google.com/p/pysimplesoap/wiki/SoapServer
When I tested it, I called it like this:
from SOAPpy import SOAPProxy
from SOAPpy import Types
namespace = "http://localhost:8008"
url = "http://localhost:8008"
proxy = SOAPProxy(url, namespace)
response = proxy.dummy(times=5, name="test")
print response
And it worked for all of my web services, but when I try to call it by using an library which is needed to specify the WSDL, it returns "Could not connect to host".
To solve my problem, I used the object ".wsdl()" to generate the correct WSDL and saved it into a file, the WSDL generated by default wasn't correct, was missing variable types and the correct server address...
The server name localhost is only meaningful on your computer. Once outside, other computers won't be able to see it.
1) find out your external IP, with http://www.whatismyip.com/ or another service. Note that IPs change over time.
2) plug the IP in to http://www.soapclient.com/soaptest.html
If your local service is answering IP requests as well as from localhost, you're done!
im trying to build an client for an webservice in python with suds. i used the tutorial
on this site: http://www.jansipke.nl/python-soap-client-with-suds. Its working with my own written Webservice and WSDL, but not with the wsdl file i got. The wsdl file is working in soapUI, i can send requests and get an answer. So the problem is, i think, how suds is parsing the wsdl file. I get following error:
urllib2.URLError: <urlopen error [Errno -2] Name or service not known>
Any ideas how to fix that? If you need more information please ask. Thank you!
The error you have given us seems to imply that the URL you are using to access the WSDL is not correct. could you show us a bit more of your code? for example the client instatiation and the url to the WSDL. this might allow others to actually help you.
Olly
# SUDS is primarily built for Python 2.6/7 (Lightweight SOAP client)
# SUDS does not work properly with other version, absolutely no support for 3.x
# Test your code with Python 2.7.12 (I am using)
from suds.client import Client
from suds.sax.text import Raw
# Use your tested URL same format with '?wsdl', Check once in SOAP-UI, below is dummy
# Make sure to use same Method name in below function 'client.service.MethodName'
url = 'http://localhost:8080/your/path/MethodName?wsdl'
#Use your Request XML, below is dummy, format xml=Raw('xml_text')
xml = Raw('<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:diag=" </soapenv:Body></soapenv:Envelope>')
def GetResCode(url, xml):
client = Client(url)
xml_response = (client.service.MethodName(__inject={'msg':xml}))
return xml_response
print(GetResCode(url,xml))
I need a tool, which can download some part of data from web server, and after that i want connection not be closed. Therfore, i thought about a script in python, which can do:
1) send request
2) read some part of response
3) will freeze - server should think that connection exist, and should not close it
is it possilbe to do it in python ? here is my code:
conn = HTTPConnection("myhost", 10000)
conn.request("GET", "/?file=myfile")
r1 = conn.getresponse()
print r1.status, r1.reason
data = r1.read(2000000)
print len(data)
When im running it, all data is received, and after that server closes connection.
thx in advance for any help
httplib doesn't support that. Use another library, like httplib2. Here's example.