firmware and firmware build details
This commit is contained in:
parent
c872b97fa3
commit
386bd3c888
7 changed files with 284 additions and 11 deletions
|
@ -0,0 +1,78 @@
|
|||
{% extends 'control/base.html' %}
|
||||
{% load i18n mesh_node %}
|
||||
|
||||
{% block heading %}{% trans 'Mesh' %}{% endblock %}
|
||||
|
||||
{% block subcontent %}
|
||||
<h4>{% trans 'Firmware Build' %}</h4>
|
||||
|
||||
<div class="columns">
|
||||
<div>
|
||||
<p>
|
||||
<strong>Project name:</strong> {{ build.version.project_name }}<br>
|
||||
<strong>Version:</strong> {{ build.version.version }}<br>
|
||||
<strong>IDF Version:</strong> {{ build.version.idf_version }}<br>
|
||||
<strong>Uploader:</strong> {{ build.version.uploader }}<br>
|
||||
<strong>Created:</strong> {{ build.version.created }}<br>
|
||||
</p>
|
||||
<o>
|
||||
<strong>Variant:</strong> {{ build.variant }}<br>
|
||||
<strong>Chip:</strong> {{ build.get_chip_display }}<br>
|
||||
</o>
|
||||
<h4>Compatible boards:</h4>
|
||||
<ul>
|
||||
{% for board in build.boards %}
|
||||
<li>{{ board.pretty_name }}</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Installed nodes</h4>
|
||||
<table>
|
||||
<tr>
|
||||
<th>{% trans 'Node' %}</th>
|
||||
<th>{% trans 'Hardware' %}</th>
|
||||
</tr>
|
||||
{% for node in installed_nodes %}
|
||||
<tr>
|
||||
<td>
|
||||
{% mesh_node node %}
|
||||
</td>
|
||||
<td>
|
||||
{{ node.board.pretty_name }} ({{ node.chip.pretty_name }})
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</table>
|
||||
|
||||
<h4>Compatible nodes</h4>
|
||||
<table>
|
||||
<tr>
|
||||
<th>{% trans 'Node' %}</th>
|
||||
<th>{% trans 'Hardware' %}</th>
|
||||
<th>{% trans 'Current Firmware' %}</th>
|
||||
</tr>
|
||||
{% for node in compatible_nodes %}
|
||||
<tr>
|
||||
<td>
|
||||
{% mesh_node node %}
|
||||
</td>
|
||||
<td>
|
||||
{{ node.board.pretty_name }} <small>({{ node.chip.pretty_name }})</small>
|
||||
</td>
|
||||
<td>
|
||||
{% if node.firmware_desc.build %}
|
||||
<a href="{% url "control.mesh.firmwares.detail" pk=node.firmware_desc.build.version.pk %}">
|
||||
{{ node.firmware_desc.project_name }} {{ node.firmware_desc.version }}
|
||||
</a><br>
|
||||
Build <a href="{% url "control.mesh.firmwares.build.detail" pk=node.firmware_desc.build.pk %}">{{ node.firmware_desc.build.variant }}</a>
|
||||
{% else %}
|
||||
{{ node.firmware_desc.project_name }} {{ node.firmware_desc.version }}
|
||||
{% endif %}
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
{% endblock %}
|
103
src/c3nav/control/templates/control/mesh_firmware_detail.html
Normal file
103
src/c3nav/control/templates/control/mesh_firmware_detail.html
Normal file
|
@ -0,0 +1,103 @@
|
|||
{% extends 'control/base.html' %}
|
||||
{% load i18n mesh_node %}
|
||||
|
||||
{% block heading %}{% trans 'Mesh' %}{% endblock %}
|
||||
|
||||
{% block subcontent %}
|
||||
<h4>{% trans 'Firmware' %}</h4>
|
||||
|
||||
<div class="columns">
|
||||
<div>
|
||||
<p>
|
||||
<strong>Project name:</strong> {{ firmware.project_name }}<br>
|
||||
<strong>Version:</strong> {{ firmware.version }}<br>
|
||||
<strong>IDF Version:</strong> {{ firmware.idf_version }}<br>
|
||||
<strong>Uploader:</strong> {{ firmware.uploader }}<br>
|
||||
<strong>Created:</strong> {{ firmware.created }}<br>
|
||||
</p>
|
||||
|
||||
<h4>Builds</h4>
|
||||
<table>
|
||||
<tr>
|
||||
<th>{% trans 'Build' %}</th>
|
||||
<th>{% trans 'Chip' %}</th>
|
||||
<th>{% trans 'Boards' %}</th>
|
||||
</tr>
|
||||
{% for build in builds %}
|
||||
<tr>
|
||||
<td>
|
||||
<a href="{% url "control.mesh.firmwares.build.detail" pk=build.pk %}">
|
||||
{{ build.variant }}
|
||||
</a>
|
||||
</td>
|
||||
<td>{{ build.get_chip_display }}</td>
|
||||
<td>
|
||||
{% for board in build.boards %}
|
||||
{{ board.pretty_name }}<br>
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Installed nodes</h4>
|
||||
<table>
|
||||
<tr>
|
||||
<th>{% trans 'Node' %}</th>
|
||||
<th>{% trans 'Hardware' %}</th>
|
||||
<th>{% trans 'Build' %}</th>
|
||||
</tr>
|
||||
{% for node in installed_nodes %}
|
||||
<tr>
|
||||
<td>
|
||||
{% mesh_node node %}
|
||||
</td>
|
||||
<td>
|
||||
{{ node.board.pretty_name }} ({{ node.chip.pretty_name }})
|
||||
</td>
|
||||
<td>
|
||||
{{ node.firmware_desc.build.variant }}
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</table>
|
||||
|
||||
<h4>Compatible nodes</h4>
|
||||
<table>
|
||||
<tr>
|
||||
<th>{% trans 'Node' %}</th>
|
||||
<th>{% trans 'Hardware' %}</th>
|
||||
<th>{% trans 'Current Firmware' %}</th>
|
||||
<th>{% trans 'Compatible Builds' %}</th>
|
||||
</tr>
|
||||
{% for node in compatible_nodes %}
|
||||
<tr>
|
||||
<td>
|
||||
{% mesh_node node %}
|
||||
</td>
|
||||
<td>
|
||||
{{ node.board.pretty_name }} <small>({{ node.chip.pretty_name }})</small>
|
||||
</td>
|
||||
<td>
|
||||
{% if node.firmware_desc.build %}
|
||||
<a href="{% url "control.mesh.firmwares.detail" pk=node.firmware_desc.build.version.pk %}">
|
||||
{{ node.firmware_desc.project_name }} {{ node.firmware_desc.version }}
|
||||
</a><br>
|
||||
Build <a href="{% url "control.mesh.firmwares.build.detail" pk=node.firmware_desc.build.pk %}">{{ node.firmware_desc.build.variant }}</a>
|
||||
{% else %}
|
||||
{{ node.firmware_desc.project_name }} {{ node.firmware_desc.version }}
|
||||
{% endif %}
|
||||
</td>
|
||||
<td>
|
||||
{% for build in node.compatible_builds %}
|
||||
{{ build.variant }}<br>
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
{% endblock %}
|
|
@ -1,7 +1,7 @@
|
|||
{% extends 'control/base.html' %}
|
||||
{% load i18n %}
|
||||
|
||||
{% block heading %}{% trans 'Mesh Firmwares' %}{% endblock %}
|
||||
{% block heading %}{% trans 'Mesh' %}{% endblock %}
|
||||
|
||||
{% block subcontent %}
|
||||
<h4>Firmwares</h4>
|
||||
|
@ -23,11 +23,17 @@
|
|||
<tr>
|
||||
<td>{{ firmware.created }}</td>
|
||||
<td>{{ firmware.uploader }}</td>
|
||||
<td>{{ firmware.project_name }} {{ firmware.version }}</td>
|
||||
<td>
|
||||
<a href="{% url "control.mesh.firmwares.detail" pk=firmware.pk %}">
|
||||
{{ firmware.project_name }} {{ firmware.version }}
|
||||
</a>
|
||||
</td>
|
||||
<td>{{ firmware.idf_version }}</td>
|
||||
<td>
|
||||
{% for build in firmware.builds.all %}
|
||||
{{ build.variant }} ({{ build.get_chip_display }})<br>
|
||||
<a href="{% url "control.mesh.firmwares.build.detail" pk=build.pk %}">
|
||||
{{ build.variant }} ({{ build.get_chip_display }})
|
||||
</a><br>
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
{% extends 'control/base.html' %}
|
||||
{% load i18n mesh_node %}
|
||||
|
||||
{% block heading %}{% trans 'Mesh Firmwares' %}{% endblock %}
|
||||
{% block heading %}{% trans 'Mesh' %}{% endblock %}
|
||||
|
||||
{% block subcontent %}
|
||||
<h4>Current Firmwares</h4>
|
||||
|
@ -22,7 +22,7 @@
|
|||
<td>{{ firmware.created }}</td>
|
||||
<td>
|
||||
{% if firmware.build %}
|
||||
<a href="#">{{ firmware.project_name }} {{ firmware.version }}</a>
|
||||
<a href="{% url "control.mesh.firmwares.detail" pk=firmware.pk %}">{{ firmware.project_name }} {{ firmware.version }}</a>
|
||||
{% else %}
|
||||
{{ firmware.project_name }} {{ firmware.version }}<br>
|
||||
<small>{{ firmware.sha256_hash }}</small>
|
||||
|
@ -30,7 +30,9 @@
|
|||
</td>
|
||||
<td>
|
||||
{% if firmware.build %}
|
||||
<a href="#">{{ firmware.build.variant }} ({{ firmware.chip.pretty_name }})</a>
|
||||
<a href="{% url "control.mesh.firmwares.build.detail" pk=firmware.build.pk %}">
|
||||
{{ firmware.build.variant }} ({{ firmware.chip.pretty_name }})
|
||||
</a>
|
||||
{% else %}
|
||||
({{ firmware.chip.pretty_name }})
|
||||
{% endif %}
|
||||
|
|
|
@ -4,9 +4,9 @@ from c3nav.control.views.access import grant_access, grant_access_qr
|
|||
from c3nav.control.views.announcements import announcement_detail, announcement_list
|
||||
from c3nav.control.views.base import ControlPanelIndexView
|
||||
from c3nav.control.views.mapupdates import map_updates
|
||||
from c3nav.control.views.mesh import (MeshFirmwaresCurrentListView, MeshFirmwaresListView, MeshLogView,
|
||||
MeshMessageListView, MeshMessageSendingView, MeshMessageSendView,
|
||||
MeshNodeDetailView, MeshNodeEditView, MeshNodeListView)
|
||||
from c3nav.control.views.mesh import (MeshFirmwareBuildDetailView, MeshFirmwareDetailView, MeshFirmwaresCurrentListView,
|
||||
MeshFirmwaresListView, MeshLogView, MeshMessageListView, MeshMessageSendingView,
|
||||
MeshMessageSendView, MeshNodeDetailView, MeshNodeEditView, MeshNodeListView)
|
||||
from c3nav.control.views.users import UserListView, user_detail
|
||||
|
||||
urlpatterns = [
|
||||
|
@ -22,6 +22,9 @@ urlpatterns = [
|
|||
path('mesh/messages/', MeshMessageListView.as_view(), name='control.mesh.messages'),
|
||||
path('mesh/firmwares/', MeshFirmwaresListView.as_view(), name='control.mesh.firmwares'),
|
||||
path('mesh/firmwares/current/', MeshFirmwaresCurrentListView.as_view(), name='control.mesh.firmwares.current'),
|
||||
path('mesh/firmwares/<int:pk>/', MeshFirmwareDetailView.as_view(), name='control.mesh.firmwares.detail'),
|
||||
path('mesh/firmwares/builds/<int:pk>/', MeshFirmwareBuildDetailView.as_view(),
|
||||
name='control.mesh.firmwares.build.detail'),
|
||||
path('mesh/<str:pk>/', MeshNodeDetailView.as_view(), name='control.mesh.node.detail'),
|
||||
path('mesh/<str:pk>/edit/', MeshNodeEditView.as_view(), name='control.mesh.node.edit'),
|
||||
path('mesh/message/sending/<uuid:uuid>/', MeshMessageSendingView.as_view(), name='control.mesh.sending'),
|
||||
|
|
|
@ -14,7 +14,7 @@ from c3nav.control.forms import MeshMessageFilterForm
|
|||
from c3nav.control.views.base import ControlPanelMixin
|
||||
from c3nav.mesh.forms import MeshMessageForm, MeshNodeForm
|
||||
from c3nav.mesh.messages import MeshMessage, MeshMessageType
|
||||
from c3nav.mesh.models import FirmwareVersion, MeshNode, NodeMessage
|
||||
from c3nav.mesh.models import FirmwareBuild, FirmwareVersion, MeshNode, NodeMessage
|
||||
from c3nav.mesh.utils import get_node_names, group_msg_type_choices
|
||||
|
||||
|
||||
|
@ -215,3 +215,76 @@ class MeshFirmwaresCurrentListView(ControlPanelMixin, TemplateView):
|
|||
**super().get_context_data(),
|
||||
"firmwares": firmwares,
|
||||
}
|
||||
|
||||
|
||||
class MeshFirmwareDetailView(ControlPanelMixin, DetailView):
|
||||
model = FirmwareVersion
|
||||
template_name = "control/mesh_firmware_detail.html"
|
||||
context_object_name = "firmware"
|
||||
|
||||
def get_queryset(self):
|
||||
return super().get_queryset().prefetch_related('builds', 'builds__firmwarebuildboard_set')
|
||||
|
||||
def get_context_data(self, **kwargs):
|
||||
ctx = super().get_context_data()
|
||||
|
||||
nodes = list(MeshNode.objects.all().prefetch_firmwares().prefetch_last_messages(
|
||||
MeshMessageType.CONFIG_BOARD,
|
||||
))
|
||||
builds = self.get_object().builds.all()
|
||||
|
||||
build_lookups = set(build.get_firmware_description().get_lookup() for build in builds)
|
||||
|
||||
installed_nodes = []
|
||||
compatible_nodes = []
|
||||
for node in nodes:
|
||||
if node.firmware_desc.get_lookup() in build_lookups:
|
||||
installed_nodes.append(node)
|
||||
else:
|
||||
node.compatible_builds = []
|
||||
for build in builds:
|
||||
if node.board in build.boards:
|
||||
node.compatible_builds.append(build)
|
||||
if node.compatible_builds:
|
||||
compatible_nodes.append(node)
|
||||
|
||||
ctx.update({
|
||||
'builds': builds,
|
||||
'installed_nodes': installed_nodes,
|
||||
'compatible_nodes': compatible_nodes,
|
||||
})
|
||||
return ctx
|
||||
|
||||
|
||||
class MeshFirmwareBuildDetailView(ControlPanelMixin, DetailView):
|
||||
model = FirmwareBuild
|
||||
template_name = "control/mesh_firmware_build_detail.html"
|
||||
context_object_name = "build"
|
||||
|
||||
def get_queryset(self):
|
||||
return super().get_queryset().prefetch_related('firmwarebuildboard_set')
|
||||
|
||||
def get_context_data(self, **kwargs):
|
||||
ctx = super().get_context_data()
|
||||
|
||||
nodes = list(MeshNode.objects.all().prefetch_firmwares().prefetch_last_messages(
|
||||
MeshMessageType.CONFIG_BOARD,
|
||||
))
|
||||
|
||||
build_lookup = self.get_object().get_firmware_description().get_lookup()
|
||||
build_boards = self.get_object().boards
|
||||
|
||||
installed_nodes = []
|
||||
compatible_nodes = []
|
||||
for node in nodes:
|
||||
if node.firmware_desc.get_lookup() == build_lookup:
|
||||
installed_nodes.append(node)
|
||||
else:
|
||||
if node.board in build_boards:
|
||||
compatible_nodes.append(node)
|
||||
|
||||
ctx.update({
|
||||
'installed_nodes': installed_nodes,
|
||||
'compatible_nodes': compatible_nodes,
|
||||
})
|
||||
return ctx
|
||||
|
|
|
@ -192,6 +192,14 @@ class MeshNode(models.Model):
|
|||
sha256_hash=firmware_msg.app_desc.app_elf_sha256,
|
||||
)
|
||||
|
||||
@cached_property
|
||||
def chip(self) -> ChipType:
|
||||
return self.last_messages[MeshMessageType.CONFIG_HARDWARE].parsed.chip
|
||||
|
||||
@cached_property
|
||||
def board(self) -> ChipType:
|
||||
return self.last_messages[MeshMessageType.CONFIG_BOARD].parsed.board_config.board
|
||||
|
||||
|
||||
class MeshUplink(models.Model):
|
||||
"""
|
||||
|
@ -278,7 +286,7 @@ class FirmwareBuild(models.Model):
|
|||
|
||||
@property
|
||||
def boards(self):
|
||||
return [board.board for board in self.firmwarebuildboard_set.all()]
|
||||
return {BoardType[board.board] for board in self.firmwarebuildboard_set.all()}
|
||||
|
||||
def serialize(self):
|
||||
return {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue