HEX
Server: LiteSpeed
System: Linux houston.panomity.com 6.8.0-100-generic #100-Ubuntu SMP PREEMPT_DYNAMIC Tue Jan 13 16:40:06 UTC 2026 x86_64
User: nudepix (1011)
PHP: 7.4.33
Disabled: pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_get_handler,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority,pcntl_async_signals,pcntl_unshare,
Upload Files
File: //opt/moodle-mlbackend-python/gen-passwd
#!/usr/bin/env python3

import argparse
import hashlib
import secrets
from getpass import getpass


def salt():
    return secrets.token_hex(16)


def new_password():
    return secrets.token_urlsafe(16)


def hash_one(password):
    name = 'sha256'
    h = hashlib.new(name)
    s = salt()
    h.update(s.encode('utf8'))
    h.update(password.encode('utf8'))
    d = h.hexdigest()
    return (name, s, d)


def entry(user, password):
    if set(',:\n') & set(user):
        raise ValueError("username can't contain colons, commas, or new lines")

    hash_name, s, digest = hash_one(password)
    return f"{user}:{hash_name}:{s}:{digest}"


def main():
    desc = 'Generate environment vars for moodle_mlbackend web auth'
    parser = argparse.ArgumentParser(description=desc)
    parser.add_argument('-g', '--generate-password', action='store_true',
                        help=('choose and print random passwords '
                              '(rather than prompt)'))
    parser.add_argument('-P', '--passwords',
                        help=('comma separated passwords '
                              '(rather than prompt)'))
    parser.add_argument('user', nargs='+',
                        help='users for which to make the password string')
    args = parser.parse_args()

    if len(set(args.user)) != len(args.user):
        parser.print_usage()
        sys.exit(1)

    if args.passwords is not None:
        passwords = args.passwords.split(',')
        if len(passwords) != len(args.user):
            print("--passwords argument should have one password per user,"
                  "separated by commas.")
            parser.print_usage()
            sys.exit(1)

    entries = []
    for user in args.user:
        if args.generate_password:
            password = new_password()
            print(f"password for {user}: {password}")
        elif args.passwords is not None:
            password = passwords.pop(0)
        else:
            password = getpass(f"password for {user}: ")

        entries.append(entry(user, password))

    print(','.join(entries))


main()