1) Added partition working to readme
2) replaced insertable_only parameter with include_readonly
3) Added empty string alias and materialized field control
This commit is contained in:
M1ha 2017-02-08 15:23:27 +05:00 committed by Itai Shirav
parent 27217102da
commit 14f2ab78b5
5 changed files with 25 additions and 18 deletions

View File

@ -193,8 +193,14 @@ and for providing access to information about how the system is working.
Usage example::
>>>> from infi.clickhouse_orm import system_models
>>>> print(system_models.SystemPart.get(Database()))
from infi.clickhouse_orm.database import Database
from infi.clickhouse_orm.system_models import SystemPart
db = Database('my_test_db', db_url='http://192.168.1.1:8050', username='scott', password='tiger')
partitions = SystemPart.get_active(db, conditions='') # Getting all active partitions of the database
if len(partitions) > 0:
partitions = sorted(partitions, key=lambda obj: obj.name) # Partition name is YYYYMM, so we can sort so
partitions[0].freeze(db) # Make a backup in /opt/clickhouse/shadow directory
partitions[0].drop() # Dropped partition
Currently the following system models are supported:

View File

@ -62,11 +62,11 @@ class Database(object):
def gen():
yield self._substitute('INSERT INTO $table FORMAT TabSeparated\n', model_class).encode('utf-8')
yield (first_instance.to_tsv(insertable_only=True) + '\n').encode('utf-8')
yield (first_instance.to_tsv(include_readonly=False) + '\n').encode('utf-8')
# Collect lines in batches of batch_size
batch = []
for instance in i:
batch.append(instance.to_tsv(insertable_only=True))
batch.append(instance.to_tsv(include_readonly=False))
if len(batch) >= batch_size:
# Return the current batch of lines
yield ('\n'.join(batch) + '\n').encode('utf-8')

View File

@ -16,8 +16,10 @@ class Field(object):
def __init__(self, default=None, alias=None, materialized=None):
assert (None, None) in {(default, alias), (alias, materialized), (default, materialized)}, \
"Only one of default, alias and materialized parameters can be given"
assert alias is None or isinstance(alias, str), "Alias field must be string field name, if given"
assert materialized is None or isinstance(materialized, str), "Materialized field must be string, if given"
assert alias is None or isinstance(alias, str) and alias != "",\
"Alias field must be string field name, if given"
assert materialized is None or isinstance(materialized, str) and alias != "",\
"Materialized field must be string, if given"
self.creation_counter = Field.creation_counter
Field.creation_counter += 1
@ -72,7 +74,7 @@ class Field(object):
@property
def readonly(self):
return self.alias is not None or self.materialized is not None
return bool(self.alias or self.materialized)
class StringField(Field):

View File

@ -153,26 +153,25 @@ class Model(with_metaclass(ModelBase)):
kwargs[name] = field.to_python(next(values), timezone_in_use)
return cls(**kwargs)
def to_tsv(self, insertable_only=False):
def to_tsv(self, include_readonly=True):
'''
Returns the instance's column values as a tab-separated line. A newline is not included.
:param bool insertable_only: If True, returns only fields, that can be inserted into database
:param bool include_readonly: If False, returns only fields, that can be inserted into database
'''
data = self.__dict__
fields = [f for f in self._fields if not f[1].readonly] if insertable_only else self._fields
fields = self._fields if include_readonly else [f for f in self._fields if not f[1].readonly]
return '\t'.join(field.to_db_string(data[name], quote=False) for name, field in fields)
def to_dict(self, insertable_only=False, field_names=None, timezone_in_use=pytz.utc):
def to_dict(self, include_readonly=True, field_names=None):
'''
Returns the instance's column values as a dict.
:param bool insertable_only: If True, returns only fields, that can be inserted into database
:param bool include_readonly: If False, returns only fields, that can be inserted into database
:param field_names: An iterable of field names to return
:param timezone_in_use: timezone to convert DateField and DateTimeField.
'''
fields = [f for f in self._fields if not f[1].readonly] if insertable_only else self._fields
fields = self._fields if include_readonly else [f for f in self._fields if not f[1].readonly]
if field_names is not None:
fields = [f for f in fields if f[0] in field_names]
data = self.__dict__
return {name: field.to_python(data[name], timezone_in_use) for name, field in fields}
return {name: data[name] for name, field in fields}

View File

@ -65,7 +65,7 @@ class ModelTestCase(unittest.TestCase):
"alias_field": 0.0,
'str_field': 'dozo'
})
self.assertDictEqual(instance.to_dict(insertable_only=True), {
self.assertDictEqual(instance.to_dict(include_readonly=False), {
"date_field": datetime.date(1973, 12, 6),
"int_field": 100,
"float_field": 7.0,
@ -73,7 +73,7 @@ class ModelTestCase(unittest.TestCase):
'str_field': 'dozo'
})
self.assertDictEqual(
instance.to_dict(insertable_only=True, field_names=('int_field', 'alias_field', 'datetime_field')), {
instance.to_dict(include_readonly=False, field_names=('int_field', 'alias_field', 'datetime_field')), {
"int_field": 100,
"datetime_field": datetime.datetime(1970, 1, 1, 0, 0, 0, tzinfo=pytz.utc)
})