    def from_tuples(self, l:List[tuple]):
        """Parse query from list of tuples

        Examples
        --------
        >>> from rocketry.pybox.query import parser
        >>> qry = parser.from_tuples([
        ...     ('mydate$min', '2021-07-01'),
        ...     ('mydate$max', '2021-07-15'),
        ...     ('mykey3', 'this'),
        ...     ('mykey3', 'that')
        ... ])
        >>> str(qry)
        "((<mydate> >= '2021-07-01') & (<mydate> <= '2021-07-15') & ((<mykey3> == 'this') | (<mykey3> == 'that')))"
        """
        key_count = Counter(item[0] for item in l)
        multi = []
        statement = None
        for key, val in l:
            substatement = self._get_operation(key, val)
            if key_count[key] > 1:
                multi.append(substatement)
                continue

            if statement is None:
                statement = substatement
            else:
                statement &= substatement

        if multi:
            substatement = Any(*multi)
            if statement is None:
                statement = substatement
            else:
                statement &= Any(*multi)

        if statement is None:
            return true
        return statement
Parse query from list of tuples

Examples
--------
>>> from rocketry.pybox.query import parser
>>> qry = parser.from_tuples([
...     ('mydate$min', '2021-07-01'),
...     ('mydate$max', '2021-07-15'),
...     ('mykey3', 'this'),
...     ('mykey3', 'that')
... ])
>>> str(qry)
"((<mydate> >= '2021-07-01') & (<mydate> <= '2021-07-15') & ((<mykey3> == 'this') | (<mykey3> == 'that')))"
rocketry/pybox/query/parse.py