namespace _espe.service.member { /** */ export type type_id = int; /** */ export type type_value = { membership_number : string; enabled : boolean; name_real_value : string; name_real_extension : (null | string); name_display : (null | string); name_login : string; password_image : (null | string); email_address_private_value : (null | string); email_address_numberbased_use : boolean; email_address_namebased_use : boolean; email_redirect_to_private : boolean; salutation : (null | string); }; /** */ var _hooks_change : Array<() => void> = []; /** */ export function listen_change( procedure : () => void ) : void { _hooks_change.push(procedure); } /** */ function notify_change( ) : void { _hooks_change.forEach( procedure => { procedure(); } ); } /** */ function store( ) : lib_plankton.storage.type_store, {}, lib_plankton.storage.type_sql_table_autokey_search_term, Record> { const store : lib_plankton.storage.type_store, {}, lib_plankton.storage.type_sql_table_autokey_search_term, Record> = lib_plankton.storage.sql_table_autokey_store( { "database_implementation": _espe.helpers.database_implementation(), "table_name": "members", "key_name": "id", } ); return store; } /** */ function encode( value : type_value ) : Record { return { "membership_number": value.membership_number, "enabled": (value.enabled ? 1 : 0), "name_real_value": value.name_real_value, "name_real_extension": value.name_real_extension, "name_display": value.name_display, "name_login": value.name_login, "password_image": value.password_image, "email_address_private_value": value.email_address_private_value, "email_address_numberbased_use": (value.email_address_numberbased_use ? 1 : 0), "email_address_namebased_use": (value.email_address_namebased_use ? 1 : 0), "email_redirect_to_private": (value.email_redirect_to_private ? 1 : 0), "salutation": value.salutation, }; } /** */ function decode( row : Record ) : type_value { return { "membership_number": row["membership_number"], "enabled": (row["enabled"] > 0), "name_real_value": row["name_real_value"], "name_real_extension": row["name_real_extension"], "name_display": row["name_display"], "name_login": row["name_login"], "password_image": row["password_image"], "email_address_private_value": row["email_address_private_value"], "email_address_numberbased_use": (row["email_address_numberbased_use"] > 0), "email_address_namebased_use": (row["email_address_namebased_use"] > 0), "email_redirect_to_private": (row["email_redirect_to_private"] > 0), "salutation": row["salutation"], }; } /** */ export async function dump( ) : Promise> { const my_store = store(); return ( (await my_store.search(null)) .map( ({"key": key, "preview": preview}) => ({ "id": key, "value": (preview as type_value), }) ) ); } /** */ export async function list( ) : Promise> { const my_store = store(); return ( (await my_store.search(null)) .map( ({"key": key, "preview": preview}) => ({ "id": key, "preview": { "membership_number": preview["membership_number"], "name_real_value": preview["name_real_value"], } }) ) ); } /** * @todo data */ export async function get( id : type_id ) : Promise { const my_store = store(); const row : Record = await my_store.read(id); return decode(row); } /** */ export async function add( value : type_value ) : Promise { const my_store = store(); const row : Record = encode(value); const id : type_id = await my_store.create(row); notify_change(); return id; } /** */ export async function modify( id : type_id, value : type_value ) : Promise { const my_store = store(); const row : Record = encode(value); await my_store.update(id, row); notify_change(); } /** */ export async function remove( id : type_id ) : Promise { const my_store = store(); await my_store.delete(id); notify_change(); } /** */ export async function register( id : type_id, data : { name_login : string; name_display : string; salutation : string; email_address_numberbased_use : boolean; email_address_namebased_use : boolean; email_redirect_to_private : boolean; password : string; } ) : Promise { const member : type_value = await get(id); if (member.name_login !== null) { return Promise.reject(new Error("already registered")); } else { member.name_login = data.name_login; member.name_display = data.name_display; member.salutation = data.salutation; member.email_address_numberbased_use = data.email_address_numberbased_use member.email_address_namebased_use = data.email_address_namebased_use member.email_redirect_to_private = data.email_redirect_to_private; member.password_image = await _espe.helpers.bcrypt_compute(data.password); await modify(id, member); } } /** */ function derive_email_address_namebased( value : type_value ) : string { return lib_plankton.string.coin( "{{value}}{{extension}}@{{domain}}", { "value": value.name_real_value.toLowerCase().replace(new RegExp(" ", "g"), "."), "extension": ( ( (value.name_real_extension === null) || (value.name_real_extension === "") ) ? "" : ("." + value.name_real_extension) ), "domain": _espe.conf.get().settings.target_domain, } ); } /** */ function derive_email_address_numberbased( value : type_value ) : string { return lib_plankton.string.coin( "{{prefix}}{{membership_number}}@{{domain}}", { "prefix": _espe.conf.get().settings.prefix_for_numberbased_email_addresses, "membership_number": value.membership_number, "domain": _espe.conf.get().settings.target_domain, } ); } /** */ function derive_email_address_to_use( value : type_value ) : (null | string) { return ( value.email_address_namebased_use ? derive_email_address_namebased(value) : ( value.email_address_numberbased_use ? derive_email_address_numberbased(value) : value.email_address_private_value ) ); } /** * @todo check validity (e.g. username characters) */ export async function export_authelia_user_file( ) : Promise { const nm_yaml = require("yaml"); return lib_plankton.call.convey( await dump(), [ x => x.map( entry => Object.assign( entry, {"email_address": derive_email_address_to_use(entry.value)} ) ), x => x.filter( entry => ( ( (entry.value.name_login !== null) && (entry.value.name_login !== "") ) && ( (entry.value.password_image !== null) && (entry.value.password_image !== "") ) && (entry.email_address !== null) ) ), x => x.map( entry => ([ entry.value.name_login, { "disabled": (! entry.value.enabled), "displayname": ( ( (entry.value.name_display !== null) && (entry.value.name_display !== "") ) ? entry.value.name_display : entry.value.name_real_value ), "email": entry.email_address, "groups": [], "password": entry.value.password_image, } ]) ), Object.fromEntries, x => ({"users": x}), x => nm_yaml.stringify(x), ] ); } }