'str' object has no attribute 'url' - python

I've looked through several articles on this topic but I could not figure out any way to adapt this to my scenario. I'm running this code in python3 console:
### API MANAGER ###
import requests, time, pandas as pd
class api_manager():
#from ipython.display import display, HTML
def __init__(self, api_identifier = 1):
test_api = "570/"
live_api = "205790/"
self.heroes = []
self.items = []
self.token = ""
self.api = ""
self.url = "https://api.steampowered.com/"
if api_identifier == 1:
self.api = live_api
else:
self.api = test_api
self.get_access_token()
self.initialize_heroes()
self.initialize_items()
pass
def get_access_token(self):
with open("conf/access.config") as file:
self.token = file.read().split(":")[1]
file.close()
pass
def initialize_heroes(self):
api_method = "IEconDOTA2_"
response = requests.get(self.url + api_method + self.api + "GetHeroes/v1/?format=JSON&language=en_us&key=" + self.token)
hero_list = response.json()
for hero_id in range(len(hero_list['result']['heroes'])):
self.heroes.append([hero_list['result']['heroes'][hero_id]['id'], hero_list['result']['heroes'][hero_id]['localized_name'], hero_list['result']['heroes'][hero_id]['name'].replace('npc_dota_hero_', "").replace("_", " ")])
#self.heroes.sort()
#heroes_df = self.pd.DataFrame(self.heroes, columns=["ID", "Hero", "Hero Tag"])
#self.pd.set_option('display.max_colwidth', -1)
#display(HTML(heroes_df.to_html(index = False)))
pass
def initialize_items(self):
api_method = "IEconDOTA2_"
response = requests.get(self.url + api_method + self.api + "GetGameItems/v1/?format=JSON&language=en_us&key=" + self.token)
item_list = response.json()
for item_id in range(len(item_list['result']['items'])):
self.items.append([item_list['result']['items'][item_id]['id'], item_list['result']['items'][item_id]['localized_name'], item_list['result']['items'][item_id]['name']])
#self.items.sort()
#items_df = self.pd.DataFrame(self.items, columns=["ID", "Item", "Item Tag"])
#self.pd.set_option('display.max_colwidth', -1)
#display(HTML(items_df.to_html(index = False)))
pass
def get_match_details(match_id, self):
api_method = "IDOTA2Match_"
response = requests.get(self.url + api_method + self.api + "GetMatchDetails/V001/?format=JSON&language=en_us&key=" + self.token + "&match_id=" + str(match_id))
print(response.json())
pass
def get_match_details_in_range(match_id, match_id_upper_bound, self):
api_method = "IDOTA2Match_"
for next_match_id in range(match_id, match_id_upper_bound):
response = requests.get(self.url + api_method + self.api + "GetMatchDetails/V001/?format=JSON&language=en_us&key=" + self.token + "&match_id=" + str(next_match_id))
print(response.json())
time.sleep(1.05)
pass
def __str__(self):
return self.url + " " + self.api
def __repr__(self):
return self.url + " " + self.api
And I'm getting this error:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "E:\Dropbox\DotA 2 WebAPI Development\Executable Python Files\dota_api_manager.py", line 77, in get_match_details
response = requests.get(self.url + api_method + self.api + "GetMatchDetails/V001/?format=JSON&language=en_us&key=" + self.token + "&match_id=" + str(match_id))
AttributeError: 'str' object has no attribute 'url'
I have tried different things like moving the import statement into the class and stuff like that and also tried implementing __str__() and __repr__() as suggested in this post but I couldn't get this to work. I'm fairly new to Python so it might be that there's something obvious that I just overlooked. Thanks in advance for you help and let me know if there's any additional information you could need!

Related

Test using mock raises exception

I have a strange error that I can't get my head around. I am trying to test whether a method is called within side another method. I have used the debugger on PyCharm and it seems to be, however, the test fails because the second function is called raises an exception.
test.py
def test_reply_to_toot(self, directory):
with patch("mastodon.Mastodon") as mastodon_mock:
mastodon_mock.return_value = Mock()
mastodon_mock.status_post.assert_called_with(bot.reply_to_toot("1", account_name="#fake", message="test"))
bot.py (method being tested)
# Set up Mastodon
mastodon = Mastodon(
access_token=os.getenv("ACCESS_TOKEN"),
api_base_url=settings.BASE_ADDRESS
)
def reply_to_toot(post_id, account_name, message=None, status_notifications=None):
media_ids = []
for fn in os.listdir(str(settings.INPUT_FOLDER)):
if fn.endswith(('.jpeg', '.png')):
print(Path(fn))
image_dict = mastodon.media_post(str(settings.INPUT_FOLDER / fn))
media_ids.append(image_dict["id"])
if message is not None:
parts = []
total_len = str(len(message) // settings.MAX_MESSAGE_LENGTH + 1)
count = 1
split_lines = message.splitlines(True)
while split_lines:
message_part = "#" + account_name + " {}/".format(count) + total_len + "\n\n"
while split_lines != [] and len(message_part) + len(split_lines[0]) < settings.MAX_MESSAGE_LENGTH:
message_part += split_lines[0]
split_lines = split_lines[1:]
parts.append(message_part)
count += 1
for part in parts:
print(part)
post_id = mastodon.status_post(status=part, media_ids=media_ids, in_reply_to_id=post_id)
else:
while media_ids:
mastodon.status_post(status=message, media_ids=media_ids[0:4], in_reply_to_id=post_id)
media_ids = media_ids[4:]
Exception raised:
Error
Traceback (most recent call last):
File "C:\Python35\lib\unittest\case.py", line 58, in testPartExecutor
yield
File "C:\Python35\lib\unittest\case.py", line 600, in run
testMethod()
File "C:\Python35\lib\unittest\mock.py", line 1157, in patched
return func(*args, **keywargs)
File "C:\Users\Hugh\PycharmProjects\summer-project\test\test.py", line 70, in test_reply_to_toot
mastodon_mock.status_post.assert_called_with(bot.reply_to_toot("1", account_name="#fake", message="test"))
File "C:\Users\Hugh\PycharmProjects\summer-project\src\bot.py", line 65, in reply_to_toot
post_id = mastodon.status_post(status=part, media_ids=media_ids, in_reply_to_id=post_id)
File "<decorator-gen-60>", line 2, in status_post
File "C:\Users\Hugh\PycharmProjects\summer-project\venv\lib\site-packages\mastodon\Mastodon.py", line 102, in wrapper
return function(self, *args, **kwargs)
File "C:\Users\Hugh\PycharmProjects\summer-project\venv\lib\site-packages\mastodon\Mastodon.py", line 1776, in status_post
return self.__api_request('POST', '/api/v1/statuses', params, headers = headers, use_json = use_json)
File "C:\Users\Hugh\PycharmProjects\summer-project\venv\lib\site-packages\mastodon\Mastodon.py", line 3429, in __api_request
error_msg)
mastodon.Mastodon.MastodonNotFoundError: ('Mastodon API returned error', 404, 'Not Found', 'The status you are trying to reply to does not appear to exist.')
Assertion failed
Assertion failed
Ran 1 test in 0.146s
FAILED (errors=1)
Process finished with exit code 1
Assertion failed
Assertion failed
Assertion failed
Assertion failed
Solution
Mock Mastodon within the context of bot module
Example
test_bot.py
import unittest
import bot
from unittest.mock import patch
class TestBot(unittest.TestCase):
#patch("bot.Mastodon")
def test_bot(self, mastodon_mock):
b = bot.Bot()
breakpoint()
mastodon_mock.return_value = Mock()
mastodon_mock.status_post.assert_called_with(
b.reply_to_toot("1", account_name="#fake", message="test")
)
bot.py
import os
from mastodon import Mastodon
class Bot(object):
# Set up Mastodon
def __init__(self, access_token="", base_address=""):
self.mastadon = Mastodon(
access_token,
base_address
)
def reply_to_toot(post_id, account_name, message=None, status_notifications=None):
media_ids = []
for fn in os.listdir(str(settings.INPUT_FOLDER)):
if fn.endswith(('.jpeg', '.png')):
print(Path(fn))
image_dict = self.mastodon.media_post(str(settings.INPUT_FOLDER / fn))
media_ids.append(image_dict["id"])
if message is not None:
parts = []
total_len = str(len(message) // settings.MAX_MESSAGE_LENGTH + 1)
count = 1
split_lines = message.splitlines(True)
while split_lines:
message_part = "#" + account_name + " {}/".format(count) + total_len + "\n\n"
while split_lines != [] and len(message_part) + len(split_lines[0]) < settings.MAX_MESSAGE_LENGTH:
message_part += split_lines[0]
split_lines = split_lines[1:]
parts.append(message_part)
count += 1
for part in parts:
print(part)
post_id = self.mastodon.status_post(status=part, media_ids=media_ids, in_reply_to_id=post_id)
else:
while media_ids:
self.mastodon.status_post(status=message, media_ids=media_ids[0:4], in_reply_to_id=post_id)
media_ids = media_ids[4:]
References
Partial Mocking: https://docs.python.org/3/library/unittest.mock-examples.html#partial-mocking

Python zlib error while bruteforcing protected zip file

Basically, i'm trying to write a script to bruteforce a protected zip file in python that tries every character combination (i.e. aa,ba,ca,da etc). But after a few tries it retrieves a strange error, and i'm not being able to find nowhere a solution for it.
Program:
import zipfile as z
class zipVictim:
def __init__(self,file):
self.found = False
self.password = ''
self.file = file
self.extracted_file_list = []
def bruteforceAttack(self,start_char: int,end_char: int,length: int,deep_loop=False,print_mode=False):
"""
Doc
"""
def _loop_chain(self,file,start_char,end_char,length):
lList = []
sPass = ''
iAttempt = 1
for iInc in range(length):
lList.append(start_char)
while lList[len(lList)-1] < end_char:
for iInc2 in range(start_char,end_char):
for iInc3 in range(len(lList)):
sPass = sPass + chr(lList[iInc3])
if iInc3 == 0:
lList[iInc3] = lList[iInc3] + 1
elif lList[iInc3 -1] > end_char:
lList[iInc3] = lList[iInc3] + 1
lList[iInc3 -1] = start_char
try:
if print_mode:
print("Attempt %s, password: %s" % (iAttempt,sPass),end='\r')
iAttempt = iAttempt + 1
oFile.extractall(pwd=sPass.encode())
self.extracted_file_list = oFile.namelist()
self.password = sPass
self.found = True
return self.found
except RuntimeError:
pass
sPass = ''
return self.found
oFile = self.file
if not deep_loop:
_loop_chain(self,oFile,start_char,end_char,length)
else:
for iInc in range(length):
_loop_chain(self,oFile,start_char,end_char,iInc+1)
if __name__ == '__main__':
file = z.ZipFile('data.zip')
s = zipVictim(file)
s.bruteforceAttack(64,125,2,print_mode=True)
Error Retrieved:
Traceback (most recent call last):
File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python36_64\lib\zipfile.py", line 925, in _read1
data = self._decompressor.decompress(data, n)
zlib.error: Error -3 while decompressing data: invalid block type
Does anybody know what trigger this error and how to solve it?

Class does not pass the self variables to functions inside of it

I am a newbie programmer
I am defining this simple class but I receive the following error
I am not able to understand what im doing wrong
from PIL import Image
class PreProcessing(object):
def __init__(self,NAME):
super(PreProcessing,self).__init__()
self.name = NAME
self.newsize = 512
PATH = '/home/alireza/Desktop/ssd'
self.pathImage = PATH + '/' + self.name + '.jpg'
self.pathAnn = PATH + '/' + self.name + '.xml'
def image_loader(self):
print(self.pathImage )
When I call
NAME = '002498'
PreProcessing.image_loader(NAME)
, i get this error:
---------------------------------------------------------------------------
AttributeError Traceback (most recent call last)
<ipython-input-38-5747710fa005> in <module>()
3 sizee = [1, 3, 375, 500]
4 # A= PreProcessing(NAME)
----> 5 PreProcessing.image_loader(NAME)
<ipython-input-37-5f788218f7e3> in image_loader(self)
10
11 def image_loader(self):
---> 12 print(self.pathImage )
AttributeError: 'str' object has no attribute 'pathImage'
As #kindall said in his comment, you aren't making an instance of your class. It'll work if you set it up like this, creating a "hello" object of class PreProcessing():
from PIL import Image
class PreProcessing(object):
def __init__(self,NAME):
super(PreProcessing,self).__init__()
self.name = NAME
self.newsize = 512
PATH = '/home/alireza/Desktop/ssd'
self.pathImage = PATH + '/' + self.name + '.jpg'
self.pathAnn = PATH + '/' + self.name + '.xml'
def image_loader(self):
print(self.pathImage )
NAME = "12345"
hello = PreProcessing(NAME)

Python script to update particular fields in webpage

I'm very new to Python, my requirement is that i have CQ webpage and need to update the status of BugID based on particular fields.
Here is the sample code i'm trying.
import httplib2
import json
import getpass
import urllib
from string import Template
from xml.dom.minidom import parseString
class Credentials():
def assign_user (self):
self._user = 'user'
def assign_passwd (self):
self._passwd = 'pawrd'
user_cred = Credentials()
class RestLink:
def __init__(self, link, baseline_cr= 'ENGR00xxxx'):
self._link = Template(link)
self.cr = baseline_cr
def get_link(self):
return self._link.safe_substitute(recordId=self.cr,
loginid=user_cred.get_user(),
password=user_cred.get_passwd())
class CQBase:
SERVER = 'cq.am.domain.net'
RESPONSE_OK = 'OK'
def __init__(self, logger):
self._logger = logger
def send_request(self):
data = ''
try:
conn = httplib2.HTTPConnectionWithTimeout(self.SERVER)
conn.request("GET", link)
res = conn.getresponse()
data = res.read()
if res.reason != self.RESPONSE_OK:
raise ParseException('Cannot execute request!')
conn.close()
except:
conn.close()
raise
return data
class CQIssueReader(CQBase):
VIEW_CR_LINK = '/cqweb/restapi/TSR/ENGR/RECORD/${recordId}?format=JSON&recordType=CR&loginId=${loginid}&password=${password}&noframes=true'
def __init__(self, cr, logger):
CQBase.__init__(self, logger)
self._cr = cr
self._headline = ''
self._subtype = ''
self._branch = ''
self._is_resolved = 0
self._is_integrated = 0
self.parse_cr()
def parse_cr(self):
self._is_resolved = False
self._is_integrated = False
data = self.send_request(RestLink(self.VIEW_CR_LINK, self._cr).get_link())
parsedData = json.loads(data)
for field in parsedData['fields']:
if field['FieldName'] == 'Headline':
self._headline = field['CurrentValue']
if field['FieldName'] == 'Integrated':
self._logger.log_details('\tIntegrated = ' + field['CurrentValue'])
if field['CurrentValue'] == 'Y':
self._is_integrated = True
if field['FieldName'] == 'State':
self._logger.log_details('\tState = ' + field['CurrentValue'])
if (field['CurrentValue'] == 'Resolved') or (field['CurrentValue'] == 'Closed')\
or (field['CurrentValue'] == 'Verified'):
self._is_resolved = True
if field['FieldName'] == 'Subtype':
self._subtype = field['CurrentValue']
if field['FieldName'] == 'BranchName':
self._branch = field['CurrentValue']
self._logger.log_details('\tBranchName = ' + self._branch)
def get_headline(self):
return self._headline
def get_subtype(self):
return self._subtype
def get_branch_name(self):
return self._branch
test = CQIssueReader(CQBase)
test_data = CQIssueReader.parse_cr()
print (test_data)
i get following error with above code:
Traceback (most recent call last):
File "test.py", line 97, in <module>
test = CQIssueReader(CQBase)
TypeError: __init__() missing 1 required positional argument: 'logger'
Kindly guide me where i'm going wrong.
According to def __init__(self, cr, logger): your Class needs a parameter called logger to work. In test = CQIssueReader(CQBase), you've not passed in a logger.

Python - global name is not defined when calling function from class __init__ method

I am new to Python and working on a class for storing meaningful data pieces about books. I have started as follows:
class BookDisplay:
def __init__(self, _name, _isbn, _price, _picture, _link):
self.name = _name
self.isbn = _isbn
self.price = _price
self.picture = _picture
self.link = _link
self.xmlString = MakeXMLString(_name, _isbn, _price, _picture, _link)
name = ""
isbn = ""
price = 0.0
picture = "" #a URL
link = ""
xmlString = ""
I thought this __init__ method would just be able to call MakeXMLString, which I defined in the same file (bookdisplay.py), right below the BookDisplay class:
def MakeXMLString(_name, _isbn, _price, _picture, _link): #python multi-line syntax
xmlString = "<name>" + _name + "</name>" \
+ "<isbn>" + _isbn + "</isbn>" \
+ "<price>" + str(_price) + "</price>" \
+ "<picture>" + _picture + "</picture>" \
+ "<link>" + _link + "</link>"
return xmlString
Originally, I actually had MakeXMLString as a method within the class, like this:
def MakeXMLString(self):
self.xmlString = "<name>" + self.name + "</name>" \
+ "<isbn>" + self.isbn + "</isbn>" \
+ "<price>" + str(self.price) + "</price>" \
+ "<picture>" + self.picture + "</picture>" \
+ "<link>" + self.link + "</link>"
In that case, __init__ contained this call:
self.xmlString = self.MakeXMLString()
In both cases, when trying to instantiate BookDisplay from another file:
from bookdisplay import BookDisplay
...
...
thumbnails = []
...
thumbnails.append(BookDisplay(titleField, "-1", float(priceField), imgField, linkField))
...I get the following global name error (this traceback in particular for the not-within-class function):
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "search.py", line 30, in ebaySearch
handleDocument(doc)
File "search.py", line 59, in handleDocument
handleItems(items, outputFile)
File "search.py", line 102, in handleItems
thumbnails.append(BookDisplay(titleField, "-1", float(priceField), imgField, linkField))
File "bookdisplay.py", line 15, in __init__
self.xmlString = MakeXMLString(_name, _isbn, _price, _picture, _link)
NameError: global name 'MakeXMLString' is not defined
What am I missing here? From what I can tell, MakeXMLString is perfectly accessible to the class.
when you defined MakeXMLString as a method, it is not returning anything so
self.xmlString = self.MakeXMLString()
will overwrite self.xmlString and make it point to the method itself.
With the way you have it defined now, MakeXMLString is not accessible from the other file, so you have to manually import it as well by doing:
from bookdisplay import BookDisplay, MakeXMLString
EDIT:
upon rereading, you aren't calling MakeXMLString from the other file, so the error is in bookDisplay.py; make sure
def MakeXMLString()
is on the same indent level as the class definition, otherwise it'll be interpreted as a method.

Categories

Resources