diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml new file mode 100644 index 0000000000000000000000000000000000000000..1cdf3153d66622f0e9b4498a4edee12b6aef0447 --- /dev/null +++ b/.pre-commit-config.yaml @@ -0,0 +1,26 @@ +default_language_version: + python: python3.11 + +exclude: snapshots/ +repos: + - repo: https://github.com/pre-commit/pre-commit-hooks + rev: v4.4.0 + hooks: + - id: trailing-whitespace + exclude: ^.*\.md$ + - id: end-of-file-fixer + - id: debug-statements + - id: mixed-line-ending + args: [--fix=lf] + - id: detect-private-key + - id: check-merge-conflict + + - repo: https://github.com/timothycrosley/isort + rev: 5.12.0 + hooks: + - id: isort + + - repo: https://github.com/psf/black + rev: 23.1.0 + hooks: + - id: black diff --git a/Dockerfile b/Dockerfile index b2f5d6cd97d6450ad13514b8a691816d13ec3ca4..9f926be9b446d0bcb7f6f1a1f6c0cc0823d6966a 100644 --- a/Dockerfile +++ b/Dockerfile @@ -17,8 +17,6 @@ RUN DATABASE_URL=postgres://x/x \ SECRET_KEY=x \ ALLOWED_HOSTS=x \ CHOBOTNICE_RV_GID=x \ - INSTAGRAM_CLIENT_ID=x \ - INSTAGRAM_CLIENT_SECRET=x \ python manage.py collectstatic --noinput --settings=rybicka.settings.production RUN bash -c "adduser --disabled-login --quiet --gecos app app && \ diff --git a/Makefile b/Makefile index 5de90eb598d0cdcfd4b2369ea5c694c5ef1145e0..0aa344656622e2bcda54d6f306af6721624dc697 100644 --- a/Makefile +++ b/Makefile @@ -11,6 +11,8 @@ help: @echo "Setup:" @echo " venv Setup virtual environment" @echo " install Install dependencies to venv" + @echo " install-hooks Install pre-commit hooks" + @echo " hooks Run pre-commit hooks manually" @echo " build Build CSS and JS files" @echo "" @echo "Application:" @@ -34,6 +36,12 @@ build: venv ${VENV}/bin/npm run build ${VENV}/bin/python manage.py collectstatic --noinput --settings=${SETTINGS} +install-hooks: + pre-commit install --install-hooks + +hooks: + pre-commit run -a + run: venv ${VENV}/bin/python manage.py runserver ${PORT} --settings=${SETTINGS} diff --git a/asset_server_resize/apps.py b/asset_server_resize/apps.py index 61081abade1ab5e8abb35c5671c764113e681af8..d678503b9b218fb8279debca6ea3b2a8eec1fe26 100644 --- a/asset_server_resize/apps.py +++ b/asset_server_resize/apps.py @@ -2,5 +2,5 @@ from django.apps import AppConfig class AutoServerResizeConfig(AppConfig): - default_auto_field = 'django.db.models.BigAutoField' - name = 'asset_server_resize' + default_auto_field = "django.db.models.BigAutoField" + name = "asset_server_resize" diff --git a/asset_server_resize/views.py b/asset_server_resize/views.py index c2f44dc9ef45a62f888bd3a3698fe9ce79cc54e7..f3953815a98b18f2443b3f618e37d3fef3e8a371 100644 --- a/asset_server_resize/views.py +++ b/asset_server_resize/views.py @@ -6,8 +6,4 @@ from django_http_exceptions import HTTPExceptions def index(request): - return render( - request, - "asset_server_resize/index.html", - {} - ) + return render(request, "asset_server_resize/index.html", {}) diff --git a/env.example b/env.example index 6c528c0e1f97c09b04947d1426c1f383d49206f2..3b703bebba92d99e88b0ba05a04d7903be5c1037 100644 --- a/env.example +++ b/env.example @@ -5,8 +5,5 @@ SECRET_KEY="%@=^sip3=tqn6d_-xvvidc1@-t0t3&*kab@vr4c4" CHOBOTNICE_API_URL="https://chobotnice.pirati.cz/graphql/" CHOBOTNICE_RV_GID="R3JvdXBUeXBlOjYyNQ==" -INSTAGRAM_CLIENT_ID=3828083077418467 -INSTAGRAM_CLIENT_SECRET=da7ea1af344e60ccd2bfcfa0f296b808 - # Production settings ALLOWED_HOSTS="tools.pirati.cz" diff --git a/mail_signature/apps.py b/mail_signature/apps.py index 7216dddc126b51d80cf8852cb1ef3fcb90bb990d..607d366cc8a962146e1bc295f89ada9036851f29 100644 --- a/mail_signature/apps.py +++ b/mail_signature/apps.py @@ -2,5 +2,5 @@ from django.apps import AppConfig class MailSignatureConfig(AppConfig): - default_auto_field = 'django.db.models.BigAutoField' - name = 'mail_signature' + default_auto_field = "django.db.models.BigAutoField" + name = "mail_signature" diff --git a/mail_signature/templates/mail_signature/index.html b/mail_signature/templates/mail_signature/index.html index d2f58072cfabd0fee25ade950bb5f52b1713d468..669b8596b8cf12925dadc37fcddd8183951fd58d 100644 --- a/mail_signature/templates/mail_signature/index.html +++ b/mail_signature/templates/mail_signature/index.html @@ -81,7 +81,7 @@ > </div> </div> - + <div class="my-4"> Do kaĹľdĂ©ho emailu doporuÄŤujeme zadat max. 3 odkazy. Do tÄ›ch se poÄŤĂtajĂ i ty na sociálnĂ sĂtÄ› v podpisu. @@ -176,7 +176,7 @@ class="border border-gray-200 p-2 rounded-md grow w-full" > </div> - + <div class="text-right"> <button id="generate" class="btn btn--icon" type="button"> <div class="btn__body-wrap"> @@ -188,7 +188,7 @@ </button> </div> </form> - + <div class="flex flex-col gap-3"> <section class="flex flex-col gap-4"> <div class="flex justify-between gap-3 items-center"> diff --git a/mail_signature/views.py b/mail_signature/views.py index 0d5779af8e0d1e7a2d10d8b77f249d64c18094e1..cd47b6caa95e1e66adc2a8f00f14c425525cd7ad 100644 --- a/mail_signature/views.py +++ b/mail_signature/views.py @@ -2,8 +2,6 @@ from django.shortcuts import render # Create your views here. + def index(request): - return render( - request, - "mail_signature/index.html" - ) + return render(request, "mail_signature/index.html") diff --git a/manage.py b/manage.py index 3580e5f0549d0ba103b3a3c2049567f192de6b13..6652229bd5ecd1ae4a3a264cad4cb750773d5524 100755 --- a/manage.py +++ b/manage.py @@ -6,7 +6,7 @@ import sys def main(): """Run administrative tasks.""" - os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'rybicka.settings') + os.environ.setdefault("DJANGO_SETTINGS_MODULE", "rybicka.settings") try: from django.core.management import execute_from_command_line except ImportError as exc: @@ -18,5 +18,5 @@ def main(): execute_from_command_line(sys.argv) -if __name__ == '__main__': +if __name__ == "__main__": main() diff --git a/member_group_size_calc/views.py b/member_group_size_calc/views.py index cda6c837076ea8d41bc9964fe97184b87c780cef..8c388f3a6442672c0f0546ae08500a4592ff9199 100644 --- a/member_group_size_calc/views.py +++ b/member_group_size_calc/views.py @@ -2,8 +2,6 @@ from django.shortcuts import render # Create your views here. + def index(request): - return render( - request, - "member_group_size_calc/index.html" - ) + return render(request, "member_group_size_calc/index.html") diff --git a/requirements/production.txt b/requirements/production.txt index 9655c9a0a7bb5c95b0bd3a2f3d344abbb9a9269e..ce5169e4440b67843ee5d28199ed63e0d8323cfc 100644 --- a/requirements/production.txt +++ b/requirements/production.txt @@ -1,2 +1,2 @@ -gunicorn==20.1.0 +gunicorn==20.1.0 whitenoise==6.3.0 diff --git a/rv_voting_calc/templates/rv_voting_calc/index.html b/rv_voting_calc/templates/rv_voting_calc/index.html index a6abb1284c12848f25c0a254150255b7a4d48b21..bc3177a02775073e1dfee9a310f4598a8f8c1739 100644 --- a/rv_voting_calc/templates/rv_voting_calc/index.html +++ b/rv_voting_calc/templates/rv_voting_calc/index.html @@ -56,7 +56,7 @@ {% endfor %} </ul> </div> - + <div> <div class="flex items-center gap-3 justify-between mb-5"> <h2 class="text-2xl font-bebas">VĂ˝sledky</h2> @@ -76,7 +76,7 @@ class="flex flex-col gap-5" id="result" > - + </ul> <div class="mt-4 flex gap-4 md:justify-end justify-center"> <a @@ -97,7 +97,7 @@ </main> {{ keyed_rv_members|json_script:"rv-members" }} - + <script> const VOTE_CALCULATION_ENDPOINT = "{% url "rv_voting_calc:get_calculated_votes" %}" diff --git a/rv_voting_calc/templatetags/index.py b/rv_voting_calc/templatetags/index.py index d20f7e2cdf360fcea86219b84130c7f5499efab5..262de0b459117db6e77e3842ced9ba0bea562342 100644 --- a/rv_voting_calc/templatetags/index.py +++ b/rv_voting_calc/templatetags/index.py @@ -1,4 +1,5 @@ from django import template + register = template.Library() # https://stackoverflow.com/a/29664945 diff --git a/rv_voting_calc/urls.py b/rv_voting_calc/urls.py index 7f3f506150c7e427ab27b88ba35abad1f15f5bf6..54329eaa8cb0008774d6b9cf3302066cde1a918b 100644 --- a/rv_voting_calc/urls.py +++ b/rv_voting_calc/urls.py @@ -5,9 +5,5 @@ from . import views app_name = "rv_voting_calc" urlpatterns = [ path("", views.index, name="index"), - path( - "calculated-votes", - views.get_calculated_votes, - name="get_calculated_votes" - ) + path("calculated-votes", views.get_calculated_votes, name="get_calculated_votes"), ] diff --git a/rv_voting_calc/views.py b/rv_voting_calc/views.py index 05261f0aa3e0004bc1e0bfb808989fbfb6b912f2..85c11c65d3ef10b6e53fed191a353cbd4e4340e7 100644 --- a/rv_voting_calc/views.py +++ b/rv_voting_calc/views.py @@ -8,15 +8,13 @@ import urllib.parse import gql import requests - -from gql.transport.exceptions import TransportQueryError -from gql.transport.requests import RequestsHTTPTransport - from django.conf import settings from django.http import HttpResponse, JsonResponse from django.shortcuts import render from django.template.loader import render_to_string from django_http_exceptions import HTTPExceptions +from gql.transport.exceptions import TransportQueryError +from gql.transport.requests import RequestsHTTPTransport def get_options_by_member(source, rv_members) -> dict: @@ -75,7 +73,7 @@ def index(request): "rv_members": rv_members, "keyed_rv_members": keyed_rv_members, "options_by_member": options_by_member, - } + }, ) @@ -143,7 +141,7 @@ def convert_rv_members_to_dict(source: list) -> dict: # Convert to username: {data} rv_members[member["username"]] = { "displayName": member["displayName"], - "officialLastName": member["officialLastName"] + "officialLastName": member["officialLastName"], } return rv_members @@ -218,7 +216,7 @@ def do_step_b_through_d( "options": options, "options_by_member": options_by_member, "options_with_support_count": options_with_support_count, - "rv_members": rv_members + "rv_members": rv_members, } html_steps.append( @@ -237,7 +235,7 @@ def do_step_b_through_d( ) # Delete options without support and those marked for deletion. - for option_key in (options_without_support + options_marked_for_deletion): + for option_key in options_without_support + options_marked_for_deletion: options.pop(option_key, None) # If no options remain, show that there are no winners and end everything. @@ -266,8 +264,7 @@ def do_step_b_through_d( # Sort options by their vote count. options = { key: value - for key, value - in sorted( + for key, value in sorted( options.items(), reverse=True, key=lambda option: option[1]["vote_count"], @@ -315,7 +312,7 @@ def do_step_b_through_d( # randomly eliminate one and continue to the next iteration. elif winner_count == len(options) and ticket_count_same: eliminated_winner = random.choice(winning_option_keys) - + options[eliminated_winner]["marked_for_deletion"] = True context = { @@ -325,7 +322,7 @@ def do_step_b_through_d( "options": options, "options_by_member": options_by_member, "rv_members": rv_members, - "randomly": True + "randomly": True, } html_steps.append( @@ -352,8 +349,7 @@ def do_step_b_through_d( # Sort options by their vote count, with lowest ranking ones first. options = { key: value - for key, value - in sorted( + for key, value in sorted( options.items(), key=lambda option: option[1]["vote_count"], ) @@ -404,9 +400,7 @@ def do_step_b_through_d( else: # If there are multiple losing options, order them by the amount of # ticket votes they have. - losing_option_keys.sort( - key=lambda key: options[key]["ticket_count"] - ) + losing_option_keys.sort(key=lambda key: options[key]["ticket_count"]) # Delete the vote with the least ticket votes. There maybe more, but # those should be taken care of in the next iteration. @@ -517,10 +511,9 @@ def get_calculated_votes(request): continue # Add this vote to the option's ticket votes. - options[option]["ticket_votes"].append({ - "member": member, - "other_acceptable": selected_options[1:] - }) + options[option]["ticket_votes"].append( + {"member": member, "other_acceptable": selected_options[1:]} + ) # Increase the vote and ticket vote counters. options[option]["ticket_count"] += 1 options[option]["vote_count"] += 1 @@ -555,8 +548,7 @@ def get_calculated_votes(request): # This is purely for aesthetic purpose. options = { key: value - for key, value - in sorted( + for key, value in sorted( options.items(), reverse=True, key=lambda option: option[1]["has_support"], @@ -568,7 +560,7 @@ def get_calculated_votes(request): "options_by_member": options_by_member, "rv_members": rv_members, "total_ticket_count": total_ticket_count, - "has_support_treshold": has_support_treshold + "has_support_treshold": has_support_treshold, } html_steps.append( @@ -598,8 +590,8 @@ def get_calculated_votes(request): request.COOKIES.get( "seed", # If neither are set, generate a default. - base64.b64encode(secrets.token_bytes()).decode("utf-8") - ) + base64.b64encode(secrets.token_bytes()).decode("utf-8"), + ), ) # Unquote the seed if it was found in the URL parameters @@ -630,10 +622,7 @@ def get_calculated_votes(request): response = render( request, "rv_voting_calc/combined_steps.html", - { - "html_steps": "\n".join(html_steps), - "md_steps": md_steps - } + {"html_steps": "\n".join(html_steps), "md_steps": md_steps}, ) # Set the random seed cookie to the one used in the calculation. @@ -644,4 +633,4 @@ def get_calculated_votes(request): return response # Step E - iteration += 1 + iteration += 1 diff --git a/rybicka/asgi.py b/rybicka/asgi.py index d7176f09847deda16890a1396a0d4a399514a0dc..851133e205c80ad01650d5120324f179fcb15f90 100644 --- a/rybicka/asgi.py +++ b/rybicka/asgi.py @@ -11,6 +11,6 @@ import os from django.core.asgi import get_asgi_application -os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'rybicka.settings') +os.environ.setdefault("DJANGO_SETTINGS_MODULE", "rybicka.settings") application = get_asgi_application() diff --git a/rybicka/settings/base.py b/rybicka/settings/base.py index ba1cefd3c84b3030936c968766a7a54129b4de38..b65109ab10fab132637758cddfa60ec48380e1eb 100644 --- a/rybicka/settings/base.py +++ b/rybicka/settings/base.py @@ -37,7 +37,7 @@ STATIC_ROOT = os.path.join(BASE_DIR, "staticfiles") # Server -SECURE_PROXY_SSL_HEADER = ('HTTP_X_FORWARDED_PROTO', 'https') +SECURE_PROXY_SSL_HEADER = ("HTTP_X_FORWARDED_PROTO", "https") # Application definition @@ -46,14 +46,11 @@ INSTALLED_APPS = [ "django.contrib.sessions", "django.contrib.messages", "django.contrib.staticfiles", - "webpack_loader", - "shared", "member_group_size_calc", "rv_voting_calc", "mail_signature", - "instagram_token", "asset_server_resize", ] @@ -64,7 +61,6 @@ MIDDLEWARE = [ "django.middleware.csrf.CsrfViewMiddleware", "django.contrib.messages.middleware.MessageMiddleware", "django.middleware.clickjacking.XFrameOptionsMiddleware", - "django_http_exceptions.middleware.ExceptionHandlerMiddleware", "django_http_exceptions.middleware.ThreadLocalRequestMiddleware", ] @@ -92,9 +88,7 @@ WSGI_APPLICATION = "rybicka.wsgi.application" # Database # https://docs.djangoproject.com/en/4.1/ref/settings/#databases -DATABASES = { - "default": dj_database_url.config(conn_max_age=600) -} +DATABASES = {"default": dj_database_url.config(conn_max_age=600)} # Internationalization # https://docs.djangoproject.com/en/4.1/topics/i18n/ @@ -126,11 +120,10 @@ WEBPACK_LOADER = { # Chobotnice -CHOBOTNICE_API_URL=env.str( - "CHOBOTNICE_API_URL", - "https://chobotnice.pirati.cz/graphql/" +CHOBOTNICE_API_URL = env.str( + "CHOBOTNICE_API_URL", "https://chobotnice.pirati.cz/graphql/" ) -CHOBOTNICE_RV_GID=env.str("CHOBOTNICE_RV_GID") +CHOBOTNICE_RV_GID = env.str("CHOBOTNICE_RV_GID") # Instagram diff --git a/rybicka/settings/dev.py b/rybicka/settings/dev.py index edd6357947baed734c59fdbed1a94a66d4e07e55..9b4f60127707e4e472aa101aacfdd3ea61fb8c43 100644 --- a/rybicka/settings/dev.py +++ b/rybicka/settings/dev.py @@ -7,4 +7,4 @@ what! from .base import * -DEBUG = True +DEBUG = True diff --git a/rybicka/urls.py b/rybicka/urls.py index 55d8d71adbb991d3b0bf44604b7f41ecc70991b8..1ddf91e069fa46fac44d2a45a5cdec2239df044f 100644 --- a/rybicka/urls.py +++ b/rybicka/urls.py @@ -19,7 +19,6 @@ urlpatterns = [ path("vypocet-skupiny-clenu/", include("member_group_size_calc.urls")), path("hlasovani-rv/", include("rv_voting_calc.urls")), path("emailove-podpisy/", include("mail_signature.urls")), - path("instagram/", include("instagram_token.urls")), path("asset-server/", include("asset_server_resize.urls")), path("", include("shared.urls")), ] diff --git a/shared/static/shared/instagram.webp b/shared/static/shared/instagram.webp deleted file mode 100644 index 014dc7e491ad8fc32c381fc2d5d907d15d52f1a3..0000000000000000000000000000000000000000 Binary files a/shared/static/shared/instagram.webp and /dev/null differ diff --git a/shared/templates/shared/index.html b/shared/templates/shared/index.html index c4650c5ea643b15d27e670b5b8b901affdb553d1..680242ceb6d3e01e6f892fd117de382fc69c626a 100644 --- a/shared/templates/shared/index.html +++ b/shared/templates/shared/index.html @@ -77,27 +77,6 @@ </div> </li> - <li class="card"> - <a href="{% url "instagram_token:index" %}" target="_blank"> - <img - src="{% static "shared/instagram.webp" %}" - alt="KalkulaÄŤka pĹ™ĂstupovĂ˝ch tokenĹŻ do Instagramu" - class="w-full h-48 object-cover" - > - </a> - <div class="p-4"> - <h2 class="mb-2 text-xl font-bold"> - <a href="{% url "instagram_token:index" %}" target="_blank"> - KalkulaÄŤka pĹ™ĂstupovĂ˝ch tokenĹŻ do Instagramu - </a> - </h2> - <div class="font-light text-sm break-words"> - PĹ™ihlášenĂm svĂ˝m účtem zĂskáš pĹ™ĂstupovĂ© Ăşdaje, kterĂ© mĹŻĹľeš vyuĹľĂt pro - synchronizaci obsahu na domovskĂ© stránce pirati.cz. - </div> - </div> - </li> - <li class="card"> <a href="{% url "asset_server_resize:index" %}"> <img diff --git a/shared/views.py b/shared/views.py index e2cf407c9e85695afc70aca11b3244284e637032..01fd9c4185b84345f3beb8e8d3ae7d8a2d71e757 100644 --- a/shared/views.py +++ b/shared/views.py @@ -2,8 +2,6 @@ from django.shortcuts import render # Create your views here. + def index(request): - return render( - request, - "shared/index.html" - ) + return render(request, "shared/index.html") diff --git a/static_src/asset_server_resize.js b/static_src/asset_server_resize.js index 275bb403c62b8fca0fd68ef2108d35cb9c6c76f8..a3092c89ff78de16121e53ff5af7cfad5c2d7d0c 100644 --- a/static_src/asset_server_resize.js +++ b/static_src/asset_server_resize.js @@ -8,7 +8,7 @@ $(window).ready( event.preventDefault(); const form = $("#asset-info-form")[0]; - + if (!form.checkValidity()) { form.reportValidity(); return; diff --git a/static_src/mail_signature.js b/static_src/mail_signature.js index e04014ab9d04360d287b456a29e380678425d5df..8c75f152a8fd35bc25d2994d6dff56276d8f3f14 100644 --- a/static_src/mail_signature.js +++ b/static_src/mail_signature.js @@ -67,17 +67,17 @@ const generateSignature = () => { <strong style="font-size:13pt;font-weight:bold">${name}</strong>`; func = escapeHTML(func); - + let funcMultiline = ""; - + for (const line of func.split("\n")) { funcMultiline += `${line}<br>`; } - + if (func !== "") { result += `<br>${funcMultiline}`; } - + result += "</div>"; } @@ -85,44 +85,44 @@ const generateSignature = () => { let email = escapeHTML($("#email").val()); let phone = escapeHTML($("#phone").val()); - + let web = escapeHTML($("#web").val()); let mastodon = escapeHTML($("#mastodon").val()); let twitter = escapeHTML($("#twitter").val()); let instagram = escapeHTML($("#instagram").val()); let linkedin = escapeHTML($("#linkedin").val()); let fejsbuk = escapeHTML($("#fejsbuk").val()); - + const containsExternalLinks = (web !== "" || mastodon !== "" || twitter !== "" || instagram !== "" || linkedin !== "" || fejsbuk !== ""); - + if (email !== "" || phone !== "" || containsExternalLinks) { result += "<div style=\"margin-bottom:0.75em;line-height:1.1em\">"; - + if (email !== "") { result += `<div style="margin-bottom:0.25em"> <img style="display:inline-block" src="${(!useExternalImages) ? emailDataURL : emailImageURL}" title="E-mail" width="15"> <span style="color:black">${email}</span> </div>`; } - + if (phone !== "") { phone = phone.replace(" ", ""); let phoneGroups = phone.match(/.?.?.?/g); - + const formattedBasePhone = phoneGroups.join(" "); const prefix = $("#phone-prefix").val(); - + result += `<div style="margin-bottom:0.25em"> <img style="display:inline-block" src="${(!useExternalImages) ? phoneDataURL : phoneImageURL}" title="TelefonnĂ ÄŤĂslo" width="11"> <span style="color:black">${prefix} ${formattedBasePhone}</span> </div>`; } - - + + if (containsExternalLinks) { result += "<div style=\"margin-top:1.25em;display:flex;column-gap:0.2em\">"; } - + if (web !== "") { result += `<a href="${web}"> <img @@ -133,7 +133,7 @@ const generateSignature = () => { > </a>`; } - + if (mastodon !== "") { result += `<a href="${mastodon}"> <img @@ -144,7 +144,7 @@ const generateSignature = () => { > </a>`; } - + if (twitter !== "") { result += `<a href="${twitter}"> <img @@ -155,7 +155,7 @@ const generateSignature = () => { > </a>`; } - + if (instagram !== "") { result += `<a href="${instagram}" @@ -168,7 +168,7 @@ const generateSignature = () => { > </a>`; } - + if (linkedin !== "") { result += `<a href="${linkedin}"> <img @@ -179,7 +179,7 @@ const generateSignature = () => { > </a>`; } - + if (fejsbuk !== "") { result += `<a href="${fejsbuk}"> <img @@ -190,12 +190,12 @@ const generateSignature = () => { > </a>`; } - + if (containsExternalLinks) { result += "</div>"; } - - + + result += "</div>"; } @@ -209,15 +209,15 @@ const generateSignature = () => { </div> </div> </div>`; - + result = result.replace(/\s\s+|\n|\r\n/g, " ").replace(/> </g, "><").replace(/;\s+/g, ";"); - + if (result.length > 10000) { $("#gmail-warning").removeClass("hidden"); } else if (!$("#gmail-warning").hasClass("hidden")) { $("#gmail-warning").addClass("hidden"); } - + $("#preview").html(result); $("#content").val(result); } @@ -230,22 +230,22 @@ $(window).ready( "click", event => { const form = $("#source")[0]; - + if (!form.checkValidity()) { form.reportValidity(); return; } - + generateSignature(); } ); - + $("#copy").on( "click", event => { if (navigator.clipboard.write) { // Chromium - + const type = "text/html"; const blob = new Blob([$("#content").val()], { type }); const data = [new window.ClipboardItem({ [type]: blob })]; @@ -264,18 +264,18 @@ $(window).ready( ); } else { // Firefox - + try { selectHTML("preview"); - + document.execCommand("copy"); - + alertify.success( "ZkopĂrováno do schránky." ); } catch (exception) { console.log("Error copying: ", exception); - + alertify.error( "Chyba pĹ™i kopĂrovánĂ do schránky. ProsĂm, zkopĂruj text manuálnÄ›." ); diff --git a/static_src/rv_voting_calc.js b/static_src/rv_voting_calc.js index 828ba0e3e8f8ab7202ca7e1634c103372a4a53b4..5821b612a26386a8cdaeb97e2ffaab96129a5854 100644 --- a/static_src/rv_voting_calc.js +++ b/static_src/rv_voting_calc.js @@ -43,7 +43,7 @@ $(window).ready( // Keep user-defined ordering. This is imperative! // http://github.com/select2/select2/issues/3106 - Thanks to kevin-brown! const element = $(event.params.data.element); - + element.detach(); $(this).append(element); $(this).trigger("change"); diff --git a/tailwind.config.js b/tailwind.config.js index c4aec83d8bf1f089ffffbc008b7825eeb011463c..689576f4a063f1736155aff77c3d3d3f48b9738c 100644 --- a/tailwind.config.js +++ b/tailwind.config.js @@ -15,6 +15,6 @@ module.exports = { }, }, plugins: [ - require("@tailwindcss/typography"), + require("@tailwindcss/typography"), ], }