first MVP to separate transformation from representation
This commit is contained in:
parent
52c3ab5c37
commit
bee767eb98
10 changed files with 146 additions and 46 deletions
158
coursebuilder/schema.py
Normal file
158
coursebuilder/schema.py
Normal file
|
@ -0,0 +1,158 @@
|
|||
import string
|
||||
|
||||
class Schema:
|
||||
|
||||
def __init__(self,schema) -> None:
|
||||
self.__schema = schema
|
||||
|
||||
def keys(self):
|
||||
return self.__schema.keys()
|
||||
|
||||
def get_template(self,field,lang='de'):
|
||||
if 'template' in self.__schema[field]:
|
||||
return self.__schema[field]['template'][lang]
|
||||
else:
|
||||
return "$value"
|
||||
|
||||
def is_translatable(self,field):
|
||||
if 'translatable' in self.__schema[field]:
|
||||
return self.__schema[field]['translatable']
|
||||
else:
|
||||
return True
|
||||
|
||||
def needs_spec(self,field):
|
||||
if 'spec' in self.__schema[field]:
|
||||
return self.__schema[field]
|
||||
else:
|
||||
return False
|
||||
|
||||
def process_label(self,field,lang='de'):
|
||||
# processes the label of a field item
|
||||
return self.__schema[field]['label'][lang]
|
||||
|
||||
def process_str(self,meta,field,lang='de'):
|
||||
if self.is_translatable(field):
|
||||
return [self.process_label(field,lang),meta[field][lang]]
|
||||
else:
|
||||
if not 'value' in meta[field]:
|
||||
raise AssertionError(field,'incomplete')
|
||||
|
||||
return [self.process_label(field,lang),meta[field]['value']]
|
||||
|
||||
def process_enum(self,meta,field,lang='de'):
|
||||
"""
|
||||
enum have a specification 'specs' option
|
||||
that can be forced by the scheme
|
||||
"""
|
||||
vv = meta[field]['value']
|
||||
enum_val = self.__schema[field]['values'][vv][lang]
|
||||
|
||||
if self.needs_spec(field):
|
||||
|
||||
t = string.Template(self.get_template(field=field,lang=lang))
|
||||
|
||||
spec = meta[field]['spec'][lang]
|
||||
|
||||
return [self.process_label(field,lang),t.substitute({'value': enum_val,'spec': spec})]
|
||||
else:
|
||||
return [self.process_label(field,lang),enum_val]
|
||||
|
||||
def process_num(self,meta,field,lang='de'):
|
||||
v = meta[field]['value']
|
||||
t = string.Template(self.get_template(field,lang))
|
||||
return [self.process_label(field,lang),t.substitute({'value' : v})]
|
||||
|
||||
|
||||
def process_multinum(self,meta,field,lang='de'):
|
||||
"""multinums have various values"""
|
||||
v = meta[field]['value']
|
||||
t = string.Template(self.get_template(field,lang))
|
||||
if hasattr(v, "__len__"):
|
||||
vv = [t.substitute({'value' : ev}) for ev in v]
|
||||
return [self.process_label(field,lang),', '.join(vv)]
|
||||
else:
|
||||
return self.process_num(meta=meta,field=field,lang=lang)
|
||||
|
||||
|
||||
def process_multikey(self,meta,field,lang='de'):
|
||||
"""
|
||||
multikey need to assign a numeric value to a key
|
||||
"""
|
||||
vs = meta[field]['value']
|
||||
t = string.Template(self.get_template(field,lang))
|
||||
|
||||
k = self.process_label(field,lang)
|
||||
|
||||
parts = []
|
||||
|
||||
for e in vs:
|
||||
kk = self.__schema[field]['keys'][e][lang]
|
||||
parts.append(t.substitute({'key': kk, 'value' : vs[e]}))
|
||||
|
||||
return [k,', '.join(parts)]
|
||||
|
||||
|
||||
def process(self,meta,fields = [],lang = 'de'):
|
||||
|
||||
table_items = []
|
||||
|
||||
# iterate over requested fields
|
||||
for field in fields:
|
||||
try:
|
||||
# correlate with schema and append
|
||||
match self.__schema[field]['type']:
|
||||
case 'str': table_items.append(self.process_str(meta,field,lang))
|
||||
case 'enum': table_items.append(self.process_enum(meta,field,lang))
|
||||
case 'int' | 'num' : table_items.append(self.process_num(meta,field,lang))
|
||||
case 'multinum' : table_items.append(self.process_multinum(meta,field,lang))
|
||||
case 'multikey': table_items.append(self.process_multikey(meta,field,lang))
|
||||
case _: raise ValueError
|
||||
except Exception as exp:
|
||||
print(field,' not resolvable in ',self.__schema,exp)
|
||||
|
||||
# maybe return tableitems as np.Dataframe?
|
||||
return table_items
|
||||
|
||||
def get_str(self,meta,field,lang='de'):
|
||||
if self.is_translatable(field):
|
||||
return meta[field][lang]
|
||||
else:
|
||||
if not 'value' in meta[field]:
|
||||
raise AssertionError(field,'incomplete')
|
||||
return meta[field]['value']
|
||||
|
||||
def get_enum(self,meta,field,lang):
|
||||
vv = meta[field]['value']
|
||||
return self.__schema[field]['values'][vv][lang]
|
||||
|
||||
# if self.needs_spec(field):
|
||||
|
||||
# t = string.Template(self.get_template(field=field,lang=lang))
|
||||
|
||||
# spec = meta[field]['spec'][lang]
|
||||
|
||||
# return [self.process_label(field,lang),t.substitute({'value': enum_val,'spec': spec})]
|
||||
# else:
|
||||
# return [self.process_label(field,lang),enum_val]
|
||||
|
||||
|
||||
|
||||
def get_value(self,meta,field,lang):
|
||||
match self.__schema[field]['type']:
|
||||
case 'str': return self.get_str(meta,field,lang)
|
||||
case 'enum': return self.get_enum(meta,field,lang)
|
||||
|
||||
|
||||
def process_raw(self,meta,fields,lang):
|
||||
|
||||
items = [{'field' : field,
|
||||
'lang' : lang,
|
||||
'type' : self.__schema[field]['type'],
|
||||
'label' : self.process_label(field,lang),
|
||||
'value' : self.get_value(meta,field,lang)
|
||||
}
|
||||
for field in fields]
|
||||
|
||||
|
||||
# maybe return tableitems as np.Dataframe?
|
||||
return items
|
Loading…
Add table
Add a link
Reference in a new issue