underbbs/ts/index.ts

230 lines
7.1 KiB
TypeScript
Raw Normal View History

2024-04-27 22:39:53 +00:00
import {Adapter} from "./adapter";
2024-04-28 18:16:23 +00:00
import {Message, Attachment} from "./message"
2024-04-22 00:02:44 +00:00
2024-04-27 22:39:53 +00:00
function _(key: string, value: any | null | undefined = undefined): any | null {
2024-04-27 16:50:27 +00:00
const x = <any>window;
2024-04-27 22:39:53 +00:00
if (value !== undefined) {
x[key] = value;
}
2024-04-27 16:50:27 +00:00
return x[key];
}
2024-04-22 00:02:44 +00:00
2024-04-27 16:50:27 +00:00
function $(id: string): HTMLElement | null {
2024-04-22 00:32:14 +00:00
return document.getElementById(id);
}
2024-04-27 16:50:27 +00:00
function main():void {
2024-04-27 22:39:53 +00:00
const settings = _("settings", JSON.parse(localStorage.getItem("settings") ?? "{}"));
const adapters = _("adapters", []);
2024-04-27 16:50:27 +00:00
if (settings != null) {
2024-05-13 00:26:44 +00:00
for (let s of settings.adapters ?? []) {
2024-04-27 22:39:53 +00:00
let a: Adapter = Adapter.create()
switch (s.protocol) {
2024-04-22 00:02:44 +00:00
case "nostr":
2024-04-27 22:39:53 +00:00
adapters.push(Adapter.toNostr(a, s));
2024-04-22 00:02:44 +00:00
break;
2024-04-27 22:39:53 +00:00
case "mastodon":
adapters.push(Adapter.toMasto(a, s));
2024-04-22 00:02:44 +00:00
}
2024-04-28 18:16:23 +00:00
}
if (adapters.length > 0) {
_("currentAdapter", 0);
// update tabbar and tabcontent with first adapter
}
2024-04-22 00:02:44 +00:00
} else {
console.log("no settings exist for this client");
2024-04-27 22:39:53 +00:00
_("settings", { adapters: [] });
2024-04-28 18:16:23 +00:00
showSettings();
2024-04-22 00:02:44 +00:00
}
2024-05-13 00:26:44 +00:00
registerServiceWorker();
2024-04-22 00:02:44 +00:00
};
2024-05-13 00:26:44 +00:00
async function registerServiceWorker() {
if ("serviceWorker" in navigator) {
try {
const registration = await navigator.serviceWorker.register("/serviceWorker.js", {
scope: "/",
});
if (registration.installing) {
console.log("Service worker installing");
} else if (registration.waiting) {
console.log("Service worker installed");
} else if (registration.active) {
console.log("Service worker active");
}
} catch (error) {
console.error(`Registration failed with ${error}`);
}
const registration = await navigator.serviceWorker.ready;
(registration as any).sync.register("testdata").then((r:any)=>{console.log("but i will see this!")});
}
};
2024-04-27 16:50:27 +00:00
function showSettings():void {
2024-04-22 00:32:14 +00:00
// tab bar hidden
2024-04-22 02:11:37 +00:00
const tabbar = $("tabbar");
2024-04-27 16:50:27 +00:00
if (tabbar) {
2024-04-22 00:32:14 +00:00
tabbar.style.display = "none";
2024-04-27 16:50:27 +00:00
}
2024-04-22 00:32:14 +00:00
// tabcontent to show settings ui
2024-04-22 02:11:37 +00:00
const tabcontent = $("tabcontent");
2024-05-13 00:26:44 +00:00
const adapters = _("adapters") as Adapter[] ?? [];
2024-04-22 00:32:14 +00:00
2024-04-27 16:50:27 +00:00
if (tabcontent) {
2024-04-28 18:16:23 +00:00
let html = "<p>this is our settings dialogue</p>";
html += "<button onclick='addAdapter()'>New</button>";
html += adapters.reduce((self: string, a: Adapter) => {
self += `<li><a href='#' onclick='editAdapter(${a.nickname})'>${a.nickname}</a></li>`
return self;
}, "<ul id='settings_adapterlist'>");
html += "</ul>";
html += "<button onclick='saveSettings()'>save</button>";
tabcontent.innerHTML = html;
2024-04-27 16:50:27 +00:00
}
2024-04-22 02:11:37 +00:00
}
2024-04-27 16:50:27 +00:00
function addAdapter(): void {
2024-04-22 02:11:37 +00:00
const tabcontent = $("tabcontent");
2024-04-27 16:50:27 +00:00
if (tabcontent) {
2024-04-28 18:16:23 +00:00
// dropdown for protocol
let html = "<select id='settings_newadapter_protocolselect' onchange='fillAdapterProtocolOptions()'>";
html += [ "nostr", "mastodon" ].reduce((self, p)=>{
self += `<option value='${p}'>${p}</option>`;
return self;
}, "");
html += "</select>";
// nostr is the first protocol, so show its options by default
html += "<div id='settings_newadapter_protocoloptions'>";
html += " <label>nickname<input id='settings_newadapter_nickname'/></label>";
html += " <label>privkey<input id='settings_newadapter_nostr_privkey'/></label>";
html += " <label>default relays<input id='settings_newadapter_nostr_default_relays'/></label>";
html += "</div>";
html += "<button onclick='saveAdapter()'>Add</button>";
html += "<button onclick='showSettings()'>Back</button>";
2024-04-22 00:32:14 +00:00
2024-04-28 18:16:23 +00:00
tabcontent.innerHTML = html;
2024-04-27 16:50:27 +00:00
}
2024-04-22 02:11:37 +00:00
}
2024-04-27 16:50:27 +00:00
function fillAdapterProtocolOptions(): void {
const proto = $("settings_newadapter_protocolselect") as HTMLSelectElement;
2024-04-27 22:39:53 +00:00
let html = "";
switch(proto?.options[proto.selectedIndex].value) {
case "nostr":
html += " <label>nickname<input id='settings_newadapter_nickname'/></label>";
html += " <label>privkey<input id='settings_newadapter_nostr_privkey'/></label>";
html += " <label>default relays<input id='settings_newadapter_nostr_default_relays'/></label>";
break;
case "mastodon":
html += " <label>nickname<input id='settings_newadapter_nickname'/></label>";
html += " <label>server<input id='settings_newadapter_masto_server'/></label>";
html += " <label>API key<input id='settings_newadapter_masto_apikey'/></label>";
break;
}
2024-04-27 16:50:27 +00:00
2024-04-27 22:39:53 +00:00
const div = $("settings_newadapter_protocoloptions");
if (div) {
div.innerHTML = html;
}
2024-04-22 00:32:14 +00:00
}
2024-04-27 16:50:27 +00:00
function saveSettings(): void {
2024-04-27 22:39:53 +00:00
const settings = _("settings");
2024-04-27 16:50:27 +00:00
if (settings) {
localStorage.setItem("settings", JSON.stringify(settings));
2024-04-22 00:32:14 +00:00
}
2024-04-22 02:11:37 +00:00
// tab bar hidden
const tabbar = $("tabbar");
2024-04-27 16:50:27 +00:00
if (tabbar) {
tabbar.style.display = "block";
}
2024-04-22 00:32:14 +00:00
// tabcontent to show settings ui
2024-04-22 02:11:37 +00:00
const tabcontent = $("tabcontent");
2024-04-27 16:50:27 +00:00
if (tabcontent) {
tabcontent.innerHTML = "";
}
2024-04-22 00:32:14 +00:00
}
2024-04-27 16:50:27 +00:00
function saveAdapter(): void {
let self: any = {};
2024-04-22 02:11:37 +00:00
// get selected adapter protocol
2024-04-27 16:50:27 +00:00
const proto = $("settings_newadapter_protocolselect") as HTMLSelectElement;
2024-04-22 02:11:37 +00:00
console.log(proto.options[proto.selectedIndex]);
2024-04-27 22:39:53 +00:00
const nickname = ($("settings_newadapter_nickname") as HTMLInputElement)?.value ?? "" ;
2024-04-22 02:11:37 +00:00
// switch protocol
switch (proto.options[proto.selectedIndex].value) {
case "nostr":
2024-04-27 16:50:27 +00:00
const privkey = ($("settings_newadapter_nostr_privkey") as HTMLInputElement)?.value ?? "";
const relays = ($("settings_newadapter_nostr_default_relays") as HTMLInputElement)?.value ?? "";
2024-04-22 02:11:37 +00:00
self = { nickname: nickname, protocol: "nostr", privkey: privkey, relays: relays.split(",").map(r=>r.trim()) };
break;
2024-04-27 22:39:53 +00:00
case "mastodon":
const server = ($("settings_newadapter_masto_server") as HTMLInputElement)?.value ?? "";
const apiKey = ($("settings_newadapter_masto_apikey") as HTMLInputElement)?.value ?? "";
self = { nickname: nickname, protocol: "mastodon", server: server, apiKey: apiKey };
2024-04-22 02:11:37 +00:00
break;
}
2024-04-27 22:39:53 +00:00
const settings = _("settings");
const adapters = _("adapters");
2024-04-27 16:50:27 +00:00
if (settings && adapters) {
2024-05-13 00:26:44 +00:00
if (!settings.adapters) {
settings.adapters = [];
}
2024-04-27 16:50:27 +00:00
settings.adapters.push(self);
2024-04-27 22:39:53 +00:00
let a: Adapter = Adapter.create();
switch (self.protocol) {
case "nostr":
adapters.push(Adapter.toNostr(a, self));
break;
case "mastodon":
adapters.push(Adapter.toMasto(a, self));
break;
}
2024-04-27 16:50:27 +00:00
localStorage.setItem("settings", JSON.stringify(settings));
showSettings();
}
2024-04-22 02:11:37 +00:00
}
2024-05-13 00:26:44 +00:00
let _conn: WebSocket | null = null;
function connect() {
// import the data from the settings
const settings = _("settings");
if (settings) {
// base64 encode the settings data
let subprotocol: string = "[";
for (let a of settings.adapters) {
subprotocol += JSON.stringify(a) + ",";
}
subprotocol += "]";
subprotocol = btoa(subprotocol);
2024-05-19 20:42:28 +00:00
// open the websocket connection with settings as subprotocol
const wsProto = location.protocol == "https:" ? "wss" : "ws";
_conn = new WebSocket(`${wsProto}://${location.host}/subscribe`, subprotocol);
2024-05-13 00:26:44 +00:00
_("websocket", _conn);
}
}
2024-04-27 22:39:53 +00:00
_("addAdapter", addAdapter);
_("saveAdapter", saveAdapter);
_("fillAdapterProtocolOptions", fillAdapterProtocolOptions);
_("showSettings", showSettings);
_("saveSettings", saveSettings);
2024-05-13 00:26:44 +00:00
_("connect", connect);
2024-04-27 16:50:27 +00:00
main();