wsrpc.go 1.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
  1. package wsrpc
  2. //go:generate folder2go client wsrpcAssets
  3. import (
  4. "net/http"
  5. "strings"
  6. "dev.hexasoftware.com/stdio/wsrpc/wsrpcAssets" // embed assets
  7. "golang.org/x/net/websocket"
  8. )
  9. // Handler wsrpc.Handler
  10. type Handler struct {
  11. wsHandler http.Handler
  12. prefix string
  13. }
  14. func (h *Handler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
  15. // Get relative path
  16. if h.prefix == "" {
  17. server := r.Context().Value(http.ServerContextKey).(*http.Server)
  18. mux, ok := server.Handler.(*http.ServeMux)
  19. if ok {
  20. _, h.prefix = mux.Handler(r)
  21. }
  22. }
  23. urlPath := strings.TrimPrefix(r.URL.String(), h.prefix)
  24. switch urlPath {
  25. case "ws", "wsrpc":
  26. h.wsHandler.ServeHTTP(w, r)
  27. case "cli.js", "wsrpc.js": // Serve client JS file
  28. w.Header().Set("Content-type", "application/javascript")
  29. w.WriteHeader(200)
  30. w.Write(wsrpcAssets.Data["wsrpc.js"])
  31. default:
  32. w.WriteHeader(http.StatusNotFound)
  33. w.Write([]byte(http.StatusText(http.StatusNotFound)))
  34. }
  35. }
  36. // New create a new WSRpc handler
  37. func New(WSRPC Func) *Handler {
  38. return &Handler{
  39. wsHandler: websocket.Handler(createCliHandler(WSRPC)),
  40. }
  41. }
  42. // Func for wsrpc
  43. type Func func(*ClientCtx)
  44. // Create a client websocket handler on connection
  45. func createCliHandler(handler Func) websocket.Handler {
  46. // Move this to clientCTX handler
  47. return func(ws *websocket.Conn) {
  48. cli := NewClient(ws)
  49. go handler(cli) // Paralell launch a client initiator
  50. cli.Process() // blocks
  51. }
  52. }