simo 2.0.41__py3-none-any.whl → 2.1.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.
- simo/__pycache__/asgi.cpython-38.pyc +0 -0
- simo/__pycache__/on_http_start.cpython-38.pyc +0 -0
- simo/__pycache__/settings.cpython-38.pyc +0 -0
- simo/__pycache__/wsgi.cpython-38.pyc +0 -0
- simo/core/__init__.py +1 -0
- simo/core/__pycache__/__init__.cpython-38.pyc +0 -0
- simo/core/__pycache__/admin.cpython-38.pyc +0 -0
- simo/core/__pycache__/api.cpython-38.pyc +0 -0
- simo/core/__pycache__/api_meta.cpython-38.pyc +0 -0
- simo/core/__pycache__/app_widgets.cpython-38.pyc +0 -0
- simo/core/__pycache__/apps.cpython-38.pyc +0 -0
- simo/core/__pycache__/base_types.cpython-38.pyc +0 -0
- simo/core/__pycache__/controllers.cpython-38.pyc +0 -0
- simo/core/__pycache__/form_fields.cpython-38.pyc +0 -0
- simo/core/__pycache__/forms.cpython-38.pyc +0 -0
- simo/core/__pycache__/gateways.cpython-38.pyc +0 -0
- simo/core/__pycache__/managers.cpython-38.pyc +0 -0
- simo/core/__pycache__/models.cpython-38.pyc +0 -0
- simo/core/__pycache__/permissions.cpython-38.pyc +0 -0
- simo/core/__pycache__/serializers.cpython-38.pyc +0 -0
- simo/core/__pycache__/signal_receivers.cpython-38.pyc +0 -0
- simo/core/admin.py +28 -10
- simo/core/api.py +24 -5
- simo/core/api_meta.py +23 -13
- simo/core/app_widgets.py +6 -0
- simo/core/apps.py +10 -0
- simo/core/base_types.py +1 -0
- simo/core/controllers.py +57 -0
- simo/core/form_fields.py +93 -0
- simo/core/forms.py +15 -3
- simo/core/gateways.py +1 -1
- simo/core/managers.py +14 -1
- simo/core/migrations/0037_auto_20240606_1057.py +33 -0
- simo/core/migrations/__pycache__/0037_auto_20240606_1057.cpython-38.pyc +0 -0
- simo/core/models.py +28 -9
- simo/core/permissions.py +6 -3
- simo/core/serializers.py +77 -5
- simo/core/signal_receivers.py +25 -0
- simo/core/static/admin/css/simo.css +14 -0
- simo/core/templates/admin/controller_widgets/button.html +8 -0
- simo/core/templates/admin/core/component_change_form.html +97 -0
- simo/core/templates/admin/formset_widget.html +88 -118
- simo/core/templates/admin/formset_widget_old.html +122 -0
- simo/core/templates/admin/wizard/wizard_add.html +16 -9
- simo/core/utils/__pycache__/admin.cpython-38.pyc +0 -0
- simo/core/utils/__pycache__/cache.cpython-38.pyc +0 -0
- simo/core/utils/__pycache__/formsets.cpython-38.pyc +0 -0
- simo/core/utils/admin.py +11 -0
- simo/core/utils/cache.py +15 -0
- simo/core/utils/formsets.py +11 -18
- simo/fleet/__pycache__/auto_urls.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/controllers.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/forms.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/gateways.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/models.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/socket_consumers.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/utils.cpython-38.pyc +0 -0
- simo/fleet/__pycache__/views.cpython-38.pyc +0 -0
- simo/fleet/auto_urls.py +7 -1
- simo/fleet/controllers.py +193 -30
- simo/fleet/forms.py +223 -87
- simo/fleet/gateways.py +53 -2
- simo/fleet/migrations/0036_auto_20240605_0702.py +68 -0
- simo/fleet/migrations/__pycache__/0036_auto_20240605_0702.cpython-38.pyc +0 -0
- simo/fleet/models.py +35 -6
- simo/fleet/socket_consumers.py +1 -1
- simo/fleet/templates/fleet/controllers_info/button.md +16 -0
- simo/fleet/utils.py +31 -1
- simo/fleet/views.py +45 -0
- simo/generic/__pycache__/controllers.cpython-38.pyc +0 -0
- simo/generic/__pycache__/forms.cpython-38.pyc +0 -0
- simo/generic/__pycache__/gateways.cpython-38.pyc +0 -0
- simo/generic/controllers.py +59 -14
- simo/generic/forms.py +4 -3
- simo/generic/gateways.py +2 -0
- simo/generic/templates/admin/controller_widgets/blinds.html +2 -1
- simo/generic/templates/generic/controllers_info/dummy.md +3 -0
- simo/generic/templates/generic/controllers_info/stateselect.md +2 -0
- simo/settings.py +20 -4
- simo/users/__init__.py +1 -0
- simo/users/__pycache__/__init__.cpython-38.pyc +0 -0
- simo/users/__pycache__/admin.cpython-38.pyc +0 -0
- simo/users/__pycache__/apps.cpython-38.pyc +0 -0
- simo/users/__pycache__/models.cpython-38.pyc +0 -0
- simo/users/apps.py +9 -0
- simo/users/migrations/__pycache__/0029_alter_instanceuser_options_instanceuser_order.cpython-38.pyc +0 -0
- simo/users/migrations/__pycache__/0030_alter_instanceuser_options_remove_instanceuser_order.cpython-38.pyc +0 -0
- simo/users/models.py +16 -3
- {simo-2.0.41.dist-info → simo-2.1.0.dist-info}/METADATA +5 -3
- {simo-2.0.41.dist-info → simo-2.1.0.dist-info}/RECORD +93 -74
- simo/wsgi.py +0 -7
- {simo-2.0.41.dist-info → simo-2.1.0.dist-info}/LICENSE.md +0 -0
- {simo-2.0.41.dist-info → simo-2.1.0.dist-info}/WHEEL +0 -0
- {simo-2.0.41.dist-info → simo-2.1.0.dist-info}/top_level.txt +0 -0
|
@@ -1,122 +1,92 @@
|
|
|
1
1
|
{% load i18n admin_urls static admin_modify %}
|
|
2
|
-
<
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
2
|
+
<div class="js-inline-admin-formset inline-group" id="{{ formset.prefix }}-group"
|
|
3
|
+
data-inline-type="tabular"
|
|
4
|
+
data-inline-formset="{{ inline_formset_data }}"
|
|
5
|
+
style="width: 100%">
|
|
6
|
+
<div class="tabular inline-related {% if forloop.last %}last-related{% endif %}">
|
|
7
|
+
{{ formset.management_form }}
|
|
8
|
+
<fieldset class="module sortable">
|
|
9
|
+
{{ formset.non_form_errors }}
|
|
10
|
+
<table>
|
|
11
|
+
<thead><tr>
|
|
12
|
+
<th class="original"></th>
|
|
13
|
+
{% for field in empty_form %}
|
|
14
|
+
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
15
|
+
<th class="column-{{ field.name }}{% if field.required %} required{% endif %}{% if field.widget.is_hidden %} hidden{% endif %}">
|
|
16
|
+
{{ field.label|capfirst }}
|
|
17
|
+
{% if field.help_text %}
|
|
18
|
+
<img src="{% static "admin/img/icon-unknown.svg" %}" class="help help-tooltip" width="10" height="10"
|
|
19
|
+
alt="({{ field.help_text|striptags }})" title="{{ field.help_text|striptags }}">
|
|
20
|
+
{% endif %}
|
|
21
|
+
</th>
|
|
22
|
+
{% endif %}
|
|
23
|
+
{% endfor %}
|
|
24
|
+
{% if formset.can_delete %}<th>{% translate "Delete?" %}</th>{% endif %}
|
|
25
|
+
</tr></thead>
|
|
26
|
+
|
|
27
|
+
<tbody>
|
|
28
|
+
{% for form in formset %}
|
|
29
|
+
{% if form.non_field_errors %}
|
|
30
|
+
<tr class="row-form-errors"><td colspan="{{ inline_admin_form|cell_count }}">{{ form.non_field_errors }}</td></tr>
|
|
31
|
+
{% endif %}
|
|
32
|
+
<tr class="form-row has_original" id="{{ formset.prefix }}-{{ forloop.counter0 }}">
|
|
33
|
+
|
|
34
|
+
<td class="original">
|
|
35
|
+
<div style="display:none">
|
|
36
|
+
{% for field in form %}
|
|
37
|
+
{% if field.is_hidden %} {{ field }} {% endif %}
|
|
38
|
+
{% endfor %}
|
|
39
|
+
</div>
|
|
40
|
+
<p>
|
|
41
|
+
<span class="sort"><i class="move-begin" role="button" {% translate "Move to first position" as move_begin %}aria-label="{{ move_begin }}" title="{{ move_begin }}"></i><i class="move-end" role="button" {% translate "Move to last position" as move_end %}aria-label="{{ move_end }}" title="{{ move_end }}"></i></span>
|
|
42
|
+
</p>
|
|
43
|
+
</td>
|
|
44
|
+
|
|
45
|
+
{% for field in form %}
|
|
46
|
+
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
47
|
+
<td{% if field.name %} class="field-{{ field.name }}"{% endif %}>
|
|
48
|
+
{{ field }}
|
|
49
|
+
{{ field.errors.as_ul }}
|
|
50
|
+
</td>
|
|
51
|
+
{% endif %}
|
|
52
|
+
{% endfor %}
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
{% if formset.can_delete %}
|
|
56
|
+
<td class="delete">{% if total_org_forms >= forloop.counter0 %}{{ form.DELETE }}{% endif %}</td>
|
|
57
|
+
{% endif %}
|
|
58
|
+
</tr>
|
|
59
|
+
{% endfor %}
|
|
60
|
+
|
|
61
|
+
<tr class="form-row has_original empty-form" id="{{ formset.prefix }}-empty">
|
|
37
62
|
|
|
38
|
-
|
|
39
|
-
<div
|
|
40
|
-
|
|
41
|
-
{
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
{% for field in form %}
|
|
67
|
-
{% if field.is_hidden %} {{ field }} {% endif %}
|
|
68
|
-
{% endfor %}
|
|
69
|
-
</td>
|
|
70
|
-
|
|
71
|
-
{% for field in form %}
|
|
72
|
-
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
73
|
-
<td{% if field.name %} class="field-{{ field.name }}"{% endif %}>
|
|
74
|
-
{{ field }}
|
|
75
|
-
{{ field.errors.as_ul }}
|
|
76
|
-
</td>
|
|
77
|
-
{% endif %}
|
|
78
|
-
{% endfor %}
|
|
79
|
-
|
|
80
|
-
{% if formset.can_delete %}
|
|
81
|
-
<td class="delete">{% if total_org_forms >= forloop.counter0 %}{{ form.DELETE }}{% endif %}</td>
|
|
82
|
-
{% endif %}
|
|
83
|
-
</tr>
|
|
84
|
-
|
|
85
|
-
{% endfor %}
|
|
86
|
-
|
|
87
|
-
<tr class="form-row empty-form" id="{{ formset.prefix }}-empty">
|
|
88
|
-
<td class="drag"> </td>
|
|
89
|
-
<td class="original hidden">
|
|
90
|
-
{% for field in empty_form %}
|
|
91
|
-
{% if field.is_hidden %} {{ field }} {% endif %}
|
|
92
|
-
{% endfor %}
|
|
93
|
-
</td>
|
|
94
|
-
|
|
95
|
-
{% for field in empty_form %}
|
|
96
|
-
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
97
|
-
<td{% if field.name %} class="field-{{ field.name }}"{% endif %}>
|
|
98
|
-
{{ field }}
|
|
99
|
-
{{ field.errors.as_ul }}
|
|
100
|
-
</td>
|
|
101
|
-
{% endif %}
|
|
102
|
-
{% endfor %}
|
|
103
|
-
|
|
104
|
-
{% if formset.can_delete %}
|
|
105
|
-
<td class="delete"></td>
|
|
106
|
-
{% endif %}
|
|
107
|
-
</tr>
|
|
108
|
-
|
|
109
|
-
</tbody>
|
|
110
|
-
</table>
|
|
111
|
-
</fieldset>
|
|
63
|
+
<td class="original">
|
|
64
|
+
<div style="display:none">
|
|
65
|
+
{% for field in empty_form %}
|
|
66
|
+
{% if field.is_hidden %} {{ field }} {% endif %}
|
|
67
|
+
{% endfor %}
|
|
68
|
+
</div>
|
|
69
|
+
<p>
|
|
70
|
+
<span class="sort"><i class="move-begin" role="button" {% translate "Move to first position" as move_begin %}aria-label="{{ move_begin }}" title="{{ move_begin }}"></i><i class="move-end" role="button" {% translate "Move to last position" as move_end %}aria-label="{{ move_end }}" title="{{ move_end }}"></i></span>
|
|
71
|
+
</p>
|
|
72
|
+
</td>
|
|
73
|
+
|
|
74
|
+
{% for field in empty_form %}
|
|
75
|
+
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
76
|
+
<td{% if field.name %} class="field-{{ field.name }}"{% endif %}>
|
|
77
|
+
{{ field }}
|
|
78
|
+
{{ field.errors.as_ul }}
|
|
79
|
+
</td>
|
|
80
|
+
{% endif %}
|
|
81
|
+
{% endfor %}
|
|
82
|
+
|
|
83
|
+
{% if formset.can_delete %}
|
|
84
|
+
<td class="delete"></td>
|
|
85
|
+
{% endif %}
|
|
86
|
+
</tr>
|
|
87
|
+
|
|
88
|
+
</tbody>
|
|
89
|
+
</table>
|
|
90
|
+
</fieldset>
|
|
112
91
|
</div>
|
|
113
92
|
</div>
|
|
114
|
-
|
|
115
|
-
<script type="application/json" class="inline-tabular-config">
|
|
116
|
-
{
|
|
117
|
-
"prefix": "{{ formset.prefix|escapejs }}",
|
|
118
|
-
"addText": "{% filter escapejs %}Add another{% endfilter %}",
|
|
119
|
-
"deleteText": "{% filter escapejs %}{% trans 'Remove' %}{% endfilter %}"
|
|
120
|
-
}
|
|
121
|
-
</script>
|
|
122
|
-
<div class="default_order_field" default_order_field="ORDER" default_order_direction=""></div>
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
{% load i18n admin_urls static admin_modify %}
|
|
2
|
+
<style>
|
|
3
|
+
.formset-table th, .formset-table th .label{
|
|
4
|
+
font-weight: normal;
|
|
5
|
+
color: var(--body-quiet-color);
|
|
6
|
+
}
|
|
7
|
+
.formset-table .label.required{
|
|
8
|
+
font-weight: bold;
|
|
9
|
+
}
|
|
10
|
+
form .aligned .formset-table ul{
|
|
11
|
+
margin-left:0;
|
|
12
|
+
}
|
|
13
|
+
.errors .formset-table input, .errors .formset-table select,
|
|
14
|
+
.errors .formset-table textarea{
|
|
15
|
+
border: 1px solid var(--border-color);
|
|
16
|
+
}
|
|
17
|
+
.errors .formset-table .select2-selection{
|
|
18
|
+
border-color: #aaa;
|
|
19
|
+
}
|
|
20
|
+
.formset-table td.errors input, .formset-table td.errors select,
|
|
21
|
+
.formset-table td.errors textarea{
|
|
22
|
+
border: 1px solid var(--error-fg);
|
|
23
|
+
}
|
|
24
|
+
.formset-table td.errors .select2-selection{
|
|
25
|
+
border-color: var(--error-fg);
|
|
26
|
+
}
|
|
27
|
+
.formset-table td.drag {
|
|
28
|
+
cursor: pointer;
|
|
29
|
+
background-image: url(/static/adminsortable2/icons/drag.png);
|
|
30
|
+
background-repeat: repeat;
|
|
31
|
+
width: 20px;
|
|
32
|
+
}
|
|
33
|
+
.formset-table .inline-deletelink{
|
|
34
|
+
float: left
|
|
35
|
+
}
|
|
36
|
+
</style>
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
<div class="inline-group sortable" id="{{ formset.prefix }}-group">
|
|
40
|
+
<div class="tabular inline-related">
|
|
41
|
+
{{ formset.management_form }}
|
|
42
|
+
<fieldset class="module">
|
|
43
|
+
{{ formset.non_form_errors }}
|
|
44
|
+
<table class="formset-table">
|
|
45
|
+
<thead><tr>
|
|
46
|
+
<th>{% trans "Sort" %}</th>
|
|
47
|
+
{% for field in empty_form %}
|
|
48
|
+
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
49
|
+
<th{% if field.required %} class="required"{% endif %}>{{ field.label|capfirst }}
|
|
50
|
+
{% if field.help_text %} <img src="{% static "admin/img/icon-unknown.svg" %}" class="help help-tooltip" width="10" height="10" alt="({{ field.help_text|striptags }})" title="{{ field.help_text|striptags }}" />{% endif %}
|
|
51
|
+
</th>
|
|
52
|
+
{% endif %}
|
|
53
|
+
{% endfor %}
|
|
54
|
+
{% if formset.can_delete %}<th>{% trans "Delete?" %}</th>{% endif %}
|
|
55
|
+
</tr></thead>
|
|
56
|
+
|
|
57
|
+
<tbody>
|
|
58
|
+
{% for form in formset %}
|
|
59
|
+
{% if form.non_field_errors %}
|
|
60
|
+
<tr><td colspan="{{ total_org_forms }}">{{ form.non_field_errors }}</td></tr>
|
|
61
|
+
{% endif %}
|
|
62
|
+
|
|
63
|
+
<tr class="form-row has_original" id="{{ formset.prefix }}-{{ forloop.counter0 }}">
|
|
64
|
+
<td class="drag"> </td>
|
|
65
|
+
<td class="original hidden">
|
|
66
|
+
{% for field in form %}
|
|
67
|
+
{% if field.is_hidden %} {{ field }} {% endif %}
|
|
68
|
+
{% endfor %}
|
|
69
|
+
</td>
|
|
70
|
+
|
|
71
|
+
{% for field in form %}
|
|
72
|
+
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
73
|
+
<td{% if field.name %} class="field-{{ field.name }}"{% endif %}>
|
|
74
|
+
{{ field }}
|
|
75
|
+
{{ field.errors.as_ul }}
|
|
76
|
+
</td>
|
|
77
|
+
{% endif %}
|
|
78
|
+
{% endfor %}
|
|
79
|
+
|
|
80
|
+
{% if formset.can_delete %}
|
|
81
|
+
<td class="delete">{% if total_org_forms >= forloop.counter0 %}{{ form.DELETE }}{% endif %}</td>
|
|
82
|
+
{% endif %}
|
|
83
|
+
</tr>
|
|
84
|
+
|
|
85
|
+
{% endfor %}
|
|
86
|
+
|
|
87
|
+
<tr class="form-row empty-form" id="{{ formset.prefix }}-empty">
|
|
88
|
+
<td class="drag"> </td>
|
|
89
|
+
<td class="original hidden">
|
|
90
|
+
{% for field in empty_form %}
|
|
91
|
+
{% if field.is_hidden %} {{ field }} {% endif %}
|
|
92
|
+
{% endfor %}
|
|
93
|
+
</td>
|
|
94
|
+
|
|
95
|
+
{% for field in empty_form %}
|
|
96
|
+
{% if not field.is_hidden and not field.name == 'DELETE' %}
|
|
97
|
+
<td{% if field.name %} class="field-{{ field.name }}"{% endif %}>
|
|
98
|
+
{{ field }}
|
|
99
|
+
{{ field.errors.as_ul }}
|
|
100
|
+
</td>
|
|
101
|
+
{% endif %}
|
|
102
|
+
{% endfor %}
|
|
103
|
+
|
|
104
|
+
{% if formset.can_delete %}
|
|
105
|
+
<td class="delete"></td>
|
|
106
|
+
{% endif %}
|
|
107
|
+
</tr>
|
|
108
|
+
|
|
109
|
+
</tbody>
|
|
110
|
+
</table>
|
|
111
|
+
</fieldset>
|
|
112
|
+
</div>
|
|
113
|
+
</div>
|
|
114
|
+
|
|
115
|
+
<script type="application/json" class="inline-tabular-config">
|
|
116
|
+
{
|
|
117
|
+
"prefix": "{{ formset.prefix|escapejs }}",
|
|
118
|
+
"addText": "{% filter escapejs %}Add another{% endfilter %}",
|
|
119
|
+
"deleteText": "{% filter escapejs %}{% trans 'Remove' %}{% endfilter %}"
|
|
120
|
+
}
|
|
121
|
+
</script>
|
|
122
|
+
<div class="default_order_field" default_order_field="ORDER" default_order_direction=""></div>
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{% extends "admin/base_site.html" %}
|
|
2
|
-
{% load i18n admin_urls static admin_modify %}
|
|
2
|
+
{% load i18n admin_urls static admin_modify markdownify %}
|
|
3
3
|
|
|
4
4
|
{% block extrahead %}{{ block.super }}
|
|
5
5
|
<script type="text/javascript" src="{% url 'admin:jsi18n' %}"></script>
|
|
@@ -49,18 +49,25 @@
|
|
|
49
49
|
<h3 style="margin-bottom: 20px; text-align: center">Step {{ current_step }} of {{ total_steps }}</h3>
|
|
50
50
|
|
|
51
51
|
<fieldset class="module aligned">
|
|
52
|
-
{% if selected_gateway %}
|
|
53
|
-
<div class="form-row
|
|
54
|
-
|
|
55
|
-
|
|
52
|
+
{% if selected_gateway or selected_type %}
|
|
53
|
+
<div class="form-row">
|
|
54
|
+
{% if selected_gateway %}
|
|
55
|
+
Gateway: <strong>{{ selected_gateway }}</strong>
|
|
56
|
+
{% endif %}
|
|
57
|
+
{% if selected_type %}
|
|
58
|
+
| Base type: <strong>{{ selected_type }}</strong>
|
|
59
|
+
{% endif %}
|
|
56
60
|
</div>
|
|
57
61
|
{% endif %}
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
<div class="
|
|
62
|
+
|
|
63
|
+
{% if info %}
|
|
64
|
+
<div class="form-row">
|
|
65
|
+
<div class="markdownified-info">
|
|
66
|
+
{{ info|markdownify }}
|
|
67
|
+
</div>
|
|
62
68
|
</div>
|
|
63
69
|
{% endif %}
|
|
70
|
+
|
|
64
71
|
{% if error %}
|
|
65
72
|
<ul class="messagelist">
|
|
66
73
|
<li class="error">{{ error }}</li>
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
simo/core/utils/admin.py
CHANGED
|
@@ -1,6 +1,11 @@
|
|
|
1
1
|
from django import forms
|
|
2
2
|
from django.shortcuts import render, redirect
|
|
3
3
|
from django.contrib.admin.helpers import Fieldset
|
|
4
|
+
from django.db import models, router
|
|
5
|
+
from django.utils.text import capfirst
|
|
6
|
+
from django.urls import NoReverseMatch, reverse
|
|
7
|
+
from django.contrib.admin.utils import NestedObjects, quote
|
|
8
|
+
from django.utils.html import format_html
|
|
4
9
|
|
|
5
10
|
|
|
6
11
|
class AdminFormActionForm(forms.Form):
|
|
@@ -55,3 +60,9 @@ class FormAction:
|
|
|
55
60
|
'fieldset': Fieldset(form, fields=form.fields.keys())
|
|
56
61
|
}
|
|
57
62
|
return render(request, 'admin/action_intermediate_form.html', context)
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
class EasyObjectsDeleteMixin:
|
|
66
|
+
|
|
67
|
+
def get_deleted_objects(self, objs, request):
|
|
68
|
+
return [], [], [], []
|
simo/core/utils/cache.py
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
from django.conf import settings
|
|
2
|
+
from django.core.cache import caches
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
def get_cached_data(
|
|
6
|
+
key, rebuild_function, cache_time=None, cache_name='default', rebuild=False
|
|
7
|
+
):
|
|
8
|
+
data = caches[cache_name].get(key, 'NONE!')
|
|
9
|
+
if data == 'NONE!' or rebuild:
|
|
10
|
+
print(f"{cache_name} cache rebuild: {rebuild_function.__name__}()")
|
|
11
|
+
data = rebuild_function()
|
|
12
|
+
if not cache_time:
|
|
13
|
+
cache_time = settings.CACHES[cache_name]['TIMEOUT']
|
|
14
|
+
caches[cache_name].set(key, data, cache_time)
|
|
15
|
+
return data
|
simo/core/utils/formsets.py
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import json
|
|
1
2
|
from django import forms
|
|
2
3
|
from django.db import models
|
|
3
4
|
from django.template.loader import render_to_string
|
|
@@ -26,21 +27,12 @@ class FormsetWidget(forms.Widget):
|
|
|
26
27
|
use_cached = False
|
|
27
28
|
|
|
28
29
|
class Media:
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
# 'all': ['adminsortable2/css/sortable.css']
|
|
33
|
-
# }
|
|
30
|
+
css = {
|
|
31
|
+
'all': ['adminsortable2/css/sortable.css']
|
|
32
|
+
}
|
|
34
33
|
js = (
|
|
35
34
|
'admin/js/inlines.js',
|
|
36
|
-
|
|
37
|
-
# 'adminsortable2/js/libs/jquery.ui.core-1.11.4.js',
|
|
38
|
-
# 'adminsortable2/js/libs/jquery.ui.widget-1.11.4.js',
|
|
39
|
-
# 'adminsortable2/js/libs/jquery.ui.mouse-1.11.4.js',
|
|
40
|
-
# 'adminsortable2/js/libs/jquery.ui.touch-punch-0.2.3.js',
|
|
41
|
-
# 'adminsortable2/js/libs/jquery.ui.sortable-1.11.4.js',
|
|
42
|
-
# 'adminsortable2/js/inline-tabular.js',
|
|
43
|
-
# 'adminsortable2/js/inline-sortable.js',
|
|
35
|
+
'adminsortable2/js/adminsortable2.js',
|
|
44
36
|
)
|
|
45
37
|
|
|
46
38
|
def render(self, name, value, attrs=None, renderer=None):
|
|
@@ -80,14 +72,15 @@ class FormsetWidget(forms.Widget):
|
|
|
80
72
|
attrs = {'id': 'id_%s-__prefix__-%s' % (prefix, name)}
|
|
81
73
|
if name == "ORDER":
|
|
82
74
|
field.initial = 9999
|
|
83
|
-
field.widget = forms.HiddenInput()
|
|
75
|
+
field.widget = forms.HiddenInput(attrs={"class": '_reorder_'})
|
|
84
76
|
set_field_html_name_and_id(
|
|
85
77
|
field, '%s-__prefix__-%s' % (prefix, name), attrs
|
|
86
78
|
)
|
|
87
79
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
80
|
+
for form in self.formset:
|
|
81
|
+
form.fields['ORDER'].widget = forms.HiddenInput(
|
|
82
|
+
attrs={"class": '_reorder_'}
|
|
83
|
+
)
|
|
91
84
|
|
|
92
85
|
cell_count = len(list(self.formset.form.declared_fields.keys())) + 1
|
|
93
86
|
if self.formset.can_order:
|
|
@@ -99,7 +92,7 @@ class FormsetWidget(forms.Widget):
|
|
|
99
92
|
render_to_string(
|
|
100
93
|
'admin/formset_widget.html', {
|
|
101
94
|
'formset': self.formset,
|
|
102
|
-
'inline_formset_data':
|
|
95
|
+
'inline_formset_data': json.dumps(inline_formset_data),
|
|
103
96
|
'cell_count': cell_count,
|
|
104
97
|
'empty_form': empty_form,
|
|
105
98
|
'total_org_forms': total_org_forms
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
simo/fleet/auto_urls.py
CHANGED
|
@@ -2,7 +2,8 @@ from django.urls import path, re_path
|
|
|
2
2
|
from .views import (
|
|
3
3
|
colonels_ping,
|
|
4
4
|
PinsSelectAutocomplete,
|
|
5
|
-
InterfaceSelectAutocomplete
|
|
5
|
+
InterfaceSelectAutocomplete,
|
|
6
|
+
ControlInputSelectAutocomplete
|
|
6
7
|
)
|
|
7
8
|
|
|
8
9
|
urlpatterns = [
|
|
@@ -17,5 +18,10 @@ urlpatterns = [
|
|
|
17
18
|
'autocomplete-colonel-interfaces',
|
|
18
19
|
InterfaceSelectAutocomplete.as_view(),
|
|
19
20
|
name='autocomplete-interfaces'
|
|
21
|
+
),
|
|
22
|
+
path(
|
|
23
|
+
'autocomplete-control-input',
|
|
24
|
+
ControlInputSelectAutocomplete.as_view(),
|
|
25
|
+
name='autocomplete-control_inputs'
|
|
20
26
|
)
|
|
21
27
|
]
|