import 'preact/debug' import 'preact/devtools' //import { signal } from 'preact/signals' import { h, Component, render, createRef } from 'preact' import htm from 'htm' import { Session } from 'session' const html = htm.bind(h) class App extends Component { constructor() {//{{{ super() this.websocket = null this.websocket_int_ping = null this.websocket_int_reconnect = null this.wsConnect() this.wsLoop() this.session = new Session(this) this.session.initialize() }//}}} render() {//{{{ if(!this.session.initialized) { return false; //return html`
Validating session
` } if(!this.session.authenticated()) { return html`<${Login} />` } return html`Welcome`; }//}}} wsLoop() {//{{{ setInterval(()=>{ if(this.websocket === null) { console.log("wsLoop connect") this.wsConnect() } }, 1000) }//}}} wsConnect() {//{{{ this.websocket = new WebSocket(`wss://notes.ahall.se/ws`) this.websocket.onopen = evt=>this.wsOpen(evt) this.websocket.onmessage = evt=>this.wsMessage(evt) this.websocket.onerror = evt=>this.wsError(evt) this.websocket.onclose = evt=>this.wsClose(evt) }//}}} wsOpen() {//{{{ this.setState({ wsConnected: true }) // A ping interval to implement a rudimentary keep-alive. }//}}} wsClose() {//{{{ console.log("Lost connection to Notes server") this.websocket = null }//}}} wsError(evt) {//{{{ console.log("websocket error", evt) this.websocket = null; }//}}} wsMessage(evt) {//{{{ let msg = JSON.parse(evt.data) // Broadcast message if(msg.ID == '') { this.broadcastHandler(msg) } else { this.msgHandler(msg) } }//}}} responseError({comm, app}) {//{{{ if(comm !== undefined) { comm.text().then(body=>alert(body)) return } if(app !== undefined && app.hasOwnProperty('error')) { alert(app.error) return } if(app !== undefined) { alert(JSON.stringify(app)) } }//}}} async request(url, params) {//{{{ return new Promise((resolve, reject)=>{ let headers = { 'Content-Type': 'application/json', } console.log(this.session) if(this.session.UUID !== '') headers['X-Session-Id'] = this.session.UUID fetch(url, { method: 'POST', headers, body: JSON.stringify(params), }) .then(response=>{ // A HTTP communication level error occured if(!response.ok || response.status != 200) return reject({comm: response}) return response.json() }) .then(json=>{ // An application level error occured if(!json.OK) return reject({app: json}) return resolve(json) }) .catch(err=>reject({comm: err})) }) }//}}} broadcastHandler(msg) {//{{{ switch(msg.Op) { case 'css_reload': refreshCSS() break; } }//}}} } class Login extends Component { render() {//{{{ return html`

Notes

{ if(evt.code == 'Enter') this.login() }} /> { if(evt.code == 'Enter') this.login() }} />
` }//}}} componentDidMount() {//{{{ document.getElementById('username').focus() }//}}} login() {//{{{ let username = document.getElementById('username').value let password = document.getElementById('password').value window._app.current.session.authenticate(username, password) }//}}} } // Init{{{ //let urlParams = new URLSearchParams(window.location.search) window._app = createRef() window._resourceModels = [] render(html`<${App} ref=${window._app} />`, document.getElementById('app')) //}}} // vim: foldmethod=marker