refactoring
This commit is contained in:
@@ -0,0 +1,130 @@
|
||||
/* Mail and password-reset administration view. */
|
||||
|
||||
class MailAdmin {
|
||||
/**
|
||||
* goal : Connect mail settings, test delivery and TLS controls to the API.
|
||||
* pre : The mail administration form exists in the document.
|
||||
* post : Save, test and TLS-change events are handled by this controller.
|
||||
* result : A directly usable mail administration controller.
|
||||
*/
|
||||
constructor(api, translate) {
|
||||
this.api = api;
|
||||
this.translate = translate;
|
||||
this.form = document.getElementById("mail-settings-form");
|
||||
this.status = document.getElementById("mail-settings-status");
|
||||
this.testButton = document.getElementById("mail-test-button");
|
||||
this.tls = document.getElementById("mail-smtp-tls");
|
||||
this.acceptUntrusted = document.getElementById(
|
||||
"mail-smtp-accept-untrusted-certificates");
|
||||
|
||||
this.form.addEventListener("submit", (event) => this.#save(event));
|
||||
this.testButton.addEventListener("click", () => this.#test());
|
||||
this.tls.addEventListener("change", () => this.#syncTlsControls());
|
||||
}
|
||||
|
||||
/**
|
||||
* goal : Load stored mail settings and initialize the test recipient.
|
||||
* pre : The current session has administrator permission.
|
||||
* post : All form controls represent the stored server configuration.
|
||||
* result : A promise that resolves after the form has been initialized.
|
||||
*/
|
||||
async load(currentUserEmail = "") {
|
||||
const settings = await this.api("/api/admin/mail-settings");
|
||||
document.getElementById("mail-public-url").value =
|
||||
settings.publicUrl || window.location.origin;
|
||||
document.getElementById("mail-smtp-host").value = settings.smtpHost || "";
|
||||
document.getElementById("mail-smtp-port").value = settings.smtpPort || "587";
|
||||
document.getElementById("mail-smtp-from").value = settings.smtpFrom || "";
|
||||
document.getElementById("mail-smtp-user").value = settings.smtpUser || "";
|
||||
document.getElementById("mail-smtp-password").value = "";
|
||||
this.tls.checked = settings.smtpTls !== false;
|
||||
this.acceptUntrusted.checked = settings.smtpAcceptUntrustedCertificates === true;
|
||||
document.getElementById("mail-reset-limit").value = settings.resetLimit || "2";
|
||||
document.getElementById("mail-test-recipient").value = currentUserEmail;
|
||||
document.getElementById("mail-password-help").textContent = settings.hasPassword
|
||||
? this.translate(
|
||||
"smtp-password-kept", "A password is stored; leave empty to keep it.")
|
||||
: "";
|
||||
this.status.textContent = "";
|
||||
this.acceptUntrusted.disabled = !this.tls.checked;
|
||||
}
|
||||
|
||||
/** Read the mail form using the public server API field names. */
|
||||
#formData() {
|
||||
return {
|
||||
publicUrl: document.getElementById("mail-public-url").value,
|
||||
smtpHost: document.getElementById("mail-smtp-host").value,
|
||||
smtpPort: document.getElementById("mail-smtp-port").value,
|
||||
smtpFrom: document.getElementById("mail-smtp-from").value,
|
||||
smtpUser: document.getElementById("mail-smtp-user").value,
|
||||
smtpPassword: document.getElementById("mail-smtp-password").value,
|
||||
smtpTls: this.tls.checked,
|
||||
smtpAcceptUntrustedCertificates: this.acceptUntrusted.checked,
|
||||
resetLimit: document.getElementById("mail-reset-limit").value
|
||||
};
|
||||
}
|
||||
|
||||
/** Store the current mail settings and retain an omitted password. */
|
||||
async #save(event) {
|
||||
event.preventDefault();
|
||||
try {
|
||||
await this.api("/api/admin/mail-settings", {
|
||||
method: "PUT",
|
||||
body: JSON.stringify(this.#formData())
|
||||
});
|
||||
document.getElementById("mail-smtp-password").value = "";
|
||||
document.getElementById("mail-password-help").textContent = this.translate(
|
||||
"smtp-password-kept", "A password is stored; leave empty to keep it.");
|
||||
this.status.textContent = this.translate("saved", "Saved");
|
||||
} catch (error) {
|
||||
this.status.textContent = error.message;
|
||||
}
|
||||
}
|
||||
|
||||
/** Send one test message using the unsaved values currently in the form. */
|
||||
async #test() {
|
||||
const recipient = document.getElementById("mail-test-recipient").value.trim();
|
||||
this.testButton.disabled = true;
|
||||
this.status.textContent = this.translate(
|
||||
"sending-test-mail", "Sending test email…");
|
||||
try {
|
||||
await this.api("/api/admin/mail-settings/test", {
|
||||
method: "POST",
|
||||
body: JSON.stringify({ ...this.#formData(), recipient })
|
||||
});
|
||||
this.status.textContent = this.translate(
|
||||
"test-mail-sent", "Test email accepted by SMTP server");
|
||||
} catch (error) {
|
||||
console.error("SMTP test failed", error);
|
||||
this.status.textContent = this.#smtpErrorMessage(error);
|
||||
} finally {
|
||||
this.testButton.disabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
/** Translate known TLS failures and retain other server error messages. */
|
||||
#smtpErrorMessage(error) {
|
||||
const message = error && error.message ? error.message : String(error);
|
||||
const certificateFailure = message.includes("certificate verify failed") ||
|
||||
message.includes("TLS certificate verification failed");
|
||||
if (certificateFailure) {
|
||||
return this.translate(
|
||||
"smtp-certificate-verification-failed",
|
||||
"The SMTP server certificate could not be verified. Install a valid certificate, or select the local-server exception if this is a trusted local SMTP server.");
|
||||
}
|
||||
if (message.includes("no protocols available")) {
|
||||
return this.translate(
|
||||
"smtp-no-modern-tls",
|
||||
"The SMTP connection attempted an obsolete TLS protocol. Install the current Racket Wiki version, which negotiates modern TLS automatically.");
|
||||
}
|
||||
return message;
|
||||
}
|
||||
|
||||
/** Disable the certificate exception whenever STARTTLS is disabled. */
|
||||
#syncTlsControls() {
|
||||
this.acceptUntrusted.disabled = !this.tls.checked;
|
||||
if (this.acceptUntrusted.disabled) this.acceptUntrusted.checked = false;
|
||||
}
|
||||
}
|
||||
|
||||
export { MailAdmin };
|
||||
Reference in New Issue
Block a user