Considering below case,
ItemList Class:
# filename: item_list.py # locators dictionary is intentionally placed outside `ItemList` class locators = { 'item_id': 'css=tr:nth-of-type({item_num}) .id', 'item_title': 'css=tr:nth-of-type({item_num}) .alert-rules', # other properties } class ItemList(Item): # --- these are data descriptors --- # getting item_id value based on its item_num item_id = TextReadOnly(locators['item_id'].format(item_num=self.item_num)) # getting item_title value based on its item_num item_title = TextReadOnly(locators['item_title'].format(item_num=self.item_num)) def __init__(self, context, item_num=0): # self.item_num can't be passed to locators self.item_num = item_num super(ItemList, self).__init__( context ) In this case, I want to pass self.item_num value to item_num inside locators dictionary in ItemList class.
The reason is I want each of item_id and item_title refers to particular item_num.
I'm stuck on this part :
item_id = TextReadOnly(locators['item_id'].format(item_num=self.item_num)) item_title = TextReadOnly(locators['item_title'].format(item_num=self.item_num)) self.item_num value can't be passed to locators when instance is already made.
Implementation:
# filename: test.py # print item_id values from item_num=1 item_1 = ItemList(context, 1) print (‘Item_id_1: ’ + item_1.id) # print item_id values from item_num=2 item_2 = ItemList(context, 2) print (‘Item_id_2: ’ + item_2.id) # ^ no result produced from item_1.id and item_2.id because self.item_num value can't be passed to locators Is it possible to update data descriptor from instance variable?
How to pass instance variable value to data descriptor parameter?
Additional info:
I tried to call item_id and item_title as instance attribute but no luck. I noticed that data descriptor can’t be instance attribute from this post: Data descriptor should be a class attribute
Item Class:
# filename: item.py import abc class Item(Page): __metaclass__ = abc.ABCMeta def __init__(self, context): self.__context = context super(Item, self).__init__( self.__context.browser ) Descriptor:
# filename: text_read_only.py class TextReadOnly(object): def __init__(self, locator): self.__locator = locator def __get__(self, instance, owner=None): try: e = instance.find_element_by_locator(self.__locator) except AttributeError: e = instance.browser.find_element_by_locator(self.__locator) return e.text def __set__(self, instance, value): pass
item_idanditem_titleto vary per instance, why make them class attributes in the first place?item_idanditem_titleas class attributes because I want to use descriptor TextReadOnly. I noticed from this post that data descriptor should be a class attribute. Is there another approach to implement it?item_idanditem_titlelook more like Instance Descriptors than Data Descriptors, so I'll make them as instance attributes. [1]: stackoverflow.com/questions/5189699/…