A lot of generalization for better scaling and overview

This commit is contained in:
Patrick Jentsch 2024-04-30 16:00:06 +02:00
parent 485a0155c6
commit 543276d766
23 changed files with 138 additions and 616 deletions

View File

@ -1,4 +1,4 @@
from apifairy import APIFairy # from apifairy import APIFairy
from config import Config from config import Config
from docker import DockerClient from docker import DockerClient
from flask import Flask from flask import Flask
@ -14,7 +14,7 @@ from flask_sqlalchemy import SQLAlchemy
from flask_hashids import Hashids from flask_hashids import Hashids
apifairy = APIFairy() # apifairy = APIFairy()
assets = Environment() assets = Environment()
db = SQLAlchemy() db = SQLAlchemy()
docker_client = DockerClient() docker_client = DockerClient()
@ -45,7 +45,7 @@ def create_app(config: Config = Config) -> Flask:
registry=app.config['NOPAQUE_DOCKER_REGISTRY'] registry=app.config['NOPAQUE_DOCKER_REGISTRY']
) )
apifairy.init_app(app) # apifairy.init_app(app)
assets.init_app(app) assets.init_app(app)
db.init_app(app) db.init_app(app)
hashids.init_app(app) hashids.init_app(app)

View File

@ -146,7 +146,8 @@ class User(HashidMixin, UserMixin, db.Model):
@password.setter @password.setter
def password(self, password): def password(self, password):
self.password_hash = generate_password_hash(password) #pbkdf2:sha256
self.password_hash = generate_password_hash(password, method='pbkdf2')
@property @property
def path(self) -> Path: def path(self) -> Path:

View File

@ -1,7 +1,7 @@
/* /*
* Spacing * Spacing
*/ */
$spacing-shortcuts: ("margin": "mg", "padding": "pd"); $spacing-shortcuts: ("margin": "m", "padding": "p");
$spacing-directions: ("top": "t", "right": "r", "bottom": "b", "left": "l"); $spacing-directions: ("top": "t", "right": "r", "bottom": "b", "left": "l");
$spacing-values: ("0": 0, "1": 0.25rem, "2": 0.5rem, "3": 0.75rem, "4": 1rem, "5": 1.5rem, "6": 3rem, "auto": auto); $spacing-values: ("0": 0, "1": 0.25rem, "2": 0.5rem, "3": 0.75rem, "4": 1rem, "5": 1.5rem, "6": 3rem, "auto": auto);

View File

@ -1,12 +0,0 @@
/*
* The sidenav-fixed class is used which causes the sidenav to be fixed and open
* on large screens and hides to the regular functionality on smaller screens.
* In order to prevent the sidenav to overlap the content, the content (in our
* case header, main and footer) gets an offset equal to the width of the
* sidenav.
*/
@media only screen and (min-width : 993px) {
header, main, footer {padding-left: 300px;}
.modal:not(.bottom-sheet) {left: 300px;}
.navbar-fixed > nav {width: calc(100% - 300px)}
}

View File

@ -1,482 +0,0 @@
/**************************
Utility Spacing Classes
**************************/
.m-0 {
margin: 0 !important;
}
.mt-0 {
margin-top: 0 !important;
}
.mr-0 {
margin-right: 0 !important;
}
.mb-0 {
margin-bottom: 0 !important;
}
.ml-0 {
margin-left: 0 !important;
}
.mx-0 {
margin-left: 0 !important;
margin-right: 0 !important;
}
.my-0 {
margin-top: 0 !important;
margin-bottom: 0 !important;
}
.m-1 {
margin: 0.25rem !important;
}
.mt-1 {
margin-top: 0.25rem !important;
}
.mr-1 {
margin-right: 0.25rem !important;
}
.mb-1 {
margin-bottom: 0.25rem !important;
}
.ml-1 {
margin-left: 0.25rem !important;
}
.mx-1 {
margin-left: 0.25rem !important;
margin-right: 0.25rem !important;
}
.my-1 {
margin-top: 0.25rem !important;
margin-bottom: 0.25rem !important;
}
.m-2 {
margin: 0.5rem !important;
}
.mt-2 {
margin-top: 0.5rem !important;
}
.mr-2 {
margin-right: 0.5rem !important;
}
.mb-2 {
margin-bottom: 0.5rem !important;
}
.ml-2 {
margin-left: 0.5rem !important;
}
.mx-2 {
margin-left: 0.5rem !important;
margin-right: 0.5rem !important;
}
.my-2 {
margin-top: 0.5rem !important;
margin-bottom: 0.5rem !important;
}
.m-3 {
margin: 0.75rem !important;
}
.mt-3 {
margin-top: 0.75rem !important;
}
.mr-3 {
margin-right: 0.75rem !important;
}
.mb-3 {
margin-bottom: 0.75rem !important;
}
.ml-3 {
margin-left: 0.75rem !important;
}
.mx-3 {
margin-left: 0.75rem !important;
margin-right: 0.75rem !important;
}
.my-3 {
margin-top: 0.75rem !important;
margin-bottom: 0.75rem !important;
}
.m-4 {
margin: 1rem !important;
}
.mt-4 {
margin-top: 1rem !important;
}
.mr-4 {
margin-right: 1rem !important;
}
.mb-4 {
margin-bottom: 1rem !important;
}
.ml-4 {
margin-left: 1rem !important;
}
.mx-4 {
margin-left: 1rem !important;
margin-right: 1rem !important;
}
.my-4 {
margin-top: 1rem !important;
margin-bottom: 1rem !important;
}
.m-5 {
margin: 1.5rem !important;
}
.mt-5 {
margin-top: 1.5rem !important;
}
.mr-5 {
margin-right: 1.5rem !important;
}
.mb-5 {
margin-bottom: 1.5rem !important;
}
.ml-5 {
margin-left: 1.5rem !important;
}
.mx-5 {
margin-left: 1.5rem !important;
margin-right: 1.5rem !important;
}
.my-5 {
margin-top: 1.5rem !important;
margin-bottom: 1.5rem !important;
}
.m-6 {
margin: 3rem !important;
}
.mt-6 {
margin-top: 3rem !important;
}
.mr-6 {
margin-right: 3rem !important;
}
.mb-6 {
margin-bottom: 3rem !important;
}
.ml-6 {
margin-left: 3rem !important;
}
.mx-6 {
margin-left: 3rem !important;
margin-right: 3rem !important;
}
.my-6 {
margin-top: 3rem !important;
margin-bottom: 3rem !important;
}
.m-auto {
margin: auto !important;
}
.mt-auto {
margin-top: auto !important;
}
.mr-auto {
margin-right: auto !important;
}
.mb-auto {
margin-bottom: auto !important;
}
.ml-auto {
margin-left: auto !important;
}
.mx-auto {
margin-left: auto !important;
margin-right: auto !important;
}
.my-auto {
margin-top: auto !important;
margin-bottom: auto !important;
}
.p-0 {
padding: 0 !important;
}
.pt-0 {
padding-top: 0 !important;
}
.pr-0 {
padding-right: 0 !important;
}
.pb-0 {
padding-bottom: 0 !important;
}
.pl-0 {
padding-left: 0 !important;
}
.px-0 {
padding-left: 0 !important;
padding-right: 0 !important;
}
.py-0 {
padding-top: 0 !important;
padding-bottom: 0 !important;
}
.p-1 {
padding: 0.25rem !important;
}
.pt-1 {
padding-top: 0.25rem !important;
}
.pr-1 {
padding-right: 0.25rem !important;
}
.pb-1 {
padding-bottom: 0.25rem !important;
}
.pl-1 {
padding-left: 0.25rem !important;
}
.px-1 {
padding-left: 0.25rem !important;
padding-right: 0.25rem !important;
}
.py-1 {
padding-top: 0.25rem !important;
padding-bottom: 0.25rem !important;
}
.p-2 {
padding: 0.5rem !important;
}
.pt-2 {
padding-top: 0.5rem !important;
}
.pr-2 {
padding-right: 0.5rem !important;
}
.pb-2 {
padding-bottom: 0.5rem !important;
}
.pl-2 {
padding-left: 0.5rem !important;
}
.px-2 {
padding-left: 0.5rem !important;
padding-right: 0.5rem !important;
}
.py-2 {
padding-top: 0.5rem !important;
padding-bottom: 0.5rem !important;
}
.p-3 {
padding: 0.75rem !important;
}
.pt-3 {
padding-top: 0.75rem !important;
}
.pr-3 {
padding-right: 0.75rem !important;
}
.pb-3 {
padding-bottom: 0.75rem !important;
}
.pl-3 {
padding-left: 0.75rem !important;
}
.px-3 {
padding-left: 0.75rem !important;
padding-right: 0.75rem !important;
}
.py-3 {
padding-top: 0.75rem !important;
padding-bottom: 0.75rem !important;
}
.p-4 {
padding: 1rem !important;
}
.pt-4 {
padding-top: 1rem !important;
}
.pr-4 {
padding-right: 1rem !important;
}
.pb-4 {
padding-bottom: 1rem !important;
}
.pl-4 {
padding-left: 1rem !important;
}
.px-4 {
padding-left: 1rem !important;
padding-right: 1rem !important;
}
.py-4 {
padding-top: 1rem !important;
padding-bottom: 1rem !important;
}
.p-5 {
padding: 1.5rem !important;
}
.pt-5 {
padding-top: 1.5rem !important;
}
.pr-5 {
padding-right: 1.5rem !important;
}
.pb-5 {
padding-bottom: 1.5rem !important;
}
.pl-5 {
padding-left: 1.5rem !important;
}
.px-5 {
padding-left: 1.5rem !important;
padding-right: 1.5rem !important;
}
.py-5 {
padding-top: 1.5rem !important;
padding-bottom: 1.5rem !important;
}
.p-6 {
padding: 3rem !important;
}
.pt-6 {
padding-top: 3rem !important;
}
.pr-6 {
padding-right: 3rem !important;
}
.pb-6 {
padding-bottom: 3rem !important;
}
.pl-6 {
padding-left: 3rem !important;
}
.px-6 {
padding-left: 3rem !important;
padding-right: 3rem !important;
}
.py-6 {
padding-top: 3rem !important;
padding-bottom: 3rem !important;
}
.p-auto {
padding: auto !important;
}
.pt-auto {
padding-top: auto !important;
}
.pr-auto {
padding-right: auto !important;
}
.pb-auto {
padding-bottom: auto !important;
}
.pl-auto {
padding-left: auto !important;
}
.px-auto {
padding-left: auto !important;
padding-right: auto !important;
}
.py-auto {
padding-top: auto !important;
padding-bottom: auto !important;
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.7 KiB

View File

@ -150,14 +150,14 @@ nopaque.App = class App {
M.CharacterCounter.init(document.querySelectorAll('input[data-length]:not(.no-autoinit), textarea[data-length]:not(.no-autoinit)')); M.CharacterCounter.init(document.querySelectorAll('input[data-length]:not(.no-autoinit), textarea[data-length]:not(.no-autoinit)'));
// Header navigation "more" Dropdown. // Header navigation "more" Dropdown.
M.Dropdown.init( // M.Dropdown.init(
document.querySelector('#nav-more-dropdown-trigger'), // document.querySelector('#nav-more-dropdown-trigger'),
{ // {
alignment: 'right', // alignment: 'right',
constrainWidth: false, // constrainWidth: false,
coverTrigger: false // coverTrigger: false
} // }
); // );
// Manual modal // Manual modal
M.Modal.init( M.Modal.init(

View File

@ -0,0 +1,26 @@
/*
* Fixed HTML Structure: https://materializecss.com/sidenav.html#variations
* The sidenav-fixed class is used which causes the sidenav to be fixed and open
* on large screens and hides to the regular functionality on smaller screens.
* In order to prevent the sidenav to overlap the content, the content (header, main and footer)
* gets an offset equal to the width of the sidenav.
*/
header, main, footer {
padding-left: 300px;
}
@media only screen and (max-width : 992px) {
header, main, footer {
padding-left: 0;
}
}
.navbar-fixed > nav {
width: calc(100% - 300px);
}
@media only screen and (max-width : 992px) {
.navbar-fixed > nav {
width: 100%;
}
}

View File

@ -9,8 +9,8 @@
*/ */
body { body {
display: flex; display: flex;
flex-direction: column;
min-height: 100vh; min-height: 100vh;
flex-direction: column;
} }
main { main {

View File

@ -2,9 +2,13 @@
font-family: 'Nopaque Icons'; font-family: 'Nopaque Icons';
font-style: normal; font-style: normal;
font-weight: 400; font-weight: 400;
/* For IE6-8 */
/* src: url("../font/NopaqueIcons-Regular.eot"); */
src: local('nopaque Icons'), src: local('nopaque Icons'),
local('NopaqueIcons-Regular'), local('NopaqueIcons-Regular'),
url(../fonts/nopaque_icons/NopaqueIcons-Regular.otf) format('opentype'); url("../font/NopaqueIcons-Regular.woff2") format('woff2'),
url("../font/NopaqueIcons-Regular.woff") format('woff'),
url("../font/nopaque_icons/NopaqueIcons-Regular.otf") format('opentype');
} }
.nopaque-icons { .nopaque-icons {

View File

@ -1,36 +1,48 @@
<div class="navbar-fixed"> <div class="navbar-fixed">
<nav> <nav>
<div class="nav-wrapper primary-color"> <div class="nav-wrapper primary-color">
{# menu icon #}
{# shown for small/medium devices #}
{% if current_user.is_authenticated %} {% if current_user.is_authenticated %}
<a href="#" data-target="sidenav" class="sidenav-trigger"><i class="material-icons">menu</i></a> <a href="#!" class="sidenav-trigger" data-target="sidenav"><i class="material-icons">menu</i></a>
{% endif %} {% endif %}
<a href="{{ url_for('main.index') }}" class="brand-logo" style="height: 100%; overflow: hidden;">
<img class="hide-on-med-and-up" src="{{ url_for('static', filename='images/nopaque_-_logo.svg') }}" style="height: 128px; margin-top: -32px; margin-left: -32px;"> {# nopaque logo+wordmark #}
<a href="{{ url_for('main.index') }}" class="brand-logo center" style="height: 100%;">
<img src="{{ url_for('static', filename='images/nopaque-logo+wordmark.png') }}" alt="" class="py-3" style="height: 100%;">
</a> </a>
<ul class="right hide-on-small-only">
<li> {# right items #}
<a class="dropdown-trigger no-autoinit" data-target="nav-more-dropdown" id="nav-more-dropdown-trigger"> {# shown on large devices #}
{% if current_user.is_authenticated %} <!--
<img src="{{ url_for('users.user_avatar', user_id=current_user.id) }}" class="left circle py-2 mr-1" style="height: 64px;"> <ul class="right hide-on-med-and-down" style="height: 100%;">
{% if current_user.is_authenticated %}
{# avatar, username and email #}
{# shown for authenticated users #}
{# <li style="height: 100%;">
<a href="#!" class="dropdown-trigger no-autoinit" data-target="nav-more-dropdown" id="nav-more-dropdown-trigger" style="height: 100%;">
<img src="{{ url_for('users.user_avatar', user_id=current_user.id) }}" alt="" class="left circle py-3 mr-1" style="height: 100%;">
{{ current_user.username }} ({{ current_user.email }}) {{ current_user.username }} ({{ current_user.email }})
{% else %}
<i class="material-icons left">more_vert</i>
{% endif %}
</a> </a>
</li> </li> #}
<li {% if request.path == url_for('settings.settings') %}class="active"{% endif %}><a href="{{ url_for('settings.settings') }}"><i class="material-icons left">settings</i>Settings</a></li>
<li><a href="{{ url_for('auth.logout') }}"><i class="material-icons left">logout</i>Log out</a></li>
{% else %}
{# log in and register items #}
{# shown for unauthenticated users on all devices #}
<li {% if request.path == url_for('auth.login') %}class="active"{% endif %}><a href="{{ url_for('auth.login') }}"><i class="material-icons left">login</i>Log in</a></li>
<li {% if request.path == url_for('auth.register') %}class="active"{% endif %}><a href="{{ url_for('auth.register') }}"><i class="material-icons left">assignment</i>Register</a></li>
{% endif %}
</ul> </ul>
-->
</div> </div>
</nav> </nav>
</div> </div>
{# {% if current_user.is_authenticated %}
<ul class="dropdown-content" id="nav-more-dropdown"> <ul class="dropdown-content" id="nav-more-dropdown">
{% if current_user.is_authenticated %}
<li><a href="{{ url_for('users.user', user_id=current_user.id) }}"><i class="material-icons left">person</i>My Profile</a></li>
<li><a href="{{ url_for('settings.settings') }}"><i class="material-icons left">settings</i>Settings</a></li> <li><a href="{{ url_for('settings.settings') }}"><i class="material-icons left">settings</i>Settings</a></li>
<li class="divider" tabindex="-1"></li> <li><a href="{{ url_for('auth.logout') }}"><i class="material-icons left">logout</i>Log out</a></li>
<li><a href="{{ url_for('auth.logout') }}">Log out</a></li>
{% else %}
<li><a href="{{ url_for('auth.register') }}"><i class="material-icons left">assignment</i>Register</a></li>
<li><a href="{{ url_for('auth.login') }}"><i class="material-icons left">login</i>Log in</a></li>
{% endif %}
</ul> </ul>
{% endif %} #}

View File

@ -1,36 +0,0 @@
<div id="roadmap-modal" class="modal">
<div class="modal-content">
<h2>Roadmap</h2>
<p>The roadmap guides you through nopaque's workflow! If you have the necessary input fie formats, you can directly jump into the corresponding process. If not, you can use the roadmap to jump right to the preceding process.</p>
<ul class="tabs tabs-fixed-width">
<li class="tab"><a{%if request.path == url_for('services.file_setup_pipeline') %} class="active"{% endif %} href="{{ url_for('services.file_setup_pipeline') }}" target="_self">File setup</a></li>
<li class="tab disabled"><i class="material-icons">navigate_next</i></li>
<li class="tab"><a{%if request.path == url_for('services.tesseract_ocr_pipeline') %} class="active"{% endif %} href="{{ url_for('services.tesseract_ocr_pipeline') }}" target="_self">OCR</a></li>
<li class="tab disabled"><i class="material-icons">more_vert</i></li>
<li class="tab"><a{%if request.path == url_for('services.transkribus_htr_pipeline') %} class="active"{% endif %} href="{{ url_for('services.transkribus_htr_pipeline') }}" target="_self">HTR</a></li>
<li class="tab disabled"><i class="material-icons">navigate_next</i></li>
<li class="tab"><a{%if request.path == url_for('services.spacy_nlp_pipeline') %} class="active"{% endif %} href="{{ url_for('services.spacy_nlp_pipeline') }}" target="_self">NLP</a></li>
<li class="tab disabled"><i class="material-icons">navigate_next</i></li>
<li class="tab"><a{%if request.path == url_for('corpora.create_corpus') %} class="active"{% endif %} href="{{ url_for('corpora.create_corpus') }}" target="_self">Create corpus</a></li>
<li class="tab disabled"><i class="material-icons">navigate_next</i></li>
{% if corpus %}
<li class="tab"><a{%if request.path == url_for('corpora.create_corpus_file', corpus_id=corpus.id) %} class="active"{% endif %} href="{{ url_for('corpora.create_corpus_file', corpus_id=corpus.id) }}" target="_self">Create corpus file(s)</a></li>
{% else %}
<li class="tab disabled tooltipped" data-tooltip="Select a corpus first" target="_self"><a>Create corpus file(s)</a></li>
{% endif %}
<li class="tab disabled"><i class="material-icons">navigate_next</i></li>
{% if corpus %}
{% if corpus.files.all() %}
<li class="tab"><a{%if request.path == url_for('corpora.analysis', corpus_id=corpus.id) %} class="active"{% endif %} href="{{ url_for('corpora.analysis', corpus_id=corpus.id) }}" target="_self">Corpus analysis</a></li>
{% else %}
<li class="tab disabled tooltipped" data-tooltip="Create at least one corpus file first"><a>Corpus analysis</a></li>
{% endif %}
{% else %}
<li class="tab disabled tooltipped" data-tooltip="Select a corpus first"><a>Corpus analysis</a></li>
{% endif %}
</ul>
</div>
<div class="modal-footer">
<a href="#!" class="modal-close waves-effect waves-green btn-flat">Close</a>
</div>
</div>

View File

@ -1,29 +1,41 @@
<ul class="sidenav sidenav-fixed" id="sidenav"> <ul class="sidenav sidenav-fixed" id="sidenav">
<li class="primary-color hide-on-small-only"> {# user view #}
<div style="overflow: hidden; height: 64px; width: 250px;">
<a href="{{ url_for('main.index') }}">
<img class="hide-on-small-only" src="{{ url_for('static', filename='images/nopaque_-_logo_name_slogan.svg') }}" style="height: 128px; margin-top: -32px;">
</a>
</div>
</li>
<li class="hide-on-med-and-up"><a class="waves-effect" href="{{ url_for('main.index') }}"><i class="material-icons left">home</i>nopaque</a></li>
<li> <li>
<a class="waves-effect" href="{{ url_for('main.news') }}"><i class="material-icons left">email</i>News</a> <div class="user-view">
<div class="background primary-color"></div>
<a><img class="circle" src="{{ url_for('users.user_avatar', user_id=current_user.id) }}" alt=""></a>
<a><span class="white-text name">{{ current_user.username }}</span></a>
<a><span class="white-text email">{{ current_user.email }}</span></a>
</div>
</li>
{# general items #}
{# {% if current_user.can('USE_API') %}
<li>
<a class="waves-effect" href="{{ url_for('apifairy.docs') }}"><i class="material-icons">api</i>API</a>
</li>
{% endif %} #}
<li>
<a class="waves-effect modal-trigger" href="#manual-modal"><i class="material-icons">school</i>Manual</a>
</li> </li>
<li> <li>
<a class="waves-effect" class="waves-effect" href="{{ url_for('main.dashboard') }}"><i class="material-icons">dashboard</i>Dashboard</a> <a class="waves-effect" href="{{ url_for('main.news') }}"><i class="material-icons">email</i>News</a>
<ul>
<li>
<a class="waves-effect" href="{{ url_for('main.dashboard', _anchor='corpora') }}" style="padding-left: 47px;"><i class="nopaque-icons">I</i>My Corpora</a>
</li>
<li>
<a class="waves-effect" href="{{ url_for('main.dashboard', _anchor='jobs') }}" style="padding-left: 47px;"><i class="nopaque-icons">J</i>My Jobs</a>
</li>
<li>
<a class="waves-effect" href="{{ url_for('main.dashboard', _anchor='contributions') }}" style="padding-left: 47px;"><i class="material-icons">new_label</i>My Contributions</a>
</li>
</ul>
</li> </li>
{# dashboard items #}
<li><div class="divider"></div></li>
<li><a class="subheader">Dashboard</a></li>
<li>
<a class="waves-effect" href="{{ url_for('main.dashboard', _anchor='corpora') }}"><i class="nopaque-icons">I</i>My Corpora</a>
</li>
<li>
<a class="waves-effect" href="{{ url_for('main.dashboard', _anchor='jobs') }}"><i class="nopaque-icons">J</i>My Jobs</a>
</li>
<li>
<a class="waves-effect" href="{{ url_for('main.dashboard', _anchor='contributions') }}"><i class="material-icons">new_label</i>My Contributions</a>
</li>
{# processes & services items #}
<li><div class="divider"></div></li> <li><div class="divider"></div></li>
<li><a class="subheader">Processes & Services</a></li> <li><a class="subheader">Processes & Services</a></li>
<li class="service-color service-color-border border-darken" data-service="file-setup-pipeline" style="border-left: 10px solid; margin-top: 5px;"> <li class="service-color service-color-border border-darken" data-service="file-setup-pipeline" style="border-left: 10px solid; margin-top: 5px;">
@ -43,36 +55,35 @@
<li class="service-color service-color-border border-darken" data-service="corpus-analysis" style="border-left: 10px solid; margin-top: 5px;"> <li class="service-color service-color-border border-darken" data-service="corpus-analysis" style="border-left: 10px solid; margin-top: 5px;">
<a class="waves-effect" href="{{ url_for('services.corpus_analysis') }}"><i class="nopaque-icons service-icons" data-service="corpus-analysis"></i>Corpus Analysis</a> <a class="waves-effect" href="{{ url_for('services.corpus_analysis') }}"><i class="nopaque-icons service-icons" data-service="corpus-analysis"></i>Corpus Analysis</a>
</li> </li>
{# social items #}
<li><div class="divider"></div></li> <li><div class="divider"></div></li>
<li><a class="subheader">Social</a></li>
<li> <li>
<a class="waves-effect" class="waves-effect" href="{{ url_for('main.social_area') }}"><i class="material-icons">rocket_launch</i>Social Area</a> <a href="{{ url_for('users.user', user_id=current_user.id) }}"><i class="material-icons">person</i>My Profile</a>
<ul>
<li><a href="{{ url_for('users.user', user_id=current_user.id) }}" style="padding-left: 47px;"><i class="material-icons left">person</i>My Profile</a></li>
<li>
<a class="waves-effect" href="{{ url_for('main.social_area', _anchor='public-users') }}" style="padding-left: 47px;"><i class="material-icons">group</i>Public Users</a>
</li>
<li>
<a class="waves-effect" href="{{ url_for('main.social_area', _anchor='public-corpora') }}" style="padding-left: 47px;"><i class="nopaque-icons">I</i>Public Corpora</a>
</li>
</ul>
</li> </li>
<li class="hide-on-large-only"><div class="divider"></div></li> <li>
<li class="hide-on-large-only"><a class="subheader">Account</a></li> <a class="waves-effect" href="{{ url_for('main.social_area', _anchor='public-users') }}"><i class="material-icons">group</i>Public Users</a>
<li class="hide-on-large-only">
<a class="waves-effect" href="{{ url_for('settings.settings') }}"><i class="material-icons left">settings</i>Settings</a>
</li> </li>
<li class="hide-on-large-only"> <li>
<a class="waves-effect" href="{{ url_for('auth.logout') }}">Log out</a> <a class="waves-effect" href="{{ url_for('main.social_area', _anchor='public-corpora') }}"><i class="nopaque-icons">I</i>Public Corpora</a>
</li> </li>
{# administration items #}
{% if current_user.can('ADMINISTRATE') %} {% if current_user.can('ADMINISTRATE') %}
<li><div class="divider"></div></li> <li><div class="divider"></div></li>
<li> <li>
<a class="waves-effect" href="{{ url_for('admin.admin') }}"><i class="material-icons">admin_panel_settings</i>Administration</a> <a class="waves-effect" href="{{ url_for('admin.admin') }}"><i class="material-icons">admin_panel_settings</i>Administration</a>
</li> </li>
{% endif %} {% endif %}
{# {% if current_user.can('USE_API') %}
{# account items #}
<li><div class="divider"></div></li>
<li><a class="subheader">Account</a></li>
<li> <li>
<a class="waves-effect" href="{{ url_for('apifairy.docs') }}"><i class="material-icons">api</i>API</a> <a class="waves-effect" href="{{ url_for('settings.settings') }}"><i class="material-icons">settings</i>Settings</a>
</li>
<li>
<a class="waves-effect" href="{{ url_for('auth.logout') }}"><i class="material-icons">logout</i>Log out</a>
</li> </li>
{% endif %} #}
</ul> </ul>

View File

@ -1,11 +1,10 @@
{% if current_user.is_authenticated %} {% if current_user.is_authenticated %}
<link href="{{ url_for('static', filename='css/materialize/sidenav_fixed.css') }}" media="screen,projection" rel="stylesheet"> <link href="{{ url_for('static', filename='materialize/css/sidenav-fixed.css') }}" rel="stylesheet">
{% endif %} {% endif %}
<link href="{{ url_for('static', filename='css/materialize/sticky_footer.css') }}" media="screen,projection" rel="stylesheet"> <link href="{{ url_for('static', filename='materialize/css/sticky-footer.css') }}" rel="stylesheet">
<link href="{{ url_for('static', filename='css/materialize/fixes.css') }}" media="screen,projection" rel="stylesheet"> <link href="{{ url_for('static', filename='materialize/css/fixes.css') }}" rel="stylesheet">
<link href="{{ url_for('static', filename='css/spacing.css') }}" media="screen,projection" rel="stylesheet"> <link href="{{ url_for('static', filename='nopaque-icons/css/nopaque-icons.css') }}" rel="stylesheet">
<link href="{{ url_for('static', filename='css/nopaque_icons.css') }}" media="screen,projection" rel="stylesheet"> <link href="{{ url_for('static', filename='css/queryBuilder.css') }}" rel="stylesheet">
<link href="{{ url_for('static', filename='css/queryBuilder.css') }}" media="screen,projection" rel="stylesheet">
{%- assets {%- assets
filters='pyscss', filters='pyscss',
output='gen/app.%(version)s.css', output='gen/app.%(version)s.css',
@ -13,5 +12,5 @@
'css/helpers.scss', 'css/helpers.scss',
'css/style.css' 'css/style.css'
%} %}
<link href="{{ ASSET_URL }}" media="screen,projection" rel="stylesheet"> <link href="{{ ASSET_URL }}" rel="stylesheet">
{%- endassets %} {%- endassets %}

View File

@ -6,6 +6,7 @@ networks:
services: services:
nopaque: nopaque:
environment: environment:
- NOPAQUE_PROXY_FIX_ENABLED=True
- NOPAQUE_PROXY_FIX_X_FOR=1 - NOPAQUE_PROXY_FIX_X_FOR=1
- NOPAQUE_PROXY_FIX_X_HOST=1 - NOPAQUE_PROXY_FIX_X_HOST=1
- NOPAQUE_PROXY_FIX_X_PORT=1 - NOPAQUE_PROXY_FIX_X_PORT=1
@ -15,16 +16,14 @@ services:
- "traefik.docker.network=traefik" - "traefik.docker.network=traefik"
- "traefik.enable=true" - "traefik.enable=true"
### <http> ### ### <http> ###
- "traefik.http.middlewares.http-nopaque-headers.headers.customrequestheaders.X-Forwarded-Proto=http"
- "traefik.http.routers.http-nopaque.entrypoints=http" - "traefik.http.routers.http-nopaque.entrypoints=http"
- "traefik.http.routers.http-nopaque.middlewares=http-nopaque-headers, redirect-to-https@file" - "traefik.http.routers.http-nopaque.middlewares=redirect-to-https@file"
# Replace <nopaque-domain> with your domain # Replace <nopaque-domain> with your domain
- "traefik.http.routers.http-nopaque.rule=Host(`<nopaque-domain>`)" - "traefik.http.routers.http-nopaque.rule=Host(`<nopaque-domain>`)"
### </http> ### ### </http> ###
### <https> ### ### <https> ###
- "traefik.http.middlewares.https-nopaque-headers.headers.customrequestheaders.X-Forwarded-Proto=https"
- "traefik.http.routers.https-nopaque.entrypoints=https" - "traefik.http.routers.https-nopaque.entrypoints=https"
- "traefik.http.routers.https-nopaque.middlewares=hsts-header@file, https-nopaque-headers" - "traefik.http.routers.https-nopaque.middlewares=hsts-header@file"
# Replace <nopaque-domain> with your domain # Replace <nopaque-domain> with your domain
- "traefik.http.routers.https-nopaque.rule=Host(`<nopaque-domain>`)" - "traefik.http.routers.https-nopaque.rule=Host(`<nopaque-domain>`)"
- "traefik.http.routers.https-nopaque.tls.certresolver=<CERTRESOLVER>" - "traefik.http.routers.https-nopaque.tls.certresolver=<CERTRESOLVER>"