Updated user manager.
This commit is contained in:
@@ -1,10 +1,12 @@
|
|||||||
# packetserver/http/auth.py
|
# packetserver/http/auth.py
|
||||||
|
import ax25
|
||||||
from persistent import Persistent
|
from persistent import Persistent
|
||||||
from argon2 import PasswordHasher
|
from argon2 import PasswordHasher
|
||||||
from argon2.exceptions import VerifyMismatchError
|
from argon2.exceptions import VerifyMismatchError
|
||||||
import time
|
import time
|
||||||
from persistent.mapping import PersistentMapping
|
from persistent.mapping import PersistentMapping
|
||||||
from persistent.list import PersistentList
|
from persistent.list import PersistentList
|
||||||
|
from packetserver.common.util import is_valid_ax25_callsign
|
||||||
|
|
||||||
ph = PasswordHasher()
|
ph = PasswordHasher()
|
||||||
|
|
||||||
@@ -22,6 +24,12 @@ class HttpUser(Persistent):
|
|||||||
self.last_login = None
|
self.last_login = None
|
||||||
self.failed_attempts = 0
|
self.failed_attempts = 0
|
||||||
|
|
||||||
|
# Check to make sure we're not storing a SSID
|
||||||
|
if is_valid_ax25_callsign(self.username):
|
||||||
|
base = ax25.Address(self.username).call
|
||||||
|
if base.upper() != self.username:
|
||||||
|
raise ValueError(f"'{self.username}' is a callsign with an SSID appended. Please use base callsign.")
|
||||||
|
|
||||||
# New fields
|
# New fields
|
||||||
self._enabled = True # HTTP access enabled by default
|
self._enabled = True # HTTP access enabled by default
|
||||||
# rf_enabled is a @property – no direct storage needed
|
# rf_enabled is a @property – no direct storage needed
|
||||||
@@ -30,11 +38,11 @@ class HttpUser(Persistent):
|
|||||||
# Simple enabled flag (admin can disable HTTP login entirely)
|
# Simple enabled flag (admin can disable HTTP login entirely)
|
||||||
# ------------------------------------------------------------------
|
# ------------------------------------------------------------------
|
||||||
@property
|
@property
|
||||||
def enabled(self) -> bool:
|
def http_enabled(self) -> bool:
|
||||||
return getattr(self, '_enabled', True)
|
return getattr(self, '_enabled', True)
|
||||||
|
|
||||||
@enabled.setter
|
@http_enabled.setter
|
||||||
def enabled(self, value: bool):
|
def http_enabled(self, value: bool):
|
||||||
self._enabled = bool(value)
|
self._enabled = bool(value)
|
||||||
self._p_changed = True
|
self._p_changed = True
|
||||||
|
|
||||||
@@ -57,7 +65,7 @@ class HttpUser(Persistent):
|
|||||||
Requires an open ZODB connection (inside a transaction).
|
Requires an open ZODB connection (inside a transaction).
|
||||||
Only allows enabling if the username is a valid AX.25 callsign.
|
Only allows enabling if the username is a valid AX.25 callsign.
|
||||||
"""
|
"""
|
||||||
from packetserver.utils import is_valid_ax25_callsign # our validator
|
from packetserver.common.util import is_valid_ax25_callsign # our validator
|
||||||
|
|
||||||
root = connection.root()
|
root = connection.root()
|
||||||
config = root.setdefault('config', PersistentMapping())
|
config = root.setdefault('config', PersistentMapping())
|
||||||
|
|||||||
@@ -214,14 +214,14 @@ def main():
|
|||||||
if not users_mapping:
|
if not users_mapping:
|
||||||
print("No HTTP users configured")
|
print("No HTTP users configured")
|
||||||
else:
|
else:
|
||||||
print(f"{'Callsign':<12} {'Enabled':<8} {'RF Enabled':<11} {'Created':<20} Last Login")
|
print(f"{'Callsign':<12} {'HTTP Enabled':<13} {'RF Enabled':<11} {'Created':<20} Last Login")
|
||||||
print("-" * 70)
|
print("-" * 75)
|
||||||
for user in sorted(users_mapping.values(), key=lambda u: u.username):
|
for user in sorted(users_mapping.values(), key=lambda u: u.username):
|
||||||
created = time.strftime("%Y-%m-%d %H:%M", time.localtime(user.created_at))
|
created = time.strftime("%Y-%m-%d %H:%M", time.localtime(user.created_at))
|
||||||
last = (time.strftime("%Y-%m-%d %H:%M", time.localtime(user.last_login))
|
last = (time.strftime("%Y-%m-%d %H:%M", time.localtime(user.last_login))
|
||||||
if user.last_login else "-")
|
if user.last_login else "-")
|
||||||
rf_status = "True" if user.is_rf_enabled(connection) else "False"
|
rf_status = "True" if user.is_rf_enabled(connection) else "False"
|
||||||
print(f"{user.username:<12} {str(user.enabled):<8} {rf_status:<11} {created:<20} {last}")
|
print(f"{user.username:<12} {str(user.http_enabled):<13} {rf_status:<11} {created:<20} {last}")
|
||||||
|
|
||||||
|
|
||||||
finally:
|
finally:
|
||||||
|
|||||||
Reference in New Issue
Block a user