diff --git a/personal/q3k/wow/panel/main.go b/personal/q3k/wow/panel/main.go
new file mode 100644
index 0000000..cd1f586
--- /dev/null
+++ b/personal/q3k/wow/panel/main.go
@@ -0,0 +1,466 @@
+package main
+
+import (
+	"context"
+	"crypto/rand"
+	"encoding/hex"
+	"encoding/json"
+	"flag"
+	"fmt"
+	"html/template"
+	"io/ioutil"
+	"net/http"
+	"sync"
+	"time"
+
+	"github.com/boltdb/bolt"
+	oidc "github.com/coreos/go-oidc"
+	"github.com/golang/glog"
+	"github.com/gorilla/sessions"
+	"golang.org/x/oauth2"
+)
+
+var (
+	flagSOAPAddress       string
+	flagSOAPUsername      string
+	flagSOAPPassword      string
+	flagListen            string
+	flagSecret            string
+	flagOAuthClientID     string
+	flagOAuthClientSecret string
+	flagOAuthRedirectURL  string
+	flagDB                string
+	flagMOTD              string
+)
+
+func init() {
+	flag.Set("logtostderr", "true")
+}
+
+func main() {
+	flag.StringVar(&flagSOAPAddress, "soap_address", "http://127.0.0.1:7878", "Address of AC SOAP server")
+	flag.StringVar(&flagSOAPUsername, "soap_username", "test1", "SOAP username")
+	flag.StringVar(&flagSOAPPassword, "soap_password", "", "SOAP password")
+	flag.StringVar(&flagListen, "listen", "127.0.0.1:8080", "HTTP listen address")
+	flag.StringVar(&flagSecret, "secret", "", "Cookie secret")
+	flag.StringVar(&flagOAuthClientID, "oauth_client_id", "", "OAuth client ID")
+	flag.StringVar(&flagOAuthClientSecret, "oauth_client_secret", "", "OAuth client secret")
+	flag.StringVar(&flagOAuthRedirectURL, "oauth_redirect_url", "", "OAuth redirect URL")
+	flag.StringVar(&flagDB, "db", "db.db", "Path to database")
+	flag.StringVar(&flagMOTD, "motd", "", "Path to MOTD")
+	flag.Parse()
+
+	if flagSecret == "" {
+		glog.Exitf("-secret must be set")
+	}
+
+	var err error
+	var motd []byte
+	if flagMOTD == "" {
+		glog.Warningf("no MOTD defined, set -motd to get one")
+	} else {
+		motd, err = ioutil.ReadFile(flagMOTD)
+		if err != nil {
+			glog.Exitf("cannot read MOTD %q: %v", flagMOTD, err)
+		}
+	}
+
+	db, err := bolt.Open(flagDB, 0600, nil)
+	if err != nil {
+		glog.Exitf("opening database failed: %v", err)
+	}
+
+	provider, err := oidc.NewProvider(context.Background(), "https://sso.hackerspace.pl")
+	if err != nil {
+		glog.Exitf("newprovider: %v", err)
+	}
+	oauth2Config := oauth2.Config{
+		ClientID:     flagOAuthClientID,
+		ClientSecret: flagOAuthClientSecret,
+		RedirectURL:  flagOAuthRedirectURL,
+
+		// Discovery returns the OAuth2 endpoints.
+		Endpoint: provider.Endpoint(),
+
+		// "openid" is a required scope for OpenID Connect flows.
+		Scopes: []string{oidc.ScopeOpenID, "profile:read"},
+	}
+
+	err = db.Update(func(tx *bolt.Tx) error {
+		for _, name := range []string{
+			"emailToAccount",
+		} {
+			_, err := tx.CreateBucketIfNotExists([]byte(name))
+			if err != nil {
+				return fmt.Errorf("create bucket %q: %s", name, err)
+			}
+		}
+		return nil
+	})
+	if err != nil {
+		glog.Exitf("db setup failed: %v", err)
+	}
+
+	s := &server{
+		db:     db,
+		store:  sessions.NewCookieStore([]byte(flagSecret)),
+		oauth2: &oauth2Config,
+		motd:   string(motd),
+	}
+
+	http.HandleFunc("/", s.viewIndex)
+	http.HandleFunc("/login", s.viewLogin)
+	http.HandleFunc("/oauth", s.viewOauth)
+	http.HandleFunc("/callback", s.viewOauthCallback)
+	http.HandleFunc("/setup", s.viewOauthSetup)
+	http.HandleFunc("/reset", s.viewReset)
+	http.HandleFunc("/logout", s.viewLogout)
+
+	err = http.ListenAndServe(flagListen, nil)
+	if err != nil {
+		glog.Exitf("ListenAndServe: %v", err)
+	}
+}
+
+type server struct {
+	db     *bolt.DB
+	store  *sessions.CookieStore
+	oauth2 *oauth2.Config
+	motd   string
+
+	onlineLock     sync.RWMutex
+	onlineData     []playerinfo
+	onlineDeadline time.Time
+}
+
+var (
+	tLogin = template.Must(template.New("login").Parse(`<html>
+<title>super wow - who are you?</title>
+<body>
+<pre>
+
+ ___ _   _ _ __   ___ _ __  __      _______      __
+/ __| | | | '_ \ / _ \ '__| \ \ /\ / / _ \ \ /\ / /
+\__ \ |_| | |_) |  __/ |     \ V  V / (_) \ V  V /
+|___/\__,_| .__/ \___|_|      \_/\_/ \___/ \_/\_/
+          |_|
+ _         _       _             _           _       _
+| | _____ | | ___ (_)___ _ _ __ | | _____   | |_   _| |__
+| |/ / _ \| |/ _ \_  / _' | '_ \| |/ / _ \  | | | | | '_ \
+|   < (_) | |  __// / (_| | | | |   < (_) | | | |_| | |_) |
+|_|\_\___/|_|\___/___\__,_|_| |_|_|\_\___/  |_|\__,_|_.__/
+
+ _         _                    __
+| | _____ | | ___  __ _  ___    \ \
+| |/ / _ \| |/ _ \/ _' |/ _ \  (_) |
+|   < (_) | |  __/ (_| | (_) |  _| |
+|_|\_\___/|_|\___|\__, |\___/  (_) |
+                  |___/         /_/
+
+</pre>
+<a href="/oauth">Sign in (or create new account) with HSWAW SSO</a>.<br/>
+
+<p>
+Not a hswaw member? Talk to q3k.
+</p>
+</body>`))
+	tSetup = template.Must(template.New("setup").Parse(`<html>
+<title>super wow - setup account</title>
+<body>
+<b>hi, please provide details for your new WoW account</b><br/>
+pick any username you want, pick a 3-16 character password that isn't the same as your sso password (duh)<br />
+(this isn't your character name, this will only be used to log into WoW)
+{{ if .Error }}
+<br /><b>error</b>: {{ .Error }}<br />
+{{ end }}
+<form method="post" action="/setup">
+username:<input name="username" value={{ .Username }}></input><br/>
+password:<input name="password" type="password"></input><br/>
+<input type=submit value="create account"/>
+</form>
+</body>`))
+	tIndex = template.Must(template.New("index").Parse(`<html>
+<title>super wow</title>
+<style type="text/css">
+    body {
+        background-color: #fff;
+    }
+    table, th, td {
+        background-color: #eee;
+        padding: 0.2em 0.4em 0.2em 0.4em;
+    }
+    table th {
+        background-color: #c0c0c0;
+    }
+    table {
+        background-color: #fff;
+        border-spacing: 0.2em;
+    }
+</style>
+<body>
+<b>Hello, {{ .Username }}.</b></br>
+<a href="/logout">Log out.</a><br />
+{{ .MOTD }}
+<p>
+Your account name is {{ .Username }}. Use the password that you entered when logging in via SSO for the first time, or <form action="/reset" method="POST"><input name="password" type="password" /><input type="submit" value="set a new password"/>.</form>
+</p>
+<b>Currently in-game:</b>
+<table>
+<tr><th>Account</th><th>Character</th></tr>
+{{ range .Online }}
+<tr><td>{{ .Account }}</td><td>{{ .Character }}</td></tr>
+{{ end }}
+</table>
+</body>`))
+)
+
+func (s *server) session(r *http.Request) *sessions.Session {
+	session, _ := s.store.Get(r, sessionName)
+	return session
+}
+
+func (s *server) sessionGet(r *http.Request, k string) string {
+	v, ok := s.session(r).Values[k]
+	if !ok {
+		return ""
+	}
+	v2, ok := v.(string)
+	if !ok {
+		return ""
+	}
+	return v2
+}
+
+func (s *server) sessionPut(w http.ResponseWriter, r *http.Request, k, v string) {
+	session := s.session(r)
+	session.Values[k] = v
+	session.Save(r, w)
+}
+
+func (s *server) online(ctx context.Context) []playerinfo {
+	s.onlineLock.RLock()
+	if s.onlineData == nil || time.Now().After(s.onlineDeadline) {
+		s.onlineLock.RUnlock()
+		s.onlineLock.Lock()
+		data, err := onlinelist(ctx)
+		if err != nil {
+			glog.Errorf("onlinelist fatch failed: %v", err)
+			s.onlineDeadline = time.Now().Add(10 * time.Second)
+		} else {
+			s.onlineData = data
+			s.onlineDeadline = time.Now().Add(60 * time.Second)
+		}
+		s.onlineLock.Unlock()
+		s.onlineLock.RLock()
+	}
+
+	res := make([]playerinfo, len(s.onlineData))
+	for i, pi := range s.onlineData {
+		res[i] = pi
+	}
+	s.onlineLock.RUnlock()
+	return res
+}
+
+func (s *server) viewIndex(w http.ResponseWriter, r *http.Request) {
+	account := s.sessionGet(r, "account")
+	if account == "" {
+		http.Redirect(w, r, "/login", 302)
+		return
+	}
+	err := tIndex.Execute(w, map[string]interface{}{
+		"Username": account,
+		"Online":   s.online(r.Context()),
+		"MOTD":     template.HTML(s.motd),
+	})
+	if err != nil {
+		glog.Errorf("/: %v", err)
+		return
+	}
+}
+
+const sessionName = "wow"
+
+func (s *server) viewLogin(w http.ResponseWriter, r *http.Request) {
+	account := s.sessionGet(r, "account")
+	if account != "" {
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+	err := tLogin.Execute(w, nil)
+	if err != nil {
+		glog.Errorf("/login: %v", err)
+		return
+	}
+}
+
+func (s *server) viewOauth(w http.ResponseWriter, r *http.Request) {
+	stateBytes := make([]byte, 8)
+	_, err := rand.Read(stateBytes)
+	if err != nil {
+		glog.Errorf("/oauth: random: %v", err)
+		return
+	}
+	state := hex.EncodeToString(stateBytes)
+	s.sessionPut(w, r, "ostate", state)
+	url := s.oauth2.AuthCodeURL(state)
+	http.Redirect(w, r, url, http.StatusTemporaryRedirect)
+}
+
+func (s *server) viewOauthCallback(w http.ResponseWriter, r *http.Request) {
+	if r.FormValue("errors") != "" {
+		fmt.Fprintf(w, "Errors: %s", r.FormValue("errors"))
+		return
+	}
+	state := s.sessionGet(r, "ostate")
+	if state == "" {
+		glog.Errorf("No state")
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+	if state != r.FormValue("state") {
+		glog.Errorf("Invalid state")
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+	oauth2Token, err := s.oauth2.Exchange(r.Context(), r.FormValue("code"))
+	if err != nil {
+		glog.Errorf("Exchange failed: %v", err)
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+	client := s.oauth2.Client(r.Context(), oauth2Token)
+	res, err := client.Get("https://sso.hackerspace.pl/api/1/userinfo")
+	if err != nil {
+		glog.Errorf("Userinfo failed: %v", err)
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+	defer res.Body.Close()
+	data, _ := ioutil.ReadAll(res.Body)
+
+	ui := userinfo{}
+	err = json.Unmarshal(data, &ui)
+	if err != nil || ui.Email == "" {
+		glog.Errorf("Userinfo unarshal failed: %v", err)
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+
+	account, err := s.accountForEmail(ui.Email)
+	if err != nil {
+		glog.Errorf("account get failed: %v", err)
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+	if account != "" {
+		s.sessionPut(w, r, "account", account)
+		http.Redirect(w, r, "/", 302)
+	} else {
+		s.sessionPut(w, r, "email", ui.Email)
+		http.Redirect(w, r, "/setup", 302)
+	}
+}
+
+func (s *server) viewOauthSetup(w http.ResponseWriter, r *http.Request) {
+	email := s.sessionGet(r, "email")
+	if email == "" {
+		glog.Errorf("No email")
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+
+	if r.Method == "GET" {
+		tSetup.Execute(w, nil)
+		return
+	}
+
+	username := r.FormValue("username")
+	password := r.FormValue("password")
+	if !reAccount.MatchString(username) {
+		tSetup.Execute(w, map[string]string{
+			"Username": username,
+			"Error":    "Invalid username - must be 3-16 a-z 0-9 - _",
+		})
+		return
+	}
+	if !rePassword.MatchString(password) {
+		tSetup.Execute(w, map[string]string{
+			"Username": username,
+			"Error":    "Invalid password - must be 3-16 a-z A-Z 0-9 - _",
+		})
+		return
+	}
+
+	// this races. ugh. no way to list users. yolo.
+	err := createAccount(r.Context(), username, password)
+	if err != nil {
+		tSetup.Execute(w, map[string]string{
+			"Username": username,
+			"Error":    "Account already exists, pick a different username",
+		})
+		return
+	}
+
+	err = s.db.Update(func(tx *bolt.Tx) error {
+		b := tx.Bucket([]byte("emailToAccount"))
+		v := string(b.Get([]byte(email)))
+		if v != "" {
+			s.sessionPut(w, r, "account", v)
+			http.Redirect(w, r, "/", 302)
+			return nil
+		}
+		b.Put([]byte(email), []byte(username))
+		s.sessionPut(w, r, "account", username)
+		http.Redirect(w, r, "/", 302)
+		return nil
+	})
+	if err != nil {
+		glog.Errorf("setup tx: %v", err)
+		http.Redirect(w, r, "/", 302)
+	}
+}
+func (s *server) viewReset(w http.ResponseWriter, r *http.Request) {
+	account := s.sessionGet(r, "account")
+	if account == "" {
+		glog.Errorf("No account")
+		http.Redirect(w, r, "/", 302)
+		return
+	}
+
+	password := r.FormValue("password")
+	if !rePassword.MatchString(password) {
+		fmt.Fprintf(w, "pick a 3-16 password with not too many special chars")
+		return
+	}
+
+	// this races. ugh. no way to list users. yolo.
+	err := ensureAccount(r.Context(), account, password)
+	if err != nil {
+		glog.Errorf("ensureAccount(%q, _): %v", account, err)
+		fmt.Fprintf(w, "something went wrong, lol")
+		return
+	}
+	fmt.Fprintf(w, "new password set.")
+}
+
+func (s *server) viewLogout(w http.ResponseWriter, r *http.Request) {
+	s.sessionPut(w, r, "account", "")
+	s.sessionPut(w, r, "email", "")
+	http.Redirect(w, r, "/", 302)
+}
+
+func (s *server) accountForEmail(email string) (string, error) {
+	res := ""
+	err := s.db.View(func(tx *bolt.Tx) error {
+		b := tx.Bucket([]byte("emailToAccount"))
+		v := b.Get([]byte(email))
+		res = string(v)
+		return nil
+	})
+	return res, err
+}
+
+type userinfo struct {
+	Email string `json:"email"`
+}
