Joshua Harper
Joshua Harper

Reputation: 43

AttributeError: 'str' object has no attribute '_request' for shodan api

import shodan
import sys
from ConfigParser import ConfigParser

#grab the api key from auth.ini
config = ConfigParser()
config.read('auth.ini')
SHODAN_API_KEY = config.get('auth','API_KEY')

#initialize the api object
api = shodan.Shodan(SHODAN_API_KEY)\

# Input validation
if len(sys.argv) == 1:
        print 'Usage: %s <search query>' % sys.argv[0]
        sys.exit(1)

try:

        query = ' '.join(sys.argv[1:])
        parent = query
        exploit = api.Exploits(parent)
        #WHY DOESNT THIS WORK 
        #AttributeError: 'str' object has no attribute '_request'
        print exploit.search(query)

except Exception, e:
        print 'Error: %s' % e
        sys.exit(1)

I a using Python 2.7 I get the AttributeError: 'str' object has no attribute '_request' traceback error shows line 79 in client.py in the Shodan API, is it just me or is their code wonky?

here is the Traceback

Traceback (most recent call last):
  File "exploitsearch.py", line 26, in <module>
    print exploit.search('query')
  File "/usr/local/lib/python2.7/dist-packages/shodan/client.py", line 79, in search
    return self.parent._request('/api/search', query_args, service='exploits')
AttributeError: 'str' object has no attribute '_request'

Upvotes: 4

Views: 5374

Answers (3)

achillean
achillean

Reputation: 560

I'm the founder of Shodan and author of the relevant library you're using. The correct answer is provided by John Gordon above:

You don't need to instantiate the Exploits class, it is done for you automatically when you create the Shodan() instance. This means that you can directly search for things without any extra work:

    api = shodan.Shodan(YOUR_API_KEY)
    results = api.exploits.search('apache')

Upvotes: 3

TayTay
TayTay

Reputation: 7170

Exploits is a subclass of the Shodan superclass. This class has a method called _request. When you initialize an instance of Exploits and execute the search method, the code internally calls the super (read: Shodan) method, _request. Since you pass a string type to the class constructor, it's attempting to call this method on the string object and (rightly) complains that the method isn't a member of str.

Here is the git repo. In line 79, you can see where this call is taking place:

return self.parent._request('/api/search', query_args, service='exploits')

Thus, you can see your parent variable should be an instance of Shodan, or your api variable.

Upvotes: 0

mic4ael
mic4ael

Reputation: 8310

The parent variable should be of type Shodan. You are initializing the Exploits class with string variable. Here is the line you causing you the problems https://github.com/achillean/shodan-python/blob/master/shodan/client.py#L79.

Upvotes: 0

Related Questions