I'm trying to execute a python script from Linux but I'm keep getting this error on the except line. Can someone figure this out?
$ python pygeo_ip.py
def search(self):
message = ''
result_count = 0
gip = pygeoip.GeoIP('GeoLIteCity.dat')
ip = self.ip_textbox.text()
try:
ip = socket.gethostbyname(str(ip))
message = "Host: %s Is Currently Available" % (str(ip))
except socket.error, e:
message = "Host: %s Is Currently Unavailable" % (key, val)
result_count += 1
msg_box("SeArCh CoMpLeTe", "%d REsults Were Found For %s"
% (result_count, str(ip))
except Exception, e: <------- Error
msg_box("", str(e))
msg_box("Search Complete", "No Results Were Found For %s" % (str(ip))
return
Error:
File "pygeo_ip.py", line 142
except Exception, e:
^
SyntaxError: invalid syntax
Pretty sure (without having tested anything) your problem is having missed the last close bracket
Line should read:
msg_box("SeArCh CoMpLeTe", "%d REsults Were Found For %s" % (result_count, str(ip)) )
When I handle an exception in python
try:
a = dict()
a[1]
except Exception as e:
print str(e)
It prints
1
I expect it to print
KeyError: 1
Is there a way to retrieve the default error message ?
Instead of this:
print str(e)
do this:
print(type(e).__name__ + ": " + str(e))
or just this:
print(type(e).__name__, e)
If you replace str(e) with repr(e) Python 2 will produce KeyError(1,) and Python 3 will produce KeyError(1)
This doesn't quite produce your desired output, but it may be close enough?
I have this code block that it should give out the CIK number when the stock ticker is supplied:
def lookup_cik(ticker, name=None):
good_read = False
ticker = ticker.strip().upper()
url = 'http://www.sec.gov/cgi-bin/browse-edgar?action+getcompany&CIK=(cik)&count=10&output=xml'.format(cik=ticker)
try:
xmlFile = urlopen ( url )
try:
xmlData = xmlFile.read()
good_read = True
finally:
xmlFile.close()
except HTTPError as e:
print( "HTTP Error:", e.code )
except URLError as e:
print( "URL Error:", e.reason )
except TimeoutError as e:
print( "Timeout Error:", e.reason )
except socket.timeout:
print( "Socket Timeout Error" )
if not good_read:
print( "Unable to lookup CIK for ticker:", ticker )
return
try:
root = ET.fromstring(xmlData)
except ET.ParseError as perr:
print( "XML Parser Error:", perr )
try:
cikElement = list(root.iter( "CIK" ))[0]
return int(cikElement.text)
except StopIteration:
pass
However when it try to input a Stock ticker i get
>>> lookup_cik(BDX)
Traceback (most recent call last):
File "<pyshell#34>", line 1, in <module>
lookup_cik(BDX)
NameError: name 'BDX' is not defined
I know that it is a NameError but i have never met an issue where the function does not recognize the supposedly inputted argument data the stock ticker which in our example is BDX.
Your function expects a string, so pass in one:
lookup_cik("BDX")
Without the quotes Python parses that as a name, but you never bound anything to that name (assigned to it).
Note that you'll also get a UnboundLocalError: local variable 'root' referenced before assignment exception if there was a parse error. You probably want to exit the function at that point:
try:
root = ET.fromstring(xmlData)
except ET.ParseError as perr:
print( "XML Parser Error:", perr )
return
You'll most likely get a parse error, because you never actually interpolate the ticker anywhere in the string; you are missing a {cik} placeholder:
url = 'http://www.sec.gov/cgi-bin/browse-edgar?action+getcompany&CIK=(cik)&count=10&output=xml'.format(cik=ticker)
You probably meant to use CIK={cik} there. A quick experiment directly calling the site also shows you need to use action=getcompany (= instead of +):
url = 'http://www.sec.gov/cgi-bin/browse-edgar?action=getcompany&CIK={cik}&count=10&output=xml'.format(cik=ticker)
Because you use list() on root.iter(), the whole expression will not raise StopIteration (list() catches that). Instead, the expression could raise a IndexError instead.
I'd use next() there instead:
cikElement = next(root.iter("CIK"), None)
return cikElement and int(cikElement.text)
or better still, just use Element.find():
cikElement = root.find("CIK")
return cikElement and int(cikElement.text)
This is part of my code in python. I want to check the error message and if HTTPError() then I want to add the host to the file ok.txt. But it doesn't work. what is the problem here?
except urllib2.URLError, e:
print '%-15s\t%15r' % (url.strip(), e)
if e == 'HTTPError()':
OK.write('%-15s' % (url.strip()) + '\n')
OK.flush()
When I run whole script the output is something like this:
http://a.com HTTPError()
http://b.com URLError(timeout('timed out',),)
http://c.com URLError(timeout('timed out',),)
http://d.com URLError(error(111, 'Connection refused'),)
http://e.com 200
Use isinstance() to check whether or not your error is of type HTTPError:
except urllib2.URLError as e: # use the "as e" instead of the old style comma delimitation.
print '%-15s\t%15r' % (url.strip(), e)
if isinstance(e, HTTPError):
OK.write('%-15s' % (url.strip()) + '\n')
OK.flush()
I'm encountering this error message:
TypeError: add_header() takes exactly 3 arguments (2 given)
when using these parameters:
testService("SomeServiceName", "POST", "[redacted valid url]", ('Content-type','application/json'), [redacted valid json])
Normally this error means I'm not passing "self" as a parameter, but seeing as this method is not being called in a class, I'm not sure what to do. I've tried passing self in as a parameter in both the parameters and inside the method. And I've tried wrapping the header in brackets and parentheses. When I pass "self" I get the error message that self is undefined, and when I use the brackets instead of parentheses, I get the same error as above.
Anyone with magical Python debugging skills out there? Thanks so much for taking the time to check this out!
def testService(name, verb, url, header="", requestBody=""):
#Log out the name of the request we're testing
if (name is not None) or (name.strip() is not ""):
print "Checking " + name + "\n\n"
# Make URL with StoreNumber
if (url is not None) or (url is not ""):
testUrl = url
# If specified verb is GET
if verb.strip().upper() == "GET":
# Create request
req = urllib2.Request(testUrl)
print "Making request with URL: " + testUrl + "\n\n"
# Send request
try:
response = urllib2.urlopen(req)
# If service returns 200 Okay
print "Connection to " + name + " Service successful. Returned with code " + str(response.code) + "\n\n"
# Log response
print "Response: " + response.read() + "\n\n"
# Handle exceptions
# If HTTP Error
except HTTPError as e:
if hasattr(e, 'reason'):
print name + ' failed to reach a server.'
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print e.code
elif hasattr(e, 'message'):
print e.message
pass
# If URL was the problem
except URLError as e:
if hasattr(e, 'reason'):
print name + ' failed to reach a server.'
if str(e.reason) == "[Errno 11004] getaddrinfo failed":
print "[Errno 11004] getaddrinfo failed with bad url: " + testUrl + "\n\n"
else:
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print 'Error code: ', e.code
elif hasattr(e, 'message'):
print e.message
pass
# If specified verb was POST
elif verb.strip().upper() == "POST":
# Check for None requestBody
if (requestBody is not None) or (requestBody.strip() is not ""):
data = urllib.urlencode(requestBody)
# Create request
req = urllib2.Request(testUrl, data)
# Check for header
if (header is not None) or (header.strip() is not ""):
req.add_header(header)
# YO YO THE BELOW CODE IS INCOMPLETE PLEASE FINISH
# Log request with URL and Data
print "Making request with URL: " + testUrl + " and data: THIS PART IS UNFINISHED PLEASE FINISH ME \n\n"
try:
response = urllib2.urlopen(req)
# If service returns 200 Okay
print "Connection to " + name + " Service successful. Returned with code " + str(response.code) + "\n\n"
# Log response
print "Response: " + response.read() + "\n\n"
# Handle exceptions
# If HTTP Error
except HTTPError as e:
if hasattr(e, 'code'):
print e.code
elif hasattr(e, 'message'):
print e.message
elif hasattr(e, 'reason'):
print name + ' failed to reach a server.'
print 'Reason: ', e.reason
pass
except URLError as e:
if hasattr(e, 'reason'):
print name + ' failed to reach a server.'
if str(e.reason) == "[Errno 11004] getaddrinfo failed":
print "[Errno 11004] getaddrinfo failed with bad url: " + url + "\n\n"
else:
print 'Reason: ', e.reason
elif hasattr(e, 'code'):
print 'Error code: ', e.code
elif hasattr(e, 'message'):
print e.message
pass
# Header non-existent in testService call
else:
print "Service header not provided. Exiting program"
sys.exit()
# Requesty Body not present in testService call
else:
print "Service request body not provided in code. Exiting program"
sys.exit()
# If specified verb is not supported (Currently only GET and POST are supported)
else:
print name + " Service written with HTTP verb other than GET or POST. Exiting program"
sys.exit()
else:
print "Service url not provided in code. Exiting program"
sys.exit()
else:
print "Service name not provided in code. Exiting program"
sys.exit()
From the documentation, add_header takes two arguments. You are calling it with one argument, a tuple with two values.
What you should do:
req.add_header(key, value)
What you are currently doing because you are getting the header as a tuple:
req.add_header((key, value,)) # aka passing a tuple with both arguments to the key parameter
You need to unpack the tuple:
req.add_header(header[0], header[1])
Or even better, using the splat operator (*):
req.add_header(*header) # Does the same thing as above
Also, you are using an empty string as the default argument for header, when when it is supplied it is a tuple. You should probably change the default value to a tuple or None.
Your header is a 2-tuple:
('Content-Type', 'application/json')
You're trying to do this:
req.add_header('Content-Type', 'application/json')
But in reality you're doing this:
req.add_header(('Content-Type', 'application/json'))
Notice that you're only passing one argument - a tuple - instead of two, a key and a value.
To fix, unpack your header when you pass it with the * (informally, 'splat') operator:
req.add_header(*header)
Take a look at the documentation: http://docs.python.org/2/library/urllib2.html#urllib2.Request.add_header.
While the function expects a key and a value, you're passing only a single object. Since you're calling this on the req object, that is the implicit "self" that's being passed as well.
You could call this function in two ways:
req.add_header(key, value)
urllib2.Request.add_header(req, key, value) # explicitly passing the reference instead of self
I'm not sure whether you're expecting the string you pass to be treated as the key or the value, but adding another paramater (or making the header parameter take a dict and then splitting appropriately in a for loop) should solve the issue. For example (with irrelevant code removed):
def testService(name, verb, url, header=None, requestBody=""):
if header is None:
header = {}
for key, value in header.iteritems():
req.add_header(key, value)