package connections import ( "crypto/rand" "cwtch.im/cwtch/event" "cwtch.im/cwtch/protocol" "cwtch.im/cwtch/server/fetch" "cwtch.im/cwtch/server/send" "git.openprivacy.ca/openprivacy/libricochet-go" "git.openprivacy.ca/openprivacy/libricochet-go/channels" "git.openprivacy.ca/openprivacy/libricochet-go/connection" "git.openprivacy.ca/openprivacy/libricochet-go/connectivity" "git.openprivacy.ca/openprivacy/libricochet-go/identity" "golang.org/x/crypto/ed25519" "net" "testing" "time" ) func ServerAuthValid(hostname string, key ed25519.PublicKey) (allowed, known bool) { return true, true } type TestServer struct { connection.AutoConnectionHandler Received bool } func (ts *TestServer) HandleGroupMessage(gm *protocol.GroupMessage) { ts.Received = true } func (ts *TestServer) HandleFetchRequest() []*protocol.GroupMessage { return []*protocol.GroupMessage{{Ciphertext: []byte("hello"), Signature: []byte{}, Spamguard: []byte{}}, {Ciphertext: []byte("hello"), Signature: []byte{}, Spamguard: []byte{}}} } func runtestserver(t *testing.T, ts *TestServer, identity identity.Identity, listenChan chan bool) { ln, _ := net.Listen("tcp", "127.0.0.1:5451") listenChan <- true conn, _ := ln.Accept() defer conn.Close() rc, err := goricochet.NegotiateVersionInbound(conn) if err != nil { t.Errorf("Negotiate Version Error: %v", err) } err = connection.HandleInboundConnection(rc).ProcessAuthAsV3Server(identity, ServerAuthValid) if err != nil { t.Errorf("ServerAuth Error: %v", err) } ts.RegisterChannelHandler("im.cwtch.server.send", func() channels.Handler { server := new(send.CwtchServerSendChannel) server.Handler = ts return server }) ts.RegisterChannelHandler("im.cwtch.server.fetch", func() channels.Handler { server := new(fetch.CwtchServerFetchChannel) server.Handler = ts return server }) rc.Process(ts) } func TestPeerServerConnection(t *testing.T) { pub, priv, _ := ed25519.GenerateKey(rand.Reader) identity := identity.InitializeV3("", &priv, &pub) ts := new(TestServer) ts.Init() listenChan := make(chan bool) go runtestserver(t, ts, identity, listenChan) <-listenChan onionAddr := identity.Hostname() manager := event.NewEventManager() engine := NewProtocolEngine(identity, priv, connectivity.LocalProvider(), manager, nil) psc := NewPeerServerConnection(engine, "127.0.0.1:5451|"+onionAddr) numcalls := 0 psc.GroupMessageHandler = func(s string, gm *protocol.GroupMessage) { numcalls++ } closedCalls := 0 psc.CloseHandler = func(s string) { closedCalls++ } state := psc.GetState() if state != DISCONNECTED { t.Errorf("new connections should start in disconnected state") } time.Sleep(time.Second * 1) go psc.Run() time.Sleep(time.Second * 2) state = psc.GetState() if state != AUTHENTICATED { t.Errorf("connection should now be authed(%v), instead was %v", AUTHENTICATED, state) } gm := &protocol.GroupMessage{Ciphertext: []byte("hello"), Signature: []byte{}} psc.SendGroupMessage(gm) time.Sleep(time.Second * 2) if ts.Received == false { t.Errorf("Should have received a group message in test server") } if numcalls != 2 { t.Errorf("Should have received 2 calls from fetch request, instead received %v", numcalls) } if closedCalls != 1 { t.Errorf("Should have closed connection 1 time, instead of %v", closedCalls) } }