simo 1.7.19__py3-none-any.whl → 2.0.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of simo might be problematic. Click here for more details.

Files changed (289) hide show
  1. simo/__pycache__/asgi.cpython-38.pyc +0 -0
  2. simo/__pycache__/on_http_start.cpython-38.pyc +0 -0
  3. simo/__pycache__/settings.cpython-38.pyc +0 -0
  4. simo/__pycache__/urls.cpython-38.pyc +0 -0
  5. simo/__pycache__/wsgi.cpython-38.pyc +0 -0
  6. simo/core/__pycache__/__init__.cpython-38.pyc +0 -0
  7. simo/core/__pycache__/admin.cpython-38.pyc +0 -0
  8. simo/core/__pycache__/api.cpython-38.pyc +0 -0
  9. simo/core/__pycache__/api_meta.cpython-38.pyc +0 -0
  10. simo/core/__pycache__/auto_urls.cpython-38.pyc +0 -0
  11. simo/core/__pycache__/autocomplete_views.cpython-38.pyc +0 -0
  12. simo/core/__pycache__/base_types.cpython-38.pyc +0 -0
  13. simo/core/__pycache__/context.cpython-38.pyc +0 -0
  14. simo/core/__pycache__/controllers.cpython-38.pyc +0 -0
  15. simo/core/__pycache__/events.cpython-38.pyc +0 -0
  16. simo/core/__pycache__/filters.cpython-38.pyc +0 -0
  17. simo/core/__pycache__/forms.cpython-38.pyc +0 -0
  18. simo/core/__pycache__/gateways.cpython-38.pyc +0 -0
  19. simo/core/__pycache__/managers.cpython-38.pyc +0 -0
  20. simo/core/__pycache__/middleware.cpython-38.pyc +0 -0
  21. simo/core/__pycache__/models.cpython-38.pyc +0 -0
  22. simo/core/__pycache__/permissions.cpython-38.pyc +0 -0
  23. simo/core/__pycache__/routing.cpython-38.pyc +0 -0
  24. simo/core/__pycache__/serializers.cpython-38.pyc +0 -0
  25. simo/core/__pycache__/signal_receivers.cpython-38.pyc +0 -0
  26. simo/core/__pycache__/socket_consumers.cpython-38.pyc +0 -0
  27. simo/core/__pycache__/tasks.cpython-38.pyc +0 -0
  28. simo/core/__pycache__/todos.cpython-38.pyc +0 -0
  29. simo/core/__pycache__/views.cpython-38.pyc +0 -0
  30. simo/core/admin.py +28 -18
  31. simo/core/api.py +157 -16
  32. simo/core/api_meta.py +87 -0
  33. simo/core/auto_urls.py +4 -1
  34. simo/core/autocomplete_views.py +8 -4
  35. simo/core/base_types.py +1 -0
  36. simo/core/context.py +3 -1
  37. simo/core/controllers.py +112 -32
  38. simo/core/db_backend/base.py +7 -22
  39. simo/core/drf_braces/README +3 -0
  40. simo/core/drf_braces/__init__.py +7 -0
  41. simo/core/drf_braces/__pycache__/__init__.cpython-38.pyc +0 -0
  42. simo/core/drf_braces/__pycache__/utils.cpython-38.pyc +0 -0
  43. simo/core/drf_braces/fields/__init__.py +5 -0
  44. simo/core/drf_braces/fields/__pycache__/__init__.cpython-38.pyc +0 -0
  45. simo/core/drf_braces/fields/__pycache__/_fields.cpython-38.pyc +0 -0
  46. simo/core/drf_braces/fields/__pycache__/custom.cpython-38.pyc +0 -0
  47. simo/core/drf_braces/fields/__pycache__/mixins.cpython-38.pyc +0 -0
  48. simo/core/drf_braces/fields/__pycache__/modified.cpython-38.pyc +0 -0
  49. simo/core/drf_braces/fields/_fields.py +48 -0
  50. simo/core/drf_braces/fields/custom.py +107 -0
  51. simo/core/drf_braces/fields/mixins.py +58 -0
  52. simo/core/drf_braces/fields/modified.py +41 -0
  53. simo/core/drf_braces/forms/__init__.py +0 -0
  54. simo/core/drf_braces/forms/fields.py +20 -0
  55. simo/core/drf_braces/forms/serializer_form.py +156 -0
  56. simo/core/drf_braces/mixins.py +52 -0
  57. simo/core/drf_braces/models.py +0 -0
  58. simo/core/drf_braces/parsers.py +72 -0
  59. simo/core/drf_braces/renderers.py +37 -0
  60. simo/core/drf_braces/serializers/__init__.py +0 -0
  61. simo/core/drf_braces/serializers/__pycache__/__init__.cpython-38.pyc +0 -0
  62. simo/core/drf_braces/serializers/__pycache__/form_serializer.cpython-38.pyc +0 -0
  63. simo/core/drf_braces/serializers/enforce_validation_serializer.py +214 -0
  64. simo/core/drf_braces/serializers/form_serializer.py +391 -0
  65. simo/core/drf_braces/serializers/swapping.py +48 -0
  66. simo/core/drf_braces/tests/__init__.py +0 -0
  67. simo/core/drf_braces/tests/fields/__init__.py +0 -0
  68. simo/core/drf_braces/tests/fields/test_custom.py +94 -0
  69. simo/core/drf_braces/tests/fields/test_fields.py +13 -0
  70. simo/core/drf_braces/tests/fields/test_mixins.py +96 -0
  71. simo/core/drf_braces/tests/fields/test_modified.py +40 -0
  72. simo/core/drf_braces/tests/forms/__init__.py +0 -0
  73. simo/core/drf_braces/tests/forms/test_fields.py +46 -0
  74. simo/core/drf_braces/tests/forms/test_serializer_form.py +256 -0
  75. simo/core/drf_braces/tests/serializers/__init__.py +0 -0
  76. simo/core/drf_braces/tests/serializers/test_enforce_validation_serializer.py +169 -0
  77. simo/core/drf_braces/tests/serializers/test_form_serializer.py +387 -0
  78. simo/core/drf_braces/tests/serializers/test_swapping.py +40 -0
  79. simo/core/drf_braces/tests/test_mixins.py +111 -0
  80. simo/core/drf_braces/tests/test_parsers.py +73 -0
  81. simo/core/drf_braces/tests/test_renderers.py +23 -0
  82. simo/core/drf_braces/tests/test_utils.py +73 -0
  83. simo/core/drf_braces/utils.py +209 -0
  84. simo/core/events.py +3 -3
  85. simo/core/forms.py +79 -37
  86. simo/core/gateways.py +31 -14
  87. simo/core/management/__pycache__/__init__.cpython-38.pyc +0 -0
  88. simo/core/management/commands/__pycache__/__init__.cpython-38.pyc +0 -0
  89. simo/core/management/commands/gateways_manager.py +0 -1
  90. simo/core/managers.py +81 -0
  91. simo/core/middleware.py +25 -0
  92. simo/core/migrations/0026_category_instance.py +20 -0
  93. simo/core/migrations/0027_remove_component_tags.py +17 -0
  94. simo/core/migrations/0028_rename_subcomponents_component_slaves.py +18 -0
  95. simo/core/migrations/0029_auto_20240229_1331.py +33 -0
  96. simo/core/migrations/__pycache__/0026_category_instance.cpython-38.pyc +0 -0
  97. simo/core/migrations/__pycache__/0027_remove_component_tags.cpython-38.pyc +0 -0
  98. simo/core/migrations/__pycache__/0028_rename_subcomponents_component_slaves.cpython-38.pyc +0 -0
  99. simo/core/migrations/__pycache__/0029_auto_20240229_1331.cpython-38.pyc +0 -0
  100. simo/core/models.py +103 -66
  101. simo/core/permissions.py +28 -2
  102. simo/core/serializers.py +330 -26
  103. simo/core/socket_consumers.py +5 -14
  104. simo/core/tasks.py +11 -1
  105. simo/core/templates/admin/base.html +37 -10
  106. simo/core/templates/admin/wizard/discovery.html +188 -0
  107. simo/core/templates/admin/wizard/wizard_add.html +5 -5
  108. simo/core/utils/__pycache__/serialization.cpython-38.pyc +0 -0
  109. simo/core/utils/admin.py +9 -2
  110. simo/core/utils/formsets.py +17 -16
  111. simo/core/utils/helpers.py +1 -0
  112. simo/core/utils/serialization.py +56 -0
  113. simo/core/utils/type_constants.py +1 -1
  114. simo/core/utils/validators.py +14 -1
  115. simo/core/views.py +13 -0
  116. simo/fleet/__pycache__/admin.cpython-38.pyc +0 -0
  117. simo/fleet/__pycache__/api.cpython-38.pyc +0 -0
  118. simo/fleet/__pycache__/auto_urls.cpython-38.pyc +0 -0
  119. simo/fleet/__pycache__/controllers.cpython-38.pyc +0 -0
  120. simo/fleet/__pycache__/forms.cpython-38.pyc +0 -0
  121. simo/fleet/__pycache__/gateways.cpython-38.pyc +0 -0
  122. simo/fleet/__pycache__/managers.cpython-38.pyc +0 -0
  123. simo/fleet/__pycache__/models.cpython-38.pyc +0 -0
  124. simo/fleet/__pycache__/serializers.cpython-38.pyc +0 -0
  125. simo/fleet/__pycache__/socket_consumers.cpython-38.pyc +0 -0
  126. simo/fleet/__pycache__/utils.cpython-38.pyc +0 -0
  127. simo/fleet/__pycache__/views.cpython-38.pyc +0 -0
  128. simo/fleet/admin.py +54 -25
  129. simo/fleet/api.py +59 -3
  130. simo/fleet/auto_urls.py +2 -3
  131. simo/fleet/controllers.py +199 -16
  132. simo/fleet/forms.py +325 -483
  133. simo/fleet/gateways.py +44 -2
  134. simo/fleet/managers.py +32 -0
  135. simo/fleet/migrations/0025_auto_20240130_1334.py +27 -0
  136. simo/fleet/migrations/0026_rename_i2cinterface_scl_pin_and_more.py +64 -0
  137. simo/fleet/migrations/0027_auto_20240306_0802.py +170 -0
  138. simo/fleet/migrations/0028_remove_i2cinterface_scl_pin_no_and_more.py +21 -0
  139. simo/fleet/migrations/0029_alter_i2cinterface_scl_pin_and_more.py +24 -0
  140. simo/fleet/migrations/0030_colonelpin_label_alter_colonel_type.py +24 -0
  141. simo/fleet/migrations/0031_alter_colonel_type.py +18 -0
  142. simo/fleet/migrations/__pycache__/0025_auto_20240130_1334.cpython-38.pyc +0 -0
  143. simo/fleet/migrations/__pycache__/0026_rename_i2cinterface_scl_pin_and_more.cpython-38.pyc +0 -0
  144. simo/fleet/migrations/__pycache__/0027_auto_20240306_0802.cpython-38.pyc +0 -0
  145. simo/fleet/migrations/__pycache__/0028_remove_i2cinterface_scl_pin_no_and_more.cpython-38.pyc +0 -0
  146. simo/fleet/migrations/__pycache__/0029_alter_i2cinterface_scl_pin_and_more.cpython-38.pyc +0 -0
  147. simo/fleet/migrations/__pycache__/0030_colonelpin_label_alter_colonel_type.cpython-38.pyc +0 -0
  148. simo/fleet/migrations/__pycache__/0031_alter_colonel_type.cpython-38.pyc +0 -0
  149. simo/fleet/models.py +134 -82
  150. simo/fleet/serializers.py +35 -1
  151. simo/fleet/socket_consumers.py +239 -76
  152. simo/fleet/utils.py +15 -53
  153. simo/fleet/views.py +28 -14
  154. simo/generic/controllers.py +13 -89
  155. simo/generic/forms.py +30 -23
  156. simo/generic/gateways.py +98 -10
  157. simo/generic/models.py +3 -3
  158. simo/multimedia/controllers.py +9 -8
  159. simo/settings.py +7 -4
  160. simo/urls.py +4 -8
  161. simo/users/__pycache__/admin.cpython-38.pyc +0 -0
  162. simo/users/__pycache__/api.cpython-38.pyc +0 -0
  163. simo/users/__pycache__/auto_urls.cpython-38.pyc +0 -0
  164. simo/users/__pycache__/models.cpython-38.pyc +0 -0
  165. simo/users/__pycache__/serializers.cpython-38.pyc +0 -0
  166. simo/users/__pycache__/sso_urls.cpython-38.pyc +0 -0
  167. simo/users/admin.py +8 -1
  168. simo/users/api.py +38 -2
  169. simo/users/auto_urls.py +2 -2
  170. simo/users/migrations/0025_rename_name_fingerprint_type_and_more.py +22 -0
  171. simo/users/migrations/__pycache__/0025_rename_name_fingerprint_type_and_more.cpython-38.pyc +0 -0
  172. simo/users/models.py +2 -3
  173. simo/users/serializers.py +15 -1
  174. simo/users/sso_urls.py +3 -3
  175. simo/wsgi.py +7 -0
  176. {simo-1.7.19.dist-info → simo-2.0.0.dist-info}/METADATA +8 -9
  177. {simo-1.7.19.dist-info → simo-2.0.0.dist-info}/RECORD +180 -210
  178. {simo-1.7.19.dist-info → simo-2.0.0.dist-info}/WHEEL +1 -1
  179. simo/core/__pycache__/__init__.cpython-37.pyc +0 -0
  180. simo/core/__pycache__/admin.cpython-37.pyc +0 -0
  181. simo/core/__pycache__/api.cpython-37.pyc +0 -0
  182. simo/core/__pycache__/apps.cpython-38.pyc +0 -0
  183. simo/core/__pycache__/controllers.cpython-37.pyc +0 -0
  184. simo/core/__pycache__/events.cpython-37.pyc +0 -0
  185. simo/core/__pycache__/forms.cpython-37.pyc +0 -0
  186. simo/core/__pycache__/gateways.cpython-37.pyc +0 -0
  187. simo/core/__pycache__/models.cpython-37.pyc +0 -0
  188. simo/core/__pycache__/scripts.cpython-37.pyc +0 -0
  189. simo/core/__pycache__/serializers.cpython-37.pyc +0 -0
  190. simo/core/__pycache__/widgets.cpython-37.pyc +0 -0
  191. simo/core/db_backend/__pycache__/__init__.cpython-38.pyc +0 -0
  192. simo/core/db_backend/__pycache__/base.cpython-38.pyc +0 -0
  193. simo/core/management/commands/__pycache__/gateways_manager.cpython-38.pyc +0 -0
  194. simo/core/management/commands/__pycache__/run_gateway.cpython-38.pyc +0 -0
  195. simo/core/migrations/__pycache__/0001_initial.cpython-38.pyc +0 -0
  196. simo/core/migrations/__pycache__/0002_load_icons.cpython-38.pyc +0 -0
  197. simo/core/migrations/__pycache__/0003_create_default_zones_and_categories.cpython-38.pyc +0 -0
  198. simo/core/migrations/__pycache__/0004_create_generic.cpython-38.pyc +0 -0
  199. simo/core/migrations/__pycache__/0005_component_subcomponents.cpython-38.pyc +0 -0
  200. simo/core/migrations/__pycache__/0006_alter_component_subcomponents.cpython-38.pyc +0 -0
  201. simo/core/migrations/__pycache__/0007_component_change_init_to.cpython-38.pyc +0 -0
  202. simo/core/migrations/__pycache__/0008_alter_component_change_init_to.cpython-38.pyc +0 -0
  203. simo/core/migrations/__pycache__/0009_auto_20220707_1404.cpython-38.pyc +0 -0
  204. simo/core/migrations/__pycache__/0010_historyaggregate.cpython-38.pyc +0 -0
  205. simo/core/migrations/__pycache__/0011_component_last_change.cpython-38.pyc +0 -0
  206. simo/core/migrations/__pycache__/0012_instance.cpython-38.pyc +0 -0
  207. simo/core/migrations/__pycache__/0013_auto_20231003_0754.cpython-38.pyc +0 -0
  208. simo/core/migrations/__pycache__/0014_zone_instance.cpython-38.pyc +0 -0
  209. simo/core/migrations/__pycache__/0015_auto_20231004_1113.cpython-38.pyc +0 -0
  210. simo/core/migrations/__pycache__/0016_auto_20231004_1113.cpython-38.pyc +0 -0
  211. simo/core/migrations/__pycache__/0017_auto_20231004_1313.cpython-38.pyc +0 -0
  212. simo/core/migrations/__pycache__/0018_auto_20231005_0622.cpython-38.pyc +0 -0
  213. simo/core/migrations/__pycache__/0019_alter_gateway_type.cpython-38.pyc +0 -0
  214. simo/core/migrations/__pycache__/0020_component_meta.cpython-38.pyc +0 -0
  215. simo/core/migrations/__pycache__/0021_auto_20231020_1041.cpython-38.pyc +0 -0
  216. simo/core/migrations/__pycache__/__init__.cpython-38.pyc +0 -0
  217. simo/core/templatetags/__pycache__/__init__.cpython-38.pyc +0 -0
  218. simo/core/templatetags/__pycache__/components_list.cpython-38.pyc +0 -0
  219. simo/core/utils/__pycache__/__init__.cpython-38.pyc +0 -0
  220. simo/core/utils/__pycache__/admin.cpython-38.pyc +0 -0
  221. simo/core/utils/__pycache__/config_values.cpython-38.pyc +0 -0
  222. simo/core/utils/__pycache__/easing.cpython-38.pyc +0 -0
  223. simo/core/utils/__pycache__/form_fields.cpython-38.pyc +0 -0
  224. simo/core/utils/__pycache__/form_widgets.cpython-38.pyc +0 -0
  225. simo/core/utils/__pycache__/formsets.cpython-38.pyc +0 -0
  226. simo/core/utils/__pycache__/helpers.cpython-38.pyc +0 -0
  227. simo/core/utils/__pycache__/logs.cpython-38.pyc +0 -0
  228. simo/core/utils/__pycache__/mixins.cpython-38.pyc +0 -0
  229. simo/core/utils/__pycache__/model_helpers.cpython-38.pyc +0 -0
  230. simo/core/utils/__pycache__/relay.cpython-38.pyc +0 -0
  231. simo/core/utils/__pycache__/type_constants.cpython-38.pyc +0 -0
  232. simo/core/utils/__pycache__/validators.cpython-38.pyc +0 -0
  233. simo/fleet/tasks.py +0 -25
  234. simo/generic/__pycache__/__init__.cpython-37.pyc +0 -0
  235. simo/generic/__pycache__/__init__.cpython-38.pyc +0 -0
  236. simo/generic/__pycache__/app_widgets.cpython-38.pyc +0 -0
  237. simo/generic/__pycache__/base_types.cpython-38.pyc +0 -0
  238. simo/generic/__pycache__/controllers.cpython-37.pyc +0 -0
  239. simo/generic/__pycache__/controllers.cpython-38.pyc +0 -0
  240. simo/generic/__pycache__/forms.cpython-38.pyc +0 -0
  241. simo/generic/__pycache__/gateways.cpython-38.pyc +0 -0
  242. simo/generic/__pycache__/models.cpython-38.pyc +0 -0
  243. simo/generic/__pycache__/routing.cpython-38.pyc +0 -0
  244. simo/generic/__pycache__/socket_consumers.cpython-38.pyc +0 -0
  245. simo/generic/__pycache__/tasks.cpython-38.pyc +0 -0
  246. simo/generic/__pycache__/widgets.cpython-37.pyc +0 -0
  247. simo/generic/tasks.py +0 -41
  248. simo/multimedia/__pycache__/__init__.cpython-38.pyc +0 -0
  249. simo/multimedia/__pycache__/admin.cpython-38.pyc +0 -0
  250. simo/multimedia/__pycache__/api.cpython-38.pyc +0 -0
  251. simo/multimedia/__pycache__/app_widgets.cpython-38.pyc +0 -0
  252. simo/multimedia/__pycache__/base_types.cpython-38.pyc +0 -0
  253. simo/multimedia/__pycache__/controllers.cpython-38.pyc +0 -0
  254. simo/multimedia/__pycache__/forms.cpython-38.pyc +0 -0
  255. simo/multimedia/__pycache__/models.cpython-38.pyc +0 -0
  256. simo/multimedia/__pycache__/serializers.cpython-38.pyc +0 -0
  257. simo/multimedia/migrations/__pycache__/0001_initial.cpython-38.pyc +0 -0
  258. simo/multimedia/migrations/__pycache__/0002_sound_length.cpython-38.pyc +0 -0
  259. simo/multimedia/migrations/__pycache__/0003_alter_sound_length.cpython-38.pyc +0 -0
  260. simo/multimedia/migrations/__pycache__/0004_auto_20231023_1055.cpython-38.pyc +0 -0
  261. simo/multimedia/migrations/__pycache__/__init__.cpython-38.pyc +0 -0
  262. simo/notifications/__pycache__/__init__.cpython-38.pyc +0 -0
  263. simo/notifications/__pycache__/admin.cpython-38.pyc +0 -0
  264. simo/notifications/__pycache__/api.cpython-38.pyc +0 -0
  265. simo/notifications/__pycache__/models.cpython-38.pyc +0 -0
  266. simo/notifications/__pycache__/serializers.cpython-38.pyc +0 -0
  267. simo/notifications/__pycache__/utils.cpython-38.pyc +0 -0
  268. simo/notifications/migrations/__pycache__/0001_initial.cpython-38.pyc +0 -0
  269. simo/notifications/migrations/__pycache__/0002_notification_instance.cpython-38.pyc +0 -0
  270. simo/notifications/migrations/__pycache__/__init__.cpython-38.pyc +0 -0
  271. simo/users/migrations/__pycache__/0001_initial.cpython-38.pyc +0 -0
  272. simo/users/migrations/__pycache__/0002_componentpermission.cpython-38.pyc +0 -0
  273. simo/users/migrations/__pycache__/0003_create_roles_and_system_user.cpython-38.pyc +0 -0
  274. simo/users/migrations/__pycache__/0004_user_secret_key.cpython-38.pyc +0 -0
  275. simo/users/migrations/__pycache__/0005_permissionsrole_instance.cpython-38.pyc +0 -0
  276. simo/users/migrations/__pycache__/0006_auto_20231003_0850.cpython-38.pyc +0 -0
  277. simo/users/migrations/__pycache__/0007_auto_20231003_1228.cpython-38.pyc +0 -0
  278. simo/users/migrations/__pycache__/0008_auto_20231003_1229.cpython-38.pyc +0 -0
  279. simo/users/migrations/__pycache__/0009_remove_user_role.cpython-38.pyc +0 -0
  280. simo/users/migrations/__pycache__/0010_auto_20231004_1313.cpython-38.pyc +0 -0
  281. simo/users/migrations/__pycache__/0011_auto_20231004_1313.cpython-38.pyc +0 -0
  282. simo/users/migrations/__pycache__/0012_alter_userinstancerole_unique_together.cpython-38.pyc +0 -0
  283. simo/users/migrations/__pycache__/0013_remove_user_roles.cpython-38.pyc +0 -0
  284. simo/users/migrations/__pycache__/0014_user_roles.cpython-38.pyc +0 -0
  285. simo/users/migrations/__pycache__/0015_remove_user_at_home.cpython-38.pyc +0 -0
  286. simo/users/migrations/__pycache__/0016_auto_20231005_1050.cpython-38.pyc +0 -0
  287. simo/users/migrations/__pycache__/__init__.cpython-38.pyc +0 -0
  288. {simo-1.7.19.dist-info → simo-2.0.0.dist-info}/LICENSE.md +0 -0
  289. {simo-1.7.19.dist-info → simo-2.0.0.dist-info}/top_level.txt +0 -0
@@ -63,7 +63,7 @@ class Script(ControllerBase, TimerMixin):
63
63
  )
64
64
  return value
65
65
 
66
- def _send_to_device(self, value):
66
+ def _prepare_for_send(self, value):
67
67
  if value == 'start':
68
68
  new_code = getattr(self.component, 'new_code', None)
69
69
  if new_code:
@@ -71,7 +71,7 @@ class Script(ControllerBase, TimerMixin):
71
71
  self.component.refresh_from_db()
72
72
  self.component.config['code'] = new_code
73
73
  self.component.save(update_fields=['config'])
74
- return super()._send_to_device(value)
74
+ return value
75
75
 
76
76
  def _val_to_success(self, value):
77
77
  if value == 'start':
@@ -208,9 +208,13 @@ class Thermostat(ControllerBase):
208
208
  heater = Component.objects.filter(
209
209
  pk=self.component.config.get('heater')
210
210
  ).first()
211
+ if heater:
212
+ heater.prepare_controller()
211
213
  cooler = Component.objects.filter(
212
214
  pk=self.component.config.get('cooler')
213
215
  ).first()
216
+ if cooler:
217
+ cooler.prepare_controller()
214
218
 
215
219
  if not temperature_sensor or not temperature_sensor.alive:
216
220
  print(f"No temperature sensor on {self.component}!")
@@ -322,47 +326,6 @@ class AlarmGroup(ControllerBase):
322
326
  )
323
327
  return value
324
328
 
325
- def _send_to_device(self, value):
326
- assert value in ('armed', 'disarmed')
327
-
328
- other_alarm_groups = {}
329
- stats = {
330
- 'disarmed': 0, 'pending-arm': 0, 'armed': 0, 'breached': 0
331
- }
332
-
333
- for c_id in self.component.config['components']:
334
- slave = Component.objects.filter(pk=c_id).first()
335
- if not slave:
336
- continue
337
- if value == 'armed':
338
- if not slave.is_in_alarm():
339
- slave.arm_status = 'armed'
340
- stats['armed'] += 1
341
- else:
342
- slave.arm_status = 'pending-arm'
343
- stats['pending-arm'] += 1
344
- elif value == 'disarmed':
345
- stats['disarmed'] += 1
346
- slave.arm_status = 'disarmed'
347
-
348
- slave.do_not_update_alarm_group = True
349
- slave.save(update_fields=['arm_status'])
350
-
351
- for other_group in Component.objects.filter(
352
- controller_uid=AlarmGroup.uid,
353
- config__components__contains=slave.id
354
- ).exclude(pk=self.component.pk):
355
- other_alarm_groups[other_group.pk] = other_group
356
-
357
- self.component.value = value
358
- if stats['pending-arm']:
359
- self.component.value = 'pending-arm'
360
- self.component.config['stats'] = stats
361
- self.component.save()
362
-
363
- for pk, other_group in other_alarm_groups.items():
364
- other_group.refresh_status()
365
-
366
329
  def arm(self):
367
330
  self.send('armed')
368
331
 
@@ -375,7 +338,6 @@ class AlarmGroup(ControllerBase):
375
338
  )
376
339
 
377
340
  def refresh_status(self):
378
-
379
341
  stats = {
380
342
  'disarmed': 0, 'pending-arm': 0, 'armed': 0, 'breached': 0
381
343
  }
@@ -515,21 +477,6 @@ class Gate(ControllerBase, TimerMixin):
515
477
  self.component.set(self.component.value + '_moving')
516
478
  threading.Thread(target=cancel_move, daemon=True).start()
517
479
 
518
- def _send_to_device(self, value):
519
- switch = Component.objects.filter(
520
- pk=self.component.config.get('action_switch')
521
- ).first()
522
- if not switch:
523
- return
524
-
525
- if self.component.config.get('action_method') == 'click':
526
- switch.click()
527
- else:
528
- if value == 'open':
529
- switch.turn_on()
530
- else:
531
- switch.turn_off()
532
-
533
480
  def open(self):
534
481
  self.send('open')
535
482
 
@@ -662,9 +609,6 @@ class Blinds(ControllerBase, TimerMixin):
662
609
 
663
610
  return value
664
611
 
665
- def _send_to_device(self, value):
666
- GatewayObjectCommand(self.component, **{'set_val': value}).publish()
667
-
668
612
  def open(self):
669
613
  self.send(0)
670
614
 
@@ -776,6 +720,7 @@ class Watering(ControllerBase):
776
720
  switch = Component.objects.get(pk=contour_data['switch'])
777
721
  except Component.DoesNotExist:
778
722
  continue
723
+ switch.prepare_controller()
779
724
  if run:
780
725
  if switch.timer_engaged():
781
726
  switch.stop_timer()
@@ -900,6 +845,7 @@ class Watering(ControllerBase):
900
845
  switch = Component.objects.get(pk=contour_data['switch'])
901
846
  except Component.DoesNotExist:
902
847
  continue
848
+ switch.prepare_controller()
903
849
  if switch.timer_engaged():
904
850
  switch.stop_timer()
905
851
  switch.turn_off()
@@ -1131,6 +1077,7 @@ class AlarmClock(ControllerBase):
1131
1077
  print(f"Reverse event {event['uid']}!")
1132
1078
  comp = Component.objects.filter(id=event['component']).first()
1133
1079
  if comp:
1080
+ comp.prepare_controller()
1134
1081
  if forward:
1135
1082
  action_name = 'play_action'
1136
1083
  else:
@@ -1370,7 +1317,8 @@ class AlarmClock(ControllerBase):
1370
1317
  return current_value
1371
1318
 
1372
1319
 
1373
- # ----------- Dummy controllers -----------------------------
1320
+ # ----------- Dummy controllers -----------------------------
1321
+
1374
1322
  class StateSelect(ControllerBase):
1375
1323
  gateway_class = DummyGatewayHandler
1376
1324
  name = _("State select")
@@ -1387,9 +1335,6 @@ class StateSelect(ControllerBase):
1387
1335
  raise ValidationError("Unsupported value!")
1388
1336
  return value
1389
1337
 
1390
- def _send_to_device(self, value):
1391
- self.component.set(value)
1392
-
1393
1338
 
1394
1339
  class DummyBinarySensor(BinarySensor):
1395
1340
  gateway_class = DummyGatewayHandler
@@ -1406,56 +1351,35 @@ class DummyMultiSensor(MultiSensor):
1406
1351
  class DummySwitch(Switch):
1407
1352
  gateway_class = DummyGatewayHandler
1408
1353
 
1409
- def _send_to_device(self, value):
1410
- self.component.set(value)
1411
-
1412
1354
 
1413
1355
  class DummyDoubleSwitch(DoubleSwitch):
1414
1356
  gateway_class = DummyGatewayHandler
1415
1357
 
1416
- def _send_to_device(self, value):
1417
- self.component.set(value)
1418
-
1419
1358
 
1420
1359
  class DummyTripleSwitch(TripleSwitch):
1421
1360
  gateway_class = DummyGatewayHandler
1422
1361
 
1423
- def _send_to_device(self, value):
1424
- self.component.set(value)
1425
-
1426
1362
 
1427
1363
  class DummyQuadrupleSwitch(QuadrupleSwitch):
1428
1364
  gateway_class = DummyGatewayHandler
1429
1365
 
1430
- def _send_to_device(self, value):
1431
- self.component.set(value)
1432
-
1433
1366
 
1434
1367
  class DummyQuintupleSwitch(QuintupleSwitch):
1435
1368
  gateway_class = DummyGatewayHandler
1436
1369
 
1437
- def _send_to_device(self, value):
1438
- self.component.set(value)
1439
-
1440
1370
 
1441
1371
  class DummyDimmer(Dimmer):
1442
1372
  gateway_class = DummyGatewayHandler
1443
1373
 
1444
- def _send_to_device(self, value):
1374
+ def _prepare_for_send(self, value):
1445
1375
  if self.component.config.get('inverse'):
1446
1376
  value = self.component.config.get('max') - value
1447
- self.component.set(value)
1377
+ return value
1448
1378
 
1449
1379
 
1450
1380
  class DummyDimmerPlus(DimmerPlus):
1451
1381
  gateway_class = DummyGatewayHandler
1452
1382
 
1453
- def _send_to_device(self, value):
1454
- self.component.set(value)
1455
-
1456
1383
 
1457
1384
  class DummyRGBWLight(RGBWLight):
1458
1385
  gateway_class = DummyGatewayHandler
1459
-
1460
- def _send_to_device(self, value):
1461
- self.component.set(value)
simo/generic/forms.py CHANGED
@@ -14,18 +14,14 @@ from dal import autocomplete, forward
14
14
  from simo.core.utils.config_values import config_to_dict
15
15
  from simo.core.utils.formsets import FormsetField
16
16
  from simo.core.utils.helpers import get_random_string
17
- from simo.core.utils.form_fields import AutocompleteSelect2
17
+ from simo.core.utils.form_fields import ListSelect2Widget
18
18
  from simo.conf import dynamic_settings
19
19
 
20
20
 
21
21
  class ScriptConfigForm(BaseComponentForm):
22
22
  autostart = forms.BooleanField(
23
23
  initial=True, required=False,
24
- help_text="Auto start my script on system boot."
25
- )
26
- autorestart = forms.BooleanField(
27
- initial=True, required=False,
28
- help_text="Wake my script up automatically if it encounters error."
24
+ help_text="Wake up every 60 s if not running."
29
25
  )
30
26
  code = forms.CharField(widget=PythonCode)
31
27
  log = forms.CharField(
@@ -49,7 +45,7 @@ class ScriptConfigForm(BaseComponentForm):
49
45
  def get_admin_fieldsets(cls, request, obj=None):
50
46
  base_fields = (
51
47
  'id', 'gateway', 'base_type', 'name', 'icon', 'zone', 'category',
52
- 'tags', 'show_in_app', 'autostart', 'autorestart',
48
+ 'show_in_app', 'autostart',
53
49
  'code', 'control', 'log'
54
50
  )
55
51
 
@@ -200,6 +196,7 @@ class AlarmGroupConfigForm(BaseComponentForm):
200
196
  "Can not cover self. Please remove - [%s]" % str(check_cmp)
201
197
  )
202
198
  if comp.base_type == 'alarm-group':
199
+ comp.prepare_controller()
203
200
  self.recurse_check_alarm_groups(
204
201
  comp.get_children(), check_cmp
205
202
  )
@@ -224,6 +221,7 @@ class AlarmGroupConfigForm(BaseComponentForm):
224
221
  c.save(update_fields=('config',))
225
222
  if obj.id:
226
223
  comp = Component.objects.get(id=obj.id)
224
+ comp.prepare_controller()
227
225
  comp.refresh_status()
228
226
  return obj
229
227
 
@@ -444,21 +442,29 @@ class WateringConfigForm(BaseComponentForm):
444
442
  )
445
443
  obj = super().save(commit=commit)
446
444
  if commit:
447
- obj.subcomponents.clear()
445
+ obj.slaves.clear()
448
446
  for contour in self.cleaned_data['contours']:
449
- obj.subcomponents.add(
447
+ obj.slaves.add(
450
448
  Component.objects.get(pk=contour['switch'])
451
449
  )
452
450
  return obj
453
451
 
454
452
 
455
453
  class StateForm(forms.Form):
456
- icon = AutocompleteSelect2(url='autocomplete-icon')
454
+ icon = forms.CharField(
455
+ widget=ListSelect2Widget(
456
+ url='autocomplete-icon', attrs={'data-html': True}
457
+ )
458
+ )
457
459
  slug = forms.SlugField(required=True)
458
460
  name = forms.CharField(required=True)
459
461
  help_text = forms.CharField(required=False, widget=forms.Textarea(attrs={'rows': 3}))
460
462
  prefix = 'states'
461
463
 
464
+ def clean(self):
465
+ print("Let's clean the data! ", self.cleaned_data)
466
+ return self.cleaned_data
467
+
462
468
 
463
469
  class StateSelectForm(BaseComponentForm):
464
470
  states = FormsetField(
@@ -497,20 +503,21 @@ class AlarmClockEventForm(forms.Form):
497
503
  def clean(self):
498
504
  if not self.cleaned_data.get('component'):
499
505
  return self.cleaned_data
500
- if not self.cleaned_data.get('play_method'):
506
+ if not self.cleaned_data.get('play_action'):
501
507
  return self.cleaned_data
502
508
  component = self.cleaned_data.get('component')
503
- if not hasattr(component, self.cleaned_data['play_method']):
509
+ component.prepare_controller()
510
+ if not hasattr(component, self.cleaned_data['play_action']):
504
511
  self.add_error(
505
- 'play_method',
506
- f"{component} has no {self.cleaned_data['play_method']} method!"
512
+ 'play_action',
513
+ f"{component} has no {self.cleaned_data['play_action']} action!"
507
514
  )
508
- if self.cleaned_data.get('reverse_method'):
509
- if not hasattr(component, self.cleaned_data['reverse_method']):
515
+ if self.cleaned_data.get('reverse_action'):
516
+ if not hasattr(component, self.cleaned_data['reverse_action']):
510
517
  self.add_error(
511
- 'reverse_method',
518
+ 'reverse_action',
512
519
  f"{component} has no "
513
- f"{self.cleaned_data['reverse_method']} method!"
520
+ f"{self.cleaned_data['reverse_action']} action!"
514
521
  )
515
522
  return self.cleaned_data
516
523
 
@@ -525,16 +532,16 @@ class AlarmClockConfigForm(BaseComponentForm):
525
532
  def clean_default_events(self):
526
533
  events = self.cleaned_data['default_events']
527
534
  for i, cont in enumerate(events):
528
- if not cont['uid']:
535
+ if not cont.get('uid'):
529
536
  cont['uid'] = get_random_string(6)
530
537
  return events
531
538
 
532
539
  def save(self, commit=True):
533
540
  obj = super().save(commit=commit)
534
541
  if commit:
535
- obj.subcomponents.clear()
542
+ obj.slaves.clear()
536
543
  for comp in self.cleaned_data['default_events']:
537
- obj.subcomponents.add(
538
- Component.objects.get(pk=comp['component'])
539
- )
544
+ c = Component.objects.filter(pk=comp['component']).first()
545
+ if c:
546
+ obj.slaves.add(c)
540
547
  return obj
simo/generic/gateways.py CHANGED
@@ -1,16 +1,14 @@
1
1
  import sys
2
- import cv2
3
2
  import logging
4
- import base64
5
3
  import pytz
6
- from logging.handlers import RotatingFileHandler
7
4
  import json
8
5
  import time
9
6
  import multiprocessing
10
7
  import threading
11
8
  from django.conf import settings
12
9
  from django.utils import timezone
13
- from django.db import close_old_connections, connection as db_connection
10
+ from django.db import connection as db_connection
11
+ from django.db.models import Q
14
12
  import paho.mqtt.client as mqtt
15
13
  from simo.core.models import Component
16
14
  from simo.core.gateways import BaseObjectCommandsGatewayHandler
@@ -21,9 +19,6 @@ from simo.core.loggers import get_gw_logger, get_component_logger
21
19
 
22
20
 
23
21
 
24
-
25
-
26
-
27
22
  class BlindsRunner(threading.Thread):
28
23
 
29
24
  def __init__(self, blinds, *args, **kwargs):
@@ -168,7 +163,9 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
168
163
  blinds_runners = {}
169
164
  periodic_tasks = (
170
165
  ('watch_thermostats', 60),
171
- ('watch_alarm_clocks', 30)
166
+ ('watch_alarm_clocks', 30),
167
+ ('watch_scripts', 60),
168
+ ('watch_watering', 60)
172
169
  )
173
170
 
174
171
  def watch_thermostats(self):
@@ -178,6 +175,7 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
178
175
  ):
179
176
  tz = pytz.timezone(thermostat.zone.instance.timezone)
180
177
  timezone.activate(tz)
178
+ thermostat.prepare_controller()
181
179
  thermostat.evaluate()
182
180
 
183
181
  def watch_alarm_clocks(self):
@@ -187,14 +185,37 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
187
185
  ):
188
186
  tz = pytz.timezone(alarm_clock.zone.instance.timezone)
189
187
  timezone.activate(tz)
188
+ alarm_clock.prepare_controller()
190
189
  alarm_clock.tick()
191
190
 
191
+ def watch_scripts(self):
192
+ from simo.generic.controllers import Script
193
+ for script in Component.objects.filter(
194
+ controller_uid=Script.uid,
195
+ config__autostart=True
196
+ ).exclude(value='running'):
197
+ script.prepare_controller()
198
+ self.start_script(script)
199
+
200
+ def watch_watering(self):
201
+ from .controllers import Watering
202
+ for watering in Component.objects.filter(controller_uid=Watering.uid):
203
+ tz = pytz.timezone(watering.zone.instance.timezone)
204
+ timezone.activate(tz)
205
+ watering.prepare_controller()
206
+ if watering.value['status'] == 'running_program':
207
+ watering.set_program_progress(
208
+ watering.value['program_progress'] + 1
209
+ )
210
+ else:
211
+ watering.controller._perform_schedule()
212
+
192
213
  def run(self, exit):
193
214
  self.exit = exit
194
215
  self.logger = get_gw_logger(self.gateway_instance.id)
195
216
  for task, period in self.periodic_tasks:
196
217
  threading.Thread(
197
- target=self._run_periodic_task, args=(task, period), daemon=True
218
+ target=self._run_periodic_task, args=(exit, task, period), daemon=True
198
219
  ).start()
199
220
 
200
221
  from simo.generic.controllers import Script, IPCamera
@@ -244,7 +265,7 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
244
265
  mqtt_client.subscribe(command.get_topic())
245
266
 
246
267
  def on_mqtt_message(self, client, userdata, msg):
247
- from simo.generic.controllers import Script, Blinds
268
+ from simo.generic.controllers import Script, Blinds, AlarmGroup, Gate
248
269
  payload = json.loads(msg.payload)
249
270
  component = get_event_obj(payload, Component)
250
271
  if not component:
@@ -258,6 +279,10 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
258
279
  return
259
280
  elif component.controller_uid == Blinds.uid:
260
281
  self.control_blinds(component, payload.get('set_val'))
282
+ elif component.controller_uid == AlarmGroup.uid:
283
+ self.control_alarm_group(component, payload.get('set_val'))
284
+ elif component.controller_uid == Gate:
285
+ self.control_gate(component, payload.get('set_val'))
261
286
 
262
287
  def start_script(self, component):
263
288
  print("START SCRIPT %s" % str(component))
@@ -308,9 +333,11 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
308
333
  open_switch = Component.objects.get(
309
334
  pk=blinds.config['open_switch']
310
335
  )
336
+ open_switch.prepare_controller()
311
337
  close_switch = Component.objects.get(
312
338
  pk=blinds.config['close_switch']
313
339
  )
340
+ close_switch.prepare_controller()
314
341
  except:
315
342
  return
316
343
 
@@ -340,9 +367,70 @@ class GenericGatewayHandler(BaseObjectCommandsGatewayHandler):
340
367
 
341
368
  self.blinds_runners[blinds.id].start()
342
369
 
370
+ def control_alarm_group(self, alarm_group, value):
371
+ from simo.generic.controllers import AlarmGroup
372
+
373
+ other_alarm_groups = {}
374
+ stats = {
375
+ 'disarmed': 0, 'pending-arm': 0, 'armed': 0, 'breached': 0
376
+ }
377
+
378
+ for c_id in alarm_group.config['components']:
379
+ slave = Component.objects.filter(pk=c_id).first()
380
+ if not slave:
381
+ continue
382
+ if value == 'armed':
383
+ if not slave.is_in_alarm():
384
+ slave.arm_status = 'armed'
385
+ stats['armed'] += 1
386
+ else:
387
+ slave.arm_status = 'pending-arm'
388
+ stats['pending-arm'] += 1
389
+ elif value == 'disarmed':
390
+ stats['disarmed'] += 1
391
+ slave.arm_status = 'disarmed'
392
+
393
+ slave.do_not_update_alarm_group = True
394
+ slave.save(update_fields=['arm_status'])
395
+
396
+ for other_group in Component.objects.filter(
397
+ controller_uid=AlarmGroup.uid,
398
+ config__components__contains=slave.id
399
+ ).exclude(pk=alarm_group.pk):
400
+ other_alarm_groups[other_group.pk] = other_group
401
+
402
+ alarm_group.value = value
403
+ if stats['pending-arm']:
404
+ alarm_group.value = 'pending-arm'
405
+ alarm_group.config['stats'] = stats
406
+ alarm_group.save()
407
+
408
+ for pk, other_group in other_alarm_groups.items():
409
+ other_group.prepare_controller()
410
+ other_group.refresh_status()
411
+
412
+
413
+ def control_gate(self, gate, value):
414
+ switch = Component.objects.filter(
415
+ pk=gate.config.get('action_switch')
416
+ ).first()
417
+ if not switch:
418
+ return
419
+ switch.prepare_controller()
343
420
 
421
+ if gate.config.get('action_method') == 'click':
422
+ switch.click()
423
+ else:
424
+ if value == 'open':
425
+ switch.turn_on()
426
+ else:
427
+ switch.turn_off()
344
428
 
345
429
 
346
430
  class DummyGatewayHandler(BaseObjectCommandsGatewayHandler):
347
431
  name = "Dummy"
348
432
  config_form = BaseGatewayForm
433
+
434
+ def perform_value_send(self, component, value):
435
+ component.controller.set(value)
436
+
simo/generic/models.py CHANGED
@@ -63,9 +63,9 @@ def handle_alarm_groups(sender, instance, *args, **kwargs):
63
63
  alarm_group.set(alarm_group_value)
64
64
 
65
65
 
66
- @receiver(pre_save, sender=Component)
67
- def set_initial_alarm_group_stats(sender, instance, *args, **kwargs):
68
- if instance.pk:
66
+ @receiver(post_save, sender=Component)
67
+ def set_initial_alarm_group_stats(sender, instance, created, *args, **kwargs):
68
+ if not created:
69
69
  return
70
70
  if instance.controller_uid != AlarmGroup.uid:
71
71
  return
@@ -1,11 +1,11 @@
1
1
  from django.utils.translation import gettext_lazy as _
2
2
  from django.core.exceptions import ValidationError
3
3
  from simo.core.controllers import BEFORE_SEND, BEFORE_SET
4
- from simo.core.controllers import ControllerBase, TimerMixin
4
+ from simo.core.controllers import Switch, TimerMixin
5
5
  from .app_widgets import AudioPlayerWidget, VideoPlayerWidget
6
6
 
7
7
 
8
- class BasePlayer(ControllerBase, TimerMixin):
8
+ class BasePlayer(Switch):
9
9
  default_config = {
10
10
  'has_volume_control': True,
11
11
  }
@@ -22,6 +22,13 @@ class BasePlayer(ControllerBase, TimerMixin):
22
22
  }
23
23
  default_value = 'stopped'
24
24
 
25
+ def _prepare_for_send(self, value):
26
+ if isinstance(value, bool):
27
+ if value:
28
+ return 'play'
29
+ return 'pause'
30
+ return value
31
+
25
32
  def _validate_val(self, value, occasion=None):
26
33
  return value
27
34
 
@@ -59,12 +66,6 @@ class BasePlayer(ControllerBase, TimerMixin):
59
66
  def play_library_item(self, val):
60
67
  self.send({'play_from_library': val})
61
68
 
62
- def turn_on(self):
63
- self.play()
64
-
65
- def turn_off(self):
66
- self.pause()
67
-
68
69
  def toggle(self):
69
70
  if self.component.value == 'playing':
70
71
  self.turn_off()
simo/settings.py CHANGED
@@ -41,7 +41,6 @@ EMAIL_BACKEND = 'django.core.mail.backends.console.EmailBackend'
41
41
 
42
42
  INSTALLED_APPS = [
43
43
  'channels',
44
- 'filebrowser',
45
44
  'dal',
46
45
  'dal_select2',
47
46
  'django.forms',
@@ -87,8 +86,11 @@ MIDDLEWARE = [
87
86
  'simo.core.middleware.instance_middleware'
88
87
  ]
89
88
 
89
+
90
+ FILE_UPLOAD_MAX_MEMORY_SIZE = 20971520 # 20Mb
91
+
90
92
  ROOT_URLCONF = 'urls'
91
- WSGI_APPLICATION = 'wsgi.application'
93
+ WSGI_APPLICATION = 'simo.wsgi.application'
92
94
 
93
95
  CHANNELS_URLCONF = 'simo.asgi'
94
96
  ASGI_APPLICATION = "asgi.application"
@@ -120,7 +122,7 @@ DATABASES = {
120
122
  'default': {
121
123
  'ENGINE': 'simo.core.db_backend',
122
124
  'NAME': 'SIMO',
123
- 'ATOMIC_REQUESTS': False
125
+ 'ATOMIC_REQUESTS': False,
124
126
  }
125
127
  }
126
128
 
@@ -185,7 +187,8 @@ REST_FRAMEWORK = {
185
187
  'DEFAULT_FILTER_BACKENDS': ['django_filters.rest_framework.DjangoFilterBackend'],
186
188
  'DEFAULT_PAGINATION_CLASS': 'rest_framework.pagination.PageNumberPagination',
187
189
  'PAGE_SIZE': 1000,
188
- 'DATETIME_FORMAT': '%s.%f'
190
+ 'DATETIME_FORMAT': '%s.%f',
191
+ 'DEFAULT_METADATA_CLASS': 'simo.core.api_meta.SIMOAPIMetadata'
189
192
  }
190
193
 
191
194
  REDIS_DB = {
simo/urls.py CHANGED
@@ -1,5 +1,6 @@
1
1
  import importlib
2
2
  import inspect
3
+ import sys
3
4
  from django.urls import path, include
4
5
  from django.conf.urls.static import static
5
6
  from django.conf import settings
@@ -9,23 +10,17 @@ from django.apps import apps
9
10
  from django.contrib.auth.views import LogoutView
10
11
  from rest_framework import routers
11
12
  from rest_framework.viewsets import GenericViewSet
12
- from filebrowser.sites import FileBrowserSite
13
13
  from django.contrib.admin import site as admin_site
14
14
  from simo.users.views import protected_static
15
15
 
16
16
 
17
- filebrowser_site = FileBrowserSite(
18
- name='filebrowser', storage=FileSystemStorage(
19
- settings.VAR_DIR, settings.VAR_DIR_URL
20
- )
21
- )
22
17
 
23
18
  rest_router = routers.DefaultRouter()
24
19
  registered_classes = []
25
20
  for name, app in apps.app_configs.items():
26
21
  try:
27
22
  apis = importlib.import_module('%s.api' % app.name)
28
- except ModuleNotFoundError:
23
+ except ModuleNotFoundError as e:
29
24
  continue
30
25
  for cls_name, cls in apis.__dict__.items():
31
26
  cls_id = '%s.%s' % (app.name, cls_name)
@@ -39,7 +34,8 @@ for name, app in apps.app_configs.items():
39
34
  urlpatterns = [
40
35
  path('', RedirectView.as_view(pattern_name='admin:index')),
41
36
  path('login/', include('simo.users.sso_urls')),
42
- path('admin/filebrowser/', filebrowser_site.urls),
37
+
38
+
43
39
  path('admin/login/',
44
40
  RedirectView.as_view(
45
41
  pattern_name='login', query_string=True
Binary file
Binary file