adding backend distribution point for sealed channels

This commit is contained in:
Roland Osborne 2022-12-03 16:57:22 -08:00
parent 67c4469dcc
commit 538094bf7f
8 changed files with 116 additions and 2 deletions

View File

@ -3762,6 +3762,8 @@ components:
type: boolean
disabled:
type: boolean
seal:
type: string
Profile:
type: object
@ -3931,6 +3933,8 @@ components:
type: string
node:
type: string
seal:
type: string
revision:
type: integer
format: int64

View File

@ -8,7 +8,7 @@ import (
//GetAccountStatus retrieves account state values
func GetAccountStatus(w http.ResponseWriter, r *http.Request) {
session, code, err := GetSession(r)
session, code, err := GetSessionDetail(r)
if err != nil {
ErrResponse(w, code, err)
return
@ -22,6 +22,10 @@ func GetAccountStatus(w http.ResponseWriter, r *http.Request) {
}
// construct response
seal := &Seal{}
seal.Salt = account.AccountDetail.SealSalt
seal.PrivateKeyEncrypted = account.AccountDetail.SealPrivate
seal.PublicKey = account.AccountDetail.SealPublic
status := &AccountStatus{}
status.StorageAvailable = getNumConfigValue(CNFStorage, 0)
for _, asset := range assets {
@ -31,6 +35,6 @@ func GetAccountStatus(w http.ResponseWriter, r *http.Request) {
status.ForwardingAddress = account.Forward
status.Searchable = account.Searchable
status.PushEnabled = session.PushEnabled
status.Seal = seal
WriteResponse(w, status)
}

View File

@ -0,0 +1,49 @@
package databag
import (
"databag/internal/store"
"gorm.io/gorm"
"net/http"
)
//SetAccountSeal sets sealing key for channels
func SetAccountSeal(w http.ResponseWriter, r *http.Request) {
account, code, err := ParamAgentToken(r, true)
if err != nil {
ErrResponse(w, code, err)
return
}
seal := Seal{}
if err := ParseRequest(r, w, &seal); err != nil {
ErrResponse(w, http.StatusBadRequest, err)
return
}
// update record
account.AccountDetail.SealSalt = seal.Salt
account.AccountDetail.SealPrivate = seal.PrivateKeyEncrypted
account.AccountDetail.SealPublic = seal.PublicKey
err = store.DB.Transaction(func(tx *gorm.DB) error {
if res := tx.Save(&account.AccountDetail).Error; res != nil {
return res
}
if res := tx.Model(&account).Update("profile_revision", account.ProfileRevision+1).Error; res != nil {
return res
}
if res := tx.Model(&account).Update("account_revision", account.AccountRevision+1).Error; res != nil {
return res
}
return nil
})
if err != nil {
ErrResponse(w, http.StatusInternalServerError, err)
return
}
SetProfileNotification(account)
SetStatus(account)
WriteResponse(w, nil)
}

View File

@ -95,6 +95,31 @@ func ParamAdminToken(r *http.Request) (int, error) {
return http.StatusOK, nil
}
//GetSessionDetail retrieves account detail specified by agent query param
func GetSessionDetail(r *http.Request) (*store.Session, int, error) {
// parse authentication token
target, access, err := ParseToken(r.FormValue("agent"))
if err != nil {
return nil, http.StatusBadRequest, err
}
// find session record
var session store.Session;
if err := store.DB.Preload("Account.AccountDetail").Where("account_id = ? AND token = ?", target, access).Find(&session).Error; err != nil {
if errors.Is(err, gorm.ErrRecordNotFound) {
return nil, http.StatusNotFound, err
}
return nil, http.StatusInternalServerError, err
}
if session.Account.Disabled {
return nil, http.StatusGone, errors.New("account is inactive")
}
return &session, http.StatusOK, nil
}
//GetSession retrieves account specified by agent query param
func GetSession(r *http.Request) (*store.Session, int, error) {

View File

@ -16,6 +16,7 @@ func getProfileModel(account *store.Account) *Profile {
Revision: account.ProfileRevision,
Version: APPVersion,
Node: getStrConfigValue(CNFDomain, ""),
Seal: account.AccountDetail.SealPublic,
}
}
@ -94,6 +95,7 @@ func getCardProfileModel(slot *store.CardSlot) *CardProfile {
ImageSet: slot.Card.Image != "",
Version: slot.Card.Version,
Node: slot.Card.Node,
Seal: slot.Card.Seal,
}
}

View File

@ -16,6 +16,8 @@ type AccountProfile struct {
ImageSet bool `json:"imageSet,omitempty"`
Seal string `json:"seal,emitempty"`
Disabled bool `json:"disabled"`
}
@ -32,6 +34,10 @@ type AccountStatus struct {
Searchable bool `json:"searchable"`
PushEnabled bool `json:"pushEnabled"`
Sealable bool `json:"sealable"`
Seal *Seal `json:"seal,omitempty"`
}
//Announce initial message sent on websocket
@ -134,6 +140,8 @@ type CardProfile struct {
ImageSet bool `json:"imageSet"`
Seal string `json:"seal,omitempty"`
Version string `json:"version,omitempty"`
Node string `json:"node"`
@ -363,6 +371,8 @@ type Profile struct {
Image string `json:"image,omitempty"`
Seal string `json:"seal,omitempty"`
Revision int64 `json:"revision"`
Version string `json:"version,omitempty"`
@ -394,6 +404,15 @@ type Revision struct {
Card int64 `json:"card"`
}
//Seal key for channel sealing
type Seal struct {
Salt string `json:"salt"`
PrivateKeyEncrypted string `json:"privateKeyEncrypted,omitempty"`
PublicKey string `json:"publicKey,omitempty"`
}
//SignedData object serialized in message
type SignedData struct {
GUID string `json:"guid"`

View File

@ -188,6 +188,13 @@ var endpoints = routes{
SetAccountNotification,
},
route{
"SetAccountSeal",
strings.ToUpper("Put"),
"/account/seal",
SetAccountSeal,
},
route{
"SetAccountSerchable",
strings.ToUpper("Put"),

View File

@ -95,6 +95,9 @@ type AccountDetail struct {
Description string
Location string
Image string
SealSalt string
SealPrivate string
SealPublic string
}
type Session struct {
@ -181,6 +184,7 @@ type Card struct {
Description string
Location string
Image string
Seal string
Version string `gorm:"not null"`
Node string `gorm:"not null"`
ProfileRevision int64 `gorm:"not null"`