2023-01-06 12:21:14 +00:00
|
|
|
package pairing
|
|
|
|
|
|
|
|
import (
|
|
|
|
"io"
|
|
|
|
"net/http"
|
|
|
|
|
|
|
|
"go.uber.org/zap"
|
|
|
|
|
|
|
|
"github.com/status-im/status-go/signal"
|
|
|
|
)
|
|
|
|
|
|
|
|
const (
|
|
|
|
// Handler routes for pairing
|
2023-02-28 12:32:45 +00:00
|
|
|
pairingBase = "/pairing"
|
2023-03-23 11:44:15 +00:00
|
|
|
pairingChallenge = pairingBase + "/challenge"
|
2023-02-28 12:32:45 +00:00
|
|
|
pairingSendAccount = pairingBase + "/sendAccount"
|
|
|
|
pairingReceiveAccount = pairingBase + "/receiveAccount"
|
2023-03-23 11:44:15 +00:00
|
|
|
pairingSendSyncDevice = pairingBase + "/sendSyncDevice"
|
|
|
|
pairingReceiveSyncDevice = pairingBase + "/receiveSyncDevice"
|
2023-02-28 12:32:45 +00:00
|
|
|
pairingSendInstallation = pairingBase + "/sendInstallation"
|
|
|
|
pairingReceiveInstallation = pairingBase + "/receiveInstallation"
|
2023-01-06 12:21:14 +00:00
|
|
|
)
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
// Account handling
|
|
|
|
|
|
|
|
func handleReceiveAccount(hs HandlerServer, pr PayloadReceiver) http.HandlerFunc {
|
|
|
|
logger := hs.GetLogger()
|
2023-01-06 12:21:14 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-04-02 23:15:13 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventConnectionSuccess, Action: ActionPairingAccount})
|
2023-01-06 12:21:14 +00:00
|
|
|
payload, err := io.ReadAll(r.Body)
|
|
|
|
if err != nil {
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionPairingAccount})
|
2023-02-28 12:32:45 +00:00
|
|
|
logger.Error("handleReceiveAccount io.ReadAll(r.Body)", zap.Error(err))
|
2023-03-23 11:44:15 +00:00
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferSuccess, Action: ActionPairingAccount})
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
err = pr.Receive(payload)
|
2023-01-06 12:21:14 +00:00
|
|
|
if err != nil {
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventProcessError, Error: err.Error(), Action: ActionPairingAccount})
|
2023-03-23 11:44:15 +00:00
|
|
|
logger.Error("handleReceiveAccount pr.Receive(payload)", zap.Error(err), zap.Binary("payload", payload))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventProcessSuccess, Action: ActionPairingAccount})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
func handleSendAccount(hs HandlerServer, pm PayloadMounter) http.HandlerFunc {
|
|
|
|
logger := hs.GetLogger()
|
2023-02-28 12:32:45 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-04-02 23:15:13 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventConnectionSuccess, Action: ActionPairingAccount})
|
2023-03-23 11:44:15 +00:00
|
|
|
w.Header().Set("Content-Type", "application/octet-stream")
|
|
|
|
err := pm.Mount()
|
2023-02-28 12:32:45 +00:00
|
|
|
if err != nil {
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionPairingAccount})
|
|
|
|
logger.Error("handleSendAccount pm.Mount()", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-02-28 12:32:45 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
_, err = w.Write(pm.ToSend())
|
2023-02-28 12:32:45 +00:00
|
|
|
if err != nil {
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionPairingAccount})
|
|
|
|
logger.Error("handleSendAccount w.Write(pm.ToSend())", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-02-28 12:32:45 +00:00
|
|
|
return
|
|
|
|
}
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferSuccess, Action: ActionPairingAccount})
|
|
|
|
|
|
|
|
pm.LockPayload()
|
2023-02-28 12:32:45 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
// Device sync handling
|
|
|
|
|
|
|
|
func handleParingSyncDeviceReceive(hs HandlerServer, pr PayloadReceiver) http.HandlerFunc {
|
|
|
|
logger := hs.GetLogger()
|
2023-01-06 12:21:14 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-04-02 23:15:13 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventConnectionSuccess, Action: ActionSyncDevice})
|
2023-01-06 12:21:14 +00:00
|
|
|
payload, err := io.ReadAll(r.Body)
|
|
|
|
if err != nil {
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionSyncDevice})
|
2023-02-28 12:32:45 +00:00
|
|
|
logger.Error("handleParingSyncDeviceReceive io.ReadAll(r.Body)", zap.Error(err))
|
2023-03-23 11:44:15 +00:00
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferSuccess, Action: ActionSyncDevice})
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
err = pr.Receive(payload)
|
2023-01-06 12:21:14 +00:00
|
|
|
if err != nil {
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventProcessError, Error: err.Error(), Action: ActionSyncDevice})
|
2023-03-23 11:44:15 +00:00
|
|
|
logger.Error("handleParingSyncDeviceReceive pr.Receive(payload)", zap.Error(err), zap.Binary("payload", payload))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventProcessSuccess, Action: ActionSyncDevice})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
func handlePairingSyncDeviceSend(hs HandlerServer, pm PayloadMounter) http.HandlerFunc {
|
|
|
|
logger := hs.GetLogger()
|
2023-01-06 12:21:14 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-04-02 23:15:13 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventConnectionSuccess, Action: ActionSyncDevice})
|
2023-01-06 12:21:14 +00:00
|
|
|
w.Header().Set("Content-Type", "application/octet-stream")
|
2023-03-23 11:44:15 +00:00
|
|
|
|
|
|
|
err := pm.Mount()
|
2023-01-06 12:21:14 +00:00
|
|
|
if err != nil {
|
2023-03-23 11:44:15 +00:00
|
|
|
// maybe better to use a new event type here instead of EventTransferError?
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionSyncDevice})
|
|
|
|
logger.Error("handlePairingSyncDeviceSend pm.Mount()", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
_, err = w.Write(pm.ToSend())
|
|
|
|
if err != nil {
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionSyncDevice})
|
|
|
|
logger.Error("handlePairingSyncDeviceSend w.Write(pm.ToSend())", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferSuccess, Action: ActionSyncDevice})
|
|
|
|
|
|
|
|
pm.LockPayload()
|
2023-01-06 12:21:14 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
// Installation data handling
|
|
|
|
|
|
|
|
func handleReceiveInstallation(hs HandlerServer, pmr PayloadMounterReceiver) http.HandlerFunc {
|
|
|
|
logger := hs.GetLogger()
|
2023-02-28 12:32:45 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-04-02 23:15:13 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventConnectionSuccess, Action: ActionPairingInstallation})
|
2023-03-23 11:44:15 +00:00
|
|
|
payload, err := io.ReadAll(r.Body)
|
2023-02-28 12:32:45 +00:00
|
|
|
if err != nil {
|
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionPairingInstallation})
|
2023-03-23 11:44:15 +00:00
|
|
|
logger.Error("handleReceiveInstallation io.ReadAll(r.Body)", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-02-28 12:32:45 +00:00
|
|
|
return
|
|
|
|
}
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferSuccess, Action: ActionPairingInstallation})
|
2023-02-28 12:32:45 +00:00
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
err = pmr.Receive(payload)
|
2023-02-28 12:32:45 +00:00
|
|
|
if err != nil {
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventProcessError, Error: err.Error(), Action: ActionPairingInstallation})
|
|
|
|
logger.Error("handleReceiveInstallation pmr.Receive(payload)", zap.Error(err), zap.Binary("payload", payload))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-02-28 12:32:45 +00:00
|
|
|
return
|
|
|
|
}
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventProcessSuccess, Action: ActionPairingInstallation})
|
2023-02-28 12:32:45 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
func handleSendInstallation(hs HandlerServer, pmr PayloadMounterReceiver) http.HandlerFunc {
|
|
|
|
logger := hs.GetLogger()
|
2023-01-06 12:21:14 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-04-02 23:15:13 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventConnectionSuccess, Action: ActionPairingInstallation})
|
2023-01-06 12:21:14 +00:00
|
|
|
w.Header().Set("Content-Type", "application/octet-stream")
|
2023-03-23 11:44:15 +00:00
|
|
|
err := pmr.Mount()
|
2023-01-06 12:21:14 +00:00
|
|
|
if err != nil {
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionPairingInstallation})
|
|
|
|
logger.Error("handleSendInstallation pmr.Mount()", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
_, err = w.Write(pmr.ToSend())
|
2023-01-06 12:21:14 +00:00
|
|
|
if err != nil {
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferError, Error: err.Error(), Action: ActionPairingInstallation})
|
|
|
|
logger.Error("handleSendInstallation w.Write(pmr.ToSend())", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
2023-03-23 11:44:15 +00:00
|
|
|
signal.SendLocalPairingEvent(Event{Type: EventTransferSuccess, Action: ActionPairingInstallation})
|
2023-01-06 12:21:14 +00:00
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
pmr.LockPayload()
|
2023-01-06 12:21:14 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-23 11:44:15 +00:00
|
|
|
// Challenge middleware and handling
|
|
|
|
|
2023-03-16 14:15:07 +00:00
|
|
|
func middlewareChallenge(cg *ChallengeGiver, next http.Handler) http.HandlerFunc {
|
2023-01-06 12:21:14 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-03-22 12:58:09 +00:00
|
|
|
err := cg.checkChallengeResponse(w, r)
|
|
|
|
if err != nil {
|
|
|
|
if cErr, ok := err.(*ChallengeError); ok {
|
|
|
|
http.Error(w, cErr.Text, cErr.HTTPCode)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
cg.logger.Error("failed to checkChallengeResponse in middlewareChallenge", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
next.ServeHTTP(w, r)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-03-16 14:15:07 +00:00
|
|
|
func handlePairingChallenge(cg *ChallengeGiver) http.HandlerFunc {
|
2023-01-06 12:21:14 +00:00
|
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
2023-03-22 12:58:09 +00:00
|
|
|
challenge, err := cg.getChallenge(w, r)
|
|
|
|
if err != nil {
|
|
|
|
if cErr, ok := err.(*ChallengeError); ok {
|
|
|
|
http.Error(w, cErr.Text, cErr.HTTPCode)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
cg.logger.Error("failed to getChallenge in handlePairingChallenge", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
w.Header().Set("Content-Type", "application/octet-stream")
|
2023-03-22 12:58:09 +00:00
|
|
|
_, err = w.Write(challenge)
|
2023-01-06 12:21:14 +00:00
|
|
|
if err != nil {
|
2023-03-22 12:58:09 +00:00
|
|
|
cg.logger.Error("failed to Write(challenge) in handlePairingChallenge", zap.Error(err))
|
|
|
|
http.Error(w, "error", http.StatusInternalServerError)
|
2023-01-06 12:21:14 +00:00
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|