2fa-0.7
This commit is contained in:
		
							parent
							
								
									fc224038a3
								
							
						
					
					
						commit
						4d2cf64f19
					
				
							
								
								
									
										
											BIN
										
									
								
								NHO8HV5OO57PVC3A.png
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										
											BIN
										
									
								
								NHO8HV5OO57PVC3A.png
									
									
									
									
									
										Normal file
									
								
							
										
											Binary file not shown.
										
									
								
							| 
		 After Width: | Height: | Size: 252 B  | 
							
								
								
									
										12
									
								
								_2fa.tpl
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								_2fa.tpl
									
									
									
									
									
								
							@ -16,11 +16,12 @@
 | 
				
			|||||||
      <h1>2FA</h1>
 | 
					      <h1>2FA</h1>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        % if data['secureAuth'] == True:
 | 
					        % if data['secureAuth'] == True:
 | 
				
			||||||
        
 | 
					            <div class="qr-code">
 | 
				
			||||||
 | 
					                <img src="{{'static/tmp/'+data['authCode']+'.png'}}" /> 
 | 
				
			||||||
 | 
					            </div>
 | 
				
			||||||
            <form name="disable2faForm" method="post" action="/disable_2fa">
 | 
					            <form name="disable2faForm" method="post" action="/disable_2fa">
 | 
				
			||||||
 | 
					
 | 
				
			||||||
                <label for="2fa">2FA</label>
 | 
					                <input id="2fa" name="2fa" type="text" value="{{data['authCode']}}" readonly>
 | 
				
			||||||
                <input id="2fa" name="2fa" type="text" value="{{data['authCode']}}">
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
                <div class="form-buttons">
 | 
					                <div class="form-buttons">
 | 
				
			||||||
                    <a href="/user"><button class="green" type="button">{{ str['back'] }}</button></a>
 | 
					                    <a href="/user"><button class="green" type="button">{{ str['back'] }}</button></a>
 | 
				
			||||||
@ -30,11 +31,10 @@
 | 
				
			|||||||
            </form>
 | 
					            </form>
 | 
				
			||||||
            
 | 
					            
 | 
				
			||||||
        % else:
 | 
					        % else:
 | 
				
			||||||
        
 | 
					
 | 
				
			||||||
            <form name="enable2faForm" method="post" action="/enable_2fa">
 | 
					            <form name="enable2faForm" method="post" action="/enable_2fa">
 | 
				
			||||||
 | 
					
 | 
				
			||||||
                <label for="2fa">2FA</label>
 | 
					                <input id="2fa" name="2fa" type="text" value="{{data['authCode']}}" readonly>
 | 
				
			||||||
                <input id="2fa" name="2fa" type="text" value="{{data['authCode']}}">
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
                <div class="form-buttons">
 | 
					                <div class="form-buttons">
 | 
				
			||||||
                    <a href="/user"><button class="green" type="button">{{ str['back'] }}</button></a>
 | 
					                    <a href="/user"><button class="green" type="button">{{ str['back'] }}</button></a>
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										92
									
								
								app.py
									
									
									
									
									
								
							
							
						
						
									
										92
									
								
								app.py
									
									
									
									
									
								
							@ -27,9 +27,10 @@ from ldap3 import Server, Connection, ALL
 | 
				
			|||||||
from ldap3 import SIMPLE, SUBTREE, MODIFY_REPLACE, MODIFY_ADD, MODIFY_DELETE, ALL_ATTRIBUTES
 | 
					from ldap3 import SIMPLE, SUBTREE, MODIFY_REPLACE, MODIFY_ADD, MODIFY_DELETE, ALL_ATTRIBUTES
 | 
				
			||||||
from ldap3.core.exceptions import LDAPBindError, LDAPConstraintViolationResult, \
 | 
					from ldap3.core.exceptions import LDAPBindError, LDAPConstraintViolationResult, \
 | 
				
			||||||
    LDAPInvalidCredentialsResult, LDAPUserNameIsMandatoryError, \
 | 
					    LDAPInvalidCredentialsResult, LDAPUserNameIsMandatoryError, \
 | 
				
			||||||
    LDAPSocketOpenError, LDAPExceptionError, LDAPAttributeOrValueExistsResult
 | 
					    LDAPSocketOpenError, LDAPExceptionError, LDAPAttributeOrValueExistsResult, \
 | 
				
			||||||
 | 
					    LDAPNoSuchAttributeResult
 | 
				
			||||||
import logging
 | 
					import logging
 | 
				
			||||||
from os import getenv, environ, path
 | 
					from os import getenv, environ, path, remove
 | 
				
			||||||
from libs import flist, slist
 | 
					from libs import flist, slist
 | 
				
			||||||
from libs.localization import *
 | 
					from libs.localization import *
 | 
				
			||||||
from libs.helper import tools
 | 
					from libs.helper import tools
 | 
				
			||||||
@ -118,11 +119,22 @@ def get_index():
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
@get('/_2fa')
 | 
					@get('/_2fa')
 | 
				
			||||||
def get_index():
 | 
					def get_index():
 | 
				
			||||||
 | 
					    #newSession().get()
 | 
				
			||||||
    try:
 | 
					    try:
 | 
				
			||||||
 | 
					        reload(newSession().get()['username'], None, None)
 | 
				
			||||||
 | 
					        #add_auth_attribute_step1(newSession().get()['username'], None, None)
 | 
				
			||||||
        return _2fa_tpl(data=newSession().get(), str=i18n.str)
 | 
					        return _2fa_tpl(data=newSession().get(), str=i18n.str)
 | 
				
			||||||
    except Exception as e:
 | 
					    except Exception as e:
 | 
				
			||||||
        return index_tpl(str=i18n.str)
 | 
					        return index_tpl(str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					@get('/enable_2fa')
 | 
				
			||||||
 | 
					@get('/disable_2fa')
 | 
				
			||||||
 | 
					def get_index():
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        return user_tpl(data=newSession().get(), str=i18n.str)
 | 
				
			||||||
 | 
					    except Exception as e:
 | 
				
			||||||
 | 
					        return index_tpl(str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@post('/user')
 | 
					@post('/user')
 | 
				
			||||||
def post_user():
 | 
					def post_user():
 | 
				
			||||||
    form = request.forms.getunicode
 | 
					    form = request.forms.getunicode
 | 
				
			||||||
@ -276,33 +288,47 @@ def post_edit_email():
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
@post('/enable_2fa')
 | 
					@post('/enable_2fa')
 | 
				
			||||||
def post_enable_2fa():
 | 
					def post_enable_2fa():
 | 
				
			||||||
    try:
 | 
					 | 
				
			||||||
        username=newSession().get()['username']
 | 
					 | 
				
			||||||
        add_auth_attribute_step1(username, tools.generate_secret(), action='enable')
 | 
					 | 
				
			||||||
        '''
 | 
					 | 
				
			||||||
        add attribute authCode
 | 
					 | 
				
			||||||
        set session data
 | 
					 | 
				
			||||||
        '''
 | 
					 | 
				
			||||||
    except Error as e:
 | 
					 | 
				
			||||||
        LOG.warning("akatsa")
 | 
					 | 
				
			||||||
        return error(str(e))
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
    return _2fa_tpl(data=newSession().get(), str=i18n.str)
 | 
					    def error(msg):
 | 
				
			||||||
 | 
					        return _2fa_tpl(alerts=[('error', msg, 'fadeOut')], data=newSession().get(), str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        if(not newSession().get()['secureAuth']):
 | 
				
			||||||
 | 
					            try:
 | 
				
			||||||
 | 
					                username=newSession().get()['username']
 | 
				
			||||||
 | 
					                add_auth_attribute_step1(username, tools.generate_secret(), action='enable')
 | 
				
			||||||
 | 
					            except Error as e:
 | 
				
			||||||
 | 
					                #add_auth_attribute_step1(newSession().get()['username'], None, None)
 | 
				
			||||||
 | 
					                reload(newSession().get()['username'], None, None)
 | 
				
			||||||
 | 
					                LOG.warning(e)
 | 
				
			||||||
 | 
					                return error('2 urratseko autentifikazioa birgaitua izan da.')
 | 
				
			||||||
 | 
					    except Error as e:
 | 
				
			||||||
 | 
					        LOG.warning(e)
 | 
				
			||||||
 | 
					        return index_tpl(alerts=[('error', e, 'fadeOut')], str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return _2fa_tpl(alerts=[('success', 'Bikain, 2 urratseko autentifikazioa gaitu da.', 'fadeOut')], data=newSession().get(), str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@post('/disable_2fa')
 | 
					@post('/disable_2fa')
 | 
				
			||||||
def post_disable_2fa():
 | 
					def post_disable_2fa():
 | 
				
			||||||
    try:
 | 
					 | 
				
			||||||
        username=newSession().get()['username']
 | 
					 | 
				
			||||||
        add_auth_attribute_step1(username, tools.generate_secret(), action='disable')
 | 
					 | 
				
			||||||
        '''
 | 
					 | 
				
			||||||
        add attribute authCode
 | 
					 | 
				
			||||||
        set session data
 | 
					 | 
				
			||||||
        '''
 | 
					 | 
				
			||||||
    except Error as e:
 | 
					 | 
				
			||||||
        LOG.warning("akatsa")
 | 
					 | 
				
			||||||
        return error(str(e))
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
    return _2fa_tpl(data=newSession().get(), str=i18n.str)
 | 
					    def error(msg):
 | 
				
			||||||
 | 
					        return _2fa_tpl(alerts=[('error', msg, 'fadeOut')], data=newSession().get(), str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        if(newSession().get()['secureAuth']):
 | 
				
			||||||
 | 
					            try:
 | 
				
			||||||
 | 
					                username=newSession().get()['username']
 | 
				
			||||||
 | 
					                add_auth_attribute_step1(username, None, action='disable')
 | 
				
			||||||
 | 
					            except Error as e:
 | 
				
			||||||
 | 
					                #add_auth_attribute_step1(newSession().get()['username'], None, None)
 | 
				
			||||||
 | 
					                reload(newSession().get()['username'], None, None)
 | 
				
			||||||
 | 
					                LOG.warning(e)
 | 
				
			||||||
 | 
					                return error(str(e))
 | 
				
			||||||
 | 
					    except Error as e:
 | 
				
			||||||
 | 
					        LOG.warning(e)
 | 
				
			||||||
 | 
					        return index_tpl(alerts=[('error', e, 'fadeOut')], str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return _2fa_tpl(alerts=[('error', '2 urratseko autentifikazioa desgaitua izan da.', 'fadeOut')], data=newSession().get(), str=i18n.str)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@post('/change_pwd')
 | 
					@post('/change_pwd')
 | 
				
			||||||
def post_change_pwd():
 | 
					def post_change_pwd():
 | 
				
			||||||
@ -366,6 +392,10 @@ def serve_static(filename):
 | 
				
			|||||||
def font(filepath):
 | 
					def font(filepath):
 | 
				
			||||||
    return static_file(filepath, root="static/fonts")
 | 
					    return static_file(filepath, root="static/fonts")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					@get("/static/tmp/<filepath:re:.*\.(png|svg)>")
 | 
				
			||||||
 | 
					def font(filepath):
 | 
				
			||||||
 | 
					    return static_file(filepath, root="static/tmp")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
def index_tpl(**kwargs):
 | 
					def index_tpl(**kwargs):
 | 
				
			||||||
    return template('index', **kwargs)
 | 
					    return template('index', **kwargs)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -728,6 +758,10 @@ def add_auth_attribute_step2(conf, *args):
 | 
				
			|||||||
        LOG.error('{}: {!s}'.format(e.__class__.__name__, e))
 | 
					        LOG.error('{}: {!s}'.format(e.__class__.__name__, e))
 | 
				
			||||||
        raise Error(i18n.msg[23])
 | 
					        raise Error(i18n.msg[23])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    except LDAPNoSuchAttributeResult as e:
 | 
				
			||||||
 | 
					        LOG.error('{}: {!s}'.format(e.__class__.__name__, e))
 | 
				
			||||||
 | 
					        raise Error('Dagoeneko desgaiturik zeneukan 2 urratseko autentifikazioa.')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    except LDAPExceptionError as e:
 | 
					    except LDAPExceptionError as e:
 | 
				
			||||||
        LOG.error('{}: {!s}'.format(e.__class__.__name__, e))
 | 
					        LOG.error('{}: {!s}'.format(e.__class__.__name__, e))
 | 
				
			||||||
        raise Error(i18n.msg[23])
 | 
					        raise Error(i18n.msg[23])
 | 
				
			||||||
@ -746,8 +780,18 @@ def add_auth_attribute_step3(conf, username, code, action):
 | 
				
			|||||||
        elif(action == 'disable'):
 | 
					        elif(action == 'disable'):
 | 
				
			||||||
            c.modify(user_dn,{'authCode': [(MODIFY_DELETE, [])]})
 | 
					            c.modify(user_dn,{'authCode': [(MODIFY_DELETE, [])]})
 | 
				
			||||||
            c.modify(user_dn,{'secureAuth': [MODIFY_REPLACE, [False]]})
 | 
					            c.modify(user_dn,{'secureAuth': [MODIFY_REPLACE, [False]]})
 | 
				
			||||||
 | 
					            #remove file
 | 
				
			||||||
 | 
					            try:
 | 
				
			||||||
 | 
					                remove('static/tmp/'+newSession().get()['authCode']+'.png')
 | 
				
			||||||
 | 
					            except OSError as e:
 | 
				
			||||||
 | 
					                LOG.warning(str(e))
 | 
				
			||||||
 | 
					                #raise Error(e)
 | 
				
			||||||
 | 
					                pass
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        newSession().set(get_user_data(user_dn, c))
 | 
					        newSession().set(get_user_data(user_dn, c))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					reload=add_auth_attribute_step1
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#CHANGE PASSWORD
 | 
					#CHANGE PASSWORD
 | 
				
			||||||
def change_passwords(username, old_pass, new_pass):
 | 
					def change_passwords(username, old_pass, new_pass):
 | 
				
			||||||
    changed = []
 | 
					    changed = []
 | 
				
			||||||
 | 
				
			|||||||
@ -4,6 +4,7 @@ import sqlite3
 | 
				
			|||||||
import re
 | 
					import re
 | 
				
			||||||
from onetimepass import valid_totp
 | 
					from onetimepass import valid_totp
 | 
				
			||||||
from secrets import choice
 | 
					from secrets import choice
 | 
				
			||||||
 | 
					import segno
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class Tools():
 | 
					class Tools():
 | 
				
			||||||
    
 | 
					    
 | 
				
			||||||
@ -44,12 +45,14 @@ class Tools():
 | 
				
			|||||||
    def pwd_validation(self, e):
 | 
					    def pwd_validation(self, e):
 | 
				
			||||||
        regex = r'^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[@$!%*#?&])[A-Za-z\d@$!#%*?&]{8,18}$'
 | 
					        regex = r'^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)(?=.*[@$!%*#?&])[A-Za-z\d@$!#%*?&]{8,18}$'
 | 
				
			||||||
        return(bool(re.fullmatch(regex, e)))
 | 
					        return(bool(re.fullmatch(regex, e)))
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    # 2FA
 | 
				
			||||||
    def generate_secret(self):  # Function to return a random string with length 16.
 | 
					    def generate_secret(self):  # Function to return a random string with length 16.
 | 
				
			||||||
        secret = ''
 | 
					        secret = ''
 | 
				
			||||||
        while len(secret) < 16:
 | 
					        while len(secret) < 16:
 | 
				
			||||||
            secret += choice('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567')
 | 
					            secret += choice('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567')
 | 
				
			||||||
 | 
					        qrcode = segno.make(secret, micro=False)
 | 
				
			||||||
 | 
					        qrcode.save('static/tmp/'+secret+'.png', scale=10)
 | 
				
			||||||
        return secret
 | 
					        return secret
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					 | 
				
			||||||
tools = Tools()
 | 
					tools = Tools()
 | 
				
			||||||
 | 
				
			|||||||
@ -194,6 +194,13 @@ button.red:hover{
 | 
				
			|||||||
  animation-name: fadeOut;
 | 
					  animation-name: fadeOut;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/**/
 | 
				
			||||||
 | 
					.qr-code {
 | 
				
			||||||
 | 
					  margin: 0 auto;
 | 
				
			||||||
 | 
					  width: max-content;
 | 
				
			||||||
 | 
					  text-align: center;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/**/
 | 
					/**/
 | 
				
			||||||
.grid-container {
 | 
					.grid-container {
 | 
				
			||||||
  display: grid;
 | 
					  display: grid;
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user