From 2ff0bb04bdd9d1d106a4b98e9d7c69a834ebccf3 Mon Sep 17 00:00:00 2001 From: Jonathan Carter Date: Wed, 18 Dec 2024 18:17:24 +0200 Subject: [PATCH] Some more initial UI work, initial translation support --- README.md | 22 ++++++------ src/applets/disks/disks.html | 4 ++- .../users/__pycache__/routes.cpython-312.pyc | Bin 680 -> 2382 bytes src/applets/users/routes.py | 21 ++++++++--- src/applets/users/users.html | 28 ++++++++------- .../__pycache__/routes.cpython-312.pyc | Bin 1803 -> 3458 bytes src/applets/welcome/routes.py | 33 ++++++++++++++++-- src/applets/welcome/welcome.html | 22 +++++++----- src/static/system-installer.css | 14 +------- src/system-installer-daemon | 14 ++++++-- src/system-installer-web-client | 2 +- src/templates/header.html | 12 ++++--- src/templates/layout.html | 10 +++--- 13 files changed, 116 insertions(+), 66 deletions(-) mode change 100644 => 120000 src/static/system-installer.css diff --git a/README.md b/README.md index 8b37084..31e0a7d 100644 --- a/README.md +++ b/README.md @@ -1,20 +1,20 @@ -Dependencies +# Welcome + +Welcome to System Installer, a powerful toolkit for setting up an installer for operating systems. + +Dependencies: - flask - - flask-babel - pytest - coverage - - libjs-htmx - - libjs-material-design-lite - - xapp-gtk3-module + - libxapp-gtk3-module + - gettext +Recommended: + - libjs-htmx (needed if the web front-end is to be used) + - sass-stylesheets-bulma (needed if the web front-end is to be used) ## Development ### Translations -Upstream PyBabel documentation: -https://python-babel.github.io/flask-babel/index.html#translating-applications - -in the ./daemon directory, run the following to regenerate the translations file: - -```pybabel extract -F babel.cfg -o messages.pot .``` +-- TODO -- diff --git a/src/applets/disks/disks.html b/src/applets/disks/disks.html index 1cb217f..2e0af87 100644 --- a/src/applets/disks/disks.html +++ b/src/applets/disks/disks.html @@ -26,7 +26,9 @@

Proposed layout:

- +
+ +
diff --git a/src/applets/users/__pycache__/routes.cpython-312.pyc b/src/applets/users/__pycache__/routes.cpython-312.pyc index 6f7cf214bd51b62fc6540ebb2dbf289329e1a672..4c06c18f72826bbe0e9de4a4f57a841cbf29b645 100644 GIT binary patch literal 2382 zcmZ`*&2Jl35Pxg0KezdEnxv#(OPa=U+SqVGqDpe0C2iEwRy4i%Vy${Pa^aOUxZJ5z#M-E%mFfxAz8?l%96zSm=&|*<+v@EWjj$$*vWFzPL)%3 zx}3H%<&2#zXN6uI^pvt9p%}u_qcfrNleZxsO8u3Qc!~}OKzZzc^^-&WR78K=NIym8 ziM>oA`zQBNkb+pXSx5(oO-rMXgA~D^d6=>wMKPtO>jY_n4U=FUL>{p!HJ1bv1Um*M z6^8Amr7;{NYGB+5G9OtUZW7aB;8xK+0(z{XHJg62FqEek; z?5J=cl{K)si>sbl6nK!le(&z)*3Dp|Zn;&>s!+_B>C|bEwlt^iX?5&p#es?qW?L^~ zfz0KBLKz&sUNKCa6=ZS>LJ5+(>(tD8FbUo*qte%~On7GiCR0EtKd-9(yInFgrj;JK zj>a0AQ!?-lwn`1N-q>+12Ah`X9)+B*nhs@}Wnlsa*mj)~C3*?cY+*+Gi7pY>W0)43 zdqF?Y3UOUV=3t{V-|+(=E%bL5otpbqIp0yvKWlW9e0%xBj&kjXYaL~?b)%PC=;jt% zw|mO`v$b!HAC+H}J8k*SF<2shX0Q!Uf}`1ZRc~PZ@f+96^~Ckcz#O1GsSxuQMS8Du zU3EvZOv7Y*s#{Y-Hv;xcYfV*$f}-mS4Qw@4ldje@)A9&j*w}J}-OysK)ZBQ9$UN*p zc-N3wAi=l@rxLm)XF-^QALZ52LPv1!b)o)7#5`IN@dk9-0Wx`s4SEhrPdXg%`%s2! zpc=vA5lkMz5)mvpf~6u@dIZZvu(!=hio{TB4k-@z;oO^TW7 zHC4?4Et8p=C2qbLObwRej$sge&iu@#2fN&bY78ZgY?5ei3S;74npY9Z}a`a z^5B7JJ5XU-)xyE_P^~f)`WN0Za9kEKnmaK9AYzz*%aC9QV+W31-Rq}B^mLFr@epeG zH@0Ce4WqO@%G4@WT?dAhON^_kbuzT*nXAlach zPd0NQ(1uG`Fcpd`AQK|^a!8eeM5dvVDDOB`v^1FkRuJCm^d}(D$7wV@0~0F0+%DYe z=C@k6+mn|%@?!6z`r_>KFIu<1Q9ANDzM6mjBwQ6%+E;FN3%9uP<&M16TP?Or_qwb1 zxuDRIS9;5Z_R53q@-`PNcI3;wl`HM5q`N}7V5uYLdlxRg$Ue8hW40ro?JdFJT*sA`Jf_!d*YGU7L5g6=lT52X zj^dIe{f;iaj!DvcuMv=APX0+E>B3PG#j>s3S7*LF^YwC9ntl~aN}ou_aTGg!B-o?e bP@$cDw<|5YipkPCSGaT}xbaD8PMr8ZJuP<# delta 300 zcmX>nw1SoIG%qg~0}yaBJWk_aoX97^m@!e^l8uQWl`%_fav`IzH1ldkkOBsV6qXi- z)et5_6i+3qCfmeoF_Rq`Mb(*sq9FWP0!U0}D1mAKYGH(F4rb6~ntYN`U8;(!v^ce> zSTCa_H%F7Ph!dz|CBtVR$uK#MDOp7T$Y2BFVtyde!0?5Ofk%3V&1G(l3oIH%d_XZj zP2S1z9Bz5HSc~#YOHzwK8j5&91W2|Br0o`mO>TZlX-=wLkqD3ra!s)rkodsN$jEq? wLH;`vBcs801|abnM10_2VB%^JYL{q~=+L;#DEyI$g;Db}GXs+dm<2W$0E7-ZZ~y=R diff --git a/src/applets/users/routes.py b/src/applets/users/routes.py index 1126a58..3992633 100644 --- a/src/applets/users/routes.py +++ b/src/applets/users/routes.py @@ -1,11 +1,24 @@ from applets.software import bp from flask import Flask, request, session, redirect, \ url_for, render_template, flash, Blueprint +# we use this neat little trick to get config data from the main app +from flask import current_ap -@bp.route('/users') -def users_root(): +def build_stringlist(): """ - Users screen for the webui. + Return all the strings that is used in this applet. """ - return render_template('users.html') + string_dict = {} + string_dict['initial_user_text'] = _("Let's set up an initial user.") + string_dict['full_name'] = _("Full Name") + string_dict['user_name'] = _("Username") + string_dict['user_name_available'] = _("This username is available") + string_dict['user_name_not_available'] = _("This username is not available") + string_dict['user_name_reserved'] = _("This username is reserved by the system") + string_dict['user_name_characters'] = _("The username must be one word, lowercase, with no special characters") + string_dict['password'] = _("Password") + string_dict['password_confirm'] = _("Password (confirm)") + string_dict['password_nomatch'] = _("These passwords do now match") + string_dict['password_tooshort'] = _("This password is too short") + return string_dict diff --git a/src/applets/users/users.html b/src/applets/users/users.html index c8aa0c6..b3522e4 100644 --- a/src/applets/users/users.html +++ b/src/applets/users/users.html @@ -1,7 +1,7 @@ {% extends "layout.html" %} {% block body %} -

Let's set up an initial user.

+

{{ string_dict['initial_user_text'] }}


@@ -10,14 +10,14 @@
-
+
- +
- + @@ -25,20 +25,22 @@
-

This username is available

-
- -
- -
- +
+

{{ string_dict['user_name_available'] }}

- +
- + +
+
+ +
+ +
+
diff --git a/src/applets/welcome/__pycache__/routes.cpython-312.pyc b/src/applets/welcome/__pycache__/routes.cpython-312.pyc index f65f4b4f5e5d24dab8cb3155308112fa58afc121..5203f8d3fb1c8b45ddf22063e721bbfd772a4f65 100644 GIT binary patch literal 3458 zcmb_eO>7&-72YM6c_NC2roffz|Ig?;F)Irdug5N;?y!ju6D^wgVEwFuf%-|UafsD+yV zU4X;)=6mnWo7s8azCX6Nw{h@%@VZ+3Oysz~FeQ9qfpG8ygl$gaG~VD$KF9M+ju;U$ znv0r3PB3G+m>JK-%|tF?iaF6t=8|SxuFbQHf}NC;JXtX0oD9B#(QbC+I$$pLE|=?! zaHvy@Kj!`Qcn)-aRS8ya`O^|bP7^=opClhg{AsQ2UG8yUk?YnZh}N?%WaPiHxeQMu z%jJwnV>5LIs1JlUK{-`9hGlmqr}MDEtn}Fl=+qA+{Q1>{$ha#%mERy1^Cs zC&FXFpWNg(_|@>_Ta3e9@*LnT^P#vIS&wDn)zfVXJPXJnilJJ?idsYpY)f%UI#D27 z138`rP2599!8TDfJ(cz6Nj8|u8g@Z75LwJbsJNmU#5wh=?#aAk((81Q-4zVQg0%M5fB?R3^yDhneC*SdHCp@;w-8+}}m6 z_l3RGn421Vv|c~=M*a4kx^C7>)^5tK&Fu?ad%~bA4DJfY_Ql>kamW>i9$Y#ASB^%I zRTaYng6&1GURk8V%^M4gG{CP*o1NX{zLy2Jn(Z9N^+&UekfR z+X*s&#F6Gzen!Tu>}cFCNGbsTnN)zF1j`;!u&oun=&=Khd7MsT23a=NXt$vgCr=7Q z&jTaruu>#hh_vJo52Xia}5#bX7)Fg9a=X>uwcxR{o^TdgLsr$pF?K=2+7W+Dr}arAFP<=%bRG%GS?b za#NRoKkcUGw_aU;1WNO{srRI_^rxcS^2wx<3AjD@}ho?MgE>SiE~rKIzIQ z8}exFO0#FA(Q~Rc+mw#&T>S0N>$l$Cm6qzl5@u!bH3DT9ll>0P!ZB@gIwO|DZ>q+J zrMm(Bh(}Y;uxJY=9Km8OSo{cb*?=sR zITcoQrfCOMy5Y&bMcX2fh>`;q0q2lVJcuSQtzdmkg$9O3)RpSM6{`ppUQ))dSq{R` znm|*d8X0^HjG(rhy@SgZCQ8Z1DfC50_s zP<^Lc2@uHdV5o6VMK09`bv1IbeyY?M z(QC86=x~J-o<7?cnG5xkryl+IlZ&8rx`NU?HCiA0e&f_Dwb^=?;tDS|0lxFe4+D6= ztEYCY**~x&ePGqDZD|i~fKng)PNV-^pr()2UpU`LUjVh}3jIx{UudMi+p53ZNS_b% z{S)I5T5^SA3gYk@H9VLUd*tcSr8 z8yLf5_Hm?1%`~SxTE}PDBx?p~%xe`r_Vv#0H=MV+PtoG5rma;BbP-<$TSg`1HVjXr zJkNi@4SyBk`LkbfFdVSqA90Q!{u9^n1(*I?JkB5gvWw%}w-$G~oZNDqITKZtUX3r~GPD2_`jdlP3Ns5+agXtso-3RBs|egUGfJVrPw8HyhZUYAq?Y zQfNUhWkkGq@nlKBgBSk5o7dSl@xs2Yt03yj z$8zmn2;kVi3`-s~J-%C*J*ycS0V3J4x^CzQFqqo%1p6(evLO;C5h4?%hTGAWQ1Q!1 zn2F^JY&x7#0y0{@=#z_T4T$y$wPP*ZClY-NTKyJ`B#CcvPuO$3 zFsTnVE0#mdRW~QzHJ?xrumOK#peLEFWR$Kp*9pz_fbA;d_&u<;@-ET@kwE);6wRYc zMZ{6XP5Y}zz!ni12|olx4%i%D^Wy^Y;{#pRkwskusdl+^1b+Y>q6 zF)`;Fb*qkNSELeo!Crt;mi?=ZX~zIHpg}@|IA(QqM1KfMt4w80(|47-;StgGzjz$k4LEr diff --git a/src/applets/welcome/routes.py b/src/applets/welcome/routes.py index 6cbc542..00686ed 100644 --- a/src/applets/welcome/routes.py +++ b/src/applets/welcome/routes.py @@ -1,12 +1,21 @@ from applets.welcome import bp from flask import Flask, request, session, redirect, \ url_for, render_template, flash, Blueprint +# we use this neat little trick to get config data from the main app +from flask import current_app import gettext import dmm.lsblk as lsblk # Set up Gettext -en_i18n = gettext.translation("welcome", './locales', fallback=True, languages=['af', 'en']) -en_i18n.install() +def set_language(LANG): + """ + Sets language for this applet + """ + translations = gettext.translation("welcome", './applets/welcome/locales', fallback=True, languages=[LANG]) + translations.install() + _ = translations.gettext + +set_language('en') @bp.route('/welcome',methods=['GET', 'POST', 'PUT']) def welcome_index(): @@ -14,9 +23,20 @@ def welcome_index(): The page you'd get if you access the root of this app in a browser. """ + if request.method == 'POST': + if "lang" in request.form.keys(): + current_app.config['CONFIG']['global_settings']['language'] = request.form["lang"] + LANG = current_app.config['CONFIG']['global_settings']['language'] + set_language(LANG) + FORMLANG = request.form["lang"] + if "keyboard" in request.form.keys(): + print(request.form["keyboard"]) + if "timezone" in request.form.keys(): + print(request.form["timezone"]) + lang = current_app.config['CONFIG']['global_settings']['language'] blkid = lsblk.list_scsi_devices() string_dict = build_stringlist() - return render_template('welcome.html', string_dict=string_dict) + return render_template('welcome.html', string_dict=string_dict, selected_lang=lang) def build_stringlist(): @@ -29,5 +49,12 @@ def build_stringlist(): string_dict['language_text'] = _("Language:") string_dict['keylayout_text'] = _("Keyboard Layout:") string_dict['timezone_text'] = _("Time Zone:") + lang_dict = {} + lang_dict['af'] = _("Afrikaans") + lang_dict['en'] = _("English (International)") + lang_dict['en-us'] = _("English (United States)") + lang_dict['en-uk'] = _("English (United Kingdom)") + lang_dict['en-za'] = _("English (South Africa)") + string_dict['lang_list'] = lang_dict return string_dict diff --git a/src/applets/welcome/welcome.html b/src/applets/welcome/welcome.html index f1ac5ce..2653092 100644 --- a/src/applets/welcome/welcome.html +++ b/src/applets/welcome/welcome.html @@ -1,38 +1,43 @@ {% extends "layout.html" %} {% block body %} -Debian Image banner +Debian Image banner +

{{ string_dict['welcome_text'] }}

{{ string_dict['confirm_text'] }}

+
{{ string_dict['language_text'] }} - +

+
{{ string_dict['keylayout_text'] }} - +

+
{{ string_dict['timezone_text'] }}
diff --git a/src/static/system-installer.css b/src/static/system-installer.css deleted file mode 100644 index 69a3ff1..0000000 --- a/src/static/system-installer.css +++ /dev/null @@ -1,13 +0,0 @@ -body { - display: flex; - font-family: Noto Sans; - min-width: 1150px; - min-height: 600px; - overflow: hidden; -} - - -html { - /* Overwrite the white that is set by bulma.css */ - background-color: transparent; -} diff --git a/src/static/system-installer.css b/src/static/system-installer.css new file mode 120000 index 0000000..6db37bc --- /dev/null +++ b/src/static/system-installer.css @@ -0,0 +1 @@ +system-installer-dark.css \ No newline at end of file diff --git a/src/system-installer-daemon b/src/system-installer-daemon index 5e14a43..2acdc35 100755 --- a/src/system-installer-daemon +++ b/src/system-installer-daemon @@ -9,24 +9,32 @@ from waitress import serve import logging import dmm.lsblk as lsblk import importlib +import yaml # configuration VERSION = "0.00" -BABEL_TRANSLATION_DIRECTORIES="translations" -BABEL_DOMAIN="translations" SECRET_KEY = "exampls" DEV_MODE = True APPS = "main welcome users disks software summary" +CONFIGFILE="templates/dmm-installer-template.yaml" if DEV_MODE: print("Note: Starting in devmode!") DEBUG = True tracebacks = True +# import config +global config +config_contents = open(CONFIGFILE, "r") +config = yaml.safe_load(config_contents) + +print(type(config)) +print(config) + # create our application in flask app = Flask(__name__) app.config.from_object(__name__) - +app.config['CONFIG'] = config # Register blueprints here for APP in APPS.split(" "): diff --git a/src/system-installer-web-client b/src/system-installer-web-client index 8f832a4..e772577 100755 --- a/src/system-installer-web-client +++ b/src/system-installer-web-client @@ -14,7 +14,7 @@ def on_closed(): window = webview.create_window('System Installer', LOCATION, transparent=True, easy_drag=False, frameless=True, width=1050, focus=True, zoomable=True, - confirm_close=True) + confirm_close=True, resizable=True) window.events.closed += on_closed webview.start() diff --git a/src/templates/header.html b/src/templates/header.html index 0958aa4..abb84fc 100644 --- a/src/templates/header.html +++ b/src/templates/header.html @@ -1,14 +1,16 @@ -
- +
- - - + +
+ + +
+
diff --git a/src/templates/layout.html b/src/templates/layout.html index 34f980a..6797708 100644 --- a/src/templates/layout.html +++ b/src/templates/layout.html @@ -5,20 +5,22 @@ + - - -
+ +
{% include "header.html" %} -
+
{% block body %} {% endblock %}
{% include "footer.html" %} +
+