Split into packages.

change-name
Robert Jacob 2018-03-28 00:26:26 +02:00
parent 2b19606b77
commit 793ad85fdd
3 changed files with 123 additions and 99 deletions

View File

@ -1,17 +1,13 @@
package main
import (
ctls "crypto/tls"
"encoding/json"
"flag"
"fmt"
"log"
"net/http"
"strings"
"git.hacknology.de/projekte/spaceapi"
"github.com/coyim/coyim/xmpp/data"
"github.com/twstrike/coyim/xmpp"
"git.hacknology.de/projekte/spaceapi/web"
"git.hacknology.de/projekte/spaceapi/xmpp"
)
var (
@ -42,103 +38,13 @@ func main() {
}
if xmppJid != "" {
if err := createXMPPListener(storage, xmppJid, xmppPassword, xmppTarget, xmppHandle); err != nil {
if err := xmpp.AddXMPPListener(storage, xmppJid, xmppPassword, xmppTarget, xmppHandle); err != nil {
log.Printf("Error creating XMPP listener: %s", err)
}
}
http.Handle(webPrefix+"/status.json", handleReadStatus(storage.Status))
http.Handle(webPrefix+"/status/state", handleSetState(storage))
http.Handle("/", http.RedirectHandler(webPrefix+"/status.json", http.StatusFound))
mux := web.CreateMux(storage, webPrefix)
log.Printf("Listening on %s...", addr)
log.Fatal(http.ListenAndServe(addr, nil))
}
func handleReadStatus(statusFunc func() spaceapi.SpaceStatus) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
status := statusFunc()
if err := json.NewEncoder(w).Encode(status); err != nil {
http.Error(w, fmt.Sprintf("Error encoding JSON: %s", err), http.StatusInternalServerError)
}
})
}
func handleSetState(storage *spaceapi.Storage) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
if r.Method != http.MethodPost {
http.Error(w, fmt.Sprintf("Invalid method: %s", r.Method), http.StatusMethodNotAllowed)
return
}
defer r.Body.Close()
var newState spaceapi.State
if err := json.NewDecoder(r.Body).Decode(&newState); err != nil {
http.Error(w, fmt.Sprintf("Error decoding body: %s", err), http.StatusBadRequest)
return
}
storage.Modify(func(status *spaceapi.SpaceStatus) {
status.State = newState
})
status := storage.Status()
if err := json.NewEncoder(w).Encode(status); err != nil {
http.Error(w, fmt.Sprintf("Error encoding JSON: %s", err), http.StatusInternalServerError)
}
})
}
type nullVerifier struct{}
func (nullVerifier) Verify(state ctls.ConnectionState, conf *ctls.Config, originDomain string) error {
return nil
}
func createXMPPListener(storage *spaceapi.Storage, jid, password, target, handle string) error {
dialer := xmpp.DialerFactory(nullVerifier{})
dialer.SetJID(jid)
dialer.SetPassword(password)
conn, err := dialer.Dial()
if err != nil {
return fmt.Errorf("error dialing server: %s", err)
}
targetTokens := strings.SplitN(target, "@", 2)
if len(targetTokens) != 2 {
return fmt.Errorf("not a valid room JID: %s", target)
}
chat := conn.GetChatContext()
room := data.Room{
ID: targetTokens[0],
Service: targetTokens[1],
}
occupant := &data.Occupant{
Room: room,
Handle: handle,
}
if err := chat.EnterRoom(occupant); err != nil {
return fmt.Errorf("error joining room: %s", err)
}
storage.AddListener(func(status spaceapi.SpaceStatus) {
if status.State.Open == nil {
return
}
msg := "Space is now OPEN!"
if !*status.State.Open {
msg = "Space is now CLOSED!"
}
if err := chat.SendChatMessage(msg, &room); err != nil {
log.Printf("Error sending message: %s", err)
}
})
return nil
log.Fatal(http.ListenAndServe(addr, mux))
}

54
web/web.go Normal file
View File

@ -0,0 +1,54 @@
package web
import (
"encoding/json"
"fmt"
"net/http"
"git.hacknology.de/projekte/spaceapi"
)
func CreateMux(storage *spaceapi.Storage, prefix string) http.Handler {
mux := http.NewServeMux()
mux.Handle(prefix+"/status.json", handleReadStatus(storage.Status))
mux.Handle(prefix+"/status/state", handleSetState(storage))
mux.Handle("/", http.RedirectHandler(prefix+"/status.json", http.StatusFound))
return mux
}
func handleReadStatus(statusFunc func() spaceapi.SpaceStatus) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
status := statusFunc()
if err := json.NewEncoder(w).Encode(status); err != nil {
http.Error(w, fmt.Sprintf("Error encoding JSON: %s", err), http.StatusInternalServerError)
}
})
}
func handleSetState(storage *spaceapi.Storage) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
if r.Method != http.MethodPost {
http.Error(w, fmt.Sprintf("Invalid method: %s", r.Method), http.StatusMethodNotAllowed)
return
}
defer r.Body.Close()
var newState spaceapi.State
if err := json.NewDecoder(r.Body).Decode(&newState); err != nil {
http.Error(w, fmt.Sprintf("Error decoding body: %s", err), http.StatusBadRequest)
return
}
storage.Modify(func(status *spaceapi.SpaceStatus) {
status.State = newState
})
status := storage.Status()
if err := json.NewEncoder(w).Encode(status); err != nil {
http.Error(w, fmt.Sprintf("Error encoding JSON: %s", err), http.StatusInternalServerError)
}
})
}

64
xmpp/xmpp.go Normal file
View File

@ -0,0 +1,64 @@
package xmpp
import (
ctls "crypto/tls"
"fmt"
"log"
"strings"
"git.hacknology.de/projekte/spaceapi"
"github.com/coyim/coyim/xmpp/data"
"github.com/twstrike/coyim/xmpp"
)
type nullVerifier struct{}
func (nullVerifier) Verify(state ctls.ConnectionState, conf *ctls.Config, originDomain string) error {
return nil
}
func AddXMPPListener(storage *spaceapi.Storage, jid, password, target, handle string) error {
dialer := xmpp.DialerFactory(nullVerifier{})
dialer.SetJID(jid)
dialer.SetPassword(password)
conn, err := dialer.Dial()
if err != nil {
return fmt.Errorf("error dialing server: %s", err)
}
targetTokens := strings.SplitN(target, "@", 2)
if len(targetTokens) != 2 {
return fmt.Errorf("not a valid room JID: %s", target)
}
chat := conn.GetChatContext()
room := data.Room{
ID: targetTokens[0],
Service: targetTokens[1],
}
occupant := &data.Occupant{
Room: room,
Handle: handle,
}
if err := chat.EnterRoom(occupant); err != nil {
return fmt.Errorf("error joining room: %s", err)
}
storage.AddListener(func(status spaceapi.SpaceStatus) {
if status.State.Open == nil {
return
}
msg := "Space is now OPEN!"
if !*status.State.Open {
msg = "Space is now CLOSED!"
}
if err := chat.SendChatMessage(msg, &room); err != nil {
log.Printf("Error sending message: %s", err)
}
})
return nil
}