simo 2.7.13__py3-none-any.whl → 2.7.15__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 (329) hide show
  1. simo/__pycache__/__init__.cpython-312.pyc +0 -0
  2. simo/__pycache__/asgi.cpython-312.pyc +0 -0
  3. simo/__pycache__/celeryc.cpython-312.pyc +0 -0
  4. simo/__pycache__/conf.cpython-312.pyc +0 -0
  5. simo/__pycache__/settings.cpython-312.pyc +0 -0
  6. simo/__pycache__/urls.cpython-312.pyc +0 -0
  7. simo/automation/__pycache__/__init__.cpython-312.pyc +0 -0
  8. simo/automation/__pycache__/app_widgets.cpython-312.pyc +0 -0
  9. simo/automation/__pycache__/controllers.cpython-312.pyc +0 -0
  10. simo/automation/__pycache__/forms.cpython-312.pyc +0 -0
  11. simo/automation/__pycache__/gateways.cpython-312.pyc +0 -0
  12. simo/automation/__pycache__/gateways.cpython-38.pyc +0 -0
  13. simo/automation/__pycache__/helpers.cpython-312.pyc +0 -0
  14. simo/automation/__pycache__/models.cpython-312.pyc +0 -0
  15. simo/automation/__pycache__/serializers.cpython-312.pyc +0 -0
  16. simo/automation/__pycache__/state.cpython-312.pyc +0 -0
  17. simo/automation/gateways.py +27 -26
  18. simo/automation/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  19. simo/automation/migrations/__pycache__/0002_update_helpers_in_scripts.cpython-312.pyc +0 -0
  20. simo/automation/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  21. simo/backups/__pycache__/__init__.cpython-312.pyc +0 -0
  22. simo/backups/__pycache__/admin.cpython-312.pyc +0 -0
  23. simo/backups/__pycache__/dynamic_settings.cpython-312.pyc +0 -0
  24. simo/backups/__pycache__/models.cpython-312.pyc +0 -0
  25. simo/backups/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  26. simo/backups/migrations/__pycache__/0002_backuplog_backup_level_backup_size.cpython-312.pyc +0 -0
  27. simo/backups/migrations/__pycache__/0003_alter_backuplog_options_alter_backup_size.cpython-312.pyc +0 -0
  28. simo/backups/migrations/__pycache__/0004_alter_backup_options_alter_backuplog_options_and_more.cpython-312.pyc +0 -0
  29. simo/backups/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  30. simo/core/__pycache__/__init__.cpython-312.pyc +0 -0
  31. simo/core/__pycache__/admin.cpython-312.pyc +0 -0
  32. simo/core/__pycache__/api.cpython-312.pyc +0 -0
  33. simo/core/__pycache__/api.cpython-38.pyc +0 -0
  34. simo/core/__pycache__/api_auth.cpython-312.pyc +0 -0
  35. simo/core/__pycache__/api_meta.cpython-312.pyc +0 -0
  36. simo/core/__pycache__/api_meta.cpython-38.pyc +0 -0
  37. simo/core/__pycache__/app_widgets.cpython-312.pyc +0 -0
  38. simo/core/__pycache__/apps.cpython-312.pyc +0 -0
  39. simo/core/__pycache__/auto_urls.cpython-312.pyc +0 -0
  40. simo/core/__pycache__/autocomplete_views.cpython-312.pyc +0 -0
  41. simo/core/__pycache__/base_types.cpython-312.pyc +0 -0
  42. simo/core/__pycache__/context.cpython-312.pyc +0 -0
  43. simo/core/__pycache__/controllers.cpython-312.pyc +0 -0
  44. simo/core/__pycache__/dynamic_settings.cpython-312.pyc +0 -0
  45. simo/core/__pycache__/events.cpython-312.pyc +0 -0
  46. simo/core/__pycache__/filters.cpython-312.pyc +0 -0
  47. simo/core/__pycache__/form_fields.cpython-312.pyc +0 -0
  48. simo/core/__pycache__/form_fields.cpython-38.pyc +0 -0
  49. simo/core/__pycache__/forms.cpython-312.pyc +0 -0
  50. simo/core/__pycache__/gateways.cpython-312.pyc +0 -0
  51. simo/core/__pycache__/loggers.cpython-312.pyc +0 -0
  52. simo/core/__pycache__/managers.cpython-312.pyc +0 -0
  53. simo/core/__pycache__/middleware.cpython-312.pyc +0 -0
  54. simo/core/__pycache__/models.cpython-312.pyc +0 -0
  55. simo/core/__pycache__/models.cpython-38.pyc +0 -0
  56. simo/core/__pycache__/permissions.cpython-312.pyc +0 -0
  57. simo/core/__pycache__/routing.cpython-312.pyc +0 -0
  58. simo/core/__pycache__/serializers.cpython-312.pyc +0 -0
  59. simo/core/__pycache__/serializers.cpython-38.pyc +0 -0
  60. simo/core/__pycache__/signal_receivers.cpython-312.pyc +0 -0
  61. simo/core/__pycache__/socket_consumers.cpython-312.pyc +0 -0
  62. simo/core/__pycache__/storage.cpython-312.pyc +0 -0
  63. simo/core/__pycache__/tasks.cpython-312.pyc +0 -0
  64. simo/core/__pycache__/todos.cpython-312.pyc +0 -0
  65. simo/core/__pycache__/views.cpython-312.pyc +0 -0
  66. simo/core/__pycache__/widgets.cpython-312.pyc +0 -0
  67. simo/core/api.py +0 -1
  68. simo/core/api_meta.py +2 -1
  69. simo/core/db_backend/__pycache__/__init__.cpython-312.pyc +0 -0
  70. simo/core/db_backend/__pycache__/base.cpython-312.pyc +0 -0
  71. simo/core/drf_braces/__pycache__/__init__.cpython-312.pyc +0 -0
  72. simo/core/drf_braces/__pycache__/utils.cpython-312.pyc +0 -0
  73. simo/core/drf_braces/fields/__pycache__/__init__.cpython-312.pyc +0 -0
  74. simo/core/drf_braces/fields/__pycache__/_fields.cpython-312.pyc +0 -0
  75. simo/core/drf_braces/fields/__pycache__/custom.cpython-312.pyc +0 -0
  76. simo/core/drf_braces/fields/__pycache__/mixins.cpython-312.pyc +0 -0
  77. simo/core/drf_braces/fields/__pycache__/modified.cpython-312.pyc +0 -0
  78. simo/core/drf_braces/serializers/__pycache__/__init__.cpython-312.pyc +0 -0
  79. simo/core/drf_braces/serializers/__pycache__/form_serializer.cpython-312.pyc +0 -0
  80. simo/core/form_fields.py +6 -0
  81. simo/core/management/__pycache__/__init__.cpython-312.pyc +0 -0
  82. simo/core/management/commands/__pycache__/__init__.cpython-312.pyc +0 -0
  83. simo/core/management/commands/__pycache__/gateways_manager.cpython-312.pyc +0 -0
  84. simo/core/management/commands/__pycache__/on_http_start.cpython-38.pyc +0 -0
  85. simo/core/management/commands/on_http_start.py +16 -0
  86. simo/core/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  87. simo/core/migrations/__pycache__/0002_load_icons.cpython-312.pyc +0 -0
  88. simo/core/migrations/__pycache__/0003_create_default_zones_and_categories.cpython-312.pyc +0 -0
  89. simo/core/migrations/__pycache__/0004_create_generic.cpython-312.pyc +0 -0
  90. simo/core/migrations/__pycache__/0005_component_subcomponents.cpython-312.pyc +0 -0
  91. simo/core/migrations/__pycache__/0006_alter_component_subcomponents.cpython-312.pyc +0 -0
  92. simo/core/migrations/__pycache__/0007_component_change_init_to.cpython-312.pyc +0 -0
  93. simo/core/migrations/__pycache__/0008_alter_component_change_init_to.cpython-312.pyc +0 -0
  94. simo/core/migrations/__pycache__/0009_auto_20220707_1404.cpython-312.pyc +0 -0
  95. simo/core/migrations/__pycache__/0010_historyaggregate.cpython-312.pyc +0 -0
  96. simo/core/migrations/__pycache__/0011_component_last_change.cpython-312.pyc +0 -0
  97. simo/core/migrations/__pycache__/0012_instance.cpython-312.pyc +0 -0
  98. simo/core/migrations/__pycache__/0013_auto_20231003_0754.cpython-312.pyc +0 -0
  99. simo/core/migrations/__pycache__/0014_zone_instance.cpython-312.pyc +0 -0
  100. simo/core/migrations/__pycache__/0015_auto_20231004_1113.cpython-312.pyc +0 -0
  101. simo/core/migrations/__pycache__/0016_auto_20231004_1113.cpython-312.pyc +0 -0
  102. simo/core/migrations/__pycache__/0017_auto_20231004_1313.cpython-312.pyc +0 -0
  103. simo/core/migrations/__pycache__/0018_auto_20231005_0622.cpython-312.pyc +0 -0
  104. simo/core/migrations/__pycache__/0019_alter_gateway_type.cpython-312.pyc +0 -0
  105. simo/core/migrations/__pycache__/0020_component_meta.cpython-312.pyc +0 -0
  106. simo/core/migrations/__pycache__/0021_auto_20231020_1041.cpython-312.pyc +0 -0
  107. simo/core/migrations/__pycache__/0022_auto_20231221_0735.cpython-312.pyc +0 -0
  108. simo/core/migrations/__pycache__/0023_auto_20231229_1352.cpython-312.pyc +0 -0
  109. simo/core/migrations/__pycache__/0024_alter_instance_device_report_history_days.cpython-312.pyc +0 -0
  110. simo/core/migrations/__pycache__/0025_auto_20240122_1321.cpython-312.pyc +0 -0
  111. simo/core/migrations/__pycache__/0026_category_instance.cpython-312.pyc +0 -0
  112. simo/core/migrations/__pycache__/0027_remove_component_tags.cpython-312.pyc +0 -0
  113. simo/core/migrations/__pycache__/0028_rename_subcomponents_component_slaves.cpython-312.pyc +0 -0
  114. simo/core/migrations/__pycache__/0029_auto_20240229_1331.cpython-312.pyc +0 -0
  115. simo/core/migrations/__pycache__/0030_alter_instance_timezone.cpython-312.pyc +0 -0
  116. simo/core/migrations/__pycache__/0031_auto_20240429_1231.cpython-312.pyc +0 -0
  117. simo/core/migrations/__pycache__/0032_auto_20240506_0834.cpython-312.pyc +0 -0
  118. simo/core/migrations/__pycache__/0033_auto_20240509_0821.cpython-312.pyc +0 -0
  119. simo/core/migrations/__pycache__/0034_component_error_msg.cpython-312.pyc +0 -0
  120. simo/core/migrations/__pycache__/0035_remove_instance_share_location.cpython-312.pyc +0 -0
  121. simo/core/migrations/__pycache__/0036_auto_20240521_0823.cpython-312.pyc +0 -0
  122. simo/core/migrations/__pycache__/0037_auto_20240606_1057.cpython-312.pyc +0 -0
  123. simo/core/migrations/__pycache__/0038_remove_instance_cover_image_and_more.cpython-312.pyc +0 -0
  124. simo/core/migrations/__pycache__/0039_instance_is_active_alter_instance_timezone.cpython-312.pyc +0 -0
  125. simo/core/migrations/__pycache__/0040_alter_instance_name.cpython-312.pyc +0 -0
  126. simo/core/migrations/__pycache__/0041_alter_instance_slug.cpython-312.pyc +0 -0
  127. simo/core/migrations/__pycache__/0042_alter_instance_timezone.cpython-312.pyc +0 -0
  128. simo/core/migrations/__pycache__/0043_alter_category_instance_alter_instance_timezone_and_more.cpython-312.pyc +0 -0
  129. simo/core/migrations/__pycache__/0044_alter_gateway_type.cpython-312.pyc +0 -0
  130. simo/core/migrations/__pycache__/0045_alter_instance_device_report_history_days_and_more.cpython-312.pyc +0 -0
  131. simo/core/migrations/__pycache__/0046_component_value_translation_alter_gateway_type.cpython-312.pyc +0 -0
  132. simo/core/migrations/__pycache__/0047_alter_component_value_translation.cpython-312.pyc +0 -0
  133. simo/core/migrations/__pycache__/0048_publicfile_privatefile.cpython-312.pyc +0 -0
  134. simo/core/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  135. simo/core/models.py +1 -1
  136. simo/core/serializers.py +26 -10
  137. simo/core/templatetags/__pycache__/__init__.cpython-312.pyc +0 -0
  138. simo/core/templatetags/__pycache__/components_list.cpython-312.pyc +0 -0
  139. simo/core/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  140. simo/core/utils/__pycache__/admin.cpython-312.pyc +0 -0
  141. simo/core/utils/__pycache__/api.cpython-312.pyc +0 -0
  142. simo/core/utils/__pycache__/cache.cpython-312.pyc +0 -0
  143. simo/core/utils/__pycache__/config_values.cpython-312.pyc +0 -0
  144. simo/core/utils/__pycache__/converters.cpython-312.pyc +0 -0
  145. simo/core/utils/__pycache__/easing.cpython-312.pyc +0 -0
  146. simo/core/utils/__pycache__/form_fields.cpython-312.pyc +0 -0
  147. simo/core/utils/__pycache__/form_widgets.cpython-312.pyc +0 -0
  148. simo/core/utils/__pycache__/formsets.cpython-312.pyc +0 -0
  149. simo/core/utils/__pycache__/helpers.cpython-312.pyc +0 -0
  150. simo/core/utils/__pycache__/json.cpython-312.pyc +0 -0
  151. simo/core/utils/__pycache__/logs.cpython-312.pyc +0 -0
  152. simo/core/utils/__pycache__/mixins.cpython-312.pyc +0 -0
  153. simo/core/utils/__pycache__/model_helpers.cpython-312.pyc +0 -0
  154. simo/core/utils/__pycache__/operations.cpython-312.pyc +0 -0
  155. simo/core/utils/__pycache__/relay.cpython-312.pyc +0 -0
  156. simo/core/utils/__pycache__/serialization.cpython-312.pyc +0 -0
  157. simo/core/utils/__pycache__/type_constants.cpython-312.pyc +0 -0
  158. simo/core/utils/__pycache__/validators.cpython-312.pyc +0 -0
  159. simo/fleet/__pycache__/__init__.cpython-312.pyc +0 -0
  160. simo/fleet/__pycache__/admin.cpython-312.pyc +0 -0
  161. simo/fleet/__pycache__/api.cpython-312.pyc +0 -0
  162. simo/fleet/__pycache__/auto_urls.cpython-312.pyc +0 -0
  163. simo/fleet/__pycache__/base_types.cpython-312.pyc +0 -0
  164. simo/fleet/__pycache__/controllers.cpython-312.pyc +0 -0
  165. simo/fleet/__pycache__/forms.cpython-312.pyc +0 -0
  166. simo/fleet/__pycache__/gateways.cpython-312.pyc +0 -0
  167. simo/fleet/__pycache__/managers.cpython-312.pyc +0 -0
  168. simo/fleet/__pycache__/models.cpython-312.pyc +0 -0
  169. simo/fleet/__pycache__/routing.cpython-312.pyc +0 -0
  170. simo/fleet/__pycache__/serializers.cpython-312.pyc +0 -0
  171. simo/fleet/__pycache__/socket_consumers.cpython-312.pyc +0 -0
  172. simo/fleet/__pycache__/utils.cpython-312.pyc +0 -0
  173. simo/fleet/__pycache__/views.cpython-312.pyc +0 -0
  174. simo/fleet/controllers.py +8 -0
  175. simo/fleet/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  176. simo/fleet/migrations/__pycache__/0002_auto_20220422_0743.cpython-312.pyc +0 -0
  177. simo/fleet/migrations/__pycache__/0003_auto_20220422_0752.cpython-312.pyc +0 -0
  178. simo/fleet/migrations/__pycache__/0004_auto_20220422_0818.cpython-312.pyc +0 -0
  179. simo/fleet/migrations/__pycache__/0005_auto_20220428_0900.cpython-312.pyc +0 -0
  180. simo/fleet/migrations/__pycache__/0006_rename_mac_colonel_uid.cpython-312.pyc +0 -0
  181. simo/fleet/migrations/__pycache__/0007_colonel_socket_connected.cpython-312.pyc +0 -0
  182. simo/fleet/migrations/__pycache__/0008_i2cinterface.cpython-312.pyc +0 -0
  183. simo/fleet/migrations/__pycache__/0009_i2cinterface_name.cpython-312.pyc +0 -0
  184. simo/fleet/migrations/__pycache__/0010_auto_20220602_0746.cpython-312.pyc +0 -0
  185. simo/fleet/migrations/__pycache__/0011_i2cinterface_freq.cpython-312.pyc +0 -0
  186. simo/fleet/migrations/__pycache__/0012_colonel_logs_stream.cpython-312.pyc +0 -0
  187. simo/fleet/migrations/__pycache__/0013_alter_colonel_last_seen.cpython-312.pyc +0 -0
  188. simo/fleet/migrations/__pycache__/0014_auto_20220614_0659.cpython-312.pyc +0 -0
  189. simo/fleet/migrations/__pycache__/0015_auto_20220614_0754.cpython-312.pyc +0 -0
  190. simo/fleet/migrations/__pycache__/0016_auto_20220704_0840.cpython-312.pyc +0 -0
  191. simo/fleet/migrations/__pycache__/0017_alter_colonel_secret.cpython-312.pyc +0 -0
  192. simo/fleet/migrations/__pycache__/0018_colonel_instance.cpython-312.pyc +0 -0
  193. simo/fleet/migrations/__pycache__/0019_auto_20231006_0749.cpython-312.pyc +0 -0
  194. simo/fleet/migrations/__pycache__/0020_instanceoptions.cpython-312.pyc +0 -0
  195. simo/fleet/migrations/__pycache__/0021_auto_20231006_0819.cpython-312.pyc +0 -0
  196. simo/fleet/migrations/__pycache__/0022_remove_colonel_secret.cpython-312.pyc +0 -0
  197. simo/fleet/migrations/__pycache__/0023_colonel_is_authorized.cpython-312.pyc +0 -0
  198. simo/fleet/migrations/__pycache__/0024_colonel_pwm_frequency.cpython-312.pyc +0 -0
  199. simo/fleet/migrations/__pycache__/0025_auto_20240130_1334.cpython-312.pyc +0 -0
  200. simo/fleet/migrations/__pycache__/0026_rename_i2cinterface_scl_pin_and_more.cpython-312.pyc +0 -0
  201. simo/fleet/migrations/__pycache__/0027_auto_20240306_0802.cpython-312.pyc +0 -0
  202. simo/fleet/migrations/__pycache__/0028_remove_i2cinterface_scl_pin_no_and_more.cpython-312.pyc +0 -0
  203. simo/fleet/migrations/__pycache__/0029_alter_i2cinterface_scl_pin_and_more.cpython-312.pyc +0 -0
  204. simo/fleet/migrations/__pycache__/0030_colonelpin_label_alter_colonel_type.cpython-312.pyc +0 -0
  205. simo/fleet/migrations/__pycache__/0031_alter_colonel_type.cpython-312.pyc +0 -0
  206. simo/fleet/migrations/__pycache__/0032_auto_20240415_0736.cpython-312.pyc +0 -0
  207. simo/fleet/migrations/__pycache__/0033_auto_20240415_0736.cpython-312.pyc +0 -0
  208. simo/fleet/migrations/__pycache__/0034_auto_20240418_0735.cpython-312.pyc +0 -0
  209. simo/fleet/migrations/__pycache__/0035_auto_20240514_0855.cpython-312.pyc +0 -0
  210. simo/fleet/migrations/__pycache__/0036_auto_20240605_0702.cpython-312.pyc +0 -0
  211. simo/fleet/migrations/__pycache__/0037_alter_colonelpin_options_alter_colonelpin_no_and_more.cpython-312.pyc +0 -0
  212. simo/fleet/migrations/__pycache__/0038_alter_colonel_type.cpython-312.pyc +0 -0
  213. simo/fleet/migrations/__pycache__/0039_auto_20241016_1047.cpython-312.pyc +0 -0
  214. simo/fleet/migrations/__pycache__/0040_alter_colonel_pwm_frequency.cpython-312.pyc +0 -0
  215. simo/fleet/migrations/__pycache__/0041_alter_colonel_instance_and_more.cpython-312.pyc +0 -0
  216. simo/fleet/migrations/__pycache__/0042_auto_20241120_1028.cpython-312.pyc +0 -0
  217. simo/fleet/migrations/__pycache__/0043_auto_20241203_0930.cpython-312.pyc +0 -0
  218. simo/fleet/migrations/__pycache__/0044_auto_20241210_0707.cpython-312.pyc +0 -0
  219. simo/fleet/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  220. simo/generic/__pycache__/__init__.cpython-312.pyc +0 -0
  221. simo/generic/__pycache__/app_widgets.cpython-312.pyc +0 -0
  222. simo/generic/__pycache__/base_types.cpython-312.pyc +0 -0
  223. simo/generic/__pycache__/controllers.cpython-312.pyc +0 -0
  224. simo/generic/__pycache__/forms.cpython-312.pyc +0 -0
  225. simo/generic/__pycache__/forms.cpython-38.pyc +0 -0
  226. simo/generic/__pycache__/gateways.cpython-312.pyc +0 -0
  227. simo/generic/__pycache__/models.cpython-312.pyc +0 -0
  228. simo/generic/__pycache__/routing.cpython-312.pyc +0 -0
  229. simo/generic/__pycache__/socket_consumers.cpython-312.pyc +0 -0
  230. simo/generic/forms.py +25 -22
  231. simo/generic/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  232. simo/generic/migrations/__pycache__/0002_auto_20241126_0726.cpython-312.pyc +0 -0
  233. simo/generic/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  234. simo/multimedia/__pycache__/__init__.cpython-312.pyc +0 -0
  235. simo/multimedia/__pycache__/admin.cpython-312.pyc +0 -0
  236. simo/multimedia/__pycache__/api.cpython-312.pyc +0 -0
  237. simo/multimedia/__pycache__/app_widgets.cpython-312.pyc +0 -0
  238. simo/multimedia/__pycache__/app_widgets.cpython-38.pyc +0 -0
  239. simo/multimedia/__pycache__/auto_urls.cpython-312.pyc +0 -0
  240. simo/multimedia/__pycache__/base_types.cpython-312.pyc +0 -0
  241. simo/multimedia/__pycache__/controllers.cpython-312.pyc +0 -0
  242. simo/multimedia/__pycache__/forms.cpython-312.pyc +0 -0
  243. simo/multimedia/__pycache__/models.cpython-312.pyc +0 -0
  244. simo/multimedia/__pycache__/serializers.cpython-312.pyc +0 -0
  245. simo/multimedia/__pycache__/views.cpython-312.pyc +0 -0
  246. simo/multimedia/app_widgets.py +1 -1
  247. simo/multimedia/controllers.py +1 -0
  248. simo/multimedia/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  249. simo/multimedia/migrations/__pycache__/0002_sound_length.cpython-312.pyc +0 -0
  250. simo/multimedia/migrations/__pycache__/0003_alter_sound_length.cpython-312.pyc +0 -0
  251. simo/multimedia/migrations/__pycache__/0004_auto_20231023_1055.cpython-312.pyc +0 -0
  252. simo/multimedia/migrations/__pycache__/0005_remove_sound_slug_sound_date_uploaded.cpython-312.pyc +0 -0
  253. simo/multimedia/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  254. simo/notifications/__pycache__/__init__.cpython-312.pyc +0 -0
  255. simo/notifications/__pycache__/admin.cpython-312.pyc +0 -0
  256. simo/notifications/__pycache__/api.cpython-312.pyc +0 -0
  257. simo/notifications/__pycache__/models.cpython-312.pyc +0 -0
  258. simo/notifications/__pycache__/serializers.cpython-312.pyc +0 -0
  259. simo/notifications/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  260. simo/notifications/migrations/__pycache__/0002_notification_instance.cpython-312.pyc +0 -0
  261. simo/notifications/migrations/__pycache__/0003_alter_notification_instance.cpython-312.pyc +0 -0
  262. simo/notifications/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  263. simo/users/__pycache__/__init__.cpython-312.pyc +0 -0
  264. simo/users/__pycache__/admin.cpython-312.pyc +0 -0
  265. simo/users/__pycache__/api.cpython-312.pyc +0 -0
  266. simo/users/__pycache__/apps.cpython-312.pyc +0 -0
  267. simo/users/__pycache__/auth_backends.cpython-312.pyc +0 -0
  268. simo/users/__pycache__/auto_urls.cpython-312.pyc +0 -0
  269. simo/users/__pycache__/dynamic_settings.cpython-312.pyc +0 -0
  270. simo/users/__pycache__/managers.cpython-312.pyc +0 -0
  271. simo/users/__pycache__/middleware.cpython-312.pyc +0 -0
  272. simo/users/__pycache__/models.cpython-312.pyc +0 -0
  273. simo/users/__pycache__/permissions.cpython-312.pyc +0 -0
  274. simo/users/__pycache__/serializers.cpython-312.pyc +0 -0
  275. simo/users/__pycache__/sso_urls.cpython-312.pyc +0 -0
  276. simo/users/__pycache__/sso_views.cpython-312.pyc +0 -0
  277. simo/users/__pycache__/utils.cpython-312.pyc +0 -0
  278. simo/users/__pycache__/views.cpython-312.pyc +0 -0
  279. simo/users/migrations/__pycache__/0001_initial.cpython-312.pyc +0 -0
  280. simo/users/migrations/__pycache__/0002_componentpermission.cpython-312.pyc +0 -0
  281. simo/users/migrations/__pycache__/0003_create_roles_and_system_user.cpython-312.pyc +0 -0
  282. simo/users/migrations/__pycache__/0004_user_secret_key.cpython-312.pyc +0 -0
  283. simo/users/migrations/__pycache__/0005_permissionsrole_instance.cpython-312.pyc +0 -0
  284. simo/users/migrations/__pycache__/0006_auto_20231003_0850.cpython-312.pyc +0 -0
  285. simo/users/migrations/__pycache__/0007_auto_20231003_1228.cpython-312.pyc +0 -0
  286. simo/users/migrations/__pycache__/0008_auto_20231003_1229.cpython-312.pyc +0 -0
  287. simo/users/migrations/__pycache__/0009_remove_user_role.cpython-312.pyc +0 -0
  288. simo/users/migrations/__pycache__/0010_auto_20231004_1313.cpython-312.pyc +0 -0
  289. simo/users/migrations/__pycache__/0011_auto_20231004_1313.cpython-312.pyc +0 -0
  290. simo/users/migrations/__pycache__/0012_alter_userinstancerole_unique_together.cpython-312.pyc +0 -0
  291. simo/users/migrations/__pycache__/0013_remove_user_roles.cpython-312.pyc +0 -0
  292. simo/users/migrations/__pycache__/0014_user_roles.cpython-312.pyc +0 -0
  293. simo/users/migrations/__pycache__/0015_remove_user_at_home.cpython-312.pyc +0 -0
  294. simo/users/migrations/__pycache__/0016_auto_20231005_1050.cpython-312.pyc +0 -0
  295. simo/users/migrations/__pycache__/0017_auto_20231221_0735.cpython-312.pyc +0 -0
  296. simo/users/migrations/__pycache__/0018_user_is_god.cpython-312.pyc +0 -0
  297. simo/users/migrations/__pycache__/0019_auto_20231221_1155.cpython-312.pyc +0 -0
  298. simo/users/migrations/__pycache__/0020_rename_is_god_user_is_master.cpython-312.pyc +0 -0
  299. simo/users/migrations/__pycache__/0021_alter_permissionsrole_instance.cpython-312.pyc +0 -0
  300. simo/users/migrations/__pycache__/0022_userdevicereportlog_instance.cpython-312.pyc +0 -0
  301. simo/users/migrations/__pycache__/0023_auto_20240105_0719.cpython-312.pyc +0 -0
  302. simo/users/migrations/__pycache__/0024_fingerprint.cpython-312.pyc +0 -0
  303. simo/users/migrations/__pycache__/0025_rename_name_fingerprint_type_and_more.cpython-312.pyc +0 -0
  304. simo/users/migrations/__pycache__/0026_fingerprint_name.cpython-312.pyc +0 -0
  305. simo/users/migrations/__pycache__/0027_permissionsrole_can_manage_components.cpython-312.pyc +0 -0
  306. simo/users/migrations/__pycache__/0028_auto_20240506_1146.cpython-312.pyc +0 -0
  307. simo/users/migrations/__pycache__/0029_alter_instanceuser_instance.cpython-312.pyc +0 -0
  308. simo/users/migrations/__pycache__/0030_userdevice_users.cpython-312.pyc +0 -0
  309. simo/users/migrations/__pycache__/0031_auto_20240923_1115.cpython-312.pyc +0 -0
  310. simo/users/migrations/__pycache__/0032_remove_userdevice_user_alter_userdevice_users.cpython-312.pyc +0 -0
  311. simo/users/migrations/__pycache__/0033_alter_user_ssh_key.cpython-312.pyc +0 -0
  312. simo/users/migrations/__pycache__/0034_instanceuser_last_seen_location_and_more.cpython-312.pyc +0 -0
  313. simo/users/migrations/__pycache__/0035_instanceuser_last_seen_speed_kmh_and_more.cpython-312.pyc +0 -0
  314. simo/users/migrations/__pycache__/0036_instanceuser_phone_on_charge_user_phone_on_charge.cpython-312.pyc +0 -0
  315. simo/users/migrations/__pycache__/0037_rename_last_seen_location_datetime_instanceuser_last_seen_and_more.cpython-312.pyc +0 -0
  316. simo/users/migrations/__pycache__/0038_userdevicereportlog_at_home_and_more.cpython-312.pyc +0 -0
  317. simo/users/migrations/__pycache__/0039_auto_20241117_1039.cpython-312.pyc +0 -0
  318. simo/users/migrations/__pycache__/0040_userdevicereportlog_location_smoothed_and_more.cpython-312.pyc +0 -0
  319. simo/users/migrations/__pycache__/0041_userdevicereportlog_speed_kmh_received.cpython-312.pyc +0 -0
  320. simo/users/migrations/__pycache__/0042_remove_userdevicereportlog_location_smoothed_and_more.cpython-312.pyc +0 -0
  321. simo/users/migrations/__pycache__/0043_userdevicereportlog_avg_speed_kmh.cpython-312.pyc +0 -0
  322. simo/users/migrations/__pycache__/__init__.cpython-312.pyc +0 -0
  323. simo-2.7.15.dist-info/METADATA +56 -0
  324. {simo-2.7.13.dist-info → simo-2.7.15.dist-info}/RECORD +328 -26
  325. {simo-2.7.13.dist-info → simo-2.7.15.dist-info}/WHEEL +1 -1
  326. simo-2.7.13.dist-info/METADATA +0 -54
  327. {simo-2.7.13.dist-info → simo-2.7.15.dist-info}/LICENSE.md +0 -0
  328. {simo-2.7.13.dist-info → simo-2.7.15.dist-info}/entry_points.txt +0 -0
  329. {simo-2.7.13.dist-info → simo-2.7.15.dist-info}/top_level.txt +0 -0
Binary file
Binary file
Binary file
Binary file
@@ -227,37 +227,47 @@ class AutomationsGatewayHandler(GatesHandler, BaseObjectCommandsGatewayHandler):
227
227
 
228
228
  terminating_scripts = set()
229
229
 
230
+ def __init__(self, *args, **kwargs):
231
+ super().__init__(*args, **kwargs)
232
+ self.last_death = 0
233
+
230
234
 
231
235
  def watch_scripts(self):
232
236
  drop_current_instance()
233
237
  # observe running scripts and drop the ones that are no longer alive
234
238
  dead_scripts = False
235
239
  for id, process in list(self.running_scripts.items()):
240
+
236
241
  comp = Component.objects.filter(id=id).first()
237
- if comp.value == 'finished':
242
+ if comp and comp.value == 'finished':
238
243
  self.running_scripts.pop(id)
239
244
  continue
245
+
240
246
  if process.is_alive():
241
247
  if not comp and id not in self.terminating_scripts:
242
- # script is deleted, or instance deactivated
248
+ # script is deleted and was not properly called to stop
249
+ self.running_scripts.pop(id)
243
250
  process.kill()
244
251
  continue
245
252
  else:
246
- if id not in self.terminating_scripts:
247
- dead_scripts = True
248
- if comp:
249
- logger = get_component_logger(comp)
250
- logger.log(logging.INFO, "-------DEAD!-------")
251
- self.stop_script(comp, 'dead')
252
-
253
- if dead_scripts:
253
+ self.last_death = time.time()
254
+ self.running_scripts.pop(id, None) # no longer running for sure!
255
+ if not comp or comp.value != 'running':
256
+ continue
257
+
258
+ if id not in self.terminating_scripts: # was not intentionaly terminated
259
+ logger = get_component_logger(comp)
260
+ logger.log(logging.INFO, "-------DEAD!-------")
261
+ comp.value = 'error'
262
+ comp.save()
263
+
264
+
265
+ if self.last_death and time.time() - self.last_death < 5:
254
266
  # give 10s air before we wake these dead scripts up!
255
267
  return
256
268
 
257
- from .controllers import Script
258
269
  for script in Component.objects.filter(
259
- controller_uid=Script.uid,
260
- config__keep_alive=True
270
+ base_type='script', config__keep_alive=True
261
271
  ).exclude(value__in=('running', 'stopped', 'finished')):
262
272
  self.start_script(script)
263
273
 
@@ -338,23 +348,14 @@ class AutomationsGatewayHandler(GatesHandler, BaseObjectCommandsGatewayHandler):
338
348
  def start_script(self, component):
339
349
  print("START SCRIPT %s" % str(component))
340
350
  if component.id in self.running_scripts:
341
- if component.value == 'finished':
351
+ if component.value in ('finished', 'error', 'stopped'):
342
352
  self.running_scripts.pop(component.id)
343
- elif component.id not in self.terminating_scripts:
353
+ elif component.id not in self.terminating_scripts \
354
+ and self.running_scripts[component.id].is_alive():
344
355
  if component.value != 'running':
345
356
  component.value = 'running'
346
357
  component.save()
347
- return
348
- else:
349
- good_to_go = False
350
- for i in range(12): # wait for 3s
351
- time.sleep(0.2)
352
- component.refresh_from_db()
353
- if component.id not in self.running_scripts:
354
- good_to_go = True
355
- break
356
- if not good_to_go:
357
- return self.stop_script(component, 'error')
358
+ return
358
359
 
359
360
  self.running_scripts[component.id] = ScriptRunHandler(
360
361
  component.id, multiprocessing.Event(),
Binary file
Binary file
simo/core/api.py CHANGED
@@ -285,7 +285,6 @@ class ComponentViewSet(
285
285
 
286
286
  @action(detail=True, methods=['post'])
287
287
  def controller(self, request, pk=None, *args, **kwargs):
288
- start = time.time()
289
288
  component = self.get_object()
290
289
  data = request.data
291
290
  if not isinstance(request.data, dict):
simo/core/api_meta.py CHANGED
@@ -9,7 +9,7 @@ from simo.core.middleware import introduce_instance
9
9
  from .serializers import (
10
10
  HiddenSerializerField, ComponentManyToManyRelatedField,
11
11
  TextAreaSerializerField, Component, LocationSerializer,
12
- SoundSerializer
12
+ SoundSerializer, PasswordSerializer
13
13
  )
14
14
 
15
15
 
@@ -19,6 +19,7 @@ class SIMOAPIMetadata(SimpleMetadata):
19
19
  serializers.Field: 'field',
20
20
  serializers.BooleanField: 'boolean',
21
21
  serializers.CharField: 'string',
22
+ PasswordSerializer: 'password',
22
23
  serializers.UUIDField: 'string',
23
24
  serializers.URLField: 'url',
24
25
  serializers.EmailField: 'email',
simo/core/form_fields.py CHANGED
@@ -189,3 +189,9 @@ class PlainLocationField(forms.fields.CharField):
189
189
  class SoundField(forms.fields.FileField):
190
190
  pass
191
191
 
192
+
193
+
194
+ class PasswordField(forms.fields.CharField):
195
+
196
+ def __init__(self, *args, **kwargs):
197
+ super().__init__(widget=forms.PasswordInput, *args, **kwargs)
@@ -4,6 +4,9 @@ import pwd
4
4
  import grp
5
5
  import sys
6
6
  import subprocess
7
+ import importlib
8
+ import traceback
9
+ from django.apps import apps
7
10
  from crontab import CronTab
8
11
  from django.conf import settings
9
12
  from django.template.loader import render_to_string
@@ -81,3 +84,16 @@ class Command(BaseCommand):
81
84
  from simo.core.tasks import maybe_update_to_latest
82
85
  maybe_update_to_latest.delay()
83
86
  update_auto_update()
87
+ for name, app in apps.app_configs.items():
88
+ if name in (
89
+ 'auth', 'admin', 'contenttypes', 'sessions', 'messages',
90
+ 'staticfiles'
91
+ ):
92
+ continue
93
+ try:
94
+ importlib.import_module('%s.on_start' % app.name)
95
+ except ModuleNotFoundError:
96
+ continue
97
+ except:
98
+ print(traceback.format_exc(), file=sys.stderr)
99
+
simo/core/models.py CHANGED
@@ -544,7 +544,7 @@ def is_in_alarm(self):
544
544
  kwargs['update_fields'].append('last_change')
545
545
 
546
546
  modifying_fields = (
547
- 'name', 'icon', 'zone', 'category', 'config', 'meta',
547
+ 'name', 'icon', 'zone', 'category', 'config',
548
548
  'value_units', 'slaves', 'show_in_app', 'alarm_category'
549
549
  )
550
550
  if any(f in dirty_fields for f in modifying_fields):
simo/core/serializers.py CHANGED
@@ -1,6 +1,7 @@
1
1
  import inspect
2
2
  import datetime
3
3
  import re
4
+ import json
4
5
  from django import forms
5
6
  from collections import OrderedDict
6
7
  from django.conf import settings
@@ -16,7 +17,7 @@ from simo.core.forms import HiddenField, FormsetField
16
17
  from simo.core.form_fields import (
17
18
  Select2ListChoiceField, Select2ModelChoiceField,
18
19
  Select2ListMultipleChoiceField, Select2ModelMultipleChoiceField,
19
- PlainLocationField, SoundField
20
+ PlainLocationField, SoundField, PasswordField
20
21
  )
21
22
  from simo.core.models import Component
22
23
  from rest_framework.relations import PrimaryKeyRelatedField, ManyRelatedField
@@ -37,6 +38,9 @@ class SoundSerializer(serializers.FileField):
37
38
  pass
38
39
 
39
40
 
41
+ class PasswordSerializer(serializers.CharField):
42
+ pass
43
+
40
44
 
41
45
  class TimestampField(serializers.Field):
42
46
 
@@ -137,6 +141,10 @@ class ComponentManyToManyRelatedField(serializers.Field):
137
141
  def to_internal_value(self, data):
138
142
  if data == [] and self.allow_blank:
139
143
  return []
144
+ if type(data) == str:
145
+ data = json.loads(data)
146
+ if not isinstance(data, Iterable):
147
+ data = [data]
140
148
  return self.queryset.filter(pk__in=data)
141
149
 
142
150
 
@@ -158,16 +166,17 @@ class ComponentFormsetField(FormSerializer):
158
166
  Select2ModelMultipleChoiceField: ComponentManyToManyRelatedField,
159
167
  forms.TypedChoiceField: serializers.ChoiceField,
160
168
  forms.FloatField: serializers.FloatField,
161
- forms.SlugField: serializers.CharField
169
+ forms.SlugField: serializers.CharField,
170
+ PasswordField: PasswordSerializer
162
171
  }
163
172
 
164
173
  def __init__(self, formset_field, *args, **kwargs):
165
174
  self.form = formset_field.formset_cls.form
166
175
  super().__init__(*args, **kwargs)
167
176
 
168
- def get_form(self, data=None, **kwargs):
177
+ def get_form(self, data=None, files=None, **kwargs):
169
178
  form_cls = self.form
170
- instance = form_cls(data=data, **kwargs)
179
+ instance = form_cls(data=data, files=files, **kwargs)
171
180
  # Handle partial validation on the form side
172
181
  if self.partial:
173
182
  set_form_partial_validation(
@@ -311,7 +320,8 @@ class ComponentSerializer(FormSerializer):
311
320
  Select2ListMultipleChoiceField: ComponentManyToManyRelatedField,
312
321
  Select2ModelMultipleChoiceField: ComponentManyToManyRelatedField,
313
322
  FormsetField: ComponentFormsetField,
314
- SoundField: SoundSerializer
323
+ SoundField: SoundSerializer,
324
+ PasswordField: PasswordSerializer
315
325
  }
316
326
 
317
327
 
@@ -435,7 +445,7 @@ class ComponentSerializer(FormSerializer):
435
445
  if controller:
436
446
  self.Meta.form = controller.config_form
437
447
 
438
- def get_form(self, data=None, instance=None, **kwargs):
448
+ def get_form(self, data=None, instance=None, files=None, **kwargs):
439
449
  if 'forms' not in self.context:
440
450
  self.context['forms'] = {}
441
451
  form_key = None
@@ -453,7 +463,7 @@ class ComponentSerializer(FormSerializer):
453
463
  else:
454
464
  controller_uid = self.instance.controller_uid
455
465
  form = self.Meta.form(
456
- data=data, request=self.context['request'],
466
+ data=data, files=files, request=self.context['request'],
457
467
  controller_uid=controller_uid, instance=instance,
458
468
  **kwargs
459
469
  )
@@ -508,7 +518,8 @@ class ComponentSerializer(FormSerializer):
508
518
  a_data = self.accomodate_formsets(form, data)
509
519
 
510
520
  form = self.get_form(
511
- data=a_data, instance=self.instance
521
+ data=a_data, files=self.context['request'].FILES,
522
+ instance=self.instance
512
523
  )
513
524
  if not form.is_valid():
514
525
  raise serializers.ValidationError(form.errors)
@@ -520,7 +531,10 @@ class ComponentSerializer(FormSerializer):
520
531
  def update(self, instance, validated_data):
521
532
  form = self.get_form(instance=instance)
522
533
  a_data = self.accomodate_formsets(form, validated_data)
523
- form = self.get_form(instance=instance, data=a_data)
534
+ form = self.get_form(
535
+ instance=instance, data=a_data,
536
+ files=self.context['request'].FILES
537
+ )
524
538
  if form.is_valid():
525
539
  instance = form.save(commit=True)
526
540
  return instance
@@ -529,7 +543,9 @@ class ComponentSerializer(FormSerializer):
529
543
  def create(self, validated_data):
530
544
  form = self.get_form()
531
545
  a_data = self.accomodate_formsets(form, validated_data)
532
- form = self.get_form(data=a_data)
546
+ form = self.get_form(
547
+ data=a_data, files=self.context['request'].FILES
548
+ )
533
549
  if form.is_valid():
534
550
  if form.controller.is_discoverable:
535
551
  form.controller.init_discovery(form.cleaned_data)