一些关于点对点加密通讯的思考: selfdata + relay
# ====================================Thinking1=============================================
c->s:
1. c.netPriv + s.netPub ===> key
2. data + key ===> edata
s->c:
1. s.netPriv + c.netPub ===> key
2. data + key ===> edata
c1->s:
1. c1.id + c1.id ==> eid1
2. c1.netPub + (c-s).key ===> s.pubc1
c2->s:
1. c2.id + c2.id ===> eid2
3. c2.netPub + (c-s).key ===> s.pubc2
c1->c2:
1. c2->s(pull): (c1.id + c1.id) ===> (eid1 + s.pubc1)
2. c2->c2(...): c2.dataPub + (c2.netPriv + s.pubc1).key ===> c2sdata
3. c2->s(push): eid1 + c2sdata + s.pubc2(swap+sign) ===> c1.mq
4. c1->s(pull): (c1.id + c1.id) ===> eid2 + c2sdata + s.pubc2
5. c1->c1(...): c2sdata + (c1.netPriv + s.pubc2).key ===> c2.dataPub
6. c1->c1(...): c1.datapub + (c1.netPriv + s.pubc2).key ===> c1sdata
7. c1->s(push): eid2 + c1sdata + s.pubc1(swap+sign) ===> c2.mq
8. c2->s(pull): (c2.id + c2.id) ===> eid2 + c1sdata + s.pubc1
9. c2->c2(...): c1sdata + (c2.netPriv + s.pubc1).key ===> c1.dataPub
# ====================================Thinking1=============================================
# ====================================Thinking2=============================================
just only for c1<->c2
1. c1.random + c2.netPub ===> erandom
2. (c1.netPriv + c2.netPub).key + c1.random ===> netKey
3. (c2.netPriv + c1.netPub).key + (erandom + c2.netPriv).random ===> netKey
push/pull list
1. public: (c1.id + c1.id).key, (public + c1.netPub + selfEncryptedKey).value
2. c1<->c2: (c1.id + netKey).key, (c2/c3/c4.id + c2/c3/c4.netPub + public + c2/c3/c4sdata + netKey).value
3. self.list: (c1.id + c1.dataPub).key, (data + c1.dataPub)
4. c<->s: cdata + s.pub ===> sedata + s.priv ===> sdata + c.pub ===> cedata + c.priv ===> c.data
# ====================================Thinking3=============================================
# ====================================Thinking3=============================================
1. self<->self: selfdata + relay, relay.store: memory.map + memory.filesystem(open source)
// 考虑是否需要
1.1. memory.filesystem: c1.fname + s.netPub ===> efname + s.netPriv ===> s.fname ===> memory.fs
1.2. memory.filesystem: efname + s.netPriv ===> s.fname + c2.netPub ===> efname ===> s.downloadURL
1.3. memory.filesystem: efname + c2.netPriv ===> s.fname + s.netPub ===> efname ===> c2.downloadURL
2. rc1<->rc2: selfdata + relay, relay.store: swap + redis + p2p.file(open source)
3. sdc1<->sdc2: selfdata + gossip/p2p(blockchain)
# ====================================Thinking3=============================================
# ====================================Thinking4=============================================
1. key for mq: (c1.id + c1.id).key + (name.id + name.id).key + (email.id + email.id).key
2. split for key: "-"
# ====================================Thinking4=============================================
package rsrelay
import (
"fmt"
"io/ioutil"
"net/http"
)
func doCheckPermission(r *http.Request) (string, string, []string) {
dparams, err := decodeNetParams(WebParams(r).Get("param"), v_sysPrivateKey)
if err != nil || len(dparams) < 3 {
LogPrint("decodeNetParams failed, detail: %+v", err, "error")
return "", "", nil
}
selfPub := ""
if bytes := getBytes(dparams[0]); len(bytes) > 0 {
selfPub = string(bytes[0])
}
if selfPub == "" {
if dparams[0] == dparams[len(dparams) - 1] {
selfPub = WebParams(r).Get("data")
} else {
LogPrint("getPublicKey failed, selfID: " + dparams[0], "error")
return "", "", nil
}
}
if tokenVerify(dparams[1], dparams[2], []byte(selfPub), []byte(v_sysPrivateKey)) != nil {
LogPrint("tokenVerify failed, selfID: " + dparams[0], "error")
return "", "", nil
}
return dparams[0], selfPub, dparams
}
func doResponseOK(w http.ResponseWriter, r *http.Request, selfPub string, datas ...[]byte) {
respBytes := make([][]byte, 0)
token, signature := tokenCreate([]byte(selfPub), []byte(v_sysPrivateKey))
respBytes = append(respBytes, token, signature)
respBytes = append(respBytes, datas...)
ResponseOk(w, r, WebOk(respBytes))
}
// GET /api/data/pull
// param: [selfID, token, signature], data: demo
func WebDataPull(w http.ResponseWriter, r *http.Request) {
if selfID, selfPub, dparams := doCheckPermission(r); dparams != nil && selfPub != "" && selfID != "" {
if pullBytes, err := doWebPullForBytes(r, selfID, selfPub, WebParams(r).Get("data")); err != nil {
ResponseError(w, r, err.Error())
} else {
doResponseOK(w, r, selfPub, pullBytes...)
vBytesCache.Delete(WebParams(r).Get("data"))
}
}
ResponseError(w, r, "permission denied")
}
// GET /api/data/push
// param: [selfID, token, signature], data: demo
func WebDataPush(w http.ResponseWriter, r *http.Request) {
if selfID, selfPub, dparams := doCheckPermission(r); dparams != nil && selfPub != "" && selfID != "" {
recvIds := dparams[3:]
failedIds := make([][]byte, 0)
for i := 0; i < len(recvIds); i++ {
if err := doWebPushForBytes(r, selfID, selfPub, recvIds[i]); err != nil {
failedIds = append(failedIds, []byte(recvIds[i]))
LogPrint(err.Error(), "error")
}
}
doResponseOK(w, r, selfPub, failedIds...)
return
}
ResponseError(w, r, "permission denied")
}
func doWebPushForBytes(r *http.Request, selfID, selfPub, pushID string) error {
// cache for bytes
buf := []byte(WebParams(r).Get("data"))
if len(buf) == 0 {
bytes, err := ioutil.ReadAll(r.Body)
if err != nil {
return err
}
buf = bytes[:]
}
if len(buf) == 0 {
return fmt.Errorf("invalid push bytes, recvID: %s", pushID)
}
addBytes(pushID, buf[:])
//infoLog("upload text successed, push: %s, size: %d", pushID, len(buf))
return nil
}
func doWebPullForBytes(r *http.Request, selfID, sdPub, pullID string) ([][]byte, error) {
return getBytes(pullID), nil
}

