def test_where_clause_rendering(self): """ tests that where clauses are rendered properly """ wc = WhereClause('a', EqualsOperator(), 'c') wc.set_context_id(5) self.assertEqual('"a" = %(5)s', six.text_type(wc), six.text_type(wc)) self.assertEqual('"a" = %(5)s', str(wc), type(wc))
def _check_partition_value_generation(self, model, state, reverse=False): """ This generates a some statements based on the partition_key_index of the model. It then validates that order of the partition key values in the statement matches the index specified in the models partition_key_index """ # Setup some unique values for statement generation uuid = uuid4() values = { "k": 5, "v": 3, "partition": uuid, "cluster": 6, "count": 42, "text": "text", "float": 3.1415, "text_2": "text_2", } res = dict((v, k) for k, v in values.items()) items = list(model._partition_key_index.items()) if reverse: items.reverse() # Add where clauses for each partition key for partition_key, position in items: wc = WhereClause(partition_key, EqualsOperator(), values.get(partition_key)) state._add_where_clause(wc) # Iterate over the partition key values check to see that their index matches # Those specified in the models partition field for indx, value in enumerate( state.partition_key_values(model._partition_key_index)): name = res.get(value) self.assertEqual(indx, model._partition_key_index.get(name))
def iff(self, *args, **kwargs): """Adds IF statements to queryset""" if len([x for x in kwargs.values() if x is None]): raise CQLEngineException("None values on iff are not allowed") clone = copy.deepcopy(self) for operator in args: if not isinstance(operator, ConditionalClause): raise QueryException( "{0} is not a valid query operator".format(operator)) clone._conditional.append(operator) for arg, val in kwargs.items(): if isinstance(val, Token): raise QueryException( "Token() values are not valid in conditionals") col_name, col_op = self._parse_filter_arg(arg) try: column = self.model._get_column(col_name) except KeyError: raise QueryException( "Can't resolve column name: '{0}'".format(col_name)) if isinstance(val, BaseQueryFunction): query_val = val else: query_val = column.to_database(val) operator_class = BaseWhereOperator.get_operator(col_op or "EQ") operator = operator_class() clone._conditional.append( WhereClause(column.db_field_name, operator, query_val)) return clone
def test_delete_conditional(self): where = [WhereClause('id', EqualsOperator(), 1)] conditionals = [ConditionalClause('f0', 'value0'), ConditionalClause('f1', 'value1')] ds = DeleteStatement('table', where=where, conditionals=conditionals) self.assertEqual(len(ds.conditionals), len(conditionals)) self.assertEqual(six.text_type(ds), 'DELETE FROM table WHERE "id" = %(0)s IF "f0" = %(1)s AND "f1" = %(2)s', six.text_type(ds)) fields = ['one', 'two'] ds = DeleteStatement('table', fields=fields, where=where, conditionals=conditionals) self.assertEqual(six.text_type(ds), 'DELETE "one", "two" FROM table WHERE "id" = %(0)s IF "f0" = %(1)s AND "f1" = %(2)s', six.text_type(ds))
def test_mintimeuuid_function(self): """ Tests that queries with helper functions are generated properly """ now = datetime.now() where = WhereClause("time", EqualsOperator(), functions.MinTimeUUID(now)) where.set_context_id(5) self.assertEqual(str(where), '"time" = MinTimeUUID(%(5)s)') ctx = {} where.update_context(ctx) self.assertEqual(ctx, {"5": columns.DateTime().to_database(now)})
def test_delete_conditional(self): where = [WhereClause("id", EqualsOperator(), 1)] conditionals = [ ConditionalClause("f0", "value0"), ConditionalClause("f1", "value1") ] ds = DeleteStatement("table", where=where, conditionals=conditionals) self.assertEqual(len(ds.conditionals), len(conditionals)) self.assertEqual( six.text_type(ds), 'DELETE FROM table WHERE "id" = %(0)s IF "f0" = %(1)s AND "f1" = %(2)s', six.text_type(ds), ) fields = ["one", "two"] ds = DeleteStatement("table", fields=fields, where=where, conditionals=conditionals) self.assertEqual( six.text_type(ds), 'DELETE "one", "two" FROM table WHERE "id" = %(0)s IF "f0" = %(1)s AND "f1" = %(2)s', six.text_type(ds), )
def filter(self, **kwargs): """ Adds WHERE arguments to the queryset, returning a new queryset See :ref:`retrieving-objects-with-filters` Returns a QuerySet filtered on the keyword arguments """ # add arguments to the where clause filters if len([x for x in kwargs.values() if x is None]): raise CQLEngineException("None values on filter are not allowed") clone = copy.deepcopy(self) for arg, val in kwargs.items(): col_name, col_op = self._parse_filter_arg(arg) quote_field = True if not isinstance(val, Token): try: column = self.model._get_column(col_name) except KeyError: raise QueryException( "Can't resolve column name: '{0}'".format(col_name) ) else: if col_name != 'pk__token': raise QueryException( "Token() values may only be compared to the " "'pk__token' virtual column" ) column = columns._PartitionKeysToken(self.model) quote_field = False partition_columns = column.partition_columns if len(partition_columns) != len(val.value): raise QueryException( 'Token() received {0} arguments but model has {1} ' 'partition keys'.format( len(val.value), len(partition_columns), ) ) val.set_columns(partition_columns) # get query operator, or use equals if not supplied operator_class = BaseWhereOperator.get_operator(col_op or 'EQ') operator = operator_class() if isinstance(operator, InOperator): if not isinstance(val, (list, tuple)): raise QueryException( 'IN queries must use a list/tuple value' ) query_val = [column.to_database(v) for v in val] elif isinstance(val, BaseQueryFunction): query_val = val elif (isinstance(operator, ContainsOperator) and isinstance(column, (columns.List, columns.Set, columns.Map))): # For ContainsOperator and collections, we query using the # value, not the container query_val = val else: query_val = column.to_database(val) if not col_op: # only equal values should be deferred clone._defer_fields.add(col_name) # map by db field name for substitution in results clone._deferred_values[column.db_field_name] = val clone._where.append( WhereClause( column.db_field_name, operator, query_val, quote_field=quote_field, ) ) return clone
def test_equality_method(self): """ tests that 2 identical where clauses evaluate as == """ wc1 = WhereClause('a', EqualsOperator(), 'c') wc2 = WhereClause('a', EqualsOperator(), 'c') assert wc1 == wc2
def test_operator_check(self): """ tests that creating a where statement with a non BaseWhereOperator object fails """ with self.assertRaises(StatementException): WhereClause('a', 'b', 'c')