context_models.py 9.1KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374
  1. # coding=utf-8
  2. import typing
  3. from datetime import datetime
  4. from slugify import slugify
  5. from sqlalchemy.orm import Session
  6. from tracim import CFG
  7. from tracim.models import User
  8. from tracim.models.auth import Profile
  9. from tracim.models.data import Content
  10. from tracim.models.data import Workspace, UserRoleInWorkspace
  11. from tracim.models.workspace_menu_entries import default_workspace_menu_entry
  12. from tracim.models.workspace_menu_entries import WorkspaceMenuEntry
  13. class MoveParams(object):
  14. """
  15. Json body params for move action
  16. """
  17. def __init__(self, new_parent_id: str, new_workspace_id: str = None):
  18. self.new_parent_id = new_parent_id
  19. self.new_workspace_id = new_workspace_id
  20. class LoginCredentials(object):
  21. """
  22. Login credentials model for login
  23. """
  24. def __init__(self, email: str, password: str):
  25. self.email = email
  26. self.password = password
  27. class WorkspaceAndContentPath(object):
  28. """
  29. Paths params with workspace id and content_id
  30. """
  31. def __init__(self, workspace_id: int, content_id: int):
  32. self.content_id = content_id
  33. self.workspace_id = workspace_id
  34. class CommentPath(object):
  35. """
  36. Paths params with workspace id and content_id
  37. """
  38. def __init__(self, workspace_id: int, content_id: int, comment_id: int):
  39. self.content_id = content_id
  40. self.workspace_id = workspace_id
  41. self.comment_id = comment_id
  42. class ContentFilter(object):
  43. """
  44. Content filter model
  45. """
  46. def __init__(
  47. self,
  48. parent_id: int = None,
  49. show_archived: int = 0,
  50. show_deleted: int = 0,
  51. show_active: int = 1,
  52. ):
  53. self.parent_id = parent_id
  54. self.show_archived = bool(show_archived)
  55. self.show_deleted = bool(show_deleted)
  56. self.show_active = bool(show_active)
  57. class ContentCreation(object):
  58. """
  59. Content creation model
  60. """
  61. def __init__(
  62. self,
  63. label: str,
  64. content_type: str,
  65. ):
  66. self.label = label
  67. self.content_type = content_type
  68. class CommentCreation(object):
  69. """
  70. Comment creation model
  71. """
  72. def __init__(
  73. self,
  74. raw_content: str,
  75. ):
  76. self.raw_content=raw_content
  77. class UserInContext(object):
  78. """
  79. Interface to get User data and User data related to context.
  80. """
  81. def __init__(self, user: User, dbsession: Session, config: CFG):
  82. self.user = user
  83. self.dbsession = dbsession
  84. self.config = config
  85. # Default
  86. @property
  87. def email(self) -> str:
  88. return self.user.email
  89. @property
  90. def user_id(self) -> int:
  91. return self.user.user_id
  92. @property
  93. def public_name(self) -> str:
  94. return self.display_name
  95. @property
  96. def display_name(self) -> str:
  97. return self.user.display_name
  98. @property
  99. def created(self) -> datetime:
  100. return self.user.created
  101. @property
  102. def is_active(self) -> bool:
  103. return self.user.is_active
  104. @property
  105. def timezone(self) -> str:
  106. return self.user.timezone
  107. @property
  108. def profile(self) -> Profile:
  109. return self.user.profile.name
  110. # Context related
  111. @property
  112. def calendar_url(self) -> typing.Optional[str]:
  113. # TODO - G-M - 20-04-2018 - [Calendar] Replace calendar code to get
  114. # url calendar url.
  115. #
  116. # from tracim.lib.calendar import CalendarManager
  117. # calendar_manager = CalendarManager(None)
  118. # return calendar_manager.get_workspace_calendar_url(self.workspace_id)
  119. return None
  120. @property
  121. def avatar_url(self) -> typing.Optional[str]:
  122. # TODO - G-M - 20-04-2018 - [Avatar] Add user avatar feature
  123. return None
  124. class WorkspaceInContext(object):
  125. """
  126. Interface to get Workspace data and Workspace data related to context.
  127. """
  128. def __init__(self, workspace: Workspace, dbsession: Session, config: CFG):
  129. self.workspace = workspace
  130. self.dbsession = dbsession
  131. self.config = config
  132. @property
  133. def workspace_id(self) -> int:
  134. """
  135. numeric id of the workspace.
  136. """
  137. return self.workspace.workspace_id
  138. @property
  139. def id(self) -> int:
  140. """
  141. alias of workspace_id
  142. """
  143. return self.workspace_id
  144. @property
  145. def label(self) -> str:
  146. """
  147. get workspace label
  148. """
  149. return self.workspace.label
  150. @property
  151. def description(self) -> str:
  152. """
  153. get workspace description
  154. """
  155. return self.workspace.description
  156. @property
  157. def slug(self) -> str:
  158. """
  159. get workspace slug
  160. """
  161. return slugify(self.workspace.label)
  162. @property
  163. def sidebar_entries(self) -> typing.List[WorkspaceMenuEntry]:
  164. """
  165. get sidebar entries, those depends on activated apps.
  166. """
  167. # TODO - G.M - 22-05-2018 - Rework on this in
  168. # order to not use hardcoded list
  169. # list should be able to change (depending on activated/disabled
  170. # apps)
  171. return default_workspace_menu_entry(self.workspace)
  172. class UserRoleWorkspaceInContext(object):
  173. """
  174. Interface to get UserRoleInWorkspace data and related content
  175. """
  176. def __init__(
  177. self,
  178. user_role: UserRoleInWorkspace,
  179. dbsession: Session,
  180. config: CFG,
  181. )-> None:
  182. self.user_role = user_role
  183. self.dbsession = dbsession
  184. self.config = config
  185. @property
  186. def user_id(self) -> int:
  187. """
  188. User who has the role has this id
  189. :return: user id as integer
  190. """
  191. return self.user_role.user_id
  192. @property
  193. def workspace_id(self) -> int:
  194. """
  195. This role apply only on the workspace with this workspace_id
  196. :return: workspace id as integer
  197. """
  198. return self.user_role.workspace_id
  199. # TODO - G.M - 23-05-2018 - Check the API spec for this this !
  200. @property
  201. def role_id(self) -> int:
  202. """
  203. role as int id, each value refer to a different role.
  204. """
  205. return self.user_role.role
  206. @property
  207. def role(self) -> str:
  208. return self.role_slug
  209. @property
  210. def role_slug(self) -> str:
  211. """
  212. simple name of the role of the user.
  213. can be anything from UserRoleInWorkspace SLUG, like
  214. 'not_applicable', 'reader',
  215. 'contributor', 'content-manager', 'workspace-manager'
  216. :return: user workspace role as slug.
  217. """
  218. return UserRoleInWorkspace.SLUG[self.user_role.role]
  219. @property
  220. def user(self) -> UserInContext:
  221. """
  222. User who has this role, with context data
  223. :return: UserInContext object
  224. """
  225. return UserInContext(
  226. self.user_role.user,
  227. self.dbsession,
  228. self.config
  229. )
  230. @property
  231. def workspace(self) -> WorkspaceInContext:
  232. """
  233. Workspace related to this role, with his context data
  234. :return: WorkspaceInContext object
  235. """
  236. return WorkspaceInContext(
  237. self.user_role.workspace,
  238. self.dbsession,
  239. self.config
  240. )
  241. class ContentInContext(object):
  242. """
  243. Interface to get Content data and Content data related to context.
  244. """
  245. def __init__(self, content: Content, dbsession: Session, config: CFG):
  246. self.content = content
  247. self.dbsession = dbsession
  248. self.config = config
  249. # Default
  250. @property
  251. def content_id(self) -> int:
  252. return self.content.content_id
  253. @property
  254. def id(self) -> int:
  255. return self.content_id
  256. @property
  257. def parent_id(self) -> int:
  258. """
  259. Return parent_id of the content
  260. """
  261. return self.content.parent_id
  262. @property
  263. def workspace_id(self) -> int:
  264. return self.content.workspace_id
  265. @property
  266. def label(self) -> str:
  267. return self.content.label
  268. @property
  269. def content_type(self) -> str:
  270. return self.content.type
  271. @property
  272. def sub_content_types(self) -> typing.List[str]:
  273. return [type.slug for type in self.content.get_allowed_content_types()]
  274. @property
  275. def status(self) -> str:
  276. return self.content.status
  277. @property
  278. def is_archived(self):
  279. return self.content.is_archived
  280. @property
  281. def is_deleted(self):
  282. return self.content.is_deleted
  283. @property
  284. def raw_content(self):
  285. return self.content.description
  286. @property
  287. def author(self):
  288. return UserInContext(
  289. dbsession=self.dbsession,
  290. config=self.config,
  291. user=self.content.owner
  292. )
  293. # Context-related
  294. @property
  295. def show_in_ui(self):
  296. # TODO - G.M - 31-05-2018 - Enable Show_in_ui params
  297. # if false, then do not show content in the treeview.
  298. # This may his maybe used for specific contents or for sub-contents.
  299. # Default is True.
  300. # In first version of the API, this field is always True
  301. return True
  302. @property
  303. def slug(self):
  304. return slugify(self.content.label)