Skip to content

[Advanced] Group Data Suites

Ivan Zhang edited this page Aug 27, 2023 · 2 revisions

Group Data Suite

The library exposes the GroupDataSuite class (defined in data_checks/classes/group_data_suite.py) which provides an additional abstraction on top of DataSuite.

Suppose you want to run the same check over many different objects. For example assume you have ItemCheck that checks if a certain Item is valid or not using various rules (i.e. quality, price, etc.). You have hundreds of these items. You could:

  1. Create a suite for each item and run them individually
  2. Pass the item as an argument to each of the check's rules for all items However both methods are tedious and inefficient. A GroupDataSuite allows you to easily define a group of items and then run the same checks on each item in the group. Begin by subclassing the GroupDataSuite class:
from data_checks.group_data_suite import GroupDataSuite

class MyFirstGroupDataSuite(GroupDataSuite):
    pass

Then override the required class methods:

class MyFirstGroupDataSuite(GroupDataSuite):
    @classmethod
    def suite_config(cls) -> dict:
        return {}

    @classmethod
    def group_name(cls) -> str:
        return "item"

    @classmethod
    def group(cls) -> list:
        return [
            Item("item1", ...),
            Item("item2", ...),
            ...
        ]

    @classmethod
    def group_checks(cls) -> list[type[Check] | str]:
        return [
            ItemCheck
        ]

In the above example we define several methods:

  • suite_config(cls) -> dict: Define the suite's configuration. The same as in DataSuite (see Data Suite).
  • group_name(cls) -> str: Identifier for each element in the group. This is the attribute that will be used to get each element in the specified checks. For example, if the group name is "item", then each element in the group will be accessed through self.item in each check.
  • group(cls) -> list: List of group's elements. Each element will be passed into the specified checks. Each element must be JSON serializable. In each check, this element can be accessed through self.group_name (i.e. self.item in this example).
  • group_checks(cls) -> list[type[Check] | str]: Checks to be run on each element in the group. For example:
    [
        CheckClass1,
        CheckClass2,
        ...
    ]
    with group
    [
        element1,
        element2,
        ...
    ]
    will run CheckClass1 on element1, CheckClass1 on element2, CheckClass2 on element1, and CheckClass2 on element2.

โ—IMPORTANT
Note that we are overriding group_checks and NOT checks.

โ—IMPORTANT
Note that group name and values need to have a __str__ method defined (see ๐Ÿ›‘ Warnings).

๐ŸŽ‰ That's it! ๐ŸŽ‰ GroupDataSuite can be instantiated and run in the same manner as DataSuite (see Instantiating and Running Suites ). Now you can access the group name and value in your checks:

from data_checks.data_check import DataCheck

class ItemCheck(DataCheck):
    ...
    def rule_discount_limit(self):
        item: Item = self.item
        assert_that(
            item.discount,
            less_than_or_equal_to(
                item.price,
            ),
            f"discount should not be greater than price for productId: {item.product_id}",
        )
    ...

See the full example in examples/operations/inventory/inventory_suite.py.

Clone this wiki locally