development setup using docker

This commit is contained in:
j3d1 2024-03-11 17:37:56 +01:00
parent c4c49931a4
commit f8dacef309
17 changed files with 414 additions and 1 deletions

1
.gitignore vendored
View file

@ -131,3 +131,4 @@ dmypy.json
staticfiles/ staticfiles/
userfiles/ userfiles/
testdata.py testdata.py
*.sqlite3

View file

@ -0,0 +1,16 @@
# Use an official Python runtime as instance_a parent image
FROM python:3.9
# Set environment variables
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
# Set work directory
WORKDIR /code
# Install dependencies
COPY requirements.txt /code/
RUN pip install --no-cache-dir -r requirements.txt
# Run the application
CMD ["python", "manage.py", "runserver", "0.0.0.0:8000", "--insecure"]

16
deploy/dev/Dockerfile.dns Normal file
View file

@ -0,0 +1,16 @@
# Use an official Python runtime as instance_a parent image
FROM python:3.9
# Set environment variables
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
# Set work directory
WORKDIR /dns
COPY dns_server.py /dns/
RUN pip install dnslib
# Run the application
CMD ["python", "dns_server.py"]

View file

@ -0,0 +1,13 @@
# Use an official Node.js runtime as instance_a parent image
FROM node:14
# Set work directory
WORKDIR /app
# Install app dependencies
# A wildcard is used to ensure both package.json AND package-lock.json are copied
COPY package.json ./
RUN npm install
CMD [ "npm", "run", "dev", "--", "--host"]

View file

@ -0,0 +1,14 @@
FROM nginx:bookworm
# snakeoil for localhost
RUN apt-get update && \
apt-get install -y openssl && \
openssl genrsa -des3 -passout pass:x -out server.pass.key 2048 && \
openssl rsa -passin pass:x -in server.pass.key -out server.key && \
rm server.pass.key && \
openssl req -new -key server.key -out server.csr \
-subj "/C=US/ST=Denial/L=Springfield/O=Dis/CN=localhost" && \
openssl x509 -req -days 365 -in server.csr -signkey server.key -out server.crt &&\
mv server.crt /etc/nginx/nginx.crt && \
mv server.key /etc/nginx/nginx.key \

View file

@ -0,0 +1,15 @@
# Use an official Python runtime as instance_a parent image
FROM python:3.9
# Set environment variables
ENV PYTHONDONTWRITEBYTECODE 1
ENV PYTHONUNBUFFERED 1
# Set work directory
WORKDIR /wiki
# Install dependencies
RUN pip install --no-cache-dir mkdocs
# Run the application
CMD ["mkdocs", "serve", "--dev-addr=0.0.0.0:8001"]

72
deploy/dev/dns_server.py Normal file
View file

@ -0,0 +1,72 @@
import http.server
import socketserver
import urllib.parse
import dnslib
import base64
try:
def resolve(zone, qname, qtype):
for record in zone:
if record["name"] == qname and record["type"] == qtype and "value" in record:
return record["value"]
class DnsHttpRequestHandler(http.server.BaseHTTPRequestHandler):
def do_GET(self):
try:
with open("/dns/zone.json", "r") as f:
import json
zone = json.load(f)
url = urllib.parse.urlparse(self.path)
if url.path != "/dns-query":
self.send_response(404)
return
query = urllib.parse.parse_qs(url.query)
if "dns" not in query:
self.send_response(400)
return
query_base64 = query["dns"][0]
padded = query_base64 + "=" * (4 - len(query_base64) % 4)
raw = base64.b64decode(padded)
dns = dnslib.DNSRecord.parse(raw)
response = dnslib.DNSRecord(dnslib.DNSHeader(id=dns.header.id, qr=1, aa=1, ra=1), q=dns.q)
record = resolve(zone, dns.q.qname, dnslib.QTYPE[dns.q.qtype])
if record:
if dns.q.qtype == dnslib.QTYPE.SRV:
print("SRV record")
reply = dnslib.SRV(record["priority"], record["weight"], record["port"], record["target"])
response.add_answer(dnslib.RR(dns.q.qname, dns.q.qtype, rdata=reply))
else:
response.header.rcode = dnslib.RCODE.NXDOMAIN
print(response)
self.send_response(200)
self.send_header("Content-type", "application/dns-message")
self.end_headers()
pack = response.pack()
self.wfile.write(pack)
return
except Exception as e:
print(f"Error: {e}")
self.send_response(500)
self.send_header("Content-type", "text/html")
self.end_headers()
self.wfile.write(b"Internal Server Error")
handler_object = DnsHttpRequestHandler
PORT = 8053
my_server = socketserver.TCPServer(("", PORT), handler_object)
# Start the server
print(f"Starting server on port {PORT}")
my_server.serve_forever()
except Exception as e:
print(f"Error: {e}")

View file

@ -0,0 +1,8 @@
# SECURITY WARNING: don't run with debug turned on in production!
DEBUG=True
# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY='e*lm&*!j0_stqaiod$1zob(vs@aq6+n-i$1%!rek)_v9n^ue$3'
ALLOWED_HOSTS="*"

View file

@ -0,0 +1,3 @@
[
"127.0.0.3:5353"
]

View file

@ -0,0 +1,3 @@
[
"a.localhost"
]

View file

@ -0,0 +1,96 @@
events {}
http {
upstream backend {
server backend-a:8000;
}
upstream frontend {
server frontend:5173;
}
upstream wiki {
server wiki:8001;
}
upstream dns {
server dns:8053;
}
server {
listen 8080 ssl;
server_name localhost;
ssl_certificate /etc/nginx/nginx.crt;
ssl_certificate_key /etc/nginx/nginx.key;
location /api {
proxy_set_header Host $host:$server_port;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host:$server_port;
proxy_set_header X-Forwarded-Port $server_port;
proxy_pass http://backend;
}
location /auth {
proxy_set_header Host $host:$server_port;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host:$server_port;
proxy_set_header X-Forwarded-Port $server_port;
proxy_pass http://backend;
}
location /docs {
proxy_pass http://backend/docs;
}
location /static {
proxy_pass http://backend/static;
}
location /wiki {
proxy_pass http://wiki/wiki;
}
location /livereload {
proxy_pass http://wiki/livereload;
}
location /local/ {
alias /var/www/;
try_files $uri.json =404;
add_header Content-Type application/json;
}
location / {
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_set_header Host $host;
proxy_pass http://frontend;
}
}
# DoH server
server {
listen 5353 ssl;
server_name localhost;
ssl_certificate /etc/nginx/nginx.crt;
ssl_certificate_key /etc/nginx/nginx.key;
location /dns-query {
proxy_pass http://dns;
# allow any origin
add_header 'Access-Control-Allow-Origin' '*';
add_header 'Access-Control-Allow-Methods' 'GET, OPTIONS';
}
}
}

View file

@ -0,0 +1,7 @@
# SECURITY WARNING: don't run with debug turned on in production!
DEBUG=True
# SECURITY WARNING: keep the secret key used in production secret!
SECRET_KEY='7ccxjje%q@@0*z+r&-$fy3(rj9n)%$!sk-k++-&rb=_u(wpjbe'
ALLOWED_HOSTS="*"

View file

@ -0,0 +1,46 @@
events {}
http {
upstream backend {
server backend-b:8000;
}
server {
listen 8080 ssl;
server_name localhost;
ssl_certificate /etc/nginx/nginx.crt;
ssl_certificate_key /etc/nginx/nginx.key;
location /api {
#proxy_set_header X-Forwarded-For "$http_x_forwarded_for, $realip_remote_addr";
proxy_set_header Host $host:$server_port;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host:$server_port;
proxy_set_header X-Forwarded-Port $server_port;
proxy_pass http://backend;
}
location /auth {
#proxy_set_header X-Forwarded-For "$http_x_forwarded_for, $realip_remote_addr";
proxy_set_header Host $host:$server_port;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host:$server_port;
proxy_set_header X-Forwarded-Port $server_port;
proxy_pass http://backend;
}
location /docs {
proxy_pass http://backend/docs;
}
location /static {
proxy_pass http://backend/static;
}
}
}

24
deploy/dev/zone.json Normal file
View file

@ -0,0 +1,24 @@
[
{
"name": "_toolshed-server._tcp.a.localhost.",
"type": "SRV",
"ttl": 60,
"value": {
"priority": 0,
"weight": 5,
"port": 8080,
"target": "127.0.0.1."
}
},
{
"name": "_toolshed-server._tcp.b.localhost.",
"type": "SRV",
"ttl": 60,
"value": {
"priority": 0,
"weight": 5,
"port": 8080,
"target": "127.0.0.2."
}
}
]

View file

@ -0,0 +1,78 @@
version: '3.8'
services:
backend-a:
build:
context: ../backend/
dockerfile: ../deploy/dev/Dockerfile.backend
volumes:
- ../backend:/code
- ../deploy/dev/instance_a/a.env:/code/.env
- ../deploy/dev/instance_a/a.sqlite3:/code/db.sqlite3
expose:
- 8000
command: bash -c "python configure.py; python configure.py testdata; python manage.py runserver 0.0.0.0:8000 --insecure"
backend-b:
build:
context: ../backend/
dockerfile: ../deploy/dev/Dockerfile.backend
volumes:
- ../backend:/code
- ../deploy/dev/instance_b/b.env:/code/.env
- ../deploy/dev/instance_b/b.sqlite3:/code/db.sqlite3
expose:
- 8000
command: bash -c "python configure.py; python configure.py testdata; python manage.py runserver 0.0.0.0:8000 --insecure"
frontend:
build:
context: ../frontend/
dockerfile: ../deploy/dev/Dockerfile.frontend
volumes:
- ../frontend:/app:ro
- /app/node_modules
expose:
- 5173
command: npm run dev -- --host
wiki:
build:
context: ../
dockerfile: deploy/dev/Dockerfile.wiki
volumes:
- ../mkdocs.yml:/wiki/mkdocs.yml
- ../docs:/wiki/docs
expose:
- 8001
command: mkdocs serve --dev-addr=0.0.0.0:8001
proxy-a:
build:
context: ./
dockerfile: dev/Dockerfile.proxy
volumes:
- ./dev/instance_a/nginx-a.dev.conf:/etc/nginx/nginx.conf:ro
- ./dev/instance_a/dns.json:/var/www/dns.json:ro
- ./dev/instance_a/domains.json:/var/www/domains.json:ro
ports:
- "127.0.0.1:8080:8080"
- "127.0.0.3:5353:5353"
proxy-b:
build:
context: ./
dockerfile: dev/Dockerfile.proxy
volumes:
- ./dev/instance_b/nginx-b.dev.conf:/etc/nginx/nginx.conf:ro
ports:
- "127.0.0.2:8080:8080"
dns:
build:
context: ./dev/
dockerfile: Dockerfile.dns
volumes:
- ./dev/zone.json:/dns/zone.json
expose:
- 8053

0
frontend/node_modules/.forgit generated vendored Normal file
View file

View file

@ -24,3 +24,4 @@ extra_javascript:
- https://cdn.jsdelivr.net/npm/mermaid/dist/mermaid.js - https://cdn.jsdelivr.net/npm/mermaid/dist/mermaid.js
extra_css: extra_css:
- toolshed.css - toolshed.css
site_url: https://localhost:8080/wiki/