From 89c1760e9cd293d8a5ac35eda44862b30f595fd4 Mon Sep 17 00:00:00 2001 From: Holger Frey Date: Tue, 31 Mar 2020 10:28:22 +0200 Subject: [PATCH] added login and logout view --- development.ini | 2 +- ordr3.sqlite | Bin 2506752 -> 2506752 bytes ordr3/__init__.py | 4 +- ordr3/static/style.css | 3 + ordr3/static/theme.css | 154 ------------------------------ ordr3/templates/layout.jinja2 | 16 ++++ ordr3/templates/root/login.jinja2 | 49 ++++++++++ ordr3/views/root.py | 62 ++++++++++++ 8 files changed, 134 insertions(+), 156 deletions(-) create mode 100644 ordr3/static/style.css delete mode 100644 ordr3/static/theme.css create mode 100644 ordr3/templates/layout.jinja2 create mode 100644 ordr3/templates/root/login.jinja2 create mode 100644 ordr3/views/root.py diff --git a/development.ini b/development.ini index b097111..f7ac672 100644 --- a/development.ini +++ b/development.ini @@ -23,7 +23,7 @@ auth.secret = "change me for production" session.secret = "change me for production" session.auto_csrf = true - +static_views.cache_max_age = 0 # By default, the toolbar only appears for clients from IP addresses # '127.0.0.1' and '::1'. diff --git a/ordr3.sqlite b/ordr3.sqlite index 8ac899971fe0b02acc3d7ec6ce4376bf307e70cf..4d79ca105b93c26b28037b6d43a3e3ba73faaf4c 100644 GIT binary patch delta 344 zcmZo@n90}x#1o_$xhBduGjeTAShn6SmVv*TA(o$wZvr1DZ#mBoo)Yfw+&Ns&xe7R6 zawc*-=Ez`w${xgal+B6tB&!30+4 z%#v>&m{^papJ$YrqEcpSXsMEGYiM9(Vql`_U=;-3>>9;vQp_{L{dVhQMenuc>0%B$$ zW&vVWAZ7z%b|B^eVoo6D0%C3;<^f_}Am#&NejpYAVnHAl0%Bnx76D>WAQl5+aUhle oVo4yD0%B<(mH}c}AeIASc_3B*VnrZU0%Bz#R@q*?U$wOX0Qic3UH||9 delta 192 zcmWN=O%lN{0Dw`URQi(;|5}Q25*O(W9Ka?s#;|1R0=6AvVVR3KLk?i&do$14hp@b5 zLf-Sekgw`lCx?bUs-HS5onGIj`s$N+7w-g{Y%yS)9fs^uGGfexDHSz)?9*_-Ax9i@ Z!YOB*Gh@yLmn^vAnj4nfe!SZm`v>ewW8nY* diff --git a/ordr3/__init__.py b/ordr3/__init__.py index 741894a..7cb90f4 100644 --- a/ordr3/__init__.py +++ b/ordr3/__init__.py @@ -9,6 +9,8 @@ __version__ = "0.0.1" from pyramid.config import Configurator from pyramid.session import JSONSerializer, SignedCookieSessionFactory +from . import resources + def main(global_config, **settings): """ This function returns a Pyramid WSGI application. @@ -23,7 +25,7 @@ def main(global_config, **settings): require_csrf=settings["session.auto_csrf"] ) - # config.set_root_factory(root_factory) + config.set_root_factory(resources.Root) config.include(".adapters") config.include(".resources") diff --git a/ordr3/static/style.css b/ordr3/static/style.css new file mode 100644 index 0000000..f459932 --- /dev/null +++ b/ordr3/static/style.css @@ -0,0 +1,3 @@ +.o3-login-card { + margin-top:7em; + } diff --git a/ordr3/static/theme.css b/ordr3/static/theme.css deleted file mode 100644 index 0f4b1a4..0000000 --- a/ordr3/static/theme.css +++ /dev/null @@ -1,154 +0,0 @@ -@import url(//fonts.googleapis.com/css?family=Open+Sans:300,400,600,700); -body { - font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif; - font-weight: 300; - color: #ffffff; - background: #bc2131; -} -h1, -h2, -h3, -h4, -h5, -h6 { - font-family: "Open Sans", "Helvetica Neue", Helvetica, Arial, sans-serif; - font-weight: 300; -} -p { - font-weight: 300; -} -.font-normal { - font-weight: 400; -} -.font-semi-bold { - font-weight: 600; -} -.font-bold { - font-weight: 700; -} -.starter-template { - margin-top: 250px; -} -.starter-template .content { - margin-left: 10px; -} -.starter-template .content h1 { - margin-top: 10px; - font-size: 60px; -} -.starter-template .content h1 .smaller { - font-size: 40px; - color: #f2b7bd; -} -.starter-template .content .lead { - font-size: 25px; - color: #f2b7bd; -} -.starter-template .content .lead .font-normal { - color: #ffffff; -} -.starter-template .links { - float: right; - right: 0; - margin-top: 125px; -} -.starter-template .links ul { - display: block; - padding: 0; - margin: 0; -} -.starter-template .links ul li { - list-style: none; - display: inline; - margin: 0 10px; -} -.starter-template .links ul li:first-child { - margin-left: 0; -} -.starter-template .links ul li:last-child { - margin-right: 0; -} -.starter-template .links ul li.current-version { - color: #f2b7bd; - font-weight: 400; -} -.starter-template .links ul li a, a { - color: #f2b7bd; - text-decoration: underline; -} -.starter-template .links ul li a:hover, a:hover { - color: #ffffff; - text-decoration: underline; -} -.starter-template .links ul li .icon-muted { - color: #eb8b95; - margin-right: 5px; -} -.starter-template .links ul li:hover .icon-muted { - color: #ffffff; -} -.starter-template .copyright { - margin-top: 10px; - font-size: 0.9em; - color: #f2b7bd; - text-transform: lowercase; - float: right; - right: 0; -} -@media (max-width: 1199px) { - .starter-template .content h1 { - font-size: 45px; - } - .starter-template .content h1 .smaller { - font-size: 30px; - } - .starter-template .content .lead { - font-size: 20px; - } -} -@media (max-width: 991px) { - .starter-template { - margin-top: 0; - } - .starter-template .logo { - margin: 40px auto; - } - .starter-template .content { - margin-left: 0; - text-align: center; - } - .starter-template .content h1 { - margin-bottom: 20px; - } - .starter-template .links { - float: none; - text-align: center; - margin-top: 60px; - } - .starter-template .copyright { - float: none; - text-align: center; - } -} -@media (max-width: 767px) { - .starter-template .content h1 .smaller { - font-size: 25px; - display: block; - } - .starter-template .content .lead { - font-size: 16px; - } - .starter-template .links { - margin-top: 40px; - } - .starter-template .links ul li { - display: block; - margin: 0; - } - .starter-template .links ul li .icon-muted { - display: none; - } - .starter-template .copyright { - margin-top: 20px; - } -} diff --git a/ordr3/templates/layout.jinja2 b/ordr3/templates/layout.jinja2 new file mode 100644 index 0000000..5a4d309 --- /dev/null +++ b/ordr3/templates/layout.jinja2 @@ -0,0 +1,16 @@ + + + + + + Ordr + + + + + + + + + + diff --git a/ordr3/templates/root/login.jinja2 b/ordr3/templates/root/login.jinja2 new file mode 100644 index 0000000..913344f --- /dev/null +++ b/ordr3/templates/root/login.jinja2 @@ -0,0 +1,49 @@ + + + + + + Ordr - Log In + + + + + + + +
+ +
+ + diff --git a/ordr3/views/root.py b/ordr3/views/root.py new file mode 100644 index 0000000..e41f46c --- /dev/null +++ b/ordr3/views/root.py @@ -0,0 +1,62 @@ +""" static and login pages """ + + +from pyramid.view import view_config +from pyramid.security import forget, remember +from pyramid.httpexceptions import HTTPFound + +from .. import security, services + + +@view_config( + context="ordr3:resources.Root", permission="view", +) +def root(context, request): + if request.user: + return HTTPFound(request.resource_path(request.root, "orders")) + else: + return HTTPFound(request.resource_path(request.root, "login")) + + +@view_config( + context="ordr3:resources.Root", + name="login", + permission="view", + request_method="GET", + renderer="ordr3:templates/root/login.jinja2", +) +def login(context, request): + return {"error": False} + + +@view_config( + context="ordr3:resources.Root", + name="login", + permission="view", + request_method="POST", + require_csrf=False, + renderer="ordr3:templates/root/login.jinja2", +) +def check_credentials(context, request): + username = request.POST.get("username", "") + password = request.POST.get("password", "") + + crypt_context = security.get_passlib_context() + user = services.verify_credentials( + request.repo, crypt_context, username, password + ) + if user is not None and user.is_active: + headers = remember(request, user.id) + return HTTPFound( + request.resource_path(request.root, "orders"), headers=headers + ) + return {"error": True} + + +@view_config(context="ordr3:resources.Root", name="logout", permission="view") +def logout(context, request): + """ logout of a user """ + headers = forget(request) + return HTTPFound( + request.resource_path(request.root, "login"), headers=headers + )