Compare commits
3 Commits
| Author | SHA1 | Date |
|---|---|---|
|
|
b0afa5c7be | |
|
|
50aed1a48a | |
|
|
02a6904834 |
|
|
@ -40,12 +40,14 @@ INSTALLED_APPS = [
|
|||
'crispy_forms',
|
||||
'crispy_bootstrap4',
|
||||
'blog.apps.BlogConfig',
|
||||
'api.apps.APIConfig',
|
||||
'django.contrib.admin',
|
||||
'django.contrib.auth',
|
||||
'django.contrib.contenttypes',
|
||||
'django.contrib.sessions',
|
||||
'django.contrib.messages',
|
||||
'django.contrib.staticfiles',
|
||||
'rest_framework',
|
||||
]
|
||||
|
||||
MIDDLEWARE = [
|
||||
|
|
@ -112,6 +114,13 @@ AUTH_PASSWORD_VALIDATORS = [
|
|||
},
|
||||
]
|
||||
|
||||
REST_FRAMEWORK = {
|
||||
'DEFAULT_AUTHENTICATION_CLASSES': (
|
||||
'rest_framework.authentication.BasicAuthentication',
|
||||
'rest_framework.authentication.SessionAuthentication',
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
# Internationalization
|
||||
# https://docs.djangoproject.com/en/3.0/topics/i18n/
|
||||
|
|
@ -138,3 +147,8 @@ MEDIA_URL = '/media/'
|
|||
CRISPY_TEMPLATE_PACK = 'bootstrap4'
|
||||
LOGIN_REDIRECT_URL = 'News'
|
||||
LOGIN_URL = 'Login'
|
||||
|
||||
# Default primary key field type
|
||||
# https://docs.djangoproject.com/en/5.0/ref/settings/#default-auto-field
|
||||
|
||||
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
|
||||
|
|
|
|||
|
|
@ -20,6 +20,7 @@ from django.urls import path, include
|
|||
|
||||
urlpatterns = [
|
||||
path('', include('blog.urls')),
|
||||
path('api/', include('api.urls')),
|
||||
path('admin/', admin.site.urls),
|
||||
]
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,9 @@
|
|||
from django.contrib import admin
|
||||
from .models import *
|
||||
|
||||
|
||||
# Register your models here.
|
||||
admin.site.register(Province)
|
||||
admin.site.register(AssaultTroop)
|
||||
admin.site.register(Player)
|
||||
admin.site.register(Server)
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
from django.apps import AppConfig
|
||||
|
||||
|
||||
class APIConfig(AppConfig):
|
||||
name = 'api'
|
||||
|
|
@ -0,0 +1,70 @@
|
|||
from django.db import models
|
||||
from django.contrib.auth.models import User
|
||||
from django.db.models.fields import CharField, IntegerField
|
||||
|
||||
|
||||
# Create your models here.
|
||||
class Province(models.Model):
|
||||
id = models.IntegerField(primary_key = True)
|
||||
name = models.CharField(max_length = 100, blank = False)
|
||||
faction = models.IntegerField() # 0 - Neutral, 1 - Allies, 2 - Axis
|
||||
map = models.CharField(max_length=255)
|
||||
mov_speed = models.IntegerField()
|
||||
ats = models.JSONField(null=True)
|
||||
|
||||
class Meta:
|
||||
ordering = ['id']
|
||||
|
||||
def __str__(self):
|
||||
return f"{self.name} - {self.faction}"
|
||||
|
||||
|
||||
class AssaultTroop(models.Model):
|
||||
id = models.IntegerField(primary_key = True)
|
||||
name = models.CharField(max_length = 100, blank = False)
|
||||
faction = models.IntegerField() # 0 - Neutral, 1 - Allies, 2 - Axis
|
||||
type = models.IntegerField()
|
||||
province = models.IntegerField() # Province ID (-1 for not deployed)
|
||||
orders = models.JSONField(null=True)
|
||||
owner = models.ForeignKey(
|
||||
'auth.User',
|
||||
related_name='ats',
|
||||
on_delete=models.CASCADE
|
||||
)
|
||||
|
||||
class Meta:
|
||||
ordering = ['id']
|
||||
|
||||
def __str__(self):
|
||||
return f"{self.name} - {self.province},{self.faction}"
|
||||
|
||||
|
||||
|
||||
class Player(models.Model):
|
||||
id = models.IntegerField(primary_key = True)
|
||||
name = models.CharField(max_length = 50, blank = False)
|
||||
faction = models.IntegerField()
|
||||
server = CharField(max_length = 20, blank = False)
|
||||
|
||||
class Meta:
|
||||
ordering = ['id']
|
||||
|
||||
def __str__(self):
|
||||
return self.name
|
||||
|
||||
|
||||
|
||||
class Server(models.Model):
|
||||
id = IntegerField(primary_key = True)
|
||||
players = IntegerField() # total current players
|
||||
capacity = IntegerField() # max player capacity
|
||||
region = CharField(max_length = 3, blank = False) # 3 letter abb. for region
|
||||
address = CharField(max_length = 20, blank = False)
|
||||
|
||||
class Meta:
|
||||
ordering = ['id']
|
||||
|
||||
def __str__(self):
|
||||
return f"{self.address} - {self.region}"
|
||||
|
||||
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
from rest_framework import serializers
|
||||
from .models import *
|
||||
|
||||
class ProvinceSerializer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = Province
|
||||
fields = ['id', 'name', 'faction', 'map', 'mov_speed', 'ats']
|
||||
|
||||
|
||||
class AssaultTroopSerializer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = AssaultTroop
|
||||
fields = ['id', 'name', 'faction', 'type', 'province', 'deployed', 'orders', 'owner']
|
||||
|
||||
|
||||
class PlayerSerializer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = Player
|
||||
fields = ['id', 'name', 'faction', 'server']
|
||||
|
||||
|
||||
class ServerSerializer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = Server
|
||||
fields = ['id', 'players', 'capacity', 'region', 'address']
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
from django.test import TestCase
|
||||
|
||||
# Create your tests here.
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
from django.urls import path
|
||||
from .views import *
|
||||
|
||||
urlpatterns = [
|
||||
path('provinces/', ProvincesView),
|
||||
path('provinces/<int:nm>/', ProvinceView),
|
||||
path('assault_troops/', AssaultTroopsView),
|
||||
path('assault_troops/<int:nm>/', AssaultTroopView),
|
||||
path('players/', PlayersView),
|
||||
path('players/<int:nm>/', PlayerView),
|
||||
path('servers/', ServersView),
|
||||
path('servers/<int:nm>/', ServerView),
|
||||
]
|
||||
|
|
@ -0,0 +1,180 @@
|
|||
from django.shortcuts import render, HttpResponseRedirect, Http404
|
||||
from rest_framework.parsers import JSONParser
|
||||
from django.http import HttpResponse, JsonResponse
|
||||
from django.views.decorators.csrf import csrf_exempt
|
||||
from .models import *
|
||||
from .serializers import *
|
||||
|
||||
# Create your views here.
|
||||
@csrf_exempt
|
||||
def ProvincesView(request):
|
||||
|
||||
if request.method == 'GET':
|
||||
items = Province.objects.all()
|
||||
serializer = ProvinceSerializer(items, many = True)
|
||||
return JsonResponse(serializer.data, safe = False)
|
||||
|
||||
elif request.method == 'POST':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = ProvinceSerializer(data = data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data,status = 201)
|
||||
return JsonResponse(serializer.errors,status = 400)
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def AssaultTroopsView(request):
|
||||
|
||||
if request.method == 'GET':
|
||||
items = AssaultTroop.objects.all()
|
||||
serializer = AssaultTroopSerializer(items, many = True)
|
||||
return JsonResponse(serializer.data, safe = False)
|
||||
|
||||
elif request.method == 'POST':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = AssaultTroopSerializer(data = data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data,status = 201)
|
||||
return JsonResponse(serializer.errors,status = 400)
|
||||
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def ProvinceView(request, nm):
|
||||
try:
|
||||
item = Province.objects.get(id = nm)
|
||||
except Province.DoesNotExist:
|
||||
raise Http404('Not found')
|
||||
|
||||
if request.method == 'GET':
|
||||
serializer = ProvinceSerializer(item)
|
||||
return JsonResponse(serializer.data)
|
||||
|
||||
if request.method == 'PUT':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = ProvinceSerializer(item,data =data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data)
|
||||
return JsonResponse(serializer.errors, status =400)
|
||||
|
||||
if request.method == "DELETE":
|
||||
item.delete()
|
||||
return HttpResponse(status =204)
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def AssaultTroopView(request, nm):
|
||||
try:
|
||||
item = AssaultTroop.objects.get(id = nm)
|
||||
except AssaultTroop.DoesNotExist:
|
||||
raise Http404('Not found')
|
||||
|
||||
if request.method == 'GET':
|
||||
serializer = AssaultTroopSerializer(item)
|
||||
return JsonResponse(serializer.data)
|
||||
|
||||
if request.method == 'PUT':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = AssaultTroopSerializer(item,data =data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data)
|
||||
return JsonResponse(serializer.errors, status =400)
|
||||
|
||||
if request.method == "DELETE":
|
||||
item.delete()
|
||||
return HttpResponse(status =204)
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def PlayersView(request):
|
||||
|
||||
if request.method == 'GET':
|
||||
items = Player.objects.all()
|
||||
serializer = PlayerSerializer(items, many = True)
|
||||
return JsonResponse(serializer.data, safe = False)
|
||||
|
||||
elif request.method == 'POST':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = PlayerSerializer(data = data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data,status = 201)
|
||||
return JsonResponse(serializer.errors,status = 400)
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def ServersView(request):
|
||||
|
||||
if request.method == 'GET':
|
||||
items = Server.objects.all()
|
||||
serializer = ServerSerializer(items, many = True)
|
||||
return JsonResponse(serializer.data, safe = False)
|
||||
|
||||
elif request.method == 'POST':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = ServerSerializer(data = data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data,status = 201)
|
||||
return JsonResponse(serializer.errors,status = 400)
|
||||
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def PlayerView(request, nm):
|
||||
try:
|
||||
item = Player.objects.get(id = nm)
|
||||
except Player.DoesNotExist:
|
||||
raise Http404('Not found')
|
||||
|
||||
if request.method == 'GET':
|
||||
serializer = PlayerSerializer(item)
|
||||
return JsonResponse(serializer.data)
|
||||
|
||||
if request.method == 'PUT':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = PlayerSerializer(item,data =data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data)
|
||||
return JsonResponse(serializer.errors, status =400)
|
||||
|
||||
if request.method == "DELETE":
|
||||
item.delete()
|
||||
return HttpResponse(status =204)
|
||||
|
||||
|
||||
@csrf_exempt
|
||||
def ServerView(request, nm):
|
||||
try:
|
||||
item = Server.objects.get(id = nm)
|
||||
except Server.DoesNotExist:
|
||||
raise Http404('Not found')
|
||||
|
||||
if request.method == 'GET':
|
||||
serializer = ServerSerializer(item)
|
||||
return JsonResponse(serializer.data)
|
||||
|
||||
if request.method == 'PUT':
|
||||
data = JSONParser().parse(request)
|
||||
serializer = ServerSerializer(item,data =data)
|
||||
|
||||
if serializer.is_valid():
|
||||
serializer.save()
|
||||
return JsonResponse(serializer.data)
|
||||
return JsonResponse(serializer.errors, status =400)
|
||||
|
||||
if request.method == "DELETE":
|
||||
item.delete()
|
||||
return HttpResponse(status =204)
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
from django import template
|
||||
from django.template.defaultfilters import stringfilter
|
||||
|
||||
import markdown as md
|
||||
|
||||
|
||||
register = template.Library()
|
||||
|
||||
@register.filter()
|
||||
@stringfilter
|
||||
def markdown(value):
|
||||
return md.markdown(value, extensions=['markdown.extensions.fenced_code'])
|
||||
|
|
@ -10,6 +10,7 @@ services:
|
|||
network_mode: "host"
|
||||
command: >
|
||||
sh -c "python manage.py makemigrations blog --noinput &&
|
||||
python manage.py makemigrations api --noinput &&
|
||||
python manage.py migrate --noinput &&
|
||||
python manage.py collectstatic --noinput &&
|
||||
gunicorn BH.wsgi:application --bind 0.0.0.0:3030 --workers ${GUNICORN_WORKERS:-3}"
|
||||
|
|
|
|||
BIN
requirements.txt
BIN
requirements.txt
Binary file not shown.
|
|
@ -1,7 +1,7 @@
|
|||
{% extends 'base.html' %}
|
||||
{% block content %}
|
||||
|
||||
{% load markdown_extras %}
|
||||
{% load blog_markdown_extras %}
|
||||
<div class="container mt-5">
|
||||
|
||||
<div class="card mb-3">
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
{% extends 'base.html' %}
|
||||
{% block content %}
|
||||
|
||||
{% load markdown_extras %}
|
||||
{% load blog_markdown_extras %}
|
||||
<!-- Main Content -->
|
||||
<div class="container mt-5">
|
||||
<div class="row">
|
||||
|
|
|
|||
Loading…
Reference in New Issue