diff --git a/artifacts/urls.py b/artifacts/urls.py index 12a717c..98323e3 100644 --- a/artifacts/urls.py +++ b/artifacts/urls.py @@ -21,4 +21,5 @@ urlpatterns = [ path("settings/users/", views.settings_users, name="settings-users"), path("settings/demo-data/", views.settings_demo_data, name="settings-demo-data"), path("settings/storage/", views.settings_storage, name="settings-storage"), + path("settings/about/", views.settings_about, name="settings-about"), ] diff --git a/artifacts/views.py b/artifacts/views.py index d463611..555c121 100644 --- a/artifacts/views.py +++ b/artifacts/views.py @@ -307,8 +307,11 @@ class CapabilitiesView(APIView): def get(self, request): if not request.user.is_authenticated and resolve_token_user(request) is None: return HttpResponseForbidden("Login or a valid API token is required") + from daybook_project import __version__ + return Response( { + "version": __version__, "artifact_kinds": [choice[0] for choice in Artifact.KIND_CHOICES], "filters": ["source", "label", "day", "kind", "q"], "views": ["rendered", "raw"], @@ -1249,6 +1252,17 @@ def settings_users(request): ) +@login_required +def settings_about(request): + from daybook_project import __version__ + + return render( + request, + "artifacts/settings_about.html", + {"active_section": "about", "version": __version__}, + ) + + @login_required def settings_demo_data(request): if request.method == "POST": diff --git a/daybook_project/__init__.py b/daybook_project/__init__.py index e69de29..29f4719 100644 --- a/daybook_project/__init__.py +++ b/daybook_project/__init__.py @@ -0,0 +1,4 @@ +# Single source of truth for the app version. Bump this, commit, then tag the +# commit `vX.Y.Z` and deploy. Surfaced on Settings -> About and in +# GET /api/capabilities ("version"). +__version__ = "0.1.0" diff --git a/static/daybook.css b/static/daybook.css index b784eb9..37002a3 100644 --- a/static/daybook.css +++ b/static/daybook.css @@ -990,6 +990,28 @@ kbd { word-break: break-all; } +.about-head { + align-items: center; + display: flex; + gap: 1rem; + margin-bottom: 1.2rem; +} + +.about-head h2 { + margin: 0; +} + +.about-logo { + height: 3rem; + width: auto; +} + +.about-version { + color: var(--muted); + font-size: 0.9rem; + margin: 0.15rem 0 0; +} + .keep-button.kept { background: var(--success-bg); border-color: var(--success-border); diff --git a/templates/artifacts/_topbar.html b/templates/artifacts/_topbar.html index 4c96a02..5dbcde5 100644 --- a/templates/artifacts/_topbar.html +++ b/templates/artifacts/_topbar.html @@ -12,6 +12,7 @@
diff --git a/templates/artifacts/settings_about.html b/templates/artifacts/settings_about.html new file mode 100644 index 0000000..030847f --- /dev/null +++ b/templates/artifacts/settings_about.html @@ -0,0 +1,20 @@ +{% extends "artifacts/settings_base.html" %} + +{% block settings_content %} +
+ Version {{ version }}
+A self-hosted, multi-user journal where AI agents, scripts, or people + publish artifacts — reports, HTML, decks, images, PDFs, JSON, CSV — and each + logged-in user browses their own time-ordered, label-filterable feed. The + server owns IDs, styling, and storage; agents publish content, not files.
+ +Post to it with a personal API token from
+ Settings → Account; the current API capabilities (including this
+ version) are available at /api/capabilities.