diff --git a/api/messages.go b/api/messages.go
index c36e5ae5e84326c56406d3a4a38c74cf261d3c97..870311ef31348cb17a14a18e41288df6e16fd0f1 100644
--- a/api/messages.go
+++ b/api/messages.go
@@ -7,6 +7,7 @@
 package api
 
 import (
+	"fmt"
 	jww "github.com/spf13/jwalterweatherman"
 	"gitlab.com/elixxir/client/globals"
 	"gitlab.com/elixxir/client/network/gateway"
@@ -14,62 +15,92 @@ import (
 	"gitlab.com/elixxir/comms/network"
 	ds "gitlab.com/elixxir/comms/network/dataStructures"
 	"gitlab.com/elixxir/primitives/states"
+	"gitlab.com/xx_network/comms/connect"
 	"gitlab.com/xx_network/primitives/id"
 	"time"
 )
 
-type RoundEventCallback interface {
-	Report(succeeded, timedout bool, rounds map[id.Round]RoundResult)
-}
-
+// Enum of possible round results to pass back
 type RoundResult uint
-const(
+
+const (
 	TimeOut RoundResult = iota
 	Failed
 	Succeeded
 )
 
+// Callback interface which reports the requested rounds.
+// Designed such that the caller may decide how much detail they need.
+// allRoundsSucceeded:
+//   Returns false if any rounds in the round map were unsuccessful.
+//   Returns true if ALL rounds were successful
+// timedOut:
+//    Returns true if any of the rounds timed out while being monitored
+//	  Returns false if all rounds statuses were returned
+// rounds contains a mapping of all previously requested rounds to
+//   their respective round results
+type RoundEventCallback interface {
+	Report(allRoundsSucceeded, timedOut bool, rounds map[id.Round]RoundResult)
+}
 
-func (c *Client)  GetRoundResults(roundList []id.Round,
-	roundCallback RoundEventCallback, timeout time.Duration) error {
+// Comm interface for RequestHistoricalRounds.
+// Constructed for testability with getRoundResults
+type historicalRoundsComm interface {
+	RequestHistoricalRounds(host *connect.Host,
+		message *pb.HistoricalRounds) (*pb.HistoricalRoundsResponse, error)
+	GetHost(hostId *id.ID) (*connect.Host, bool)
 }
 
-// Adjudicates on the rounds requested. Checks if they are older rounds or in progress rounds.
-// Sends updates on the rounds with callbacks
-func (c *Client)  getRoundResults(roundList []id.Round,
-	roundCallback RoundEventCallback,  timeout time.Duration, sendResults chan ds.EventReturn, ) error {
-	// Get the oldest round in the buffer
-	networkInstance := c.network.GetInstance()
+// Adjudicates on the rounds requested. Checks if they are
+// older rounds or in progress rounds.
+func (c *Client) GetRoundResults(roundList []id.Round, timeout time.Duration,
+	roundCallback RoundEventCallback) error {
 
-	/*check message delivery*/
-	roundEvents := c.GetRoundEvents()
-	numResults := 0
+	sendResults := make(chan ds.EventReturn, len(roundList))
+
+	return c.getRoundResults(roundList, timeout, roundCallback,
+		sendResults, c.comms)
+}
 
-	// Generate a message
+// Helper function which does all the logic for GetRoundResults
+func (c *Client) getRoundResults(roundList []id.Round, timeout time.Duration,
+	roundCallback RoundEventCallback, sendResults chan ds.EventReturn,
+	commsInterface historicalRoundsComm) error {
+
+	networkInstance := c.network.GetInstance()
+
+	// Generate a message to track all older rounds
 	historicalRequest := &pb.HistoricalRounds{
 		Rounds: []uint64{},
 	}
 
+	// Generate all tracking structures for rounds
+	roundEvents := c.GetRoundEvents()
+	roundsResults := make(map[id.Round]RoundResult)
+	allRoundsSucceeded := true
+	numResults := 0
 
-	rounds := make(map[id.Round]RoundResult)
-	succeeded := true
-
+	// Parse and adjudicate every round
 	for _, rnd := range roundList {
-		rounds[rnd]=TimeOut
+		// Every round is timed out by default, until proven to have finished
+		roundsResults[rnd] = TimeOut
 		roundInfo, err := networkInstance.GetRound(rnd)
-
-		if err==nil{
+		// If we have the round in the buffer
+		if err == nil {
+			// Check if the round is done (completed or failed) or in progress
 			if states.Round(roundInfo.State) == states.COMPLETED {
-				rounds[rnd] = Succeeded
-			}else if states.Round(roundInfo.State) ==  states.FAILED {
-				rounds[rnd] = Failed
-				succeeded = false
-			}else{
+				roundsResults[rnd] = Succeeded
+			} else if states.Round(roundInfo.State) == states.FAILED {
+				roundsResults[rnd] = Failed
+				fmt.Printf("Round %d considered %v\n", roundInfo.ID, roundInfo.State)
+				allRoundsSucceeded = false
+			} else {
+				// If in progress, add a channel monitoring its status
 				roundEvents.AddRoundEventChan(rnd, sendResults,
 					timeout-time.Millisecond, states.COMPLETED, states.FAILED)
 				numResults++
 			}
-		}else {
+		} else {
 			jww.DEBUG.Printf("Failed to ger round [%d] in buffer: %v", rnd, err)
 			// Update oldest round (buffer may have updated externally)
 			oldestRound := networkInstance.GetOldestRoundID()
@@ -78,7 +109,8 @@ func (c *Client)  getRoundResults(roundList []id.Round,
 				// Add it to the historical round request (performed later)
 				historicalRequest.Rounds = append(historicalRequest.Rounds, uint64(rnd))
 				numResults++
-			}else{
+			} else {
+				// Otherwise, monitor it's progress
 				roundEvents.AddRoundEventChan(rnd, sendResults,
 					timeout-time.Millisecond, states.COMPLETED, states.FAILED)
 				numResults++
@@ -86,41 +118,49 @@ func (c *Client)  getRoundResults(roundList []id.Round,
 		}
 	}
 
-	//request historical rounds if any are needed
-	if len(historicalRequest.Rounds)>0{
-		// Find out what happened to old (historical) rounds
-		go c.getHistoricalRounds(historicalRequest, networkInstance, sendResults)
+	// Find out what happened to old (historical) rounds if any are needed
+	if len(historicalRequest.Rounds) > 0 {
+		go c.getHistoricalRounds(historicalRequest, networkInstance, sendResults, commsInterface)
 	}
 
-	// Determine the success of all rounds requested
+	// Determine the results of all rounds requested
 	go func() {
-		//create the results timer
+		// Create the results timer
 		timer := time.NewTimer(timeout)
 		for {
-			//if we know about all rounds, return
-			if numResults==0{
-				roundCallback.Report(succeeded, true, rounds)
+			fmt.Printf("looping at most: %v\n", numResults)
+
+			// If we know about all rounds, return
+			if numResults == 0 {
+				fmt.Printf("passing to report the following: %v\n", allRoundsSucceeded)
+				roundCallback.Report(allRoundsSucceeded, false, roundsResults)
 				return
 			}
 
-			//wait for info about rounds or the timeout to occur
+			// Wait for info about rounds or the timeout to occur
 			select {
-			case <- timer.C:
-				roundCallback.Report(false, true, rounds)
+			case <-timer.C:
+				fmt.Printf("timed out\n")
+				roundCallback.Report(false, true, roundsResults)
 				return
 			case roundReport := <-sendResults:
+				fmt.Printf("roundReport: %v\n", roundReport)
 				numResults--
-				// skip if the round is nil (unknown from historical rounds)
+				// Skip if the round is nil (unknown from historical rounds)
 				// they default to timed out, so correct behavior is preserved
-				if roundReport.RoundInfo==nil || roundReport.TimedOut{
-					succeeded = false
-				}else{
-					//if available, denote the result
-					if states.Round(roundReport.RoundInfo.State) == states.COMPLETED{
-						rounds[id.Round(roundReport.RoundInfo.ID)] = Succeeded
-					} else{
-						rounds[id.Round(roundReport.RoundInfo.ID)] = Failed
-						succeeded = false
+				if roundReport.RoundInfo == nil || roundReport.TimedOut {
+					allRoundsSucceeded = false
+				} else {
+					// If available, denote the result
+					roundId := id.Round(roundReport.RoundInfo.ID)
+					if states.Round(roundReport.RoundInfo.State) == states.COMPLETED {
+						fmt.Printf("round %d marked successful\n", roundId)
+						roundsResults[roundId] = Succeeded
+					} else {
+						roundsResults[roundId] = Failed
+						allRoundsSucceeded = false
+						fmt.Printf("Round [unknown] considered [failed]\n")
+
 					}
 				}
 			}
@@ -133,13 +173,14 @@ func (c *Client)  getRoundResults(roundList []id.Round,
 // Helper function which asynchronously pings a random gateway until
 // it gets information on it's requested historical rounds
 func (c *Client) getHistoricalRounds(msg *pb.HistoricalRounds,
-	instance *network.Instance, sendResults chan ds.EventReturn) {
+	instance *network.Instance, sendResults chan ds.EventReturn,
+	comms historicalRoundsComm) {
 
 	var resp *pb.HistoricalRoundsResponse
 
 	for {
 		// Find a gateway to request about the roundRequests
-		gwHost, err := gateway.Get(instance.GetPartialNdf().Get(), c.comms, c.rng.GetStream())
+		gwHost, err := gateway.Get(instance.GetPartialNdf().Get(), comms, c.rng.GetStream())
 		if err != nil {
 			globals.Log.FATAL.Panicf("Failed to track network, NDF has corrupt "+
 				"data: %s", err)
@@ -147,8 +188,8 @@ func (c *Client) getHistoricalRounds(msg *pb.HistoricalRounds,
 
 		// If an error, retry with (potentially) a different gw host.
 		// If no error from received gateway request, exit loop
-		//vand process rounds
-		resp, err = c.comms.RequestHistoricalRounds(gwHost, msg)
+		// and process rounds
+		resp, err = comms.RequestHistoricalRounds(gwHost, msg)
 		if err == nil {
 			break
 		}
@@ -156,9 +197,10 @@ func (c *Client) getHistoricalRounds(msg *pb.HistoricalRounds,
 
 	// Process historical rounds, sending back to the caller thread
 	for _, ri := range resp.Rounds {
-		sendResults<-  ds.EventReturn{
+		fmt.Printf("received rounds from gateway: %v\n", ri)
+		sendResults <- ds.EventReturn{
 			ri,
 			false,
 		}
 	}
-}
\ No newline at end of file
+}
diff --git a/api/messages_test.go b/api/messages_test.go
new file mode 100644
index 0000000000000000000000000000000000000000..a643e5ef97512b77297387ca605e0f498c8df3f9
--- /dev/null
+++ b/api/messages_test.go
@@ -0,0 +1,226 @@
+///////////////////////////////////////////////////////////////////////////////
+// Copyright © 2020 xx network SEZC                                          //
+//                                                                           //
+// Use of this source code is governed by a license that can be found in the //
+// LICENSE file                                                              //
+///////////////////////////////////////////////////////////////////////////////
+package api
+
+import (
+	pb "gitlab.com/elixxir/comms/mixmessages"
+	ds "gitlab.com/elixxir/comms/network/dataStructures"
+	"gitlab.com/elixxir/primitives/states"
+	"gitlab.com/xx_network/primitives/id"
+	"os"
+	"testing"
+	"time"
+)
+
+const numRounds = 10
+
+var testClient *Client
+
+func TestMain(m *testing.M) {
+	var err error
+	testClient, err = newTestingClient(m)
+	t := testing.T{}
+	if err != nil {
+		t.Errorf("Failed in setup: %v", err)
+	}
+
+	os.Exit(m.Run())
+}
+
+// Happy path
+func TestClient_GetRoundResults(t *testing.T) {
+	// Populate a round list to request
+	var roundList []id.Round
+	for i := 0; i < numRounds; i++ {
+		roundList = append(roundList, id.Round(i))
+	}
+
+	// Pre-populate the results channel with successful rounds
+	sendResults := make(chan ds.EventReturn, len(roundList))
+	for i := 0; i < numRounds; i++ {
+		sendResults <- ds.EventReturn{
+			RoundInfo: &pb.RoundInfo{
+				ID:    uint64(i),
+				State: uint32(states.COMPLETED),
+			},
+			TimedOut: false,
+		}
+	}
+
+	// Create a new copy of the test client for this test
+	client := &Client{}
+	*client = *testClient
+
+	// Call the round results
+	receivedRCB := NewMockRoundCB()
+	err := client.getRoundResults(roundList, time.Duration(10)*time.Millisecond,
+		receivedRCB, sendResults, NewNoHistoricalRoundsComm())
+	if err != nil {
+		t.Errorf("Error in happy path: %v", err)
+	}
+
+	// Sleep to allow the report to come through the pipeline
+	time.Sleep(1 * time.Second)
+
+	// If any rounds timed out or any round failed, the happy path has failed
+	if receivedRCB.timedOut || !receivedRCB.allRoundsSucceeded {
+		t.Errorf("Unexpected round failures in happy path. "+
+			"Expected all rounds to succeed with no timeouts."+
+			"\n\tTimedOut: %v"+
+			"\n\tallRoundsSucceeded: %v", receivedRCB.timedOut, receivedRCB.allRoundsSucceeded)
+	}
+
+}
+
+// Checks that an two failed rounds (one timed out, one failure)
+// affects the values in the report.
+// Kept separately to ensure uncoupled failed rounds
+// affect both report booleans
+func TestClient_GetRoundResults_FailedRounds(t *testing.T) {
+	// Populate a round list to request
+	var roundList []id.Round
+	for i := 0; i < numRounds; i++ {
+		roundList = append(roundList, id.Round(i))
+	}
+
+	// Pre-populate the results channel with mostly successful rounds
+	sendResults := make(chan ds.EventReturn, len(roundList))
+	for i := 0; i < numRounds; i++ {
+		// Last two rounds will have a failure and a timeout respectively
+		result := ds.EventReturn{
+			RoundInfo: &pb.RoundInfo{
+				ID:    uint64(i),
+				State: uint32(states.COMPLETED),
+			},
+			TimedOut: false,
+		}
+		if i == numRounds-2 {
+			result.RoundInfo.State = uint32(states.FAILED)
+			sendResults <- result
+		} else if i == numRounds-1 {
+			result.TimedOut = true
+			sendResults <- result
+		} else {
+			sendResults <- result
+		}
+
+	}
+
+	// Create a new copy of the test client for this test
+	client := &Client{}
+	*client = *testClient
+
+	// Call the round results
+	receivedRCB := NewMockRoundCB()
+	err := client.getRoundResults(roundList, time.Duration(10)*time.Millisecond,
+		receivedRCB, sendResults, NewNoHistoricalRoundsComm())
+	if err != nil {
+		t.Errorf("Error in happy path: %v", err)
+	}
+
+	// Sleep to allow the report to come through the pipeline
+	time.Sleep(2 * time.Second)
+
+	// If no rounds have timed out or no round failed, this test has failed
+	if !receivedRCB.timedOut || receivedRCB.allRoundsSucceeded {
+		t.Errorf("Expected some rounds to fail and others to timeout. "+
+			"\n\tTimedOut: %v"+
+			"\n\tallRoundsSucceeded: %v", receivedRCB.timedOut, receivedRCB.allRoundsSucceeded)
+	}
+
+}
+
+// Force some timeouts by not populating the entire results channel
+func TestClient_GetRoundResults_Timeout(t *testing.T) {
+	// Populate a round list to request
+	var roundList []id.Round
+	for i := 0; i < numRounds; i++ {
+		roundList = append(roundList, id.Round(i))
+	}
+
+	// Generate a results which never sends (empty chan)
+	sendResults := make(chan ds.EventReturn)
+
+	// Create a new copy of the test client for this test
+	client := &Client{}
+	*client = *testClient
+
+	// Call the round results
+	receivedRCB := NewMockRoundCB()
+	err := client.getRoundResults(roundList, time.Duration(10)*time.Millisecond,
+		receivedRCB, sendResults, NewNoHistoricalRoundsComm())
+	if err != nil {
+		t.Errorf("Error in happy path: %v", err)
+	}
+	// Sleep to allow the report to come through the pipeline
+	time.Sleep(2*time.Second)
+
+	// If no rounds have timed out , this test has failed
+	if !receivedRCB.timedOut  {
+		t.Errorf("Unexpected round failures in happy path. "+
+			"Expected all rounds to succeed with no timeouts."+
+			"\n\tTimedOut: %v", receivedRCB.timedOut)
+	}
+
+}
+
+// Use the historical rounds interface which actually sends back rounds
+func TestClient_GetRoundResults_HistoricalRounds(t *testing.T)  {
+	// Populate a round list to request
+	var roundList []id.Round
+	for i := 0; i < numRounds; i++ {
+		roundList = append(roundList, id.Round(i))
+	}
+
+	// Pre-populate the results channel with successful rounds
+	sendResults := make(chan ds.EventReturn, len(roundList)-2)
+	for i := 0; i < numRounds; i++ {
+		// Skip sending rounds intended for historical rounds comm
+		if i == failedHistoricalRoundID ||
+			i == completedHistoricalRoundID {continue}
+
+		sendResults <- ds.EventReturn{
+			RoundInfo: &pb.RoundInfo{
+				ID:    uint64(i),
+				State: uint32(states.COMPLETED),
+			},
+			TimedOut: false,
+		}
+	}
+
+
+	// Create a new copy of the test client for this test
+	client := &Client{}
+	*client = *testClient
+
+
+	// Overpopulate the round buffer, ensuring a circle back of the ring buffer
+	for i := 1; i <= ds.RoundInfoBufLen + completedHistoricalRoundID + 1 ; i++ {
+		ri := &pb.RoundInfo{ID: uint64(i)}
+		signRoundInfo(ri)
+		client.network.GetInstance().RoundUpdate(ri)
+
+	}
+
+	// Call the round results
+	receivedRCB := NewMockRoundCB()
+	err := client.getRoundResults(roundList, time.Duration(10)*time.Millisecond,
+		receivedRCB, sendResults, NewHistoricalRoundsComm())
+	if err != nil {
+		t.Errorf("Error in happy path: %v", err)
+	}
+	// Sleep to allow the report to come through the pipeline
+	time.Sleep(2*time.Second)
+
+	// If no round failed, this test has failed
+	if  receivedRCB.allRoundsSucceeded {
+		t.Errorf("Unexpected round failures in happy path. "+
+			"Expected all rounds to succeed with no timeouts."+
+			"\n\tTimedOut: %v"+
+			"\n\tallRoundsSucceeded: %v", receivedRCB.timedOut, receivedRCB.allRoundsSucceeded)
+	}
+}
\ No newline at end of file
diff --git a/api/utilsInterfaces_test.go b/api/utilsInterfaces_test.go
new file mode 100644
index 0000000000000000000000000000000000000000..e496fc7f762c4de24f552bd9c858dd569fce64c4
--- /dev/null
+++ b/api/utilsInterfaces_test.go
@@ -0,0 +1,144 @@
+///////////////////////////////////////////////////////////////////////////////
+// Copyright © 2020 xx network SEZC                                          //
+//                                                                           //
+// Use of this source code is governed by a license that can be found in the //
+// LICENSE file                                                              //
+///////////////////////////////////////////////////////////////////////////////
+package api
+
+import (
+	"fmt"
+	"gitlab.com/elixxir/client/interfaces"
+	"gitlab.com/elixxir/client/interfaces/message"
+	"gitlab.com/elixxir/client/interfaces/params"
+	"gitlab.com/elixxir/client/stoppable"
+	pb "gitlab.com/elixxir/comms/mixmessages"
+	"gitlab.com/elixxir/comms/network"
+	cE2e "gitlab.com/elixxir/crypto/e2e"
+	"gitlab.com/elixxir/primitives/format"
+	"gitlab.com/elixxir/primitives/states"
+	"gitlab.com/xx_network/comms/connect"
+	"gitlab.com/xx_network/primitives/id"
+	"gitlab.com/xx_network/primitives/id/ephemeral"
+)
+
+// A mock structure which should conform to the callback for getRoundResults
+type mockRoundCallback struct {
+	allRoundsSucceeded bool
+	timedOut           bool
+	rounds             map[id.Round]RoundResult
+}
+
+func NewMockRoundCB() *mockRoundCallback {
+	return &mockRoundCallback{}
+}
+
+// Report simply stores the passed in values in the structure
+func (mrc *mockRoundCallback) Report(allRoundsSucceeded, timedOut bool,
+	rounds map[id.Round]RoundResult) {
+	fmt.Printf("allRoundsSucceeded: %v\n", allRoundsSucceeded)
+	fmt.Printf("timedOut: %v\n", timedOut)
+
+	mrc.allRoundsSucceeded = allRoundsSucceeded
+	mrc.timedOut = timedOut
+	mrc.rounds = rounds
+}
+
+// Generate a mock comm which returns no historical round data
+type noHistoricalRounds struct{}
+
+func NewNoHistoricalRoundsComm() *noHistoricalRounds {
+	return &noHistoricalRounds{}
+}
+
+// Returns no rounds back
+func (ht *noHistoricalRounds) RequestHistoricalRounds(host *connect.Host,
+	message *pb.HistoricalRounds) (*pb.HistoricalRoundsResponse, error) {
+	return nil, nil
+}
+func (ht *noHistoricalRounds) GetHost(hostId *id.ID) (*connect.Host, bool) {
+	return nil, false
+}
+
+// Generate a mock comm which returns some historical round data
+type historicalRounds struct{}
+
+func NewHistoricalRoundsComm() *historicalRounds {
+	return &historicalRounds{}
+}
+
+// Return one successful and one failed mock round
+const failedHistoricalRoundID = 7
+const completedHistoricalRoundID = 8
+
+func (ht *historicalRounds) RequestHistoricalRounds(host *connect.Host,
+	message *pb.HistoricalRounds) (*pb.HistoricalRoundsResponse, error) {
+	failedRound := &pb.RoundInfo{
+		ID:    failedHistoricalRoundID,
+		State: uint32(states.FAILED),
+	}
+
+	completedRound := &pb.RoundInfo{
+		ID:    completedHistoricalRoundID,
+		State: uint32(states.COMPLETED),
+	}
+
+	return &pb.HistoricalRoundsResponse{
+		Rounds: []*pb.RoundInfo{failedRound, completedRound},
+	}, nil
+}
+
+func (ht *historicalRounds) GetHost(hostId *id.ID) (*connect.Host, bool) {
+	return nil, true
+}
+
+// Contains a test implementation of the networkManager interface.
+type testNetworkManagerGeneric struct {
+	instance *network.Instance
+}
+
+func (t *testNetworkManagerGeneric) GetHealthTracker() interfaces.HealthTracker {
+	return nil
+}
+
+func (t *testNetworkManagerGeneric) Follow() (stoppable.Stoppable, error) {
+	return nil, nil
+}
+
+func (t *testNetworkManagerGeneric) CheckGarbledMessages() {
+	return
+}
+
+func (t *testNetworkManagerGeneric) SendE2E(m message.Send, p params.E2E) (
+	[]id.Round, cE2e.MessageID, error) {
+	rounds := []id.Round{id.Round(0), id.Round(1), id.Round(2)}
+	return rounds, cE2e.MessageID{}, nil
+
+}
+
+func (t *testNetworkManagerGeneric) SendUnsafe(m message.Send, p params.Unsafe) ([]id.Round, error) {
+
+	return nil, nil
+}
+
+func (t *testNetworkManagerGeneric) SendCMIX(message format.Message, rid *id.ID, p params.CMIX) (id.Round, ephemeral.Id, error) {
+
+	return id.Round(0), ephemeral.Id{}, nil
+
+}
+
+func (t *testNetworkManagerGeneric) GetInstance() *network.Instance {
+	return t.instance
+
+}
+
+func (t *testNetworkManagerGeneric) RegisterWithPermissioning(string) ([]byte, error) {
+	return nil, nil
+}
+
+func (t *testNetworkManagerGeneric) GetRemoteVersion() (string, error) {
+	return "test", nil
+}
+func (t *testNetworkManagerGeneric) GetStoppable() stoppable.Stoppable {
+	return &stoppable.Multi{}
+}
diff --git a/api/utils_test.go b/api/utils_test.go
new file mode 100644
index 0000000000000000000000000000000000000000..dee8810ee4e037ea7e463138447002b3855b76ec
--- /dev/null
+++ b/api/utils_test.go
@@ -0,0 +1,153 @@
+///////////////////////////////////////////////////////////////////////////////
+// Copyright © 2020 xx network SEZC                                          //
+//                                                                           //
+// Use of this source code is governed by a license that can be found in the //
+// LICENSE file                                                              //
+///////////////////////////////////////////////////////////////////////////////
+
+package api
+
+import (
+	"github.com/pkg/errors"
+	"gitlab.com/elixxir/client/globals"
+	"gitlab.com/elixxir/client/interfaces/params"
+	pb "gitlab.com/elixxir/comms/mixmessages"
+	"gitlab.com/elixxir/comms/network"
+	"gitlab.com/elixxir/comms/testkeys"
+	"gitlab.com/xx_network/comms/connect"
+	"gitlab.com/xx_network/comms/signature"
+	"gitlab.com/xx_network/crypto/signature/rsa"
+	"gitlab.com/xx_network/crypto/tls"
+	"gitlab.com/xx_network/primitives/id"
+	"gitlab.com/xx_network/primitives/ndf"
+	"gitlab.com/xx_network/primitives/utils"
+	"testing"
+)
+
+func newTestingClient(face interface{}) (*Client, error) {
+	switch face.(type) {
+	case *testing.T, *testing.M, *testing.B, *testing.PB:
+		break
+	default:
+		globals.Log.FATAL.Panicf("InitTestingSession is restricted to testing only. Got %T", face)
+	}
+
+	def := getNDF(face)
+	marshalledDef, _ := def.Marshal()
+	storageDir := "ignore.1"
+	password := []byte("hunter2")
+	err := NewClient(string(marshalledDef), storageDir, password, "AAAA")
+	if err != nil {
+		return nil, errors.Errorf("Could not construct a mock client: %v", err)
+	}
+
+	c, err := OpenClient(storageDir, password, params.GetDefaultNetwork())
+	if err != nil {
+		return nil, errors.Errorf("Could not open a mock client: %v", err)
+	}
+
+	commsManager := connect.NewManagerTesting(face)
+
+	cert, err := utils.ReadFile(testkeys.GetNodeCertPath())
+	if err != nil {
+		globals.Log.FATAL.Panicf("Failed to create new test Instance: %v", err)
+	}
+
+	commsManager.AddHost(&id.Permissioning, "", cert, connect.GetDefaultHostParams())
+	instanceComms := &connect.ProtoComms{
+		Manager: commsManager,
+	}
+
+
+	thisInstance, err := network.NewInstanceTesting(instanceComms, def, def, nil, nil, face)
+	if err != nil {
+		return nil, nil
+	}
+
+	c.network = &testNetworkManagerGeneric{instance: thisInstance}
+
+	return c, nil
+}
+
+// Helper function which generates an ndf for testing
+func getNDF(face interface{}) *ndf.NetworkDefinition {
+	switch face.(type) {
+	case *testing.T, *testing.M, *testing.B, *testing.PB:
+		break
+	default:
+		globals.Log.FATAL.Panicf("InitTestingSession is restricted to testing only. Got %T", face)
+	}
+
+	cert, _ := utils.ReadFile(testkeys.GetNodeCertPath())
+	nodeID := id.NewIdFromBytes([]byte("gateway"), face)
+	return &ndf.NetworkDefinition{
+		Registration: ndf.Registration{
+			TlsCertificate: string(cert),
+		},
+		Nodes: []ndf.Node {
+			{
+				ID:    nodeID.Bytes(),
+				Address:        "",
+				TlsCertificate: string(cert),
+			},
+		},
+		Gateways: []ndf.Gateway {
+			{
+				ID:    nodeID.Bytes(),
+				Address:        "",
+				TlsCertificate: string(cert),
+			},
+		},
+		E2E: ndf.Group{
+			Prime: "E2EE983D031DC1DB6F1A7A67DF0E9A8E5561DB8E8D49413394C049B" +
+				"7A8ACCEDC298708F121951D9CF920EC5D146727AA4AE535B0922C688B55B3DD2AE" +
+				"DF6C01C94764DAB937935AA83BE36E67760713AB44A6337C20E7861575E745D31F" +
+				"8B9E9AD8412118C62A3E2E29DF46B0864D0C951C394A5CBBDC6ADC718DD2A3E041" +
+				"023DBB5AB23EBB4742DE9C1687B5B34FA48C3521632C4A530E8FFB1BC51DADDF45" +
+				"3B0B2717C2BC6669ED76B4BDD5C9FF558E88F26E5785302BEDBCA23EAC5ACE9209" +
+				"6EE8A60642FB61E8F3D24990B8CB12EE448EEF78E184C7242DD161C7738F32BF29" +
+				"A841698978825B4111B4BC3E1E198455095958333D776D8B2BEEED3A1A1A221A6E" +
+				"37E664A64B83981C46FFDDC1A45E3D5211AAF8BFBC072768C4F50D7D7803D2D4F2" +
+				"78DE8014A47323631D7E064DE81C0C6BFA43EF0E6998860F1390B5D3FEACAF1696" +
+				"015CB79C3F9C2D93D961120CD0E5F12CBB687EAB045241F96789C38E89D796138E" +
+				"6319BE62E35D87B1048CA28BE389B575E994DCA755471584A09EC723742DC35873" +
+				"847AEF49F66E43873",
+			Generator: "2",
+		},
+		CMIX: ndf.Group{
+			Prime: "9DB6FB5951B66BB6FE1E140F1D2CE5502374161FD6538DF1648218642F0B5C48" +
+				"C8F7A41AADFA187324B87674FA1822B00F1ECF8136943D7C55757264E5A1A44F" +
+				"FE012E9936E00C1D3E9310B01C7D179805D3058B2A9F4BB6F9716BFE6117C6B5" +
+				"B3CC4D9BE341104AD4A80AD6C94E005F4B993E14F091EB51743BF33050C38DE2" +
+				"35567E1B34C3D6A5C0CEAA1A0F368213C3D19843D0B4B09DCB9FC72D39C8DE41" +
+				"F1BF14D4BB4563CA28371621CAD3324B6A2D392145BEBFAC748805236F5CA2FE" +
+				"92B871CD8F9C36D3292B5509CA8CAA77A2ADFC7BFD77DDA6F71125A7456FEA15" +
+				"3E433256A2261C6A06ED3693797E7995FAD5AABBCFBE3EDA2741E375404AE25B",
+			Generator: "5C7FF6B06F8F143FE8288433493E4769C4D988ACE5BE25A0E24809670716C613" +
+				"D7B0CEE6932F8FAA7C44D2CB24523DA53FBE4F6EC3595892D1AA58C4328A06C4" +
+				"6A15662E7EAA703A1DECF8BBB2D05DBE2EB956C142A338661D10461C0D135472" +
+				"085057F3494309FFA73C611F78B32ADBB5740C361C9F35BE90997DB2014E2EF5" +
+				"AA61782F52ABEB8BD6432C4DD097BC5423B285DAFB60DC364E8161F4A2A35ACA" +
+				"3A10B1C4D203CC76A470A33AFDCBDD92959859ABD8B56E1725252D78EAC66E71" +
+				"BA9AE3F1DD2487199874393CD4D832186800654760E1E34C09E4D155179F9EC0" +
+				"DC4473F996BDCE6EED1CABED8B6F116F7AD9CF505DF0F998E34AB27514B0FFE7",
+		},
+	}
+}
+
+// Signs a passed round info with the key tied to the test node cert
+// used throughout utils and other tests
+func signRoundInfo(ri *pb.RoundInfo) error {
+	privKeyFromFile := testkeys.LoadFromPath(testkeys.GetNodeKeyPath())
+
+	pk, err := tls.LoadRSAPrivateKey(string(privKeyFromFile))
+	if err != nil {
+		return errors.Errorf("Couldn't load private key: %+v", err)
+	}
+
+	ourPrivateKey := &rsa.PrivateKey{PrivateKey: *pk}
+
+	return signature.Sign(ri, ourPrivateKey)
+
+
+}
\ No newline at end of file
diff --git a/go.mod b/go.mod
index 967c9b29ad88b03270845eb40fc4e6f0f1188e64..cf25ee888d46042bd41068b01b3c96587955cc7f 100644
--- a/go.mod
+++ b/go.mod
@@ -25,10 +25,10 @@ require (
 	gitlab.com/xx_network/crypto v0.0.5-0.20210210215543-446333e9022e
 	gitlab.com/xx_network/primitives v0.0.4-0.20210212180522-50ec526a6c12
 	golang.org/x/crypto v0.0.0-20201221181555-eec23a3978ad
-	golang.org/x/net v0.0.0-20201224014010-6772e930b67b // indirect
+	golang.org/x/net v0.0.0-20201224014010-6772e930b67b
 	golang.org/x/sys v0.0.0-20210105210732-16f7687f5001 // indirect
 	google.golang.org/genproto v0.0.0-20210105202744-fe13368bc0e1 // indirect
-	google.golang.org/grpc v1.34.0 // indirect
+	google.golang.org/grpc v1.34.0
 	google.golang.org/protobuf v1.25.0
 	gopkg.in/ini.v1 v1.62.0 // indirect
 )