Пример #1
0
    def filter(self, *args, **kwargs):
        """
        Returns a ResourceSet object.
        The returned ResourceSet object will be filtered based on
        the arguments and keyword arguments.

        Arguments can be RQL filter expressions as strings
        or R objects.

        Ex.

        .. code-block:: python

            rs = collection.filter('eq(field,value)', 'eq(another.field,value2)')
            rs = collection.filter(R().field.eq('value'), R().another.field.eq('value2'))

        All the arguments will be combined with logical ``and``.

        Filters can be also specified as keyword argument using the ``__`` (double underscore)
        notation.

        Ex.

        .. code-block:: python

            rs = collection.filter(
                field=value,
                another__field=value,
                field2__in=('a', 'b'),
                field3__null=True,
            )

        Also keyword arguments will be combined with logical ``and``.


        :raises TypeError: If arguments are neither strings nor R objects.
        :return: A ResourceSet with the filters applied.
        :rtype: ResourceSet
        """
        query = R()
        for arg in args:
            if isinstance(arg, str):
                query &= R(_expr=arg)
                continue
            if isinstance(arg, R):
                query &= arg
                continue
            raise TypeError(f'arguments must be string or R not {type(arg)}')

        if kwargs:
            query &= R(**kwargs)

        return ResourceSet(
            self._client,
            self._path,
            query=query,
        )
Пример #2
0
def generate(client, parameters, progress_callback, renderer_type,
             extra_context):
    """
    Extracts data from Connect using the ConnectClient instance
    and input parameters provided as arguments, applies
    required transformations (if any) and returns an iterator of rows
    that will be used to fill the Excel file.
    Each element returned by the iterator must be an iterator over
    the columns value.

    :param client: An instance of the CloudBlue Connect
                    client.
    :type client: cnct.ConnectClient
    :param parameters: Input parameters used to calculate the
                        resulting dataset.
    :type parameters: dict
    :param progress_callback: A function that accepts t
                                argument of type int that must
                                be invoked to notify the progress
                                of the report generation.
    :type progress_callback: func
    """

    filters = R().visibility.catalog.eq(True) & R().status.eq('published')

    count = client.products.filter(filters).count()

    i = 0

    ctx = {
        'products_count': count,
        'vendors_count': 0,
        'generation_date': date.today().strftime('%B %d, %Y'),
    }

    vendors = set()

    data = []

    for prod in client.products.filter(filters):
        i += 1
        data.append(prod)
        vendors.add(prod['owner']['id'])
        progress_callback(i, count)

    ctx['vendors_count'] = len(vendors)

    extra_context(ctx)

    return data
Пример #3
0
def test_collection_filter(col_factory):
    collection = col_factory(path='resource')

    rs = collection.filter()

    assert isinstance(rs, ResourceSet)
    assert rs._client == collection._client
    assert rs.path == collection.path
    assert bool(rs.query) is False

    rs = collection.filter('eq(field,value)')

    assert rs._client == collection._client
    assert rs.path == collection.path
    assert str(rs.query) == 'eq(field,value)'

    rs = collection.filter(R().field.eq('value'))

    assert rs._client == collection._client
    assert rs.path == collection.path
    assert str(rs.query) == 'eq(field,value)'

    rs = collection.filter(status__in=('status1', 'status2'))

    assert rs._client == collection._client
    assert rs.path == collection.path
    assert str(rs.query) == 'in(status,(status1,status2))'
Пример #4
0
    def __init__(
        self,
        client,
        path,
        query=None,
    ):

        self._client = client
        self._path = path
        self._query = query or R()
        self._results = None
        self._limit = self._client.default_limit or 100
        self._offset = 0
        self._slice = False
        self._content_range = None
        self._fields = None
        self._search = None
        self._select = []
        self._ordering = []
        self._config = {}
Пример #5
0
def test_rs_filter(rs_factory):
    rs = rs_factory()

    assert rs.query is not None

    s1 = rs.filter()

    assert s1 != rs
    assert bool(s1.query) is False

    s1 = rs.filter('eq(field,value)')

    assert str(s1.query) == 'eq(field,value)'

    s1 = rs.filter(R().field.eq('value'))

    assert str(s1.query) == 'eq(field,value)'

    s2 = s1.filter(status__in=('status1', 'status2'))

    assert s1 != s2

    assert str(s2.query) == 'and(eq(field,value),in(status,(status1,status2)))'
Пример #6
0
    def sync(self):  # noqa: CCR001
        ws = self._wb["Items"]

        row_indexes = trange(
            2,
            ws.max_row + 1,
            disable=self._silent,
            leave=True,
            bar_format=DEFAULT_BAR_FORMAT,
        )
        for row_idx in row_indexes:
            data = _RowData(
                *[ws.cell(row_idx, col_idx).value for col_idx in range(1, 14)])
            row_indexes.set_description(
                f'Processing item {data.id or data.mpn}')
            if data.action == '-':
                self._mstats.skipped()
                continue
            row_errors = self._validate_row(data)
            if row_errors:
                self._mstats.error(row_errors, row_idx)
                continue

            if data.action == 'create':
                rql = R().mpn.eq(data.mpn)
                item = (self._client.products[self._product_id].items.filter(
                    rql).first())
                if item:
                    self._mstats.error(
                        f'Cannot create item: item with MPN `{data.mpn}`'
                        f' already exists with ID `{item["id"]}`.',
                        row_idx,
                    )
                    continue
                row_indexes.set_description(f"Creating item {data[1]}")
                try:
                    item = create_item(
                        self._client,
                        self._product_id,
                        self._get_item_payload(data),
                    )
                    self._mstats.created()
                    self._update_sheet_row(ws, row_idx, item)
                except Exception as e:
                    self._mstats.error(str(e), row_idx)

            if data.action == 'update':
                item = self._get_item(data)

                if not item:
                    field = 'ID' if data.id else 'MPN'
                    value = data.id if data.id else data.mpn
                    self._mstats.error(
                        f'Cannot update item: item with {field} `{value}` '
                        f'the item does not exist.',
                        row_idx,
                    )
                    continue

                row_indexes.set_description(f"Updating item {item['id']}")
                if item['status'] == 'published':
                    payload = {
                        'name': data.name,
                        'mpn': data.mpn,
                        'description': data.description,
                        'ui': {
                            'visibility': True
                        },
                    }
                else:
                    payload = self._get_item_payload(data)
                    if item['type'] == 'ppu':
                        del payload['period']
                try:
                    item = update_item(
                        self._client,
                        self._product_id,
                        item['id'],
                        payload,
                    )
                    self._mstats.updated()
                    self._update_sheet_row(ws, row_idx, item)
                except Exception as e:
                    self._mstats.error(str(e), row_idx)

            if data.action == 'delete':
                item = self._get_item(data)

                if not item:
                    field = 'ID' if data.id else 'MPN'
                    value = data.id if data.id else data.mpn
                    self._mstats.error(
                        f'Cannot update item: item with {field} `{value}` '
                        f'the item does not exist.',
                        row_idx,
                    )
                    continue
                try:
                    delete_item(
                        self._client,
                        self._product_id,
                        item['id'],
                    )
                    self._mstats.deleted()
                except Exception as e:
                    self._mstats.error(str(e), row_idx)
Пример #7
0
def generate(client, parameters, progress_callback, renderer_type,
             extra_context):

    account = client.collection('accounts').all().first()
    account_id = account['id']
    agreements_filter = R().type.eq('service')

    available_products = {}
    agreements_count = 0
    for agreement in client.agreements.filter(agreements_filter):
        if agreement['owner']['id'] != account_id:
            agreements_count += 1
            for product in client.collection('agreements', ).resource(
                    agreement['id'], ).collection('products', ).all():
                if not product['id'] in available_products:
                    available_products[product['id']] = product
                    available_products[product['id']]['agreements'] = [
                        agreement['id']
                    ]
                else:
                    available_products[product['id']]['agreements'].append(
                        agreement['id'])
    i = 0
    count = len(available_products) * 2
    ctx = {
        'products_count': len(available_products),
        'vendors_count': 0,
        'distributors_count': agreements_count,
        'generation_date': date.today().strftime('%B %d, %Y'),
        'api_url': client.endpoint.replace('/public/v1', ''),
        'account_name': account['name'],
        'account_id': account['id'],
    }

    vendors = set()

    data = []

    for prod in available_products:
        i += 1
        available_products[prod]['marketplaces'] = []
        for agreement in available_products[prod]['agreements']:
            marketplaces = client.collection('agreements', ).resource(
                agreement, ).collection('products', ).resource(
                    prod, ).collection('marketplaces', ).all()
            for marketplace in marketplaces:
                available_products[prod]['marketplaces'].append(marketplace)
        progress_callback(i, count)

    for prod in client.collection('products').all().order_by('name'):
        if prod['id'] in available_products:
            prod['marketplaces'] = available_products[
                prod['id']]['marketplaces']
            data.append(prod)
            vendors.add(prod['owner']['id'])
        i += 1
        progress_callback(i, count)

    ctx['vendors_count'] = len(vendors)
    extra_context(ctx)

    return data