Improve/tweak templates

This commit is contained in:
Thomas Sileo 2022-07-15 20:01:55 +02:00
parent 12f09743fd
commit d38fec6570
15 changed files with 96 additions and 51 deletions

2
.gitignore vendored
View file

@ -4,4 +4,4 @@ __pycache__/
.pytest_cache/ .pytest_cache/
docs/dist/ docs/dist/
requirements.txt requirements.txt
app/scss/vars.scss app/scss/_vars.scss

View file

@ -1,5 +1,6 @@
import hashlib import hashlib
from datetime import datetime from datetime import datetime
from functools import cached_property
from typing import Any from typing import Any
import pydantic import pydantic
@ -26,7 +27,7 @@ class Object:
def is_from_inbox(self) -> bool: def is_from_inbox(self) -> bool:
return False return False
@property @cached_property
def ap_type(self) -> str: def ap_type(self) -> str:
return self.ap_object["type"] return self.ap_object["type"]
@ -42,7 +43,7 @@ class Object:
def ap_actor_id(self) -> str: def ap_actor_id(self) -> str:
return ap.get_actor_id(self.ap_object) return ap.get_actor_id(self.ap_object)
@property @cached_property
def ap_published_at(self) -> datetime | None: def ap_published_at(self) -> datetime | None:
# TODO: default to None? or now()? # TODO: default to None? or now()?
if "published" in self.ap_object: if "published" in self.ap_object:
@ -55,7 +56,7 @@ class Object:
def actor(self) -> Actor: def actor(self) -> Actor:
raise NotImplementedError() raise NotImplementedError()
@property @cached_property
def visibility(self) -> ap.VisibilityEnum: def visibility(self) -> ap.VisibilityEnum:
return ap.object_visibility(self.ap_object, self.actor) return ap.object_visibility(self.ap_object, self.actor)
@ -71,7 +72,7 @@ class Object:
def tags(self) -> list[ap.RawObject]: def tags(self) -> list[ap.RawObject]:
return ap.as_list(self.ap_object.get("tag", [])) return ap.as_list(self.ap_object.get("tag", []))
@property @cached_property
def attachments(self) -> list["Attachment"]: def attachments(self) -> list["Attachment"]:
attachments = [] attachments = []
for obj in ap.as_list(self.ap_object.get("attachment", [])): for obj in ap.as_list(self.ap_object.get("attachment", [])):
@ -130,7 +131,7 @@ class Object:
return None return None
@property @cached_property
def content(self) -> str | None: def content(self) -> str | None:
content = self.ap_object.get("content") content = self.ap_object.get("content")
if not content: if not content:
@ -146,7 +147,7 @@ class Object:
def summary(self) -> str | None: def summary(self) -> str | None:
return self.ap_object.get("summary") return self.ap_object.get("summary")
@property @cached_property
def permalink_id(self) -> str: def permalink_id(self) -> str:
return ( return (
"permalink-" "permalink-"

View file

@ -75,6 +75,7 @@ _RESIZED_CACHE: MutableMapping[tuple[str, int], tuple[bytes, str, Any]] = LFUCac
# #
# Next: # Next:
# - fix stream (only content from follows + mention, and dedup shares) # - fix stream (only content from follows + mention, and dedup shares)
# - custom emoji in data/
# - handle remove activity # - handle remove activity
# - retries httpx? # - retries httpx?
# - DB models for webmentions # - DB models for webmentions

1
app/scss/_theme.scss Symbolic link
View file

@ -0,0 +1 @@
../../data/_theme.scss

View file

@ -10,7 +10,7 @@ $form-text-color: #333;
$muted-color: #555; // solarized comment text $muted-color: #555; // solarized comment text
// Load custom theme // Load custom theme
// @import "vars.scss"; // @import "theme.scss";
.light-background { .light-background {
@ -142,22 +142,31 @@ footer {
} }
} }
@mixin admin-button() {
font-size: 20px;
line-height: 32px;
font-family: $font-stack;
background: $form-background-color;
color: $form-text-color;
border: 1px solid $background;
padding: 8px 10px 5px 10px;
cursor: pointer;
&:hover {
border: 1px solid $form-text-color;
}
}
.show-sensitive-btn, .show-more-btn {
@include admin-button;
margin: 20px 0;
}
nav { nav {
form { form {
margin: 15px 0; margin: 15px 0;
} }
input[type=submit], button { input[type=submit], button {
font-size: 20px; @include admin-button;
line-height: 32px;
font-family: $font-stack;
background: $form-background-color;
color: $form-text-color;
border: 1px solid $background;
padding: 8px 10px 5px 10px;
cursor: pointer;
&:hover {
border: 1px solid $form-text-color;
}
} }
} }

View file

@ -1,5 +1,10 @@
{%- import "utils.html" as utils with context -%} {%- import "utils.html" as utils with context -%}
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %}
<title>{{ local_actor.display_name }} - New</title>
{% endblock %}
{% block content %} {% block content %}
{% if in_reply_to_object %} {% if in_reply_to_object %}

View file

@ -1,5 +1,10 @@
{%- import "utils.html" as utils with context -%} {%- import "utils.html" as utils with context -%}
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %}
<title>{{ local_actor.display_name }}'s followers</title>
{% endblock %}
{% block content %} {% block content %}
{% include "header.html" %} {% include "header.html" %}
<div id="followers"> <div id="followers">

View file

@ -1,5 +1,10 @@
{%- import "utils.html" as utils with context -%} {%- import "utils.html" as utils with context -%}
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %}
<title>{{ local_actor.display_name }}'s follows</title>
{% endblock %}
{% block content %} {% block content %}
{% include "header.html" %} {% include "header.html" %}
<div id="following"> <div id="following">

View file

@ -2,6 +2,7 @@
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %} {% block head %}
<title>{{ local_actor.display_name }}'s microblog</title>
<link rel="indieauth-metadata" href="{{ url_for("well_known_authorization_server") }}"> <link rel="indieauth-metadata" href="{{ url_for("well_known_authorization_server") }}">
<link rel="authorization_endpoint" href="{{ url_for("indieauth_authorization_endpoint") }}"> <link rel="authorization_endpoint" href="{{ url_for("indieauth_authorization_endpoint") }}">
<link rel="token_endpoint" href="{{ url_for("indieauth_token_endpoint") }}"> <link rel="token_endpoint" href="{{ url_for("indieauth_token_endpoint") }}">

View file

@ -1,5 +1,10 @@
{%- import "utils.html" as utils with context -%} {%- import "utils.html" as utils with context -%}
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %}
<title>{{ local_actor.display_name }} - Lookup</title>
{% endblock %}
{% block content %} {% block content %}
<div class="box"> <div class="box">

View file

@ -1,5 +1,10 @@
{%- import "utils.html" as utils with context -%} {%- import "utils.html" as utils with context -%}
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %}
<title>{{ local_actor.display_name }} - Notifications</title>
{% endblock %}
{% block content %} {% block content %}
<div class="box"> <div class="box">
<h2>Notifications</h2> <h2>Notifications</h2>

View file

@ -3,14 +3,16 @@
{% block head %} {% block head %}
{% if outbox_object %} {% if outbox_object %}
{% set excerpt = outbox_object.content | html2text | trim | truncate(50) %}
<title>{{ local_actor.display_name }}: "{{ excerpt }}"</title>
<link rel="webmention" href="{{ url_for("webmention_endpoint") }}"> <link rel="webmention" href="{{ url_for("webmention_endpoint") }}">
<link rel="alternate" href="{{ request.url }}" type="application/activity+json"> <link rel="alternate" href="{{ request.url }}" type="application/activity+json">
<meta name="description" content="{{ outbox_object.content | html2text | trim | truncate(50) }}"> <meta name="description" content="{{ excerpt }}">
<meta content="article" property="og:type" /> <meta content="article" property="og:type" />
<meta content="{{ outbox_object.url }}" property="og:url" /> <meta content="{{ outbox_object.url }}" property="og:url" />
<meta content="{{ local_actor.display_name }}'s microblog" property="og:site_name" /> <meta content="{{ local_actor.display_name }}'s microblog" property="og:site_name" />
<meta content="Note" property="og:title" /> <meta content="Note" property="og:title" />
<meta content="{{ outbox_object.content | html2text | trim | truncate(50) }}" property="og:description" /> <meta content="{{ excerpt }}" property="og:description" />
<meta content="{{ local_actor.icon_url }}" property="og:image" /> <meta content="{{ local_actor.icon_url }}" property="og:image" />
<meta content="summary" property="twitter:card" /> <meta content="summary" property="twitter:card" />
{% endif %} {% endif %}

View file

@ -1,5 +1,10 @@
{%- import "utils.html" as utils with context -%} {%- import "utils.html" as utils with context -%}
{% extends "layout.html" %} {% extends "layout.html" %}
{% block head %}
<title>Remote follow {{ local_actor.display_name }}</title>
{% endblock %}
{% block content %} {% block content %}
{% include "header.html" %} {% include "header.html" %}

View file

@ -2,8 +2,8 @@
<input type="hidden" name="csrf_token" value="{{ csrf_token }}"> <input type="hidden" name="csrf_token" value="{{ csrf_token }}">
{% endmacro %} {% endmacro %}
{% macro embed_redirect_url() %} {% macro embed_redirect_url(permalink_id=None) %}
<input type="hidden" name="redirect_url" value="{{ request.url }}"> <input type="hidden" name="redirect_url" value="{{ request.url }}{% if permalink_id %}#{{ permalink_id }}{% endif %}">
{% endmacro %} {% endmacro %}
{% macro admin_follow_button(actor) %} {% macro admin_follow_button(actor) %}
@ -15,46 +15,46 @@
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_like_button(ap_object_id) %} {% macro admin_like_button(ap_object_id, permalink_id) %}
<form action="{{ request.url_for("admin_actions_like") }}" method="POST"> <form action="{{ request.url_for("admin_actions_like") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="like"> <input type="submit" value="like">
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_bookmark_button(ap_object_id) %} {% macro admin_bookmark_button(ap_object_id, permalink_id) %}
<form action="{{ request.url_for("admin_actions_bookmark") }}" method="POST"> <form action="{{ request.url_for("admin_actions_bookmark") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="bookmark"> <input type="submit" value="bookmark">
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_unbookmark_button(ap_object_id) %} {% macro admin_unbookmark_button(ap_object_id, permalink_id) %}
<form action="{{ request.url_for("admin_actions_unbookmark") }}" method="POST"> <form action="{{ request.url_for("admin_actions_unbookmark") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="unbookmark"> <input type="submit" value="unbookmark">
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_pin_button(ap_object_id) %} {% macro admin_pin_button(ap_object_id, permalink_id) %}
<form action="{{ request.url_for("admin_actions_pin") }}" method="POST"> <form action="{{ request.url_for("admin_actions_pin") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="pin"> <input type="submit" value="pin">
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_unpin_button(ap_object_id) %} {% macro admin_unpin_button(ap_object_id, permalink_id) %}
<form action="{{ request.url_for("admin_actions_unpin") }}" method="POST"> <form action="{{ request.url_for("admin_actions_unpin") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="unpin"> <input type="submit" value="unpin">
</form> </form>
@ -69,41 +69,41 @@
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_announce_button(ap_object_id, disabled=False) %} {% macro admin_announce_button(ap_object_id, disabled=False, permalink_id=None) %}
<form action="{{ request.url_for("admin_actions_announce") }}" method="POST"> <form action="{{ request.url_for("admin_actions_announce") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="share" {% if disabled %}title="Cannot share non-public content" disabled{% endif %}> <input type="submit" value="share" {% if disabled %}title="Cannot share non-public content" disabled{% endif %}>
</form> </form>
{% endmacro %} {% endmacro %}
{% macro admin_undo_button(ap_object_id, action="Undo") %} {% macro admin_undo_button(ap_object_id, action="undo", permalink_id=None) %}
<form action="{{ request.url_for("admin_actions_undo") }}" method="POST"> <form action="{{ request.url_for("admin_actions_undo") }}" method="POST">
{{ embed_csrf_token() }} {{ embed_csrf_token() }}
{{ embed_redirect_url() }} {{ embed_redirect_url(permalink_id) }}
<input type="hidden" name="ap_object_id" value="{{ ap_object_id }}"> <input type="hidden" name="ap_object_id" value="{{ ap_object_id }}">
<input type="submit" value="{{ action }}"> <input type="submit" value="{{ action }}">
</form> </form>
{% endmacro %} {% endmacro %}
{% macro sensitive_button(permalink_id) %} {% macro sensitive_button(permalink_id) %}
<form action="" method="GET"> <form action="{{ request.url }}#{{ permalink_id }}" method="GET">
<input type="hidden" name="show_sensitive" value="{{ permalink_id }}"> <input type="hidden" name="show_sensitive" value="{{ permalink_id }}">
{% for k, v in request.query_params.items() %} {% for k, v in request.query_params.items() %}
<input type="hidden" name="{{k}}" value="{{v}}"> <input type="hidden" name="{{k}}" value="{{v}}">
{% endfor %} {% endfor %}
<button type="submit">display sensitive content</button> <button type="submit" class="show-sensitive-btn">display sensitive content</button>
</form> </form>
{% endmacro %} {% endmacro %}
{% macro show_more_button(permalink_id) %} {% macro show_more_button(permalink_id) %}
<form action="" method="GET"> <form action="{{ request.url }}#{{ permalink_id }}" method="GET">
<input type="hidden" name="show_more" value="{{ permalink_id }}"> <input type="hidden" name="show_more" value="{{ permalink_id }}">
{% for k, v in request.query_params.items() %} {% for k, v in request.query_params.items() %}
<input type="hidden" name="{{k}}" value="{{v}}"> <input type="hidden" name="{{k}}" value="{{v}}">
{% endfor %} {% endfor %}
<button type="submit">show more</button> <button type="submit" class="show-more-btn">show more</button>
</form> </form>
{% endmacro %} {% endmacro %}
@ -320,9 +320,9 @@
<li> <li>
{% if object.is_pinned %} {% if object.is_pinned %}
{{ admin_unpin_button(object.ap_id) }} {{ admin_unpin_button(object.ap_id, object.permalink_id) }}
{% else %} {% else %}
{{ admin_pin_button(object.ap_id) }} {{ admin_pin_button(object.ap_id, object.permalink) }}
{% endif %} {% endif %}
</li> </li>
{% endif %} {% endif %}
@ -333,17 +333,17 @@
<li> <li>
{% if object.liked_via_outbox_object_ap_id %} {% if object.liked_via_outbox_object_ap_id %}
{{ admin_undo_button(object.liked_via_outbox_object_ap_id, "unlike") }} {{ admin_undo_button(object.liked_via_outbox_object_ap_id, "unlike", object.permalink_id) }}
{% else %} {% else %}
{{ admin_like_button(object.ap_id) }} {{ admin_like_button(object.ap_id, object.permalink_id) }}
{% endif %} {% endif %}
</li> </li>
<li> <li>
{% if object.is_bookmarked %} {% if object.is_bookmarked %}
{{ admin_unbookmark_button(object.ap_id) }} {{ admin_unbookmark_button(object.ap_id, object.permalink_id) }}
{% else %} {% else %}
{{ admin_bookmark_button(object.ap_id) }} {{ admin_bookmark_button(object.ap_id, object.permalink_id) }}
{% endif %} {% endif %}
</li> </li>
@ -351,7 +351,7 @@
{% if object.announced_via_outbox_object_ap_id %} {% if object.announced_via_outbox_object_ap_id %}
{{ admin_undo_button(object.liked_via_outbox_object_ap_id, "unshare") }} {{ admin_undo_button(object.liked_via_outbox_object_ap_id, "unshare") }}
{% else %} {% else %}
{{ admin_announce_button(object.ap_id, disabled=object.visibility not in [visibility_enum.PUBLIC, visibility_enum.UNLISTED]) }} {{ admin_announce_button(object.ap_id, disabled=object.visibility not in [visibility_enum.PUBLIC, visibility_enum.UNLISTED], permalink_id=object.permalink_id) }}
{% endif %} {% endif %}
</li> </li>

View file

@ -41,9 +41,9 @@ def lint(ctx):
@task @task
def compile_scss(ctx, watch=False): def compile_scss(ctx, watch=False):
# type: (Context, bool) -> None # type: (Context, bool) -> None
vars_file = Path("app/scss/vars.scss") theme_file = Path("data/_theme.scss")
if not vars_file.exists(): if not theme_file.exists():
vars_file.write_text("") theme_file.write_text("// override vars for theming here")
if watch: if watch:
run("poetry run boussole watch", echo=True) run("poetry run boussole watch", echo=True)