barebone app with django and react, sse, jwt token, comport reader, test comport writer, requires com0com, users with groups, sample table vehicles, tokens for access and refresh
This commit is contained in:
@@ -0,0 +1,3 @@
|
||||
from django.contrib import admin
|
||||
|
||||
# Register your models here.
|
||||
@@ -0,0 +1,6 @@
|
||||
from django.apps import AppConfig
|
||||
|
||||
|
||||
class VehiclesConfig(AppConfig):
|
||||
default_auto_field = "django.db.models.BigAutoField"
|
||||
name = "vehicles"
|
||||
@@ -0,0 +1,52 @@
|
||||
# Generated by Django 4.2.8 on 2026-01-13 16:51
|
||||
|
||||
from django.db import migrations, models
|
||||
import django.db.models.deletion
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
initial = True
|
||||
|
||||
dependencies = []
|
||||
|
||||
operations = [
|
||||
migrations.CreateModel(
|
||||
name="Vehicle",
|
||||
fields=[
|
||||
(
|
||||
"id",
|
||||
models.BigAutoField(
|
||||
auto_created=True,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
verbose_name="ID",
|
||||
),
|
||||
),
|
||||
("vehicle_number", models.CharField(max_length=15, unique=True)),
|
||||
],
|
||||
),
|
||||
migrations.CreateModel(
|
||||
name="VehicleExtra",
|
||||
fields=[
|
||||
(
|
||||
"id",
|
||||
models.BigAutoField(
|
||||
auto_created=True,
|
||||
primary_key=True,
|
||||
serialize=False,
|
||||
verbose_name="ID",
|
||||
),
|
||||
),
|
||||
("data", models.JSONField(default=dict)),
|
||||
(
|
||||
"vehicle",
|
||||
models.OneToOneField(
|
||||
on_delete=django.db.models.deletion.CASCADE,
|
||||
related_name="extra",
|
||||
to="vehicles.vehicle",
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
]
|
||||
@@ -0,0 +1,14 @@
|
||||
from django.db import models
|
||||
|
||||
# Create your models here.
|
||||
class Vehicle(models.Model):
|
||||
vehicle_number = models.CharField(max_length=15, unique=True)
|
||||
|
||||
def __str__(self):
|
||||
return f"{self.vehicle_number}"
|
||||
|
||||
class VehicleExtra(models.Model):
|
||||
vehicle = models.OneToOneField(
|
||||
Vehicle, on_delete=models.CASCADE, related_name="extra"
|
||||
)
|
||||
data = models.JSONField(default=dict)
|
||||
@@ -0,0 +1,7 @@
|
||||
from rest_framework import serializers
|
||||
from .models import Vehicle
|
||||
|
||||
class VehicleSerializer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = Vehicle
|
||||
fields = ['id', 'vehicle_number']
|
||||
@@ -0,0 +1,3 @@
|
||||
from django.test import TestCase
|
||||
|
||||
# Create your tests here.
|
||||
@@ -0,0 +1,10 @@
|
||||
from django.urls import path
|
||||
from vehicles.views import vehiclesView, VehicleListCreateAPIView, VehicleRetrieveUpdateDestroyAPIView, get_vehicles
|
||||
|
||||
urlpatterns = [
|
||||
path("", vehiclesView.as_view(), name='list_vehicles'),
|
||||
# API endpoints
|
||||
path("api/", VehicleListCreateAPIView.as_view(), name='vehicles-list-create'),
|
||||
path("api/<int:pk>/", VehicleRetrieveUpdateDestroyAPIView.as_view(), name='vehicles-detail'),
|
||||
path("api/list/", get_vehicles, name='get-vehicles'),
|
||||
]
|
||||
@@ -0,0 +1,70 @@
|
||||
from django.shortcuts import render
|
||||
|
||||
from django.shortcuts import render
|
||||
from django.views.generic.list import ListView
|
||||
from rest_framework import generics, status
|
||||
from rest_framework.decorators import api_view, permission_classes
|
||||
from rest_framework.permissions import IsAuthenticated
|
||||
from rest_framework.response import Response
|
||||
|
||||
from .models import Vehicle
|
||||
from .serializers import VehicleSerializer
|
||||
from scalesapp.sse import broadcast_update
|
||||
|
||||
# Create your views here.
|
||||
class CountriesView(ListView):
|
||||
pass
|
||||
|
||||
# API Views
|
||||
class VehicleListCreateAPIView(generics.ListCreateAPIView):
|
||||
queryset =Vehicle.objects.all()
|
||||
serializer_class = VehicleSerializer
|
||||
permission_classes = [IsAuthenticated]
|
||||
|
||||
def create(self, request, *args, **kwargs):
|
||||
"""Override create to broadcast SSE message"""
|
||||
serializer = self.get_serializer(data=request.data)
|
||||
serializer.is_valid(raise_exception=True)
|
||||
self.perform_create(serializer)
|
||||
|
||||
# Broadcast SSE update
|
||||
broadcast_update('vehicle', 'created', serializer.data)
|
||||
|
||||
return Response(serializer.data, status=status.HTTP_201_CREATED)
|
||||
|
||||
class VehicleRetrieveUpdateDestroyAPIView(generics.RetrieveUpdateDestroyAPIView):
|
||||
queryset = Vehicle.objects.all()
|
||||
serializer_class = VehicleSerializer
|
||||
permission_classes = [IsAuthenticated]
|
||||
|
||||
def update(self, request, *args, **kwargs):
|
||||
"""Override update to broadcast SSE message"""
|
||||
partial = kwargs.pop('partial', False)
|
||||
instance = self.get_object()
|
||||
serializer = self.get_serializer(instance, data=request.data, partial=partial)
|
||||
serializer.is_valid(raise_exception=True)
|
||||
self.perform_update(serializer)
|
||||
|
||||
# Broadcast SSE update
|
||||
broadcast_update('vehicle', 'updated', serializer.data)
|
||||
|
||||
return Response(serializer.data)
|
||||
|
||||
def destroy(self, request, *args, **kwargs):
|
||||
"""Override destroy to broadcast SSE message"""
|
||||
instance = self.get_object()
|
||||
country_data = CountrySerializer(instance).data
|
||||
self.perform_destroy(instance)
|
||||
|
||||
# Broadcast SSE update
|
||||
broadcast_update('vehicle', 'deleted', country_data)
|
||||
|
||||
return Response(status=status.HTTP_204_NO_CONTENT)
|
||||
|
||||
@api_view(['GET'])
|
||||
@permission_classes([IsAuthenticated])
|
||||
def get_vehicles(request):
|
||||
"""API endpoint for getting countries list"""
|
||||
vehicles = Vehicle.objects.all().order_by('id')
|
||||
serializer = VehicleSerializer(vehicles, many=True)
|
||||
return Response(serializer.data)
|
||||
Reference in New Issue
Block a user