Release v1.0.0
Some checks failed
CI / Checks (push) Failing after 13m2s

This commit is contained in:
2025-08-20 21:00:50 +02:00
commit b4338e2769
401 changed files with 23576 additions and 0 deletions

View File

@@ -0,0 +1,12 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
from django.apps import AppConfig
from django.utils.translation import gettext_lazy as _
class CoreConfig(AppConfig):
default_auto_field = 'django.db.models.BigAutoField'
label = 'core'
name = 'hotpocket_backend.apps.core'
verbose_name = _('Core')

View File

@@ -0,0 +1,8 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
from django.conf import settings as django_settings
from .types import PSettings
settings: PSettings = django_settings

View File

@@ -0,0 +1,14 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
import contextvars
from hotpocket_common.constants import NULL_UUID
REQUEST_ID: contextvars.ContextVar[str] = contextvars.ContextVar(
'request_id', default=str(NULL_UUID),
)
def get_request_id() -> str:
return REQUEST_ID.get()

View File

@@ -0,0 +1,12 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
import logging
from hotpocket_backend.apps.core.context import get_request_id
class RequestIDFilter(logging.Filter):
def filter(self, record: logging.LogRecord) -> bool:
record.request_id = get_request_id()
return True

View File

@@ -0,0 +1 @@
from .request_id import RequestIDMiddleware # noqa: F401

View File

@@ -0,0 +1,23 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
import uuid
from django.http import HttpHeaders, HttpRequest
from hotpocket_backend.apps.core.context import REQUEST_ID
class RequestIDMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request: HttpRequest) -> HttpHeaders:
request_id = str(uuid.uuid4())
REQUEST_ID.set(request_id)
response = self.get_response(request)
response["X-RequestID"] = REQUEST_ID.get()
return response

View File

@@ -0,0 +1 @@
from .base import Model # noqa: F401

View File

@@ -0,0 +1,54 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
from django.db import models
from django.utils.timezone import now
import uuid6
class Model(models.Model):
id = models.UUIDField(
primary_key=True,
null=False,
default=uuid6.uuid7,
editable=False,
)
account_uuid = models.UUIDField(
blank=False, null=False, default=None, db_index=True,
)
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
deleted_at = models.DateTimeField(
blank=True,
null=True,
default=None,
db_index=True,
editable=False,
)
class Meta:
abstract = True
@property
def is_active(self) -> bool:
return self.deleted_at is None
def save(self,
force_insert=False,
force_update=False,
using=None,
update_fields=None,
):
self.full_clean()
super().save(
force_insert=force_insert,
force_update=force_update,
using=using,
update_fields=update_fields,
)
def soft_delete(self, save=True) -> None:
self.deleted_at = now()
if save is True:
self.save()

View File

@@ -0,0 +1,13 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
import typing
from hotpocket_common.loader import load_module_attribute
from .conf import settings
def get_adapter(setting: str, default: str) -> typing.Any:
import_path = getattr(settings, setting, default)
return load_module_attribute(import_path)

View File

@@ -0,0 +1,22 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
import logging
from celery import shared_task
LOGGER = logging.getLogger(__name__)
@shared_task
def ping():
LOGGER.info('PONG')
@shared_task(bind=True)
def debug_request(self):
LOGGER.warning(
'request.id=`%s` request.properties=`%s`',
self.request.id,
self.request.properties,
)

View File

@@ -0,0 +1,83 @@
{% extends "admin/base_site.html" %}
{% load i18n static %}
{% block title %}{% if form.errors %}{% translate "Error:" %} {% endif %}{{ block.super }}{% endblock %}
{% block extrastyle %}{{ block.super }}<link rel="stylesheet" href="{% static "admin/css/login.css" %}">
{{ form.media }}
{% endblock %}
{% block bodyclass %}{{ block.super }} login{% endblock %}
{% block usertools %}{% endblock %}
{% block nav-global %}{% endblock %}
{% block nav-sidebar %}{% endblock %}
{% block content_title %}{% endblock %}
{% block nav-breadcrumbs %}{% endblock %}
{% block content %}
{% if form.errors and not form.non_field_errors %}
<p class="errornote">
{% blocktranslate count counter=form.errors.items|length %}Please correct the error below.{% plural %}Please correct the errors below.{% endblocktranslate %}
</p>
{% endif %}
{% if form.non_field_errors %}
{% for error in form.non_field_errors %}
<p class="errornote">
{{ error }}
</p>
{% endfor %}
{% endif %}
<div id="content-main">
{% if user.is_authenticated %}
<p class="errornote">
{% blocktranslate trimmed %}
You are authenticated as {{ username }}, but are not authorized to
access this page. Would you like to login to a different account?
{% endblocktranslate %}
</p>
{% endif %}
<form action="{{ app_path }}" method="post" id="login-form">{% csrf_token %}
{% if not MODEL_AUTH_IS_DISABLED %}
<div class="form-row">
{{ form.username.errors }}
{{ form.username.label_tag }} {{ form.username }}
</div>
<div class="form-row">
{{ form.password.errors }}
{{ form.password.label_tag }} {{ form.password }}
<input type="hidden" name="next" value="{{ next }}">
</div>
{% url 'admin_password_reset' as password_reset_url %}
{% if password_reset_url %}
<div class="password-reset-link">
<a href="{{ password_reset_url }}">{% translate 'Forgotten your login credentials?' %}</a>
</div>
{% endif %}
<div class="submit-row">
<input type="submit" value="{% translate 'Log in' %}">
</div>
{% endif %}
{% if HOTPOCKET_OIDC_IS_ENABLED %}
<div class="submit-row">
<a
class="button"
href="{% url 'social:begin' 'hotpocket_oidc' %}"
style="display: block;"
>
{% blocktranslate %}Log in with {{ HOTPOCKET_OIDC_DISPLAY_NAME }}{% endblocktranslate %}
</a>
</div>
{% endif %}
</form>
</div>
{% endblock %}

View File

@@ -0,0 +1,32 @@
# -*- coding: utf-8 -*-
from __future__ import annotations
import pathlib
import typing
from hotpocket_backend.secrets.admin import AdminSecrets
from hotpocket_backend.secrets.webapp import WebAppSecrets
from hotpocket_common.constants import App, Env
class PSettings(typing.Protocol):
DEBUG: bool
TESTING: bool
ALLOWED_HOSTS: list[str]
SECRET_KEY: str
APP: App
ENV: Env
SECRETS: AdminSecrets | WebAppSecrets
MODEL_AUTH_IS_DISABLED: bool
SITE_TITLE: str
SITE_SHORT_TITLE: str
IMAGE_ID: str
SAVES_SAVE_ADAPTER: str
SAVES_ASSOCIATION_ADAPTER: str
UPLOADS_PATH: pathlib.Path