No Description
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

classes.py 5.4KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. # -*- coding: utf-8 -*-
  2. ## @file classes.py
  3. # @see EditorialModel::classes::EmClass
  4. import logging as logger
  5. from EditorialModel.components import EmComponent, EmComponentNotExistError, EmComponentExistError
  6. from Database import sqlutils
  7. import sqlalchemy as sql
  8. import EditorialModel.fieldtypes as ftypes
  9. import EditorialModel
  10. ## @brief Manipulate Classes of the Editorial Model
  11. # Create classes of object.
  12. #@see EmClass, EmType, EmFieldGroup, EmField
  13. class EmClass(EmComponent):
  14. table = 'em_class'
  15. ranked_in = 'classtype'
  16. ## @brief Specific EmClass fields
  17. # @see EditorialModel::components::EmComponent::_fields
  18. _fields = [
  19. ('classtype', ftypes.EmField_char),
  20. ('icon', ftypes.EmField_integer),
  21. ('sortcolumn', ftypes.EmField_char)
  22. ]
  23. ## Create a new class
  24. # @param name str: name of the new class
  25. # @param class_type EmClasstype: type of the class
  26. # @return An EmClass instance
  27. # @throw EmComponentExistError if an EmClass with this name and a different classtype exists
  28. # @todo Check class_type argument
  29. @classmethod
  30. def create(cls, name, class_type):
  31. return cls._create_db(name, class_type)
  32. @classmethod
  33. ## Isolate SQL for EmClass::create
  34. # @todo Remove hardcoded default value for icon
  35. # @return An instance of EmClass
  36. def _create_db(cls, name, class_type):
  37. #Create a new entry in the em_class table
  38. values = {'name': name, 'classtype': class_type['name'], 'icon': 0}
  39. result = super(EmClass, cls).create(**values)
  40. dbe = result.db_engine()
  41. conn = dbe.connect()
  42. #Create a new table storing LodelObjects of this EmClass
  43. meta = sql.MetaData()
  44. emclasstable = sql.Table(result.class_table_name, meta, sql.Column('uid', sql.VARCHAR(50), primary_key=True))
  45. emclasstable.create(conn)
  46. conn.close()
  47. return result
  48. @property
  49. ## @brief Return the table name used to stores data on this class
  50. def class_table_name(self):
  51. return self.name
  52. ## @brief Delete a class if it's ''empty''
  53. # If a class has no fieldgroups delete it
  54. # @return bool : True if deleted False if deletion aborded
  55. def delete(self):
  56. do_delete = True
  57. fieldgroups = self.fieldgroups()
  58. if len(fieldgroups) > 0:
  59. do_delete = False
  60. return False
  61. dbe = self.__class__.db_engine()
  62. meta = sqlutils.meta(dbe)
  63. #Here we have to give a connection
  64. class_table = sql.Table(self.name, meta)
  65. meta.drop_all(tables=[class_table], bind=dbe)
  66. return super(EmClass, self).delete()
  67. ## Retrieve list of the field_groups of this class
  68. # @return A list of fieldgroups instance
  69. def fieldgroups(self):
  70. records = self._fieldgroups_db()
  71. fieldgroups = [EditorialModel.fieldgroups.EmFieldGroup(int(record.uid)) for record in records]
  72. return fieldgroups
  73. ## Isolate SQL for EmClass::fieldgroups
  74. # @return An array of dict (sqlalchemy fetchall)
  75. def _fieldgroups_db(self):
  76. dbe = self.__class__.db_engine()
  77. emfg = sql.Table(EditorialModel.fieldgroups.EmFieldGroup.table, sqlutils.meta(dbe))
  78. req = emfg.select().where(emfg.c.class_id == self.uid)
  79. conn = dbe.connect()
  80. res = conn.execute(req)
  81. return res.fetchall()
  82. ## Retrieve list of fields
  83. # @return fields [EmField]:
  84. def fields(self):
  85. fieldgroups = self.fieldgroups()
  86. fields = []
  87. for fieldgroup in fieldgroups:
  88. fields += fieldgroup.fields()
  89. return fields
  90. ## Retrieve list of type of this class
  91. # @return types [EmType]:
  92. def types(self):
  93. records = self._types_db()
  94. types = [EditorialModel.types.EmType(int(record.uid)) for record in records]
  95. return types
  96. ## Isolate SQL for EmCLass::types
  97. # @return An array of dict (sqlalchemy fetchall)
  98. def _types_db(self):
  99. dbe = self.__class__.db_engine()
  100. emtype = sql.Table(EditorialModel.types.EmType.table, sqlutils.meta(dbe))
  101. req = emtype.select().where(emtype.c.class_id == self.uid)
  102. conn = dbe.connect()
  103. res = conn.execute(req)
  104. return res.fetchall()
  105. ## Add a new EmType that can ben linked to this class
  106. # @param em_type EmType: type to link
  107. # @return success bool: done or not
  108. def link_type(self, em_type):
  109. table_name = self.name + '_' + em_type.name
  110. self._link_type_db(table_name)
  111. return True
  112. def _link_type_db(self, table_name):
  113. #Create a new table storing LodelObjects that are linked to this EmClass
  114. conn = self.__class__.db_engine().connect()
  115. meta = sql.MetaData()
  116. emlinketable = sql.Table(table_name, meta, sql.Column('uid', sql.VARCHAR(50), primary_key=True))
  117. emlinketable.create(conn)
  118. conn.close()
  119. ## Retrieve list of EmType that are linked to this class
  120. # @return types [EmType]:
  121. def linked_types(self):
  122. return self._linked_types_db()
  123. def _linked_types_db(self):
  124. dbe = self.__class__.db_engine()
  125. meta = sql.MetaData()
  126. meta.reflect(dbe)
  127. linked_types = []
  128. for table in meta.tables.values():
  129. table_name_elements = table.name.split('_')
  130. if len(table_name_elements) == 2:
  131. linked_types.append(EditorialModel.types.EmType(table_name_elements[1]))
  132. return linked_types