Python - 如何将实例变量值传递给描述符参数?



考虑到以下情况,

项目列表类:

# 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
)

在这种情况下,我想self.item_num值传递给类中的item_num内部定位器字典ItemList

原因是我想要item_id中的每一个,item_title都指的是特定的item_num

我被困在这一部分:

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值无法传递给定位符。

实现:

# 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

是否可以从实例变量更新数据描述符?

如何将实例变量值传递给数据描述符参数?


附加信息:

我试图调用item_iditem_title作为实例属性,但没有运气。我注意到数据描述符不能是这篇文章中的实例属性:数据描述符应该是类属性

项目类别:

# 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
)

描述符:

# 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

我找到了这篇文章,并想出了将描述符添加到对象的解决方案。

下面的解决方案对我有用:

  1. __getattribute____setattr__添加到项目类

    # 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
    )
    def __getattribute__(self, name):
    value = object.__getattribute__(self, name)
    if hasattr(value, '__get__'):
    value = value.__get__(self, self.__class__)
    return value
    def __setattr__(self, name, value):
    try:
    obj = object.__getattribute__(self, name)
    except AttributeError:
    pass
    else:
    if hasattr(obj, '__set__'):
    return obj.__set__(self, value)
    return object.__setattr__(self, name, value)
    
  2. 将类属性移动到ItemList构造函数中的实例属性

    # 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):
    def __init__(self, context, item_num=0):
    self.item_num = item_num
    # self.item_num is able to be passed to locators
    self.item_id = TextReadOnly(locators['item_id'].format(item_num=self.item_num))
    self.item_title = TextReadOnly(locators['item_title'].format(item_num=self.item_num))
    super(ItemList, self).__init__(
    context
    )
    

最新更新