Source code for pom.ui.table

"""
---------
POM table
---------
"""

# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#    http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied.
# See the License for the specific language governing permissions and
# limitations under the License.

from selenium.webdriver.common.by import By

from .base import Block, register_ui
from ..utils import log, cache

__all__ = [
    'Row',
    'Header',
    'Body',
    'Footer',
    'Table',
    'List',
]


def _merge_xpath(xpath, attr):
    if xpath.endswith(']'):
        return xpath[:-1] + ' and {}]'.format(attr)
    else:
        return xpath + '[{}]'.format(attr)


class _CellsMixin(object):

    @property
    @log
    def cells(self):
        locator = By.XPATH, self.cell_xpath
        _cells = []

        for index, element in enumerate(self.find_elements(locator)):
            if element.is_displayed():

                cell = self.cell_cls(locator[0], locator[1], index=index)
                cell.container = self
                _cells.append(cell)

        return _cells

    def cell(self, name):
        cell = self.cell_cls(By.XPATH, self._cell_selector(name))
        cell.container = self
        return cell

    def _cell_selector(self, name):
        position = self.container.columns[name]
        return _merge_xpath(self.cell_xpath, 'position()={}'.format(position))


class _RowsMixin(object):

    @property
    @log
    def rows(self):
        """Visible rows."""
        locator = By.XPATH, self.row_xpath
        _rows = []

        for index, element in enumerate(self.find_elements(locator)):
            if element.is_displayed():

                row = self.row_cls(locator[0], locator[1], index=index)
                row.container = self
                _rows.append(row)

        return _rows


[docs]class Row(Block, _CellsMixin): """Row of table.""" cell_cls = Block cell_xpath = './/td'
class Header(Block, _CellsMixin): """Header of table.""" cell_cls = Block cell_xpath = './/th' class Body(Block, _RowsMixin): """Table body.""" @property @cache def row_cls(self): """Row table class.""" return self.container.row_cls @property @cache def row_xpath(self): """Row xpath.""" return self.container.row_xpath @property @cache def columns(self): """Table columns.""" return self.container.columns def row(self, **kwgs): """Get row of table.""" row = self.row_cls(By.XPATH, self._row_selector(**kwgs)) row.container = self return row def _row_selector(self, **kwgs): pos_tmpl = 'position()={} and contains(., "{}")' cell_selectors = [] for name, value in kwgs.items(): position = self.columns[name] cell_xpath = _merge_xpath(self.row_cls.cell_xpath, pos_tmpl.format(position, value)) cell_selectors.append(cell_xpath) cell_selector = " and ".join(cell_selectors) return _merge_xpath(self.row_xpath, cell_selector) class Footer(Block): """Table footer.""" @register_ui( header=Header(By.TAG_NAME, 'thead'), body=Body(By.TAG_NAME, 'tbody'), footer=Footer(By.TAG_NAME, 'tfoot'))
[docs]class Table(Block): """Table.""" row_cls = Row row_xpath = './/tr' columns = None @property def rows(self): """Table rows.""" return self.body.rows
[docs] def row(self, **kwgs): """Get row of table.""" return self.body.row(**kwgs)
[docs]class List(Block, _RowsMixin): """List.""" row_cls = Row row_xpath = ".//li"
[docs] def row(self, content): """Get row of table.""" xpath = _merge_xpath(self.row_xpath, 'contains(., "{}")'.format(content)) row = self.row_cls(By.XPATH, xpath) row.container = self return row